aboutsummaryrefslogtreecommitdiffhomepage
path: root/src/core
diff options
context:
space:
mode:
authorGravatar Craig Tiller <ctiller@google.com>2016-06-20 08:36:53 -0700
committerGravatar Craig Tiller <ctiller@google.com>2016-06-20 08:36:53 -0700
commit56565fca7532fcc559cd8149e437eb0a7ecdfd9b (patch)
treecda9ac78bc376af655c5bf2344105aff8cce4696 /src/core
parent4e29480e430b94392105934750adfd85cb7849ce (diff)
Force receiving a SETTINGS frame as the first frame
Diffstat (limited to 'src/core')
-rw-r--r--src/core/ext/transport/chttp2/transport/chttp2_transport.c3
-rw-r--r--src/core/ext/transport/chttp2/transport/internal.h1
-rw-r--r--src/core/ext/transport/chttp2/transport/parsing.c11
3 files changed, 14 insertions, 1 deletions
diff --git a/src/core/ext/transport/chttp2/transport/chttp2_transport.c b/src/core/ext/transport/chttp2/transport/chttp2_transport.c
index 9aa39ba26c..a8c4b271fe 100644
--- a/src/core/ext/transport/chttp2/transport/chttp2_transport.c
+++ b/src/core/ext/transport/chttp2/transport/chttp2_transport.c
@@ -264,6 +264,7 @@ static void init_transport(grpc_exec_ctx *exec_ctx, grpc_chttp2_transport *t,
t->parsing.is_client = is_client;
t->parsing.deframe_state =
is_client ? GRPC_DTS_FH_0 : GRPC_DTS_CLIENT_PREFIX_0;
+ t->parsing.is_first_frame = true;
t->writing.is_client = is_client;
t->optional_drop_message = gpr_empty_slice();
grpc_connectivity_state_init(
@@ -1805,7 +1806,7 @@ static void post_reading_action_locked(grpc_exec_ctx *exec_ctx,
UNREF_TRANSPORT(exec_ctx, t, "reading_action");
}
- GRPC_ERROR_UNREF(error);
+ GRPC_LOG_IF_ERROR("close_transport", error);
}
/*******************************************************************************
diff --git a/src/core/ext/transport/chttp2/transport/internal.h b/src/core/ext/transport/chttp2/transport/internal.h
index 54e72ebd24..64385b4372 100644
--- a/src/core/ext/transport/chttp2/transport/internal.h
+++ b/src/core/ext/transport/chttp2/transport/internal.h
@@ -265,6 +265,7 @@ struct grpc_chttp2_transport_parsing {
uint8_t incoming_frame_type;
uint8_t incoming_frame_flags;
uint8_t header_eof;
+ bool is_first_frame;
uint32_t expect_continuation_stream_id;
uint32_t incoming_frame_size;
uint32_t incoming_stream_id;
diff --git a/src/core/ext/transport/chttp2/transport/parsing.c b/src/core/ext/transport/chttp2/transport/parsing.c
index 785134091f..991d7729af 100644
--- a/src/core/ext/transport/chttp2/transport/parsing.c
+++ b/src/core/ext/transport/chttp2/transport/parsing.c
@@ -468,6 +468,17 @@ grpc_error *grpc_chttp2_perform_read(
static grpc_error *init_frame_parser(
grpc_exec_ctx *exec_ctx, grpc_chttp2_transport_parsing *transport_parsing) {
+ if (transport_parsing->is_first_frame &&
+ transport_parsing->incoming_frame_type != GRPC_CHTTP2_FRAME_SETTINGS) {
+ char *msg;
+ gpr_asprintf(
+ &msg, "Expected SETTINGS frame as the first frame, got frame type %d",
+ transport_parsing->incoming_frame_type);
+ grpc_error *err = GRPC_ERROR_CREATE(msg);
+ gpr_free(msg);
+ return err;
+ }
+ transport_parsing->is_first_frame = false;
if (transport_parsing->expect_continuation_stream_id != 0) {
if (transport_parsing->incoming_frame_type !=
GRPC_CHTTP2_FRAME_CONTINUATION) {