|
|
|
@ -608,10 +608,8 @@ void op_state_machine(void* arg, grpc_error* error) { |
|
|
|
|
if (other->recv_message_op) { |
|
|
|
|
message_transfer_locked(s, other); |
|
|
|
|
maybe_schedule_op_closure_locked(other, GRPC_ERROR_NONE); |
|
|
|
|
} else if (!s->t->is_client && |
|
|
|
|
(s->trailing_md_sent || other->recv_trailing_md_op)) { |
|
|
|
|
// A server send will never be matched if the client is waiting
|
|
|
|
|
// for trailing metadata already
|
|
|
|
|
} else if (!s->t->is_client && s->trailing_md_sent) { |
|
|
|
|
// A server send will never be matched if the server already sent status
|
|
|
|
|
s->send_message_op->payload->send_message.send_message.reset(); |
|
|
|
|
complete_if_batch_end_locked( |
|
|
|
|
s, GRPC_ERROR_NONE, s->send_message_op, |
|
|
|
@ -622,11 +620,15 @@ void op_state_machine(void* arg, grpc_error* error) { |
|
|
|
|
// Pause a send trailing metadata if there is still an outstanding
|
|
|
|
|
// send message unless we know that the send message will never get
|
|
|
|
|
// matched to a receive. This happens on the client if the server has
|
|
|
|
|
// already sent status.
|
|
|
|
|
// already sent status or on the server if the client has requested
|
|
|
|
|
// status
|
|
|
|
|
if (s->send_trailing_md_op && |
|
|
|
|
(!s->send_message_op || |
|
|
|
|
(s->t->is_client && |
|
|
|
|
(s->trailing_md_recvd || s->to_read_trailing_md_filled)))) { |
|
|
|
|
(s->trailing_md_recvd || s->to_read_trailing_md_filled)) || |
|
|
|
|
(!s->t->is_client && other && |
|
|
|
|
(other->trailing_md_recvd || other->to_read_trailing_md_filled || |
|
|
|
|
other->recv_trailing_md_op)))) { |
|
|
|
|
grpc_metadata_batch* dest = (other == nullptr) |
|
|
|
|
? &s->write_buffer_trailing_md |
|
|
|
|
: &other->to_read_trailing_md; |
|
|
|
@ -724,16 +726,6 @@ void op_state_machine(void* arg, grpc_error* error) { |
|
|
|
|
maybe_schedule_op_closure_locked(other, GRPC_ERROR_NONE); |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
if (s->recv_trailing_md_op && s->t->is_client && other && |
|
|
|
|
other->send_message_op) { |
|
|
|
|
INPROC_LOG(GPR_INFO, |
|
|
|
|
"op_state_machine %p scheduling trailing-metadata-ready %p", s, |
|
|
|
|
GRPC_ERROR_NONE); |
|
|
|
|
GRPC_CLOSURE_SCHED(s->recv_trailing_md_op->payload->recv_trailing_metadata |
|
|
|
|
.recv_trailing_metadata_ready, |
|
|
|
|
GRPC_ERROR_NONE); |
|
|
|
|
maybe_schedule_op_closure_locked(other, GRPC_ERROR_NONE); |
|
|
|
|
} |
|
|
|
|
if (s->to_read_trailing_md_filled) { |
|
|
|
|
if (s->trailing_md_recvd) { |
|
|
|
|
new_err = |
|
|
|
@ -749,6 +741,7 @@ void op_state_machine(void* arg, grpc_error* error) { |
|
|
|
|
if (s->recv_message_op != nullptr) { |
|
|
|
|
// This message needs to be wrapped up because it will never be
|
|
|
|
|
// satisfied
|
|
|
|
|
*s->recv_message_op->payload->recv_message.recv_message = nullptr; |
|
|
|
|
INPROC_LOG(GPR_INFO, "op_state_machine %p scheduling message-ready", s); |
|
|
|
|
GRPC_CLOSURE_SCHED( |
|
|
|
|
s->recv_message_op->payload->recv_message.recv_message_ready, |
|
|
|
@ -811,6 +804,7 @@ void op_state_machine(void* arg, grpc_error* error) { |
|
|
|
|
// No further message will come on this stream, so finish off the
|
|
|
|
|
// recv_message_op
|
|
|
|
|
INPROC_LOG(GPR_INFO, "op_state_machine %p scheduling message-ready", s); |
|
|
|
|
*s->recv_message_op->payload->recv_message.recv_message = nullptr; |
|
|
|
|
GRPC_CLOSURE_SCHED( |
|
|
|
|
s->recv_message_op->payload->recv_message.recv_message_ready, |
|
|
|
|
GRPC_ERROR_NONE); |
|
|
|
@ -1013,18 +1007,18 @@ void perform_stream_op(grpc_transport* gt, grpc_stream* gs, |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
// We want to initiate the closure if:
|
|
|
|
|
// 1. We want to send a message and the other side wants to receive or end
|
|
|
|
|
// 1. We want to send a message and the other side wants to receive
|
|
|
|
|
// 2. We want to send trailing metadata and there isn't an unmatched send
|
|
|
|
|
// or the other side wants trailing metadata
|
|
|
|
|
// 3. We want initial metadata and the other side has sent it
|
|
|
|
|
// 4. We want to receive a message and there is a message ready
|
|
|
|
|
// 5. There is trailing metadata, even if nothing specifically wants
|
|
|
|
|
// that because that can shut down the receive message as well
|
|
|
|
|
if ((op->send_message && other && |
|
|
|
|
((other->recv_message_op != nullptr) || |
|
|
|
|
(other->recv_trailing_md_op != nullptr))) || |
|
|
|
|
(op->send_trailing_metadata && !op->send_message) || |
|
|
|
|
if ((op->send_message && other && other->recv_message_op != nullptr) || |
|
|
|
|
(op->send_trailing_metadata && |
|
|
|
|
(!s->send_message_op || (other && other->recv_trailing_md_op))) || |
|
|
|
|
(op->recv_initial_metadata && s->to_read_initial_md_filled) || |
|
|
|
|
(op->recv_message && other && (other->send_message_op != nullptr)) || |
|
|
|
|
(op->recv_message && other && other->send_message_op != nullptr) || |
|
|
|
|
(s->to_read_trailing_md_filled || s->trailing_md_recvd)) { |
|
|
|
|
if (!s->op_closure_scheduled) { |
|
|
|
|
GRPC_CLOSURE_SCHED(&s->op_closure, GRPC_ERROR_NONE); |
|
|
|
|