grpc 1.3.4 → 1.4.0
Sign up to get free protection for your applications and to get access to all the features.
Potentially problematic release.
This version of grpc might be problematic. Click here for more details.
- checksums.yaml +4 -4
- data/Makefile +581 -450
- data/include/grpc/census.h +49 -49
- data/include/grpc/grpc.h +16 -70
- data/include/grpc/grpc_security.h +59 -59
- data/include/grpc/grpc_security_constants.h +9 -9
- data/include/grpc/impl/codegen/atm.h +1 -1
- data/include/grpc/impl/codegen/atm_windows.h +4 -4
- data/include/grpc/impl/codegen/byte_buffer_reader.h +2 -2
- data/include/grpc/impl/codegen/compression_types.h +4 -5
- data/include/grpc/impl/codegen/gpr_slice.h +5 -5
- data/include/grpc/impl/codegen/gpr_types.h +6 -7
- data/include/grpc/impl/codegen/grpc_types.h +128 -59
- data/include/grpc/impl/codegen/port_platform.h +6 -0
- data/include/grpc/impl/codegen/propagation_bits.h +2 -2
- data/include/grpc/impl/codegen/slice.h +13 -12
- data/include/grpc/impl/codegen/status.h +23 -18
- data/include/grpc/impl/codegen/sync.h +1 -1
- data/include/grpc/load_reporting.h +6 -6
- data/include/grpc/slice.h +47 -25
- data/include/grpc/slice_buffer.h +18 -14
- data/include/grpc/support/alloc.h +7 -7
- data/include/grpc/support/cmdline.h +10 -10
- data/include/grpc/support/cpu.h +3 -3
- data/include/grpc/support/histogram.h +1 -1
- data/include/grpc/support/host_port.h +2 -2
- data/include/grpc/support/log.h +9 -9
- data/include/grpc/support/log_windows.h +1 -1
- data/include/grpc/support/string_util.h +3 -3
- data/include/grpc/support/subprocess.h +3 -3
- data/include/grpc/support/sync.h +31 -31
- data/include/grpc/support/thd.h +11 -11
- data/include/grpc/support/time.h +12 -12
- data/include/grpc/support/tls.h +1 -1
- data/include/grpc/support/tls_gcc.h +2 -2
- data/include/grpc/support/tls_msvc.h +1 -1
- data/include/grpc/support/tls_pthread.h +1 -1
- data/include/grpc/support/useful.h +2 -2
- data/include/grpc/support/workaround_list.h +46 -0
- data/src/core/ext/census/context.c +1 -1
- data/src/core/ext/census/intrusive_hash_map.c +319 -0
- data/src/core/ext/census/intrusive_hash_map.h +167 -0
- data/src/core/ext/census/intrusive_hash_map_internal.h +63 -0
- data/src/core/ext/census/resource.c +3 -1
- data/src/core/ext/filters/client_channel/channel_connectivity.c +1 -1
- data/src/core/ext/filters/client_channel/client_channel.c +173 -103
- data/src/core/ext/filters/client_channel/client_channel_plugin.c +3 -2
- data/src/core/ext/filters/client_channel/lb_policy.c +2 -1
- data/src/core/ext/filters/client_channel/lb_policy.h +8 -7
- data/src/core/ext/filters/client_channel/lb_policy/grpclb/client_load_reporting_filter.c +153 -0
- data/src/core/ext/filters/client_channel/lb_policy/grpclb/client_load_reporting_filter.h +42 -0
- data/src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb.c +405 -102
- data/src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb_client_stats.c +133 -0
- data/src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb_client_stats.h +65 -0
- data/src/core/ext/filters/client_channel/lb_policy/grpclb/load_balancer_api.c +90 -51
- data/src/core/ext/filters/client_channel/lb_policy/grpclb/load_balancer_api.h +7 -1
- data/src/core/ext/filters/client_channel/lb_policy/grpclb/proto/grpc/lb/v1/load_balancer.pb.c +19 -8
- data/src/core/ext/filters/client_channel/lb_policy/grpclb/proto/grpc/lb/v1/load_balancer.pb.h +63 -34
- data/src/core/ext/filters/client_channel/lb_policy/pick_first/pick_first.c +2 -1
- data/src/core/ext/filters/client_channel/lb_policy/round_robin/round_robin.c +188 -294
- data/src/core/ext/filters/client_channel/lb_policy_factory.c +28 -5
- data/src/core/ext/filters/client_channel/lb_policy_factory.h +18 -4
- data/src/core/ext/filters/client_channel/parse_address.c +90 -59
- data/src/core/ext/filters/client_channel/parse_address.h +17 -8
- data/src/core/ext/filters/client_channel/resolver/dns/c_ares/dns_resolver_ares.c +11 -7
- data/src/core/ext/filters/client_channel/resolver/dns/c_ares/grpc_ares_wrapper.c +59 -14
- data/src/core/ext/filters/client_channel/resolver/dns/c_ares/grpc_ares_wrapper.h +6 -0
- data/src/core/ext/filters/client_channel/resolver/sockaddr/sockaddr_resolver.c +3 -3
- data/src/core/ext/filters/client_channel/subchannel.c +20 -17
- data/src/core/ext/filters/client_channel/subchannel.h +1 -0
- data/src/core/ext/filters/client_channel/subchannel_index.c +11 -1
- data/src/core/ext/filters/client_channel/uri_parser.c +36 -22
- data/src/core/ext/filters/client_channel/uri_parser.h +1 -1
- data/src/core/{lib/channel → ext/filters/deadline}/deadline_filter.c +42 -17
- data/src/core/{lib/channel → ext/filters/deadline}/deadline_filter.h +8 -9
- data/src/core/{lib/channel → ext/filters/http/client}/http_client_filter.c +19 -11
- data/src/core/{lib/channel → ext/filters/http/client}/http_client_filter.h +3 -6
- data/src/core/ext/filters/http/http_filters_plugin.c +104 -0
- data/src/core/{lib/channel/compress_filter.c → ext/filters/http/message_compress/message_compress_filter.c} +124 -23
- data/src/core/{lib/channel/compress_filter.h → ext/filters/http/message_compress/message_compress_filter.h} +5 -6
- data/src/core/{lib/channel → ext/filters/http/server}/http_server_filter.c +4 -6
- data/src/core/{lib/channel → ext/filters/http/server}/http_server_filter.h +3 -3
- data/src/core/ext/filters/load_reporting/load_reporting.c +2 -25
- data/src/core/ext/filters/load_reporting/load_reporting_filter.c +26 -1
- data/src/core/ext/filters/max_age/max_age_filter.c +14 -14
- data/src/core/{lib/channel → ext/filters/message_size}/message_size_filter.c +91 -47
- data/src/core/{lib/channel → ext/filters/message_size}/message_size_filter.h +3 -3
- data/src/core/ext/filters/workarounds/workaround_cronet_compression_filter.c +223 -0
- data/src/core/ext/filters/workarounds/workaround_cronet_compression_filter.h +40 -0
- data/src/core/ext/filters/workarounds/workaround_utils.c +65 -0
- data/src/core/ext/filters/workarounds/workaround_utils.h +52 -0
- data/src/core/ext/transport/chttp2/client/insecure/channel_create.c +1 -1
- data/src/core/ext/transport/chttp2/server/chttp2_server.c +3 -2
- data/src/core/ext/transport/chttp2/transport/bin_decoder.c +2 -2
- data/src/core/ext/transport/chttp2/transport/bin_encoder.c +3 -3
- data/src/core/ext/transport/chttp2/transport/chttp2_transport.c +319 -175
- data/src/core/ext/transport/chttp2/transport/chttp2_transport.h +3 -2
- data/src/core/ext/transport/chttp2/transport/frame_data.c +203 -164
- data/src/core/ext/transport/chttp2/transport/frame_data.h +8 -14
- data/src/core/ext/transport/chttp2/transport/frame_goaway.c +1 -1
- data/src/core/ext/transport/chttp2/transport/frame_ping.c +1 -1
- data/src/core/ext/transport/chttp2/transport/frame_rst_stream.c +1 -1
- data/src/core/ext/transport/chttp2/transport/frame_settings.c +5 -5
- data/src/core/ext/transport/chttp2/transport/frame_window_update.c +1 -1
- data/src/core/ext/transport/chttp2/transport/hpack_encoder.c +4 -4
- data/src/core/ext/transport/chttp2/transport/hpack_parser.c +2 -4
- data/src/core/ext/transport/chttp2/transport/hpack_table.c +4 -3
- data/src/core/ext/transport/chttp2/transport/internal.h +50 -33
- data/src/core/ext/transport/chttp2/transport/parsing.c +10 -11
- data/src/core/ext/transport/chttp2/transport/writing.c +32 -13
- data/src/core/lib/channel/channel_args.c +30 -9
- data/src/core/lib/channel/channel_args.h +5 -1
- data/src/core/lib/channel/channel_stack.c +1 -1
- data/src/core/lib/channel/channel_stack.h +2 -2
- data/src/core/lib/channel/channel_stack_builder.c +13 -1
- data/src/core/lib/channel/channel_stack_builder.h +5 -1
- data/src/core/lib/channel/connected_channel.c +3 -1
- data/src/core/lib/channel/context.h +2 -2
- data/src/core/lib/compression/message_compress.c +2 -2
- data/src/core/lib/debug/trace.c +13 -6
- data/src/core/lib/debug/trace.h +27 -1
- data/src/core/lib/http/httpcli.c +1 -1
- data/src/core/lib/http/httpcli_security_connector.c +9 -11
- data/src/core/lib/http/parser.c +2 -2
- data/src/core/lib/http/parser.h +2 -1
- data/src/core/lib/iomgr/combiner.c +6 -6
- data/src/core/lib/iomgr/combiner.h +2 -1
- data/src/core/lib/iomgr/error.c +12 -5
- data/src/core/lib/iomgr/error.h +13 -13
- data/src/core/lib/iomgr/ev_epoll1_linux.c +984 -0
- data/src/core/lib/iomgr/ev_epoll1_linux.h +44 -0
- data/src/core/lib/iomgr/ev_epoll_limited_pollers_linux.c +2146 -0
- data/src/core/lib/iomgr/ev_epoll_limited_pollers_linux.h +43 -0
- data/src/core/lib/iomgr/ev_epoll_thread_pool_linux.c +1337 -0
- data/src/core/lib/iomgr/ev_epoll_thread_pool_linux.h +43 -0
- data/src/core/lib/iomgr/ev_epollex_linux.c +1511 -0
- data/src/core/lib/iomgr/ev_epollex_linux.h +43 -0
- data/src/core/lib/iomgr/{ev_epoll_linux.c → ev_epollsig_linux.c} +41 -33
- data/src/core/lib/iomgr/{ev_epoll_linux.h → ev_epollsig_linux.h} +4 -4
- data/src/core/lib/iomgr/ev_poll_posix.c +12 -27
- data/src/core/lib/iomgr/ev_poll_posix.h +2 -2
- data/src/core/lib/iomgr/ev_posix.c +22 -8
- data/src/core/lib/iomgr/ev_posix.h +4 -3
- data/src/core/lib/iomgr/ev_windows.c +43 -0
- data/src/core/lib/iomgr/exec_ctx.c +5 -0
- data/src/core/lib/iomgr/exec_ctx.h +2 -0
- data/src/core/lib/iomgr/iomgr.c +4 -0
- data/src/core/lib/iomgr/iomgr.h +3 -0
- data/src/core/lib/iomgr/is_epollexclusive_available.c +116 -0
- data/src/core/lib/iomgr/is_epollexclusive_available.h +41 -0
- data/src/core/lib/iomgr/lockfree_event.c +16 -0
- data/src/core/lib/iomgr/pollset.h +2 -5
- data/src/core/lib/iomgr/pollset_uv.c +1 -1
- data/src/core/lib/iomgr/pollset_windows.c +3 -3
- data/src/core/lib/iomgr/resource_quota.c +9 -8
- data/src/core/lib/iomgr/resource_quota.h +2 -1
- data/src/core/lib/iomgr/sockaddr_utils.h +1 -1
- data/src/core/lib/iomgr/socket_mutator.h +2 -0
- data/src/core/lib/iomgr/sys_epoll_wrapper.h +43 -0
- data/src/core/lib/iomgr/tcp_client_posix.c +6 -6
- data/src/core/lib/iomgr/tcp_client_uv.c +3 -3
- data/src/core/lib/iomgr/tcp_posix.c +7 -7
- data/src/core/lib/iomgr/tcp_posix.h +2 -1
- data/src/core/lib/iomgr/tcp_server_posix.c +1 -1
- data/src/core/lib/iomgr/tcp_uv.c +6 -6
- data/src/core/lib/iomgr/tcp_uv.h +2 -1
- data/src/core/lib/iomgr/tcp_windows.c +1 -1
- data/src/core/lib/iomgr/timer_generic.c +24 -25
- data/src/core/lib/iomgr/timer_manager.c +276 -0
- data/src/core/lib/iomgr/timer_manager.h +52 -0
- data/src/core/lib/iomgr/timer_uv.c +6 -0
- data/src/core/lib/iomgr/udp_server.c +42 -9
- data/src/core/lib/iomgr/udp_server.h +3 -1
- data/src/core/lib/security/credentials/credentials.c +0 -1
- data/src/core/lib/security/credentials/fake/fake_credentials.c +23 -0
- data/src/core/lib/security/credentials/fake/fake_credentials.h +12 -9
- data/src/core/lib/security/credentials/google_default/google_default_credentials.c +1 -1
- data/src/core/lib/security/credentials/jwt/jwt_credentials.c +1 -1
- data/src/core/lib/security/credentials/oauth2/oauth2_credentials.c +1 -1
- data/src/core/lib/security/credentials/ssl/ssl_credentials.c +24 -53
- data/src/core/lib/security/transport/client_auth_filter.c +9 -3
- data/src/core/lib/security/transport/secure_endpoint.c +7 -7
- data/src/core/lib/security/transport/secure_endpoint.h +1 -1
- data/src/core/lib/security/transport/security_connector.c +45 -57
- data/src/core/lib/security/transport/security_connector.h +10 -14
- data/src/core/lib/security/transport/security_handshaker.c +123 -97
- data/src/core/lib/slice/b64.c +1 -1
- data/src/core/lib/slice/percent_encoding.c +3 -3
- data/src/core/lib/slice/slice.c +66 -33
- data/src/core/lib/slice/slice_buffer.c +25 -6
- data/src/core/lib/slice/slice_hash_table.c +33 -35
- data/src/core/lib/slice/slice_hash_table.h +7 -12
- data/src/core/lib/support/atomic.h +45 -0
- data/src/core/lib/support/atomic_with_atm.h +70 -0
- data/src/core/lib/support/atomic_with_std.h +48 -0
- data/src/core/lib/support/avl.c +14 -14
- data/src/core/lib/support/cmdline.c +3 -3
- data/src/core/lib/support/histogram.c +2 -2
- data/src/core/lib/support/host_port.c +1 -1
- data/src/core/lib/support/memory.h +74 -0
- data/src/core/lib/support/mpscq.c +36 -2
- data/src/core/lib/support/mpscq.h +28 -1
- data/src/core/lib/support/stack_lockfree.c +3 -36
- data/src/core/lib/support/string.c +12 -12
- data/src/core/lib/support/string_posix.c +1 -1
- data/src/core/lib/support/subprocess_posix.c +2 -2
- data/src/core/lib/support/thd_posix.c +1 -1
- data/src/core/lib/support/time_posix.c +8 -0
- data/src/core/lib/support/tmpfile_posix.c +10 -10
- data/src/core/lib/surface/alarm.c +3 -1
- data/src/core/lib/surface/api_trace.c +2 -1
- data/src/core/lib/surface/api_trace.h +2 -2
- data/src/core/lib/surface/byte_buffer_reader.c +1 -1
- data/src/core/lib/surface/call.c +65 -22
- data/src/core/lib/surface/call.h +4 -2
- data/src/core/lib/surface/channel_init.c +2 -19
- data/src/core/lib/surface/channel_stack_type.c +18 -0
- data/src/core/lib/surface/channel_stack_type.h +2 -0
- data/src/core/lib/surface/completion_queue.c +694 -247
- data/src/core/lib/surface/completion_queue.h +30 -13
- data/src/core/lib/surface/completion_queue_factory.c +24 -9
- data/src/core/lib/surface/init.c +1 -52
- data/src/core/lib/surface/{lame_client.c → lame_client.cc} +37 -26
- data/src/core/lib/surface/server.c +79 -110
- data/src/core/lib/surface/server.h +2 -1
- data/src/core/lib/surface/version.c +2 -2
- data/src/core/lib/transport/bdp_estimator.c +25 -9
- data/src/core/lib/transport/bdp_estimator.h +7 -1
- data/src/core/lib/transport/byte_stream.c +23 -9
- data/src/core/lib/transport/byte_stream.h +15 -6
- data/src/core/lib/transport/connectivity_state.c +6 -6
- data/src/core/lib/transport/connectivity_state.h +2 -1
- data/src/core/lib/transport/service_config.c +6 -13
- data/src/core/lib/transport/service_config.h +2 -2
- data/src/core/lib/transport/static_metadata.c +403 -389
- data/src/core/lib/transport/static_metadata.h +127 -114
- data/src/core/plugin_registry/grpc_plugin_registry.c +16 -0
- data/src/core/tsi/fake_transport_security.c +5 -4
- data/src/core/tsi/ssl_transport_security.c +71 -82
- data/src/core/tsi/ssl_transport_security.h +39 -61
- data/src/core/tsi/transport_security.c +83 -2
- data/src/core/tsi/transport_security.h +27 -2
- data/src/core/tsi/transport_security_adapter.c +236 -0
- data/src/core/tsi/transport_security_adapter.h +62 -0
- data/src/core/tsi/transport_security_interface.h +179 -66
- data/src/ruby/ext/grpc/extconf.rb +2 -1
- data/src/ruby/ext/grpc/rb_byte_buffer.c +8 -6
- data/src/ruby/ext/grpc/rb_call.c +56 -48
- data/src/ruby/ext/grpc/rb_call.h +3 -4
- data/src/ruby/ext/grpc/rb_call_credentials.c +23 -22
- data/src/ruby/ext/grpc/rb_channel.c +2 -3
- data/src/ruby/ext/grpc/rb_channel_args.c +11 -9
- data/src/ruby/ext/grpc/rb_channel_credentials.c +16 -12
- data/src/ruby/ext/grpc/rb_completion_queue.c +7 -9
- data/src/ruby/ext/grpc/rb_compression_options.c +7 -6
- data/src/ruby/ext/grpc/rb_event_thread.c +10 -12
- data/src/ruby/ext/grpc/rb_event_thread.h +1 -2
- data/src/ruby/ext/grpc/rb_grpc.c +11 -15
- data/src/ruby/ext/grpc/rb_grpc.h +2 -2
- data/src/ruby/ext/grpc/rb_grpc_imports.generated.c +16 -6
- data/src/ruby/ext/grpc/rb_grpc_imports.generated.h +25 -10
- data/src/ruby/ext/grpc/rb_server.c +26 -28
- data/src/ruby/lib/grpc/grpc.rb +1 -1
- data/src/ruby/lib/grpc/version.rb +1 -1
- data/third_party/cares/config_linux/ares_config.h +36 -2
- data/third_party/zlib/adler32.c +14 -7
- data/third_party/zlib/compress.c +24 -18
- data/third_party/zlib/crc32.c +29 -12
- data/third_party/zlib/deflate.c +499 -303
- data/third_party/zlib/deflate.h +19 -16
- data/third_party/zlib/gzguts.h +16 -7
- data/third_party/zlib/gzlib.c +17 -14
- data/third_party/zlib/gzread.c +108 -48
- data/third_party/zlib/gzwrite.c +210 -122
- data/third_party/zlib/infback.c +2 -2
- data/third_party/zlib/inffast.c +34 -51
- data/third_party/zlib/inflate.c +86 -37
- data/third_party/zlib/inflate.h +7 -4
- data/third_party/zlib/inftrees.c +12 -14
- data/third_party/zlib/trees.c +38 -61
- data/third_party/zlib/uncompr.c +66 -32
- data/third_party/zlib/zconf.h +32 -9
- data/third_party/zlib/zlib.h +298 -154
- data/third_party/zlib/zutil.c +25 -24
- data/third_party/zlib/zutil.h +35 -17
- metadata +63 -30
@@ -31,12 +31,12 @@
|
|
31
31
|
*
|
32
32
|
*/
|
33
33
|
|
34
|
-
#ifndef
|
35
|
-
#define
|
34
|
+
#ifndef GRPC_CORE_EXT_FILTERS_HTTP_SERVER_HTTP_SERVER_FILTER_H
|
35
|
+
#define GRPC_CORE_EXT_FILTERS_HTTP_SERVER_HTTP_SERVER_FILTER_H
|
36
36
|
|
37
37
|
#include "src/core/lib/channel/channel_stack.h"
|
38
38
|
|
39
39
|
/* Processes metadata on the client side for HTTP2 transports */
|
40
40
|
extern const grpc_channel_filter grpc_http_server_filter;
|
41
41
|
|
42
|
-
#endif /*
|
42
|
+
#endif /* GRPC_CORE_EXT_FILTERS_HTTP_SERVER_HTTP_SERVER_FILTER_H */
|
@@ -47,32 +47,9 @@
|
|
47
47
|
#include "src/core/lib/surface/call.h"
|
48
48
|
#include "src/core/lib/surface/channel_init.h"
|
49
49
|
|
50
|
-
static void destroy_lr_cost_context(void *c) {
|
51
|
-
grpc_exec_ctx exec_ctx = GRPC_EXEC_CTX_INIT;
|
52
|
-
grpc_load_reporting_cost_context *cost_ctx = c;
|
53
|
-
for (size_t i = 0; i < cost_ctx->values_count; ++i) {
|
54
|
-
grpc_slice_unref_internal(&exec_ctx, cost_ctx->values[i]);
|
55
|
-
}
|
56
|
-
grpc_exec_ctx_finish(&exec_ctx);
|
57
|
-
gpr_free(cost_ctx->values);
|
58
|
-
gpr_free(cost_ctx);
|
59
|
-
}
|
60
|
-
|
61
|
-
void grpc_call_set_load_reporting_cost_context(
|
62
|
-
grpc_call *call, grpc_load_reporting_cost_context *ctx) {
|
63
|
-
grpc_call_context_set(call, GRPC_CONTEXT_LR_COST, ctx,
|
64
|
-
destroy_lr_cost_context);
|
65
|
-
}
|
66
|
-
|
67
50
|
static bool is_load_reporting_enabled(const grpc_channel_args *a) {
|
68
|
-
|
69
|
-
|
70
|
-
if (0 == strcmp(a->args[i].key, GRPC_ARG_ENABLE_LOAD_REPORTING)) {
|
71
|
-
return a->args[i].type == GRPC_ARG_INTEGER &&
|
72
|
-
a->args[i].value.integer != 0;
|
73
|
-
}
|
74
|
-
}
|
75
|
-
return false;
|
51
|
+
return grpc_channel_arg_get_bool(
|
52
|
+
grpc_channel_args_find(a, GRPC_ARG_ENABLE_LOAD_REPORTING), false);
|
76
53
|
}
|
77
54
|
|
78
55
|
static bool maybe_add_load_reporting_filter(grpc_exec_ctx *exec_ctx,
|
@@ -48,6 +48,8 @@
|
|
48
48
|
|
49
49
|
typedef struct call_data {
|
50
50
|
intptr_t id; /**< an id unique to the call */
|
51
|
+
bool have_trailing_md_string;
|
52
|
+
grpc_slice trailing_md_string;
|
51
53
|
bool have_initial_md_string;
|
52
54
|
grpc_slice initial_md_string;
|
53
55
|
bool have_service_method;
|
@@ -140,6 +142,9 @@ static void destroy_call_elem(grpc_exec_ctx *exec_ctx, grpc_call_element *elem,
|
|
140
142
|
if (calld->have_initial_md_string) {
|
141
143
|
grpc_slice_unref_internal(exec_ctx, calld->initial_md_string);
|
142
144
|
}
|
145
|
+
if (calld->have_trailing_md_string) {
|
146
|
+
grpc_slice_unref_internal(exec_ctx, calld->trailing_md_string);
|
147
|
+
}
|
143
148
|
if (calld->have_service_method) {
|
144
149
|
grpc_slice_unref_internal(exec_ctx, calld->service_method);
|
145
150
|
}
|
@@ -183,6 +188,18 @@ static void destroy_channel_elem(grpc_exec_ctx *exec_ctx,
|
|
183
188
|
*/
|
184
189
|
}
|
185
190
|
|
191
|
+
static grpc_filtered_mdelem lr_trailing_md_filter(grpc_exec_ctx *exec_ctx,
|
192
|
+
void *user_data,
|
193
|
+
grpc_mdelem md) {
|
194
|
+
grpc_call_element *elem = user_data;
|
195
|
+
call_data *calld = elem->call_data;
|
196
|
+
if (grpc_slice_eq(GRPC_MDKEY(md), GRPC_MDSTR_LB_COST_BIN)) {
|
197
|
+
calld->trailing_md_string = GRPC_MDVALUE(md);
|
198
|
+
return GRPC_FILTERED_REMOVE();
|
199
|
+
}
|
200
|
+
return GRPC_FILTERED_MDELEM(md);
|
201
|
+
}
|
202
|
+
|
186
203
|
static void lr_start_transport_stream_op_batch(
|
187
204
|
grpc_exec_ctx *exec_ctx, grpc_call_element *elem,
|
188
205
|
grpc_transport_stream_op_batch *op) {
|
@@ -190,13 +207,21 @@ static void lr_start_transport_stream_op_batch(
|
|
190
207
|
call_data *calld = elem->call_data;
|
191
208
|
|
192
209
|
if (op->recv_initial_metadata) {
|
210
|
+
/* substitute our callback for the higher callback */
|
193
211
|
calld->recv_initial_metadata =
|
194
212
|
op->payload->recv_initial_metadata.recv_initial_metadata;
|
195
|
-
/* substitute our callback for the higher callback */
|
196
213
|
calld->ops_recv_initial_metadata_ready =
|
197
214
|
op->payload->recv_initial_metadata.recv_initial_metadata_ready;
|
198
215
|
op->payload->recv_initial_metadata.recv_initial_metadata_ready =
|
199
216
|
&calld->on_initial_md_ready;
|
217
|
+
} else if (op->send_trailing_metadata) {
|
218
|
+
GRPC_LOG_IF_ERROR(
|
219
|
+
"grpc_metadata_batch_filter",
|
220
|
+
grpc_metadata_batch_filter(
|
221
|
+
exec_ctx,
|
222
|
+
op->payload->send_trailing_metadata.send_trailing_metadata,
|
223
|
+
lr_trailing_md_filter, elem,
|
224
|
+
"LR trailing metadata filtering error"));
|
200
225
|
}
|
201
226
|
grpc_call_next_op(exec_ctx, elem, op);
|
202
227
|
|
@@ -47,6 +47,11 @@
|
|
47
47
|
#define DEFAULT_MAX_CONNECTION_IDLE_MS INT_MAX
|
48
48
|
#define MAX_CONNECTION_AGE_JITTER 0.1
|
49
49
|
|
50
|
+
#define MAX_CONNECTION_AGE_INTEGER_OPTIONS \
|
51
|
+
(grpc_integer_options) { DEFAULT_MAX_CONNECTION_AGE_MS, 1, INT_MAX }
|
52
|
+
#define MAX_CONNECTION_IDLE_INTEGER_OPTIONS \
|
53
|
+
(grpc_integer_options) { DEFAULT_MAX_CONNECTION_IDLE_MS, 1, INT_MAX }
|
54
|
+
|
50
55
|
typedef struct channel_data {
|
51
56
|
/* We take a reference to the channel stack for the timer callback */
|
52
57
|
grpc_channel_stack* channel_stack;
|
@@ -315,8 +320,7 @@ static grpc_error* init_channel_elem(grpc_exec_ctx* exec_ctx,
|
|
315
320
|
if (0 == strcmp(args->channel_args->args[i].key,
|
316
321
|
GRPC_ARG_MAX_CONNECTION_AGE_MS)) {
|
317
322
|
const int value = grpc_channel_arg_get_integer(
|
318
|
-
&args->channel_args->args[i],
|
319
|
-
(grpc_integer_options){DEFAULT_MAX_CONNECTION_AGE_MS, 1, INT_MAX});
|
323
|
+
&args->channel_args->args[i], MAX_CONNECTION_AGE_INTEGER_OPTIONS);
|
320
324
|
chand->max_connection_age =
|
321
325
|
value == INT_MAX
|
322
326
|
? gpr_inf_future(GPR_TIMESPAN)
|
@@ -334,8 +338,7 @@ static grpc_error* init_channel_elem(grpc_exec_ctx* exec_ctx,
|
|
334
338
|
} else if (0 == strcmp(args->channel_args->args[i].key,
|
335
339
|
GRPC_ARG_MAX_CONNECTION_IDLE_MS)) {
|
336
340
|
const int value = grpc_channel_arg_get_integer(
|
337
|
-
&args->channel_args->args[i],
|
338
|
-
(grpc_integer_options){DEFAULT_MAX_CONNECTION_IDLE_MS, 1, INT_MAX});
|
341
|
+
&args->channel_args->args[i], MAX_CONNECTION_IDLE_INTEGER_OPTIONS);
|
339
342
|
chand->max_connection_idle =
|
340
343
|
value == INT_MAX ? gpr_inf_future(GPR_TIMESPAN)
|
341
344
|
: gpr_time_from_millis(value, GPR_TIMESPAN);
|
@@ -412,16 +415,13 @@ static bool maybe_add_max_age_filter(grpc_exec_ctx* exec_ctx,
|
|
412
415
|
void* arg) {
|
413
416
|
const grpc_channel_args* channel_args =
|
414
417
|
grpc_channel_stack_builder_get_channel_arguments(builder);
|
415
|
-
|
416
|
-
|
417
|
-
|
418
|
-
|
419
|
-
|
420
|
-
|
421
|
-
|
422
|
-
if (a != NULL && a->type == GRPC_ARG_INTEGER && a->value.integer != INT_MAX) {
|
423
|
-
enable = true;
|
424
|
-
}
|
418
|
+
bool enable =
|
419
|
+
grpc_channel_arg_get_integer(
|
420
|
+
grpc_channel_args_find(channel_args, GRPC_ARG_MAX_CONNECTION_AGE_MS),
|
421
|
+
MAX_CONNECTION_AGE_INTEGER_OPTIONS) != INT_MAX &&
|
422
|
+
grpc_channel_arg_get_integer(
|
423
|
+
grpc_channel_args_find(channel_args, GRPC_ARG_MAX_CONNECTION_IDLE_MS),
|
424
|
+
MAX_CONNECTION_IDLE_INTEGER_OPTIONS) != INT_MAX;
|
425
425
|
if (enable) {
|
426
426
|
return grpc_channel_stack_builder_prepend_filter(
|
427
427
|
builder, &grpc_max_age_filter, NULL, NULL);
|
@@ -29,7 +29,7 @@
|
|
29
29
|
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
30
30
|
//
|
31
31
|
|
32
|
-
#include "src/core/
|
32
|
+
#include "src/core/ext/filters/message_size/message_size_filter.h"
|
33
33
|
|
34
34
|
#include <limits.h>
|
35
35
|
#include <string.h>
|
@@ -40,7 +40,9 @@
|
|
40
40
|
#include <grpc/support/string_util.h>
|
41
41
|
|
42
42
|
#include "src/core/lib/channel/channel_args.h"
|
43
|
+
#include "src/core/lib/channel/channel_stack_builder.h"
|
43
44
|
#include "src/core/lib/support/string.h"
|
45
|
+
#include "src/core/lib/surface/channel_init.h"
|
44
46
|
#include "src/core/lib/transport/service_config.h"
|
45
47
|
|
46
48
|
typedef struct message_size_limits {
|
@@ -48,19 +50,10 @@ typedef struct message_size_limits {
|
|
48
50
|
int max_recv_size;
|
49
51
|
} message_size_limits;
|
50
52
|
|
51
|
-
static void* message_size_limits_copy(void* value) {
|
52
|
-
void* new_value = gpr_malloc(sizeof(message_size_limits));
|
53
|
-
memcpy(new_value, value, sizeof(message_size_limits));
|
54
|
-
return new_value;
|
55
|
-
}
|
56
|
-
|
57
53
|
static void message_size_limits_free(grpc_exec_ctx* exec_ctx, void* value) {
|
58
54
|
gpr_free(value);
|
59
55
|
}
|
60
56
|
|
61
|
-
static const grpc_slice_hash_table_vtable message_size_limits_vtable = {
|
62
|
-
message_size_limits_free, message_size_limits_copy};
|
63
|
-
|
64
57
|
static void* message_size_limits_create_from_json(const grpc_json* json) {
|
65
58
|
int max_request_message_bytes = -1;
|
66
59
|
int max_response_message_bytes = -1;
|
@@ -89,8 +82,7 @@ static void* message_size_limits_create_from_json(const grpc_json* json) {
|
|
89
82
|
}
|
90
83
|
|
91
84
|
typedef struct call_data {
|
92
|
-
|
93
|
-
int max_recv_size;
|
85
|
+
message_size_limits limits;
|
94
86
|
// Receive closures are chained: we inject this closure as the
|
95
87
|
// recv_message_ready up-call on transport_stream_op, and remember to
|
96
88
|
// call our next_recv_message_ready member after handling it.
|
@@ -102,8 +94,7 @@ typedef struct call_data {
|
|
102
94
|
} call_data;
|
103
95
|
|
104
96
|
typedef struct channel_data {
|
105
|
-
|
106
|
-
int max_recv_size;
|
97
|
+
message_size_limits limits;
|
107
98
|
// Maps path names to message_size_limits structs.
|
108
99
|
grpc_slice_hash_table* method_limit_table;
|
109
100
|
} channel_data;
|
@@ -114,12 +105,12 @@ static void recv_message_ready(grpc_exec_ctx* exec_ctx, void* user_data,
|
|
114
105
|
grpc_error* error) {
|
115
106
|
grpc_call_element* elem = user_data;
|
116
107
|
call_data* calld = elem->call_data;
|
117
|
-
if (*calld->recv_message != NULL && calld->max_recv_size >= 0 &&
|
118
|
-
(*calld->recv_message)->length > (size_t)calld->max_recv_size) {
|
108
|
+
if (*calld->recv_message != NULL && calld->limits.max_recv_size >= 0 &&
|
109
|
+
(*calld->recv_message)->length > (size_t)calld->limits.max_recv_size) {
|
119
110
|
char* message_string;
|
120
111
|
gpr_asprintf(&message_string,
|
121
112
|
"Received message larger than max (%u vs. %d)",
|
122
|
-
(*calld->recv_message)->length, calld->max_recv_size);
|
113
|
+
(*calld->recv_message)->length, calld->limits.max_recv_size);
|
123
114
|
grpc_error* new_error = grpc_error_set_int(
|
124
115
|
GRPC_ERROR_CREATE_FROM_COPIED_STRING(message_string),
|
125
116
|
GRPC_ERROR_INT_GRPC_STATUS, GRPC_STATUS_RESOURCE_EXHAUSTED);
|
@@ -130,6 +121,8 @@ static void recv_message_ready(grpc_exec_ctx* exec_ctx, void* user_data,
|
|
130
121
|
GRPC_ERROR_UNREF(new_error);
|
131
122
|
}
|
132
123
|
gpr_free(message_string);
|
124
|
+
} else {
|
125
|
+
GRPC_ERROR_REF(error);
|
133
126
|
}
|
134
127
|
// Invoke the next callback.
|
135
128
|
grpc_closure_run(exec_ctx, calld->next_recv_message_ready, error);
|
@@ -141,13 +134,13 @@ static void start_transport_stream_op_batch(
|
|
141
134
|
grpc_transport_stream_op_batch* op) {
|
142
135
|
call_data* calld = elem->call_data;
|
143
136
|
// Check max send message size.
|
144
|
-
if (op->send_message && calld->max_send_size >= 0 &&
|
137
|
+
if (op->send_message && calld->limits.max_send_size >= 0 &&
|
145
138
|
op->payload->send_message.send_message->length >
|
146
|
-
(size_t)calld->max_send_size) {
|
139
|
+
(size_t)calld->limits.max_send_size) {
|
147
140
|
char* message_string;
|
148
141
|
gpr_asprintf(&message_string, "Sent message larger than max (%u vs. %d)",
|
149
142
|
op->payload->send_message.send_message->length,
|
150
|
-
calld->max_send_size);
|
143
|
+
calld->limits.max_send_size);
|
151
144
|
grpc_transport_stream_op_batch_finish_with_failure(
|
152
145
|
exec_ctx, op,
|
153
146
|
grpc_error_set_int(GRPC_ERROR_CREATE_FROM_COPIED_STRING(message_string),
|
@@ -180,21 +173,20 @@ static grpc_error* init_call_elem(grpc_exec_ctx* exec_ctx,
|
|
180
173
|
// Note: Per-method config is only available on the client, so we
|
181
174
|
// apply the max request size to the send limit and the max response
|
182
175
|
// size to the receive limit.
|
183
|
-
calld->
|
184
|
-
calld->max_recv_size = chand->max_recv_size;
|
176
|
+
calld->limits = chand->limits;
|
185
177
|
if (chand->method_limit_table != NULL) {
|
186
178
|
message_size_limits* limits = grpc_method_config_table_get(
|
187
179
|
exec_ctx, chand->method_limit_table, args->path);
|
188
180
|
if (limits != NULL) {
|
189
181
|
if (limits->max_send_size >= 0 &&
|
190
|
-
(limits->max_send_size < calld->max_send_size ||
|
191
|
-
calld->max_send_size < 0)) {
|
192
|
-
calld->max_send_size = limits->max_send_size;
|
182
|
+
(limits->max_send_size < calld->limits.max_send_size ||
|
183
|
+
calld->limits.max_send_size < 0)) {
|
184
|
+
calld->limits.max_send_size = limits->max_send_size;
|
193
185
|
}
|
194
186
|
if (limits->max_recv_size >= 0 &&
|
195
|
-
(limits->max_recv_size < calld->max_recv_size ||
|
196
|
-
calld->max_recv_size < 0)) {
|
197
|
-
calld->max_recv_size = limits->max_recv_size;
|
187
|
+
(limits->max_recv_size < calld->limits.max_recv_size ||
|
188
|
+
calld->limits.max_recv_size < 0)) {
|
189
|
+
calld->limits.max_recv_size = limits->max_recv_size;
|
198
190
|
}
|
199
191
|
}
|
200
192
|
}
|
@@ -206,30 +198,45 @@ static void destroy_call_elem(grpc_exec_ctx* exec_ctx, grpc_call_element* elem,
|
|
206
198
|
const grpc_call_final_info* final_info,
|
207
199
|
grpc_closure* ignored) {}
|
208
200
|
|
201
|
+
static int default_size(const grpc_channel_args* args,
|
202
|
+
int without_minimal_stack) {
|
203
|
+
if (grpc_channel_args_want_minimal_stack(args)) {
|
204
|
+
return -1;
|
205
|
+
}
|
206
|
+
return without_minimal_stack;
|
207
|
+
}
|
208
|
+
|
209
|
+
message_size_limits get_message_size_limits(
|
210
|
+
const grpc_channel_args* channel_args) {
|
211
|
+
message_size_limits lim;
|
212
|
+
lim.max_send_size =
|
213
|
+
default_size(channel_args, GRPC_DEFAULT_MAX_SEND_MESSAGE_LENGTH);
|
214
|
+
lim.max_recv_size =
|
215
|
+
default_size(channel_args, GRPC_DEFAULT_MAX_RECV_MESSAGE_LENGTH);
|
216
|
+
for (size_t i = 0; i < channel_args->num_args; ++i) {
|
217
|
+
if (strcmp(channel_args->args[i].key, GRPC_ARG_MAX_SEND_MESSAGE_LENGTH) ==
|
218
|
+
0) {
|
219
|
+
const grpc_integer_options options = {lim.max_send_size, -1, INT_MAX};
|
220
|
+
lim.max_send_size =
|
221
|
+
grpc_channel_arg_get_integer(&channel_args->args[i], options);
|
222
|
+
}
|
223
|
+
if (strcmp(channel_args->args[i].key,
|
224
|
+
GRPC_ARG_MAX_RECEIVE_MESSAGE_LENGTH) == 0) {
|
225
|
+
const grpc_integer_options options = {lim.max_recv_size, -1, INT_MAX};
|
226
|
+
lim.max_recv_size =
|
227
|
+
grpc_channel_arg_get_integer(&channel_args->args[i], options);
|
228
|
+
}
|
229
|
+
}
|
230
|
+
return lim;
|
231
|
+
}
|
232
|
+
|
209
233
|
// Constructor for channel_data.
|
210
234
|
static grpc_error* init_channel_elem(grpc_exec_ctx* exec_ctx,
|
211
235
|
grpc_channel_element* elem,
|
212
236
|
grpc_channel_element_args* args) {
|
213
237
|
GPR_ASSERT(!args->is_last);
|
214
238
|
channel_data* chand = elem->channel_data;
|
215
|
-
chand->
|
216
|
-
chand->max_recv_size = GRPC_DEFAULT_MAX_RECV_MESSAGE_LENGTH;
|
217
|
-
for (size_t i = 0; i < args->channel_args->num_args; ++i) {
|
218
|
-
if (strcmp(args->channel_args->args[i].key,
|
219
|
-
GRPC_ARG_MAX_SEND_MESSAGE_LENGTH) == 0) {
|
220
|
-
const grpc_integer_options options = {
|
221
|
-
GRPC_DEFAULT_MAX_SEND_MESSAGE_LENGTH, -1, INT_MAX};
|
222
|
-
chand->max_send_size =
|
223
|
-
grpc_channel_arg_get_integer(&args->channel_args->args[i], options);
|
224
|
-
}
|
225
|
-
if (strcmp(args->channel_args->args[i].key,
|
226
|
-
GRPC_ARG_MAX_RECEIVE_MESSAGE_LENGTH) == 0) {
|
227
|
-
const grpc_integer_options options = {
|
228
|
-
GRPC_DEFAULT_MAX_RECV_MESSAGE_LENGTH, -1, INT_MAX};
|
229
|
-
chand->max_recv_size =
|
230
|
-
grpc_channel_arg_get_integer(&args->channel_args->args[i], options);
|
231
|
-
}
|
232
|
-
}
|
239
|
+
chand->limits = get_message_size_limits(args->channel_args);
|
233
240
|
// Get method config table from channel args.
|
234
241
|
const grpc_arg* channel_arg =
|
235
242
|
grpc_channel_args_find(args->channel_args, GRPC_ARG_SERVICE_CONFIG);
|
@@ -241,7 +248,7 @@ static grpc_error* init_channel_elem(grpc_exec_ctx* exec_ctx,
|
|
241
248
|
chand->method_limit_table =
|
242
249
|
grpc_service_config_create_method_config_table(
|
243
250
|
exec_ctx, service_config, message_size_limits_create_from_json,
|
244
|
-
|
251
|
+
message_size_limits_free);
|
245
252
|
grpc_service_config_destroy(service_config);
|
246
253
|
}
|
247
254
|
}
|
@@ -268,3 +275,40 @@ const grpc_channel_filter grpc_message_size_filter = {
|
|
268
275
|
grpc_call_next_get_peer,
|
269
276
|
grpc_channel_next_get_info,
|
270
277
|
"message_size"};
|
278
|
+
|
279
|
+
static bool maybe_add_message_size_filter(grpc_exec_ctx* exec_ctx,
|
280
|
+
grpc_channel_stack_builder* builder,
|
281
|
+
void* arg) {
|
282
|
+
const grpc_channel_args* channel_args =
|
283
|
+
grpc_channel_stack_builder_get_channel_arguments(builder);
|
284
|
+
bool enable = false;
|
285
|
+
message_size_limits lim = get_message_size_limits(channel_args);
|
286
|
+
if (lim.max_send_size != -1 || lim.max_recv_size != -1) {
|
287
|
+
enable = true;
|
288
|
+
}
|
289
|
+
const grpc_arg* a =
|
290
|
+
grpc_channel_args_find(channel_args, GRPC_ARG_SERVICE_CONFIG);
|
291
|
+
if (a != NULL) {
|
292
|
+
enable = true;
|
293
|
+
}
|
294
|
+
if (enable) {
|
295
|
+
return grpc_channel_stack_builder_prepend_filter(
|
296
|
+
builder, &grpc_message_size_filter, NULL, NULL);
|
297
|
+
} else {
|
298
|
+
return true;
|
299
|
+
}
|
300
|
+
}
|
301
|
+
|
302
|
+
void grpc_message_size_filter_init(void) {
|
303
|
+
grpc_channel_init_register_stage(GRPC_CLIENT_SUBCHANNEL,
|
304
|
+
GRPC_CHANNEL_INIT_BUILTIN_PRIORITY,
|
305
|
+
maybe_add_message_size_filter, NULL);
|
306
|
+
grpc_channel_init_register_stage(GRPC_CLIENT_DIRECT_CHANNEL,
|
307
|
+
GRPC_CHANNEL_INIT_BUILTIN_PRIORITY,
|
308
|
+
maybe_add_message_size_filter, NULL);
|
309
|
+
grpc_channel_init_register_stage(GRPC_SERVER_CHANNEL,
|
310
|
+
GRPC_CHANNEL_INIT_BUILTIN_PRIORITY,
|
311
|
+
maybe_add_message_size_filter, NULL);
|
312
|
+
}
|
313
|
+
|
314
|
+
void grpc_message_size_filter_shutdown(void) {}
|
@@ -29,11 +29,11 @@
|
|
29
29
|
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
30
30
|
//
|
31
31
|
|
32
|
-
#ifndef
|
33
|
-
#define
|
32
|
+
#ifndef GRPC_CORE_EXT_FILTERS_MESSAGE_SIZE_MESSAGE_SIZE_FILTER_H
|
33
|
+
#define GRPC_CORE_EXT_FILTERS_MESSAGE_SIZE_MESSAGE_SIZE_FILTER_H
|
34
34
|
|
35
35
|
#include "src/core/lib/channel/channel_stack.h"
|
36
36
|
|
37
37
|
extern const grpc_channel_filter grpc_message_size_filter;
|
38
38
|
|
39
|
-
#endif /*
|
39
|
+
#endif /* GRPC_CORE_EXT_FILTERS_MESSAGE_SIZE_MESSAGE_SIZE_FILTER_H */
|
@@ -0,0 +1,223 @@
|
|
1
|
+
//
|
2
|
+
// Copyright 2017, Google Inc.
|
3
|
+
// All rights reserved.
|
4
|
+
//
|
5
|
+
// Redistribution and use in source and binary forms, with or without
|
6
|
+
// modification, are permitted provided that the following conditions are
|
7
|
+
// met:
|
8
|
+
//
|
9
|
+
// * Redistributions of source code must retain the above copyright
|
10
|
+
// notice, this list of conditions and the following disclaimer.
|
11
|
+
// * Redistributions in binary form must reproduce the above
|
12
|
+
// copyright notice, this list of conditions and the following disclaimer
|
13
|
+
// in the documentation and/or other materials provided with the
|
14
|
+
// distribution.
|
15
|
+
// * Neither the name of Google Inc. nor the names of its
|
16
|
+
// contributors may be used to endorse or promote products derived from
|
17
|
+
// this software without specific prior written permission.
|
18
|
+
//
|
19
|
+
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
20
|
+
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
21
|
+
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
|
22
|
+
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
23
|
+
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
24
|
+
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
|
25
|
+
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
26
|
+
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
27
|
+
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
28
|
+
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
29
|
+
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
30
|
+
//
|
31
|
+
|
32
|
+
#include "src/core/ext/filters/workarounds/workaround_cronet_compression_filter.h"
|
33
|
+
|
34
|
+
#include <string.h>
|
35
|
+
|
36
|
+
#include <grpc/support/alloc.h>
|
37
|
+
|
38
|
+
#include "src/core/ext/filters/workarounds/workaround_utils.h"
|
39
|
+
#include "src/core/lib/channel/channel_stack_builder.h"
|
40
|
+
#include "src/core/lib/surface/channel_init.h"
|
41
|
+
#include "src/core/lib/transport/metadata.h"
|
42
|
+
|
43
|
+
typedef struct call_data {
|
44
|
+
// Receive closures are chained: we inject this closure as the
|
45
|
+
// recv_initial_metadata_ready up-call on transport_stream_op, and remember to
|
46
|
+
// call our next_recv_initial_metadata_ready member after handling it.
|
47
|
+
grpc_closure recv_initial_metadata_ready;
|
48
|
+
// Used by recv_initial_metadata_ready.
|
49
|
+
grpc_metadata_batch* recv_initial_metadata;
|
50
|
+
// Original recv_initial_metadata_ready callback, invoked after our own.
|
51
|
+
grpc_closure* next_recv_initial_metadata_ready;
|
52
|
+
|
53
|
+
// Marks whether the workaround is active
|
54
|
+
bool workaround_active;
|
55
|
+
} call_data;
|
56
|
+
|
57
|
+
// Find the user agent metadata element in the batch
|
58
|
+
static bool get_user_agent_mdelem(const grpc_metadata_batch* batch,
|
59
|
+
grpc_mdelem* md) {
|
60
|
+
if (batch->idx.named.user_agent != NULL) {
|
61
|
+
*md = batch->idx.named.user_agent->md;
|
62
|
+
return true;
|
63
|
+
}
|
64
|
+
return false;
|
65
|
+
}
|
66
|
+
|
67
|
+
// Callback invoked when we receive an initial metadata.
|
68
|
+
static void recv_initial_metadata_ready(grpc_exec_ctx* exec_ctx,
|
69
|
+
void* user_data, grpc_error* error) {
|
70
|
+
grpc_call_element* elem = user_data;
|
71
|
+
call_data* calld = elem->call_data;
|
72
|
+
|
73
|
+
if (GRPC_ERROR_NONE == error) {
|
74
|
+
grpc_mdelem md;
|
75
|
+
if (get_user_agent_mdelem(calld->recv_initial_metadata, &md)) {
|
76
|
+
grpc_workaround_user_agent_md* user_agent_md = grpc_parse_user_agent(md);
|
77
|
+
if (user_agent_md
|
78
|
+
->workaround_active[GRPC_WORKAROUND_ID_CRONET_COMPRESSION]) {
|
79
|
+
calld->workaround_active = true;
|
80
|
+
}
|
81
|
+
}
|
82
|
+
}
|
83
|
+
|
84
|
+
// Invoke the next callback.
|
85
|
+
grpc_closure_run(exec_ctx, calld->next_recv_initial_metadata_ready,
|
86
|
+
GRPC_ERROR_REF(error));
|
87
|
+
}
|
88
|
+
|
89
|
+
// Start transport stream op.
|
90
|
+
static void start_transport_stream_op_batch(
|
91
|
+
grpc_exec_ctx* exec_ctx, grpc_call_element* elem,
|
92
|
+
grpc_transport_stream_op_batch* op) {
|
93
|
+
call_data* calld = elem->call_data;
|
94
|
+
|
95
|
+
// Inject callback for receiving initial metadata
|
96
|
+
if (op->recv_initial_metadata) {
|
97
|
+
calld->next_recv_initial_metadata_ready =
|
98
|
+
op->payload->recv_initial_metadata.recv_initial_metadata_ready;
|
99
|
+
op->payload->recv_initial_metadata.recv_initial_metadata_ready =
|
100
|
+
&calld->recv_initial_metadata_ready;
|
101
|
+
calld->recv_initial_metadata =
|
102
|
+
op->payload->recv_initial_metadata.recv_initial_metadata;
|
103
|
+
}
|
104
|
+
|
105
|
+
if (op->send_message) {
|
106
|
+
/* Send message happens after client's user-agent (initial metadata) is
|
107
|
+
* received, so workaround_active must be set already */
|
108
|
+
if (calld->workaround_active) {
|
109
|
+
op->payload->send_message.send_message->flags |= GRPC_WRITE_NO_COMPRESS;
|
110
|
+
}
|
111
|
+
}
|
112
|
+
|
113
|
+
// Chain to the next filter.
|
114
|
+
grpc_call_next_op(exec_ctx, elem, op);
|
115
|
+
}
|
116
|
+
|
117
|
+
// Constructor for call_data.
|
118
|
+
static grpc_error* init_call_elem(grpc_exec_ctx* exec_ctx,
|
119
|
+
grpc_call_element* elem,
|
120
|
+
const grpc_call_element_args* args) {
|
121
|
+
call_data* calld = elem->call_data;
|
122
|
+
calld->next_recv_initial_metadata_ready = NULL;
|
123
|
+
calld->workaround_active = false;
|
124
|
+
grpc_closure_init(&calld->recv_initial_metadata_ready,
|
125
|
+
recv_initial_metadata_ready, elem,
|
126
|
+
grpc_schedule_on_exec_ctx);
|
127
|
+
return GRPC_ERROR_NONE;
|
128
|
+
}
|
129
|
+
|
130
|
+
// Destructor for call_data.
|
131
|
+
static void destroy_call_elem(grpc_exec_ctx* exec_ctx, grpc_call_element* elem,
|
132
|
+
const grpc_call_final_info* final_info,
|
133
|
+
grpc_closure* ignored) {}
|
134
|
+
|
135
|
+
// Constructor for channel_data.
|
136
|
+
static grpc_error* init_channel_elem(grpc_exec_ctx* exec_ctx,
|
137
|
+
grpc_channel_element* elem,
|
138
|
+
grpc_channel_element_args* args) {
|
139
|
+
return GRPC_ERROR_NONE;
|
140
|
+
}
|
141
|
+
|
142
|
+
// Destructor for channel_data.
|
143
|
+
static void destroy_channel_elem(grpc_exec_ctx* exec_ctx,
|
144
|
+
grpc_channel_element* elem) {}
|
145
|
+
|
146
|
+
// Parse the user agent
|
147
|
+
static bool parse_user_agent(grpc_mdelem md) {
|
148
|
+
const char grpc_objc_specifier[] = "grpc-objc/";
|
149
|
+
const size_t grpc_objc_specifier_len = sizeof(grpc_objc_specifier) - 1;
|
150
|
+
const char cronet_specifier[] = "cronet_http";
|
151
|
+
const size_t cronet_specifier_len = sizeof(cronet_specifier) - 1;
|
152
|
+
|
153
|
+
char* user_agent_str = grpc_slice_to_c_string(GRPC_MDVALUE(md));
|
154
|
+
bool grpc_objc_specifier_seen = false;
|
155
|
+
bool cronet_specifier_seen = false;
|
156
|
+
char *major_version_str = user_agent_str, *minor_version_str;
|
157
|
+
long major_version, minor_version;
|
158
|
+
|
159
|
+
char* head = strtok(user_agent_str, " ");
|
160
|
+
while (head != NULL) {
|
161
|
+
if (!grpc_objc_specifier_seen &&
|
162
|
+
0 == strncmp(head, grpc_objc_specifier, grpc_objc_specifier_len)) {
|
163
|
+
major_version_str = head + grpc_objc_specifier_len;
|
164
|
+
grpc_objc_specifier_seen = true;
|
165
|
+
} else if (grpc_objc_specifier_seen &&
|
166
|
+
0 == strncmp(head, cronet_specifier, cronet_specifier_len)) {
|
167
|
+
cronet_specifier_seen = true;
|
168
|
+
break;
|
169
|
+
}
|
170
|
+
|
171
|
+
head = strtok(NULL, " ");
|
172
|
+
}
|
173
|
+
if (grpc_objc_specifier_seen) {
|
174
|
+
major_version_str = strtok(major_version_str, ".");
|
175
|
+
minor_version_str = strtok(NULL, ".");
|
176
|
+
major_version = atol(major_version_str);
|
177
|
+
minor_version = atol(minor_version_str);
|
178
|
+
}
|
179
|
+
|
180
|
+
gpr_free(user_agent_str);
|
181
|
+
return (grpc_objc_specifier_seen && cronet_specifier_seen &&
|
182
|
+
(major_version < 1 || (major_version == 1 && minor_version <= 3)));
|
183
|
+
}
|
184
|
+
|
185
|
+
const grpc_channel_filter grpc_workaround_cronet_compression_filter = {
|
186
|
+
start_transport_stream_op_batch,
|
187
|
+
grpc_channel_next_op,
|
188
|
+
sizeof(call_data),
|
189
|
+
init_call_elem,
|
190
|
+
grpc_call_stack_ignore_set_pollset_or_pollset_set,
|
191
|
+
destroy_call_elem,
|
192
|
+
0,
|
193
|
+
init_channel_elem,
|
194
|
+
destroy_channel_elem,
|
195
|
+
grpc_call_next_get_peer,
|
196
|
+
grpc_channel_next_get_info,
|
197
|
+
"workaround_cronet_compression"};
|
198
|
+
|
199
|
+
static bool register_workaround_cronet_compression(
|
200
|
+
grpc_exec_ctx* exec_ctx, grpc_channel_stack_builder* builder, void* arg) {
|
201
|
+
const grpc_channel_args* channel_args =
|
202
|
+
grpc_channel_stack_builder_get_channel_arguments(builder);
|
203
|
+
const grpc_arg* a = grpc_channel_args_find(
|
204
|
+
channel_args, GRPC_ARG_WORKAROUND_CRONET_COMPRESSION);
|
205
|
+
if (a == NULL) {
|
206
|
+
return true;
|
207
|
+
}
|
208
|
+
if (grpc_channel_arg_get_bool(a, false) == false) {
|
209
|
+
return true;
|
210
|
+
}
|
211
|
+
return grpc_channel_stack_builder_prepend_filter(
|
212
|
+
builder, &grpc_workaround_cronet_compression_filter, NULL, NULL);
|
213
|
+
}
|
214
|
+
|
215
|
+
void grpc_workaround_cronet_compression_filter_init(void) {
|
216
|
+
grpc_channel_init_register_stage(
|
217
|
+
GRPC_SERVER_CHANNEL, GRPC_WORKAROUND_PRIORITY_HIGH,
|
218
|
+
register_workaround_cronet_compression, NULL);
|
219
|
+
grpc_register_workaround(GRPC_WORKAROUND_ID_CRONET_COMPRESSION,
|
220
|
+
parse_user_agent);
|
221
|
+
}
|
222
|
+
|
223
|
+
void grpc_workaround_cronet_compression_filter_shutdown(void) {}
|