|
|
@ -33,11 +33,11 @@ |
|
|
|
|
|
|
|
|
|
|
|
#include "src/core/transport/stream_op.h" |
|
|
|
#include "src/core/transport/stream_op.h" |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
#include <string.h> |
|
|
|
|
|
|
|
|
|
|
|
#include <grpc/support/alloc.h> |
|
|
|
#include <grpc/support/alloc.h> |
|
|
|
#include <grpc/support/log.h> |
|
|
|
#include <grpc/support/log.h> |
|
|
|
|
|
|
|
|
|
|
|
#include <string.h> |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
/* Exponential growth function: Given x, return a larger x.
|
|
|
|
/* Exponential growth function: Given x, return a larger x.
|
|
|
|
Currently we grow by 1.5 times upon reallocation. */ |
|
|
|
Currently we grow by 1.5 times upon reallocation. */ |
|
|
|
#define GROW(x) (3 * (x) / 2) |
|
|
|
#define GROW(x) (3 * (x) / 2) |
|
|
@ -91,19 +91,32 @@ void grpc_stream_ops_unref_owned_objects(grpc_stream_op *ops, size_t nops) { |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
static void assert_contained_metadata_ok(grpc_stream_op *ops, size_t nops) { |
|
|
|
|
|
|
|
size_t i; |
|
|
|
|
|
|
|
for (i = 0; i < nops; i++) { |
|
|
|
|
|
|
|
if (ops[i].type == GRPC_OP_METADATA) { |
|
|
|
|
|
|
|
grpc_metadata_batch_assert_ok(&ops[i].data.metadata); |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
static void expandto(grpc_stream_op_buffer *sopb, size_t new_capacity) { |
|
|
|
static void expandto(grpc_stream_op_buffer *sopb, size_t new_capacity) { |
|
|
|
sopb->capacity = new_capacity; |
|
|
|
sopb->capacity = new_capacity; |
|
|
|
|
|
|
|
assert_contained_metadata_ok(sopb->ops, sopb->nops); |
|
|
|
if (sopb->ops == sopb->inlined_ops) { |
|
|
|
if (sopb->ops == sopb->inlined_ops) { |
|
|
|
sopb->ops = gpr_malloc(sizeof(grpc_stream_op) * new_capacity); |
|
|
|
sopb->ops = gpr_malloc(sizeof(grpc_stream_op) * new_capacity); |
|
|
|
memcpy(sopb->ops, sopb->inlined_ops, sopb->nops * sizeof(grpc_stream_op)); |
|
|
|
memcpy(sopb->ops, sopb->inlined_ops, sopb->nops * sizeof(grpc_stream_op)); |
|
|
|
} else { |
|
|
|
} else { |
|
|
|
sopb->ops = gpr_realloc(sopb->ops, sizeof(grpc_stream_op) * new_capacity); |
|
|
|
sopb->ops = gpr_realloc(sopb->ops, sizeof(grpc_stream_op) * new_capacity); |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
assert_contained_metadata_ok(sopb->ops, sopb->nops); |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
static grpc_stream_op *add(grpc_stream_op_buffer *sopb) { |
|
|
|
static grpc_stream_op *add(grpc_stream_op_buffer *sopb) { |
|
|
|
grpc_stream_op *out; |
|
|
|
grpc_stream_op *out; |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
assert_contained_metadata_ok(sopb->ops, sopb->nops); |
|
|
|
|
|
|
|
|
|
|
|
if (sopb->nops == sopb->capacity) { |
|
|
|
if (sopb->nops == sopb->capacity) { |
|
|
|
expandto(sopb, GROW(sopb->capacity)); |
|
|
|
expandto(sopb, GROW(sopb->capacity)); |
|
|
|
} |
|
|
|
} |
|
|
@ -114,6 +127,7 @@ static grpc_stream_op *add(grpc_stream_op_buffer *sopb) { |
|
|
|
|
|
|
|
|
|
|
|
void grpc_sopb_add_no_op(grpc_stream_op_buffer *sopb) { |
|
|
|
void grpc_sopb_add_no_op(grpc_stream_op_buffer *sopb) { |
|
|
|
add(sopb)->type = GRPC_NO_OP; |
|
|
|
add(sopb)->type = GRPC_NO_OP; |
|
|
|
|
|
|
|
assert_contained_metadata_ok(sopb->ops, sopb->nops); |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
void grpc_sopb_add_begin_message(grpc_stream_op_buffer *sopb, gpr_uint32 length, |
|
|
|
void grpc_sopb_add_begin_message(grpc_stream_op_buffer *sopb, gpr_uint32 length, |
|
|
@ -122,6 +136,7 @@ void grpc_sopb_add_begin_message(grpc_stream_op_buffer *sopb, gpr_uint32 length, |
|
|
|
op->type = GRPC_OP_BEGIN_MESSAGE; |
|
|
|
op->type = GRPC_OP_BEGIN_MESSAGE; |
|
|
|
op->data.begin_message.length = length; |
|
|
|
op->data.begin_message.length = length; |
|
|
|
op->data.begin_message.flags = flags; |
|
|
|
op->data.begin_message.flags = flags; |
|
|
|
|
|
|
|
assert_contained_metadata_ok(sopb->ops, sopb->nops); |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
void grpc_sopb_add_metadata(grpc_stream_op_buffer *sopb, grpc_metadata_batch b) { |
|
|
|
void grpc_sopb_add_metadata(grpc_stream_op_buffer *sopb, grpc_metadata_batch b) { |
|
|
@ -129,12 +144,15 @@ void grpc_sopb_add_metadata(grpc_stream_op_buffer *sopb, grpc_metadata_batch b) |
|
|
|
grpc_metadata_batch_assert_ok(&b); |
|
|
|
grpc_metadata_batch_assert_ok(&b); |
|
|
|
op->type = GRPC_OP_METADATA; |
|
|
|
op->type = GRPC_OP_METADATA; |
|
|
|
op->data.metadata = b; |
|
|
|
op->data.metadata = b; |
|
|
|
|
|
|
|
grpc_metadata_batch_assert_ok(&op->data.metadata); |
|
|
|
|
|
|
|
assert_contained_metadata_ok(sopb->ops, sopb->nops); |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
void grpc_sopb_add_slice(grpc_stream_op_buffer *sopb, gpr_slice slice) { |
|
|
|
void grpc_sopb_add_slice(grpc_stream_op_buffer *sopb, gpr_slice slice) { |
|
|
|
grpc_stream_op *op = add(sopb); |
|
|
|
grpc_stream_op *op = add(sopb); |
|
|
|
op->type = GRPC_OP_SLICE; |
|
|
|
op->type = GRPC_OP_SLICE; |
|
|
|
op->data.slice = slice; |
|
|
|
op->data.slice = slice; |
|
|
|
|
|
|
|
assert_contained_metadata_ok(sopb->ops, sopb->nops); |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
void grpc_sopb_add_flow_ctl_cb(grpc_stream_op_buffer *sopb, |
|
|
|
void grpc_sopb_add_flow_ctl_cb(grpc_stream_op_buffer *sopb, |
|
|
@ -144,6 +162,7 @@ void grpc_sopb_add_flow_ctl_cb(grpc_stream_op_buffer *sopb, |
|
|
|
op->type = GRPC_OP_FLOW_CTL_CB; |
|
|
|
op->type = GRPC_OP_FLOW_CTL_CB; |
|
|
|
op->data.flow_ctl_cb.cb = cb; |
|
|
|
op->data.flow_ctl_cb.cb = cb; |
|
|
|
op->data.flow_ctl_cb.arg = arg; |
|
|
|
op->data.flow_ctl_cb.arg = arg; |
|
|
|
|
|
|
|
assert_contained_metadata_ok(sopb->ops, sopb->nops); |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
void grpc_sopb_append(grpc_stream_op_buffer *sopb, grpc_stream_op *ops, |
|
|
|
void grpc_sopb_append(grpc_stream_op_buffer *sopb, grpc_stream_op *ops, |
|
|
@ -151,12 +170,15 @@ void grpc_sopb_append(grpc_stream_op_buffer *sopb, grpc_stream_op *ops, |
|
|
|
size_t orig_nops = sopb->nops; |
|
|
|
size_t orig_nops = sopb->nops; |
|
|
|
size_t new_nops = orig_nops + nops; |
|
|
|
size_t new_nops = orig_nops + nops; |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
assert_contained_metadata_ok(ops, nops); |
|
|
|
|
|
|
|
assert_contained_metadata_ok(sopb->ops, sopb->nops); |
|
|
|
if (new_nops > sopb->capacity) { |
|
|
|
if (new_nops > sopb->capacity) { |
|
|
|
expandto(sopb, GPR_MAX(GROW(sopb->capacity), new_nops)); |
|
|
|
expandto(sopb, GPR_MAX(GROW(sopb->capacity), new_nops)); |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
memcpy(sopb->ops + orig_nops, ops, sizeof(grpc_stream_op) * nops); |
|
|
|
memcpy(sopb->ops + orig_nops, ops, sizeof(grpc_stream_op) * nops); |
|
|
|
sopb->nops = new_nops; |
|
|
|
sopb->nops = new_nops; |
|
|
|
|
|
|
|
assert_contained_metadata_ok(sopb->ops, sopb->nops); |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
@ -183,13 +205,19 @@ void grpc_metadata_batch_assert_ok(grpc_metadata_batch *comd) { |
|
|
|
assert_valid_list(&comd->garbage); |
|
|
|
assert_valid_list(&comd->garbage); |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
void grpc_metadata_batch_init(grpc_metadata_batch *comd) { abort(); } |
|
|
|
void grpc_metadata_batch_init(grpc_metadata_batch *comd) {
|
|
|
|
|
|
|
|
comd->list.head = comd->list.tail = comd->garbage.head = comd->garbage.tail = NULL; |
|
|
|
void grpc_metadata_batch_destroy(grpc_metadata_batch *comd) { abort(); } |
|
|
|
comd->deadline = gpr_inf_future; |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
void grpc_metadata_batch_merge(grpc_metadata_batch *target, |
|
|
|
void grpc_metadata_batch_destroy(grpc_metadata_batch *comd) {
|
|
|
|
grpc_metadata_batch *add) { |
|
|
|
grpc_linked_mdelem *l; |
|
|
|
abort(); |
|
|
|
for (l = comd->list.head; l; l = l->next) { |
|
|
|
|
|
|
|
grpc_mdelem_unref(l->md); |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
for (l = comd->garbage.head; l; l = l->next) { |
|
|
|
|
|
|
|
grpc_mdelem_unref(l->md); |
|
|
|
|
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
void grpc_metadata_batch_add_head(grpc_metadata_batch *comd, |
|
|
|
void grpc_metadata_batch_add_head(grpc_metadata_batch *comd, |
|
|
@ -246,6 +274,20 @@ void grpc_metadata_batch_link_tail(grpc_metadata_batch *comd, |
|
|
|
link_tail(&comd->list, storage); |
|
|
|
link_tail(&comd->list, storage); |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
void grpc_metadata_batch_merge(grpc_metadata_batch *target, |
|
|
|
|
|
|
|
grpc_metadata_batch *add) { |
|
|
|
|
|
|
|
grpc_linked_mdelem *l; |
|
|
|
|
|
|
|
grpc_linked_mdelem *next; |
|
|
|
|
|
|
|
for (l = add->list.head; l; l = next) { |
|
|
|
|
|
|
|
next = l->next; |
|
|
|
|
|
|
|
link_tail(&target->list, l); |
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
for (l = add->garbage.head; l; l = next) { |
|
|
|
|
|
|
|
next = l->next; |
|
|
|
|
|
|
|
link_tail(&target->garbage, l); |
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
void grpc_metadata_batch_filter(grpc_metadata_batch *comd, |
|
|
|
void grpc_metadata_batch_filter(grpc_metadata_batch *comd, |
|
|
|
grpc_mdelem *(*filter)(void *user_data, |
|
|
|
grpc_mdelem *(*filter)(void *user_data, |
|
|
|
grpc_mdelem *elem), |
|
|
|
grpc_mdelem *elem), |
|
|
|