|
|
@ -37,10 +37,11 @@ |
|
|
|
#include <grpc/support/log.h> |
|
|
|
#include <grpc/support/log.h> |
|
|
|
|
|
|
|
|
|
|
|
typedef struct call_data { |
|
|
|
typedef struct call_data { |
|
|
|
int sent_status; |
|
|
|
gpr_uint8 sent_status; |
|
|
|
int seen_scheme; |
|
|
|
gpr_uint8 seen_scheme; |
|
|
|
int seen_method; |
|
|
|
gpr_uint8 seen_method; |
|
|
|
int seen_te_trailers; |
|
|
|
gpr_uint8 seen_te_trailers; |
|
|
|
|
|
|
|
grpc_mdelem *path; |
|
|
|
} call_data; |
|
|
|
} call_data; |
|
|
|
|
|
|
|
|
|
|
|
typedef struct channel_data { |
|
|
|
typedef struct channel_data { |
|
|
@ -52,6 +53,7 @@ typedef struct channel_data { |
|
|
|
grpc_mdelem *grpc_scheme; |
|
|
|
grpc_mdelem *grpc_scheme; |
|
|
|
grpc_mdelem *content_type; |
|
|
|
grpc_mdelem *content_type; |
|
|
|
grpc_mdelem *status; |
|
|
|
grpc_mdelem *status; |
|
|
|
|
|
|
|
grpc_mdstr *path_key; |
|
|
|
} channel_data; |
|
|
|
} channel_data; |
|
|
|
|
|
|
|
|
|
|
|
/* used to silence 'variable not used' warnings */ |
|
|
|
/* used to silence 'variable not used' warnings */ |
|
|
@ -120,6 +122,13 @@ static void call_op(grpc_call_element *elem, grpc_call_element *from_elem, |
|
|
|
grpc_mdelem_unref(op->data.metadata); |
|
|
|
grpc_mdelem_unref(op->data.metadata); |
|
|
|
op->done_cb(op->user_data, GRPC_OP_OK); |
|
|
|
op->done_cb(op->user_data, GRPC_OP_OK); |
|
|
|
grpc_call_element_send_cancel(elem); |
|
|
|
grpc_call_element_send_cancel(elem); |
|
|
|
|
|
|
|
} else if (op->data.metadata->key == channeld->path_key) { |
|
|
|
|
|
|
|
if (calld->path != NULL) { |
|
|
|
|
|
|
|
gpr_log(GPR_ERROR, "Received :path twice"); |
|
|
|
|
|
|
|
grpc_mdelem_unref(calld->path); |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
calld->path = grpc_mdelem_ref(op->data.metadata); |
|
|
|
|
|
|
|
op->done_cb(op->user_data, GRPC_OP_OK); |
|
|
|
} else { |
|
|
|
} else { |
|
|
|
/* pass the event up */ |
|
|
|
/* pass the event up */ |
|
|
|
grpc_call_next_op(elem, op); |
|
|
|
grpc_call_next_op(elem, op); |
|
|
@ -129,7 +138,10 @@ static void call_op(grpc_call_element *elem, grpc_call_element *from_elem, |
|
|
|
/* Have we seen the required http2 transport headers?
|
|
|
|
/* Have we seen the required http2 transport headers?
|
|
|
|
(:method, :scheme, content-type, with :path and :authority covered |
|
|
|
(:method, :scheme, content-type, with :path and :authority covered |
|
|
|
at the channel level right now) */ |
|
|
|
at the channel level right now) */ |
|
|
|
if (calld->seen_method && calld->seen_scheme && calld->seen_te_trailers) { |
|
|
|
if (calld->seen_method && calld->seen_scheme && calld->seen_te_trailers && |
|
|
|
|
|
|
|
calld->path) { |
|
|
|
|
|
|
|
grpc_call_element_recv_metadata(elem, calld->path); |
|
|
|
|
|
|
|
calld->path = NULL; |
|
|
|
grpc_call_next_op(elem, op); |
|
|
|
grpc_call_next_op(elem, op); |
|
|
|
} else { |
|
|
|
} else { |
|
|
|
if (!calld->seen_method) { |
|
|
|
if (!calld->seen_method) { |
|
|
@ -189,6 +201,7 @@ static void init_call_elem(grpc_call_element *elem, |
|
|
|
ignore_unused(channeld); |
|
|
|
ignore_unused(channeld); |
|
|
|
|
|
|
|
|
|
|
|
/* initialize members */ |
|
|
|
/* initialize members */ |
|
|
|
|
|
|
|
calld->path = NULL; |
|
|
|
calld->sent_status = 0; |
|
|
|
calld->sent_status = 0; |
|
|
|
calld->seen_scheme = 0; |
|
|
|
calld->seen_scheme = 0; |
|
|
|
calld->seen_method = 0; |
|
|
|
calld->seen_method = 0; |
|
|
@ -201,8 +214,11 @@ static void destroy_call_elem(grpc_call_element *elem) { |
|
|
|
call_data *calld = elem->call_data; |
|
|
|
call_data *calld = elem->call_data; |
|
|
|
channel_data *channeld = elem->channel_data; |
|
|
|
channel_data *channeld = elem->channel_data; |
|
|
|
|
|
|
|
|
|
|
|
ignore_unused(calld); |
|
|
|
|
|
|
|
ignore_unused(channeld); |
|
|
|
ignore_unused(channeld); |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
if (calld->path) { |
|
|
|
|
|
|
|
grpc_mdelem_unref(calld->path); |
|
|
|
|
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
/* Constructor for channel_data */ |
|
|
|
/* Constructor for channel_data */ |
|
|
@ -225,6 +241,7 @@ static void init_channel_elem(grpc_channel_element *elem, |
|
|
|
channeld->http_scheme = grpc_mdelem_from_strings(mdctx, ":scheme", "http"); |
|
|
|
channeld->http_scheme = grpc_mdelem_from_strings(mdctx, ":scheme", "http"); |
|
|
|
channeld->https_scheme = grpc_mdelem_from_strings(mdctx, ":scheme", "https"); |
|
|
|
channeld->https_scheme = grpc_mdelem_from_strings(mdctx, ":scheme", "https"); |
|
|
|
channeld->grpc_scheme = grpc_mdelem_from_strings(mdctx, ":scheme", "grpc"); |
|
|
|
channeld->grpc_scheme = grpc_mdelem_from_strings(mdctx, ":scheme", "grpc"); |
|
|
|
|
|
|
|
channeld->path_key = grpc_mdstr_from_string(mdctx, ":path"); |
|
|
|
channeld->content_type = |
|
|
|
channeld->content_type = |
|
|
|
grpc_mdelem_from_strings(mdctx, "content-type", "application/grpc"); |
|
|
|
grpc_mdelem_from_strings(mdctx, "content-type", "application/grpc"); |
|
|
|
} |
|
|
|
} |
|
|
@ -241,6 +258,7 @@ static void destroy_channel_elem(grpc_channel_element *elem) { |
|
|
|
grpc_mdelem_unref(channeld->https_scheme); |
|
|
|
grpc_mdelem_unref(channeld->https_scheme); |
|
|
|
grpc_mdelem_unref(channeld->grpc_scheme); |
|
|
|
grpc_mdelem_unref(channeld->grpc_scheme); |
|
|
|
grpc_mdelem_unref(channeld->content_type); |
|
|
|
grpc_mdelem_unref(channeld->content_type); |
|
|
|
|
|
|
|
grpc_mdstr_unref(channeld->path_key); |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
const grpc_channel_filter grpc_http_server_filter = { |
|
|
|
const grpc_channel_filter grpc_http_server_filter = { |
|
|
|