Compare commits

..

3 Commits

Author SHA1 Message Date
Hannah Shi 1c00c39bb3 bump ios.deployment_target to 12.0 for C++17 2025-02-26 10:36:59 -08:00
Hannah Shi 4469511bae upgrade swift package c++ standard to 17 2025-02-26 09:01:37 -08:00
Hannah Shi 83f9e5678f Sync c-core 1.70.1-pre2 2025-02-26 09:01:37 -08:00
1109 changed files with 35376 additions and 52224 deletions

View File

@ -23,7 +23,7 @@ env:
jobs:
release-cocoapod:
runs-on: macos-14
runs-on: macos-12
steps:
- name: Repo checkout
uses: actions/checkout@v3

View File

@ -24,7 +24,7 @@ let package = Package(
],
dependencies: [
.package(url: "https://github.com/firebase/abseil-cpp-SwiftPM.git", "0.20250127.0"..<"0.20250128.0"),
.package(url: "https://github.com/firebase/abseil-cpp-SwiftPM.git", "0.20240722.0"..<"0.20240723.0"),
.package(url: "https://github.com/firebase/boringssl-SwiftPM.git", "0.32.0"..<"0.33.0"),
],
@ -41,13 +41,14 @@ let package = Package(
"src/cpp/",
"third_party/upb/upb/port/def.inc",
"third_party/upb/upb/port/undef.inc",
"third_party/utf8_range/utf8_range_sse.inc",
"third_party/utf8_range/utf8_range_neon.inc",
"third_party/re2/LICENSE",
"third_party/utf8_range/LICENSE",
"third_party/xxhash/LICENSE",
"third_party/zlib/LICENSE",
"tests",
"include/grpc/grpc_cronet.h",
"src/core/ext/transport/cronet/",
"third_party/objective_c/Cronet/bidirectional_stream_c.h",
],
sources: [
@ -84,8 +85,8 @@ let package = Package(
path: basePath,
exclude: [
"tests",
"include/grpcpp/ports_undef.inc",
"include/grpcpp/ports_def.inc",
"include/grpcpp/security/cronet_credentials.h",
"src/cpp/client/cronet_credentials.cc",
],
sources: [
"src/cpp/",

View File

@ -22,7 +22,7 @@
Pod::Spec.new do |s|
s.name = 'gRPC-C++'
# TODO (mxyan): use version that match gRPC version when pod is stabilized
version = '1.73.1'
version = '1.71.0-pre2'
s.version = version
s.summary = 'gRPC C++ library'
s.homepage = 'https://grpc.io'
@ -34,8 +34,8 @@ Pod::Spec.new do |s|
:tag => "v#{version}",
}
s.ios.deployment_target = '15.0'
s.osx.deployment_target = '11.0'
s.ios.deployment_target = '12.0'
s.osx.deployment_target = '10.14'
s.tvos.deployment_target = '13.0'
s.watchos.deployment_target = '6.0'
s.visionos.deployment_target = '1.0'
@ -232,7 +232,7 @@ Pod::Spec.new do |s|
ss.dependency "#{s.name}/Privacy", version
ss.dependency "#{s.name}/Interface", version
ss.dependency 'gRPC-Core', version
abseil_version = '~> 1.20250127.1'
abseil_version = '~> 1.20240722.0'
ss.dependency 'abseil/algorithm/container', abseil_version
ss.dependency 'abseil/base/base', abseil_version
ss.dependency 'abseil/base/config', abseil_version
@ -240,7 +240,6 @@ Pod::Spec.new do |s|
ss.dependency 'abseil/base/log_severity', abseil_version
ss.dependency 'abseil/base/no_destructor', abseil_version
ss.dependency 'abseil/cleanup/cleanup', abseil_version
ss.dependency 'abseil/container/btree', abseil_version
ss.dependency 'abseil/container/flat_hash_map', abseil_version
ss.dependency 'abseil/container/flat_hash_set', abseil_version
ss.dependency 'abseil/container/inlined_vector', abseil_version
@ -272,30 +271,10 @@ Pod::Spec.new do |s|
ss.dependency 'abseil/types/span', abseil_version
ss.dependency 'abseil/utility/utility', abseil_version
ss.source_files = 'src/core/call/call_arena_allocator.h',
'src/core/call/call_destination.h',
'src/core/call/call_filters.h',
'src/core/call/call_finalization.h',
'src/core/call/call_spine.h',
'src/core/call/call_state.h',
'src/core/call/client_call.h',
'src/core/call/custom_metadata.h',
'src/core/call/interception_chain.h',
'src/core/call/message.h',
'src/core/call/metadata.h',
'src/core/call/metadata_batch.h',
'src/core/call/metadata_compression_traits.h',
'src/core/call/metadata_info.h',
'src/core/call/parsed_metadata.h',
'src/core/call/request_buffer.h',
'src/core/call/security_context.h',
'src/core/call/server_call.h',
'src/core/call/simple_slice_based_metadata.h',
'src/core/call/status_util.h',
ss.source_files = 'src/core/call/request_buffer.h',
'src/core/channelz/channel_trace.h',
'src/core/channelz/channelz.h',
'src/core/channelz/channelz_registry.h',
'src/core/channelz/ztrace_collector.h',
'src/core/client_channel/backup_poller.h',
'src/core/client_channel/client_channel.h',
'src/core/client_channel/client_channel_args.h',
@ -323,54 +302,6 @@ Pod::Spec.new do |s|
'src/core/config/config_vars.h',
'src/core/config/core_configuration.h',
'src/core/config/load_config.h',
'src/core/credentials/call/call_credentials.h',
'src/core/credentials/call/call_creds_util.h',
'src/core/credentials/call/composite/composite_call_credentials.h',
'src/core/credentials/call/external/aws_external_account_credentials.h',
'src/core/credentials/call/external/aws_request_signer.h',
'src/core/credentials/call/external/external_account_credentials.h',
'src/core/credentials/call/external/file_external_account_credentials.h',
'src/core/credentials/call/external/url_external_account_credentials.h',
'src/core/credentials/call/gcp_service_account_identity/gcp_service_account_identity_credentials.h',
'src/core/credentials/call/iam/iam_credentials.h',
'src/core/credentials/call/json_util.h',
'src/core/credentials/call/jwt/json_token.h',
'src/core/credentials/call/jwt/jwt_credentials.h',
'src/core/credentials/call/jwt/jwt_verifier.h',
'src/core/credentials/call/oauth2/oauth2_credentials.h',
'src/core/credentials/call/plugin/plugin_credentials.h',
'src/core/credentials/call/token_fetcher/token_fetcher_credentials.h',
'src/core/credentials/transport/alts/alts_credentials.h',
'src/core/credentials/transport/alts/alts_security_connector.h',
'src/core/credentials/transport/alts/check_gcp_environment.h',
'src/core/credentials/transport/alts/grpc_alts_credentials_options.h',
'src/core/credentials/transport/channel_creds_registry.h',
'src/core/credentials/transport/composite/composite_channel_credentials.h',
'src/core/credentials/transport/fake/fake_credentials.h',
'src/core/credentials/transport/fake/fake_security_connector.h',
'src/core/credentials/transport/google_default/google_default_credentials.h',
'src/core/credentials/transport/insecure/insecure_credentials.h',
'src/core/credentials/transport/insecure/insecure_security_connector.h',
'src/core/credentials/transport/local/local_credentials.h',
'src/core/credentials/transport/local/local_security_connector.h',
'src/core/credentials/transport/security_connector.h',
'src/core/credentials/transport/ssl/ssl_credentials.h',
'src/core/credentials/transport/ssl/ssl_security_connector.h',
'src/core/credentials/transport/tls/certificate_provider_factory.h',
'src/core/credentials/transport/tls/certificate_provider_registry.h',
'src/core/credentials/transport/tls/grpc_tls_certificate_distributor.h',
'src/core/credentials/transport/tls/grpc_tls_certificate_provider.h',
'src/core/credentials/transport/tls/grpc_tls_certificate_verifier.h',
'src/core/credentials/transport/tls/grpc_tls_credentials_options.h',
'src/core/credentials/transport/tls/grpc_tls_crl_provider.h',
'src/core/credentials/transport/tls/load_system_roots.h',
'src/core/credentials/transport/tls/load_system_roots_supported.h',
'src/core/credentials/transport/tls/ssl_utils.h',
'src/core/credentials/transport/tls/tls_credentials.h',
'src/core/credentials/transport/tls/tls_security_connector.h',
'src/core/credentials/transport/tls/tls_utils.h',
'src/core/credentials/transport/transport_credentials.h',
'src/core/credentials/transport/xds/xds_credentials.h',
'src/core/ext/filters/backend_metrics/backend_metric_filter.h',
'src/core/ext/filters/backend_metrics/backend_metric_provider.h',
'src/core/ext/filters/channel_idle/idle_filter_state.h',
@ -395,6 +326,7 @@ Pod::Spec.new do |s|
'src/core/ext/transport/chttp2/transport/bin_encoder.h',
'src/core/ext/transport/chttp2/transport/call_tracer_wrapper.h',
'src/core/ext/transport/chttp2/transport/chttp2_transport.h',
'src/core/ext/transport/chttp2/transport/context_list_entry.h',
'src/core/ext/transport/chttp2/transport/decode_huff.h',
'src/core/ext/transport/chttp2/transport/flow_control.h',
'src/core/ext/transport/chttp2/transport/frame.h',
@ -412,11 +344,8 @@ Pod::Spec.new do |s|
'src/core/ext/transport/chttp2/transport/hpack_parser.h',
'src/core/ext/transport/chttp2/transport/hpack_parser_table.h',
'src/core/ext/transport/chttp2/transport/http2_settings.h',
'src/core/ext/transport/chttp2/transport/http2_status.h',
'src/core/ext/transport/chttp2/transport/http2_ztrace_collector.h',
'src/core/ext/transport/chttp2/transport/huffsyms.h',
'src/core/ext/transport/chttp2/transport/internal.h',
'src/core/ext/transport/chttp2/transport/internal_channel_arg_names.h',
'src/core/ext/transport/chttp2/transport/legacy_frame.h',
'src/core/ext/transport/chttp2/transport/ping_abuse_policy.h',
'src/core/ext/transport/chttp2/transport/ping_callbacks.h',
@ -914,7 +843,6 @@ Pod::Spec.new do |s|
'src/core/ext/upbdefs-gen/xds/type/v3/cel.upbdefs.h',
'src/core/ext/upbdefs-gen/xds/type/v3/range.upbdefs.h',
'src/core/ext/upbdefs-gen/xds/type/v3/typed_struct.upbdefs.h',
'src/core/filter/auth/auth_filters.h',
'src/core/filter/blackboard.h',
'src/core/filter/filter_args.h',
'src/core/handshaker/endpoint_info/endpoint_info_handshaker.h',
@ -931,6 +859,7 @@ Pod::Spec.new do |s|
'src/core/handshaker/tcp_connect/tcp_connect_handshaker.h',
'src/core/lib/address_utils/parse_address.h',
'src/core/lib/address_utils/sockaddr_utils.h',
'src/core/lib/channel/call_finalization.h',
'src/core/lib/channel/channel_args.h',
'src/core/lib/channel/channel_args_preconditioning.h',
'src/core/lib/channel/channel_fwd.h',
@ -939,6 +868,7 @@ Pod::Spec.new do |s|
'src/core/lib/channel/channel_stack_builder_impl.h',
'src/core/lib/channel/connected_channel.h',
'src/core/lib/channel/promise_based_filter.h',
'src/core/lib/channel/status_util.h',
'src/core/lib/compression/compression_internal.h',
'src/core/lib/compression/message_compress.h',
'src/core/lib/debug/trace.h',
@ -954,13 +884,9 @@ Pod::Spec.new do |s|
'src/core/lib/event_engine/default_event_engine.h',
'src/core/lib/event_engine/default_event_engine_factory.h',
'src/core/lib/event_engine/event_engine_context.h',
'src/core/lib/event_engine/extensions/blocking_dns.h',
'src/core/lib/event_engine/extensions/can_track_errors.h',
'src/core/lib/event_engine/extensions/channelz.h',
'src/core/lib/event_engine/extensions/chaotic_good_extension.h',
'src/core/lib/event_engine/extensions/iomgr_compatible.h',
'src/core/lib/event_engine/extensions/supports_fd.h',
'src/core/lib/event_engine/extensions/supports_win_sockets.h',
'src/core/lib/event_engine/extensions/tcp_trace.h',
'src/core/lib/event_engine/forkable.h',
'src/core/lib/event_engine/grpc_polled_fd.h',
@ -1034,6 +960,7 @@ Pod::Spec.new do |s|
'src/core/lib/iomgr/event_engine_shims/endpoint.h',
'src/core/lib/iomgr/event_engine_shims/tcp_client.h',
'src/core/lib/iomgr/exec_ctx.h',
'src/core/lib/iomgr/executor.h',
'src/core/lib/iomgr/internal_errqueue.h',
'src/core/lib/iomgr/iocp_windows.h',
'src/core/lib/iomgr/iomgr.h',
@ -1122,6 +1049,54 @@ Pod::Spec.new do |s|
'src/core/lib/security/authorization/matchers.h',
'src/core/lib/security/authorization/rbac_policy.h',
'src/core/lib/security/authorization/stdout_logger.h',
'src/core/lib/security/certificate_provider/certificate_provider_factory.h',
'src/core/lib/security/certificate_provider/certificate_provider_registry.h',
'src/core/lib/security/context/security_context.h',
'src/core/lib/security/credentials/alts/alts_credentials.h',
'src/core/lib/security/credentials/alts/check_gcp_environment.h',
'src/core/lib/security/credentials/alts/grpc_alts_credentials_options.h',
'src/core/lib/security/credentials/call_creds_util.h',
'src/core/lib/security/credentials/channel_creds_registry.h',
'src/core/lib/security/credentials/composite/composite_credentials.h',
'src/core/lib/security/credentials/credentials.h',
'src/core/lib/security/credentials/external/aws_external_account_credentials.h',
'src/core/lib/security/credentials/external/aws_request_signer.h',
'src/core/lib/security/credentials/external/external_account_credentials.h',
'src/core/lib/security/credentials/external/file_external_account_credentials.h',
'src/core/lib/security/credentials/external/url_external_account_credentials.h',
'src/core/lib/security/credentials/fake/fake_credentials.h',
'src/core/lib/security/credentials/gcp_service_account_identity/gcp_service_account_identity_credentials.h',
'src/core/lib/security/credentials/google_default/google_default_credentials.h',
'src/core/lib/security/credentials/iam/iam_credentials.h',
'src/core/lib/security/credentials/insecure/insecure_credentials.h',
'src/core/lib/security/credentials/jwt/json_token.h',
'src/core/lib/security/credentials/jwt/jwt_credentials.h',
'src/core/lib/security/credentials/jwt/jwt_verifier.h',
'src/core/lib/security/credentials/local/local_credentials.h',
'src/core/lib/security/credentials/oauth2/oauth2_credentials.h',
'src/core/lib/security/credentials/plugin/plugin_credentials.h',
'src/core/lib/security/credentials/ssl/ssl_credentials.h',
'src/core/lib/security/credentials/tls/grpc_tls_certificate_distributor.h',
'src/core/lib/security/credentials/tls/grpc_tls_certificate_provider.h',
'src/core/lib/security/credentials/tls/grpc_tls_certificate_verifier.h',
'src/core/lib/security/credentials/tls/grpc_tls_credentials_options.h',
'src/core/lib/security/credentials/tls/grpc_tls_crl_provider.h',
'src/core/lib/security/credentials/tls/tls_credentials.h',
'src/core/lib/security/credentials/tls/tls_utils.h',
'src/core/lib/security/credentials/token_fetcher/token_fetcher_credentials.h',
'src/core/lib/security/credentials/xds/xds_credentials.h',
'src/core/lib/security/security_connector/alts/alts_security_connector.h',
'src/core/lib/security/security_connector/fake/fake_security_connector.h',
'src/core/lib/security/security_connector/insecure/insecure_security_connector.h',
'src/core/lib/security/security_connector/load_system_roots.h',
'src/core/lib/security/security_connector/load_system_roots_supported.h',
'src/core/lib/security/security_connector/local/local_security_connector.h',
'src/core/lib/security/security_connector/security_connector.h',
'src/core/lib/security/security_connector/ssl/ssl_security_connector.h',
'src/core/lib/security/security_connector/ssl_utils.h',
'src/core/lib/security/security_connector/tls/tls_security_connector.h',
'src/core/lib/security/transport/auth_filters.h',
'src/core/lib/security/util/json_util.h',
'src/core/lib/slice/percent_encoding.h',
'src/core/lib/slice/slice.h',
'src/core/lib/slice/slice_buffer.h',
@ -1135,6 +1110,7 @@ Pod::Spec.new do |s|
'src/core/lib/surface/channel_create.h',
'src/core/lib/surface/channel_init.h',
'src/core/lib/surface/channel_stack_type.h',
'src/core/lib/surface/client_call.h',
'src/core/lib/surface/completion_queue.h',
'src/core/lib/surface/completion_queue_factory.h',
'src/core/lib/surface/connection_context.h',
@ -1144,11 +1120,27 @@ Pod::Spec.new do |s|
'src/core/lib/surface/init_internally.h',
'src/core/lib/surface/lame_client.h',
'src/core/lib/surface/legacy_channel.h',
'src/core/lib/surface/server_call.h',
'src/core/lib/surface/validate_metadata.h',
'src/core/lib/transport/bdp_estimator.h',
'src/core/lib/transport/call_arena_allocator.h',
'src/core/lib/transport/call_destination.h',
'src/core/lib/transport/call_filters.h',
'src/core/lib/transport/call_final_info.h',
'src/core/lib/transport/call_spine.h',
'src/core/lib/transport/call_state.h',
'src/core/lib/transport/connectivity_state.h',
'src/core/lib/transport/custom_metadata.h',
'src/core/lib/transport/error_utils.h',
'src/core/lib/transport/http2_errors.h',
'src/core/lib/transport/interception_chain.h',
'src/core/lib/transport/message.h',
'src/core/lib/transport/metadata.h',
'src/core/lib/transport/metadata_batch.h',
'src/core/lib/transport/metadata_compression_traits.h',
'src/core/lib/transport/metadata_info.h',
'src/core/lib/transport/parsed_metadata.h',
'src/core/lib/transport/simple_slice_based_metadata.h',
'src/core/lib/transport/status_conversion.h',
'src/core/lib/transport/timeout_encoding.h',
'src/core/lib/transport/transport.h',
@ -1209,16 +1201,11 @@ Pod::Spec.new do |s|
'src/core/service_config/service_config_impl.h',
'src/core/service_config/service_config_parser.h',
'src/core/telemetry/call_tracer.h',
'src/core/telemetry/context_list_entry.h',
'src/core/telemetry/default_tcp_tracer.h',
'src/core/telemetry/histogram_view.h',
'src/core/telemetry/metrics.h',
'src/core/telemetry/stats.h',
'src/core/telemetry/stats_data.h',
'src/core/telemetry/tcp_tracer.h',
'src/core/transport/auth_context.h',
'src/core/transport/endpoint_transport.h',
'src/core/transport/endpoint_transport_client_channel_factory.h',
'src/core/tsi/alts/crypt/gsec.h',
'src/core/tsi/alts/frame_protector/alts_counter.h',
'src/core/tsi/alts/frame_protector/alts_crypter.h',
@ -1253,7 +1240,6 @@ Pod::Spec.new do |s|
'src/core/util/avl.h',
'src/core/util/backoff.h',
'src/core/util/bitset.h',
'src/core/util/check_class_size.h',
'src/core/util/chunked_vector.h',
'src/core/util/construct_destruct.h',
'src/core/util/cpp_impl_of.h',
@ -1267,7 +1253,6 @@ Pod::Spec.new do |s|
'src/core/util/event_log.h',
'src/core/util/examine_stack.h',
'src/core/util/fork.h',
'src/core/util/function_signature.h',
'src/core/util/gcp_metadata_query.h',
'src/core/util/gethostname.h',
'src/core/util/glob.h',
@ -1304,7 +1289,6 @@ Pod::Spec.new do |s|
'src/core/util/ref_counted_ptr.h',
'src/core/util/ref_counted_string.h',
'src/core/util/ring_buffer.h',
'src/core/util/shared_bit_gen.h',
'src/core/util/single_set_ptr.h',
'src/core/util/sorted_pack.h',
'src/core/util/spinlock.h',
@ -1486,8 +1470,8 @@ Pod::Spec.new do |s|
'third_party/upb/upb/message/copy.h',
'third_party/upb/upb/message/internal/accessors.h',
'third_party/upb/upb/message/internal/array.h',
'third_party/upb/upb/message/internal/compare_unknown.h',
'third_party/upb/upb/message/internal/extension.h',
'third_party/upb/upb/message/internal/iterator.h',
'third_party/upb/upb/message/internal/map.h',
'third_party/upb/upb/message/internal/map_entry.h',
'third_party/upb/upb/message/internal/map_sorter.h',
@ -1575,8 +1559,6 @@ Pod::Spec.new do |s|
'third_party/upb/upb/wire/reader.h',
'third_party/upb/upb/wire/types.h',
'third_party/utf8_range/utf8_range.h',
'third_party/utf8_range/utf8_range_neon.inc',
'third_party/utf8_range/utf8_range_sse.inc',
'third_party/xxhash/xxhash.h',
'third_party/zlib/crc32.h',
'third_party/zlib/deflate.h',
@ -1590,30 +1572,10 @@ Pod::Spec.new do |s|
'third_party/zlib/zlib.h',
'third_party/zlib/zutil.h'
ss.private_header_files = 'src/core/call/call_arena_allocator.h',
'src/core/call/call_destination.h',
'src/core/call/call_filters.h',
'src/core/call/call_finalization.h',
'src/core/call/call_spine.h',
'src/core/call/call_state.h',
'src/core/call/client_call.h',
'src/core/call/custom_metadata.h',
'src/core/call/interception_chain.h',
'src/core/call/message.h',
'src/core/call/metadata.h',
'src/core/call/metadata_batch.h',
'src/core/call/metadata_compression_traits.h',
'src/core/call/metadata_info.h',
'src/core/call/parsed_metadata.h',
'src/core/call/request_buffer.h',
'src/core/call/security_context.h',
'src/core/call/server_call.h',
'src/core/call/simple_slice_based_metadata.h',
'src/core/call/status_util.h',
ss.private_header_files = 'src/core/call/request_buffer.h',
'src/core/channelz/channel_trace.h',
'src/core/channelz/channelz.h',
'src/core/channelz/channelz_registry.h',
'src/core/channelz/ztrace_collector.h',
'src/core/client_channel/backup_poller.h',
'src/core/client_channel/client_channel.h',
'src/core/client_channel/client_channel_args.h',
@ -1641,54 +1603,6 @@ Pod::Spec.new do |s|
'src/core/config/config_vars.h',
'src/core/config/core_configuration.h',
'src/core/config/load_config.h',
'src/core/credentials/call/call_credentials.h',
'src/core/credentials/call/call_creds_util.h',
'src/core/credentials/call/composite/composite_call_credentials.h',
'src/core/credentials/call/external/aws_external_account_credentials.h',
'src/core/credentials/call/external/aws_request_signer.h',
'src/core/credentials/call/external/external_account_credentials.h',
'src/core/credentials/call/external/file_external_account_credentials.h',
'src/core/credentials/call/external/url_external_account_credentials.h',
'src/core/credentials/call/gcp_service_account_identity/gcp_service_account_identity_credentials.h',
'src/core/credentials/call/iam/iam_credentials.h',
'src/core/credentials/call/json_util.h',
'src/core/credentials/call/jwt/json_token.h',
'src/core/credentials/call/jwt/jwt_credentials.h',
'src/core/credentials/call/jwt/jwt_verifier.h',
'src/core/credentials/call/oauth2/oauth2_credentials.h',
'src/core/credentials/call/plugin/plugin_credentials.h',
'src/core/credentials/call/token_fetcher/token_fetcher_credentials.h',
'src/core/credentials/transport/alts/alts_credentials.h',
'src/core/credentials/transport/alts/alts_security_connector.h',
'src/core/credentials/transport/alts/check_gcp_environment.h',
'src/core/credentials/transport/alts/grpc_alts_credentials_options.h',
'src/core/credentials/transport/channel_creds_registry.h',
'src/core/credentials/transport/composite/composite_channel_credentials.h',
'src/core/credentials/transport/fake/fake_credentials.h',
'src/core/credentials/transport/fake/fake_security_connector.h',
'src/core/credentials/transport/google_default/google_default_credentials.h',
'src/core/credentials/transport/insecure/insecure_credentials.h',
'src/core/credentials/transport/insecure/insecure_security_connector.h',
'src/core/credentials/transport/local/local_credentials.h',
'src/core/credentials/transport/local/local_security_connector.h',
'src/core/credentials/transport/security_connector.h',
'src/core/credentials/transport/ssl/ssl_credentials.h',
'src/core/credentials/transport/ssl/ssl_security_connector.h',
'src/core/credentials/transport/tls/certificate_provider_factory.h',
'src/core/credentials/transport/tls/certificate_provider_registry.h',
'src/core/credentials/transport/tls/grpc_tls_certificate_distributor.h',
'src/core/credentials/transport/tls/grpc_tls_certificate_provider.h',
'src/core/credentials/transport/tls/grpc_tls_certificate_verifier.h',
'src/core/credentials/transport/tls/grpc_tls_credentials_options.h',
'src/core/credentials/transport/tls/grpc_tls_crl_provider.h',
'src/core/credentials/transport/tls/load_system_roots.h',
'src/core/credentials/transport/tls/load_system_roots_supported.h',
'src/core/credentials/transport/tls/ssl_utils.h',
'src/core/credentials/transport/tls/tls_credentials.h',
'src/core/credentials/transport/tls/tls_security_connector.h',
'src/core/credentials/transport/tls/tls_utils.h',
'src/core/credentials/transport/transport_credentials.h',
'src/core/credentials/transport/xds/xds_credentials.h',
'src/core/ext/filters/backend_metrics/backend_metric_filter.h',
'src/core/ext/filters/backend_metrics/backend_metric_provider.h',
'src/core/ext/filters/channel_idle/idle_filter_state.h',
@ -1713,6 +1627,7 @@ Pod::Spec.new do |s|
'src/core/ext/transport/chttp2/transport/bin_encoder.h',
'src/core/ext/transport/chttp2/transport/call_tracer_wrapper.h',
'src/core/ext/transport/chttp2/transport/chttp2_transport.h',
'src/core/ext/transport/chttp2/transport/context_list_entry.h',
'src/core/ext/transport/chttp2/transport/decode_huff.h',
'src/core/ext/transport/chttp2/transport/flow_control.h',
'src/core/ext/transport/chttp2/transport/frame.h',
@ -1730,11 +1645,8 @@ Pod::Spec.new do |s|
'src/core/ext/transport/chttp2/transport/hpack_parser.h',
'src/core/ext/transport/chttp2/transport/hpack_parser_table.h',
'src/core/ext/transport/chttp2/transport/http2_settings.h',
'src/core/ext/transport/chttp2/transport/http2_status.h',
'src/core/ext/transport/chttp2/transport/http2_ztrace_collector.h',
'src/core/ext/transport/chttp2/transport/huffsyms.h',
'src/core/ext/transport/chttp2/transport/internal.h',
'src/core/ext/transport/chttp2/transport/internal_channel_arg_names.h',
'src/core/ext/transport/chttp2/transport/legacy_frame.h',
'src/core/ext/transport/chttp2/transport/ping_abuse_policy.h',
'src/core/ext/transport/chttp2/transport/ping_callbacks.h',
@ -2232,7 +2144,6 @@ Pod::Spec.new do |s|
'src/core/ext/upbdefs-gen/xds/type/v3/cel.upbdefs.h',
'src/core/ext/upbdefs-gen/xds/type/v3/range.upbdefs.h',
'src/core/ext/upbdefs-gen/xds/type/v3/typed_struct.upbdefs.h',
'src/core/filter/auth/auth_filters.h',
'src/core/filter/blackboard.h',
'src/core/filter/filter_args.h',
'src/core/handshaker/endpoint_info/endpoint_info_handshaker.h',
@ -2249,6 +2160,7 @@ Pod::Spec.new do |s|
'src/core/handshaker/tcp_connect/tcp_connect_handshaker.h',
'src/core/lib/address_utils/parse_address.h',
'src/core/lib/address_utils/sockaddr_utils.h',
'src/core/lib/channel/call_finalization.h',
'src/core/lib/channel/channel_args.h',
'src/core/lib/channel/channel_args_preconditioning.h',
'src/core/lib/channel/channel_fwd.h',
@ -2257,6 +2169,7 @@ Pod::Spec.new do |s|
'src/core/lib/channel/channel_stack_builder_impl.h',
'src/core/lib/channel/connected_channel.h',
'src/core/lib/channel/promise_based_filter.h',
'src/core/lib/channel/status_util.h',
'src/core/lib/compression/compression_internal.h',
'src/core/lib/compression/message_compress.h',
'src/core/lib/debug/trace.h',
@ -2272,13 +2185,9 @@ Pod::Spec.new do |s|
'src/core/lib/event_engine/default_event_engine.h',
'src/core/lib/event_engine/default_event_engine_factory.h',
'src/core/lib/event_engine/event_engine_context.h',
'src/core/lib/event_engine/extensions/blocking_dns.h',
'src/core/lib/event_engine/extensions/can_track_errors.h',
'src/core/lib/event_engine/extensions/channelz.h',
'src/core/lib/event_engine/extensions/chaotic_good_extension.h',
'src/core/lib/event_engine/extensions/iomgr_compatible.h',
'src/core/lib/event_engine/extensions/supports_fd.h',
'src/core/lib/event_engine/extensions/supports_win_sockets.h',
'src/core/lib/event_engine/extensions/tcp_trace.h',
'src/core/lib/event_engine/forkable.h',
'src/core/lib/event_engine/grpc_polled_fd.h',
@ -2352,6 +2261,7 @@ Pod::Spec.new do |s|
'src/core/lib/iomgr/event_engine_shims/endpoint.h',
'src/core/lib/iomgr/event_engine_shims/tcp_client.h',
'src/core/lib/iomgr/exec_ctx.h',
'src/core/lib/iomgr/executor.h',
'src/core/lib/iomgr/internal_errqueue.h',
'src/core/lib/iomgr/iocp_windows.h',
'src/core/lib/iomgr/iomgr.h',
@ -2440,6 +2350,54 @@ Pod::Spec.new do |s|
'src/core/lib/security/authorization/matchers.h',
'src/core/lib/security/authorization/rbac_policy.h',
'src/core/lib/security/authorization/stdout_logger.h',
'src/core/lib/security/certificate_provider/certificate_provider_factory.h',
'src/core/lib/security/certificate_provider/certificate_provider_registry.h',
'src/core/lib/security/context/security_context.h',
'src/core/lib/security/credentials/alts/alts_credentials.h',
'src/core/lib/security/credentials/alts/check_gcp_environment.h',
'src/core/lib/security/credentials/alts/grpc_alts_credentials_options.h',
'src/core/lib/security/credentials/call_creds_util.h',
'src/core/lib/security/credentials/channel_creds_registry.h',
'src/core/lib/security/credentials/composite/composite_credentials.h',
'src/core/lib/security/credentials/credentials.h',
'src/core/lib/security/credentials/external/aws_external_account_credentials.h',
'src/core/lib/security/credentials/external/aws_request_signer.h',
'src/core/lib/security/credentials/external/external_account_credentials.h',
'src/core/lib/security/credentials/external/file_external_account_credentials.h',
'src/core/lib/security/credentials/external/url_external_account_credentials.h',
'src/core/lib/security/credentials/fake/fake_credentials.h',
'src/core/lib/security/credentials/gcp_service_account_identity/gcp_service_account_identity_credentials.h',
'src/core/lib/security/credentials/google_default/google_default_credentials.h',
'src/core/lib/security/credentials/iam/iam_credentials.h',
'src/core/lib/security/credentials/insecure/insecure_credentials.h',
'src/core/lib/security/credentials/jwt/json_token.h',
'src/core/lib/security/credentials/jwt/jwt_credentials.h',
'src/core/lib/security/credentials/jwt/jwt_verifier.h',
'src/core/lib/security/credentials/local/local_credentials.h',
'src/core/lib/security/credentials/oauth2/oauth2_credentials.h',
'src/core/lib/security/credentials/plugin/plugin_credentials.h',
'src/core/lib/security/credentials/ssl/ssl_credentials.h',
'src/core/lib/security/credentials/tls/grpc_tls_certificate_distributor.h',
'src/core/lib/security/credentials/tls/grpc_tls_certificate_provider.h',
'src/core/lib/security/credentials/tls/grpc_tls_certificate_verifier.h',
'src/core/lib/security/credentials/tls/grpc_tls_credentials_options.h',
'src/core/lib/security/credentials/tls/grpc_tls_crl_provider.h',
'src/core/lib/security/credentials/tls/tls_credentials.h',
'src/core/lib/security/credentials/tls/tls_utils.h',
'src/core/lib/security/credentials/token_fetcher/token_fetcher_credentials.h',
'src/core/lib/security/credentials/xds/xds_credentials.h',
'src/core/lib/security/security_connector/alts/alts_security_connector.h',
'src/core/lib/security/security_connector/fake/fake_security_connector.h',
'src/core/lib/security/security_connector/insecure/insecure_security_connector.h',
'src/core/lib/security/security_connector/load_system_roots.h',
'src/core/lib/security/security_connector/load_system_roots_supported.h',
'src/core/lib/security/security_connector/local/local_security_connector.h',
'src/core/lib/security/security_connector/security_connector.h',
'src/core/lib/security/security_connector/ssl/ssl_security_connector.h',
'src/core/lib/security/security_connector/ssl_utils.h',
'src/core/lib/security/security_connector/tls/tls_security_connector.h',
'src/core/lib/security/transport/auth_filters.h',
'src/core/lib/security/util/json_util.h',
'src/core/lib/slice/percent_encoding.h',
'src/core/lib/slice/slice.h',
'src/core/lib/slice/slice_buffer.h',
@ -2453,6 +2411,7 @@ Pod::Spec.new do |s|
'src/core/lib/surface/channel_create.h',
'src/core/lib/surface/channel_init.h',
'src/core/lib/surface/channel_stack_type.h',
'src/core/lib/surface/client_call.h',
'src/core/lib/surface/completion_queue.h',
'src/core/lib/surface/completion_queue_factory.h',
'src/core/lib/surface/connection_context.h',
@ -2462,11 +2421,27 @@ Pod::Spec.new do |s|
'src/core/lib/surface/init_internally.h',
'src/core/lib/surface/lame_client.h',
'src/core/lib/surface/legacy_channel.h',
'src/core/lib/surface/server_call.h',
'src/core/lib/surface/validate_metadata.h',
'src/core/lib/transport/bdp_estimator.h',
'src/core/lib/transport/call_arena_allocator.h',
'src/core/lib/transport/call_destination.h',
'src/core/lib/transport/call_filters.h',
'src/core/lib/transport/call_final_info.h',
'src/core/lib/transport/call_spine.h',
'src/core/lib/transport/call_state.h',
'src/core/lib/transport/connectivity_state.h',
'src/core/lib/transport/custom_metadata.h',
'src/core/lib/transport/error_utils.h',
'src/core/lib/transport/http2_errors.h',
'src/core/lib/transport/interception_chain.h',
'src/core/lib/transport/message.h',
'src/core/lib/transport/metadata.h',
'src/core/lib/transport/metadata_batch.h',
'src/core/lib/transport/metadata_compression_traits.h',
'src/core/lib/transport/metadata_info.h',
'src/core/lib/transport/parsed_metadata.h',
'src/core/lib/transport/simple_slice_based_metadata.h',
'src/core/lib/transport/status_conversion.h',
'src/core/lib/transport/timeout_encoding.h',
'src/core/lib/transport/transport.h',
@ -2527,16 +2502,11 @@ Pod::Spec.new do |s|
'src/core/service_config/service_config_impl.h',
'src/core/service_config/service_config_parser.h',
'src/core/telemetry/call_tracer.h',
'src/core/telemetry/context_list_entry.h',
'src/core/telemetry/default_tcp_tracer.h',
'src/core/telemetry/histogram_view.h',
'src/core/telemetry/metrics.h',
'src/core/telemetry/stats.h',
'src/core/telemetry/stats_data.h',
'src/core/telemetry/tcp_tracer.h',
'src/core/transport/auth_context.h',
'src/core/transport/endpoint_transport.h',
'src/core/transport/endpoint_transport_client_channel_factory.h',
'src/core/tsi/alts/crypt/gsec.h',
'src/core/tsi/alts/frame_protector/alts_counter.h',
'src/core/tsi/alts/frame_protector/alts_crypter.h',
@ -2571,7 +2541,6 @@ Pod::Spec.new do |s|
'src/core/util/avl.h',
'src/core/util/backoff.h',
'src/core/util/bitset.h',
'src/core/util/check_class_size.h',
'src/core/util/chunked_vector.h',
'src/core/util/construct_destruct.h',
'src/core/util/cpp_impl_of.h',
@ -2585,7 +2554,6 @@ Pod::Spec.new do |s|
'src/core/util/event_log.h',
'src/core/util/examine_stack.h',
'src/core/util/fork.h',
'src/core/util/function_signature.h',
'src/core/util/gcp_metadata_query.h',
'src/core/util/gethostname.h',
'src/core/util/glob.h',
@ -2622,7 +2590,6 @@ Pod::Spec.new do |s|
'src/core/util/ref_counted_ptr.h',
'src/core/util/ref_counted_string.h',
'src/core/util/ring_buffer.h',
'src/core/util/shared_bit_gen.h',
'src/core/util/single_set_ptr.h',
'src/core/util/sorted_pack.h',
'src/core/util/spinlock.h',
@ -2754,8 +2721,8 @@ Pod::Spec.new do |s|
'third_party/upb/upb/message/copy.h',
'third_party/upb/upb/message/internal/accessors.h',
'third_party/upb/upb/message/internal/array.h',
'third_party/upb/upb/message/internal/compare_unknown.h',
'third_party/upb/upb/message/internal/extension.h',
'third_party/upb/upb/message/internal/iterator.h',
'third_party/upb/upb/message/internal/map.h',
'third_party/upb/upb/message/internal/map_entry.h',
'third_party/upb/upb/message/internal/map_sorter.h',
@ -2843,8 +2810,6 @@ Pod::Spec.new do |s|
'third_party/upb/upb/wire/reader.h',
'third_party/upb/upb/wire/types.h',
'third_party/utf8_range/utf8_range.h',
'third_party/utf8_range/utf8_range_neon.inc',
'third_party/utf8_range/utf8_range_sse.inc',
'third_party/xxhash/xxhash.h',
'third_party/zlib/crc32.h',
'third_party/zlib/deflate.h',
@ -2869,6 +2834,25 @@ Pod::Spec.new do |s|
'include/grpcpp/impl/codegen/proto_utils.h'
end
s.subspec 'Cronet-Interface' do |ss|
ss.header_mappings_dir = 'include/grpcpp'
ss.public_header_files = "include/grpcpp/security/cronet_credentials.h",
"include/grpcpp/security/cronet_credentials_impl.h"
ss.source_files = "include/grpcpp/security/cronet_credentials.h",
"include/grpcpp/security/cronet_credentials_impl.h"
end
s.subspec 'Cronet-Implementation' do |ss|
ss.header_mappings_dir = '.'
ss.dependency "#{s.name}/Cronet-Interface", version
ss.dependency "#{s.name}/Implementation", version
ss.dependency "#{s.name}/Privacy", version
ss.dependency 'gRPC-Core/Cronet-Implementation', version
ss.source_files = "src/cpp/client/cronet_credentials.cc"
end
# patch include of openssl to openssl_grpc
s.prepare_command = <<-END_OF_COMMAND
set -e

View File

@ -21,7 +21,7 @@
Pod::Spec.new do |s|
s.name = 'gRPC-Core'
version = '1.73.1'
version = '1.71.0-pre2'
s.version = version
s.summary = 'Core cross-platform gRPC library, written in C'
s.homepage = 'https://grpc.io'
@ -38,8 +38,8 @@ Pod::Spec.new do |s|
# which was released in Cocoapods v1.2.0.
s.cocoapods_version = '>= 1.2.0'
s.ios.deployment_target = '15.0'
s.osx.deployment_target = '11.0'
s.ios.deployment_target = '12.0'
s.osx.deployment_target = '10.14'
s.tvos.deployment_target = '13.0'
s.watchos.deployment_target = '6.0'
s.visionos.deployment_target = '1.0'
@ -47,7 +47,7 @@ Pod::Spec.new do |s|
s.requires_arc = false
name = 'grpc'
abseil_version = '~> 1.20250127.1'
abseil_version = '~> 1.20240722.0'
# When creating a dynamic framework, name it grpc.framework instead of gRPC-Core.framework.
# This lets users write their includes like `#include <grpc/grpc.h>` as opposed to `#include
@ -127,7 +127,6 @@ Pod::Spec.new do |s|
'include/grpc/event_engine/extensible.h',
'include/grpc/event_engine/internal/memory_allocator_impl.h',
'include/grpc/event_engine/internal/slice_cast.h',
'include/grpc/event_engine/internal/write_event.h',
'include/grpc/event_engine/memory_allocator.h',
'include/grpc/event_engine/memory_request.h',
'include/grpc/event_engine/port.h',
@ -201,7 +200,7 @@ Pod::Spec.new do |s|
ss.libraries = 'z'
ss.dependency "#{s.name}/Interface", version
ss.dependency "#{s.name}/Privacy", version
ss.dependency 'BoringSSL-GRPC', '0.0.41'
ss.dependency 'BoringSSL-GRPC', '0.0.39'
ss.dependency 'abseil/algorithm/container', abseil_version
ss.dependency 'abseil/base/base', abseil_version
ss.dependency 'abseil/base/config', abseil_version
@ -209,7 +208,6 @@ Pod::Spec.new do |s|
ss.dependency 'abseil/base/log_severity', abseil_version
ss.dependency 'abseil/base/no_destructor', abseil_version
ss.dependency 'abseil/cleanup/cleanup', abseil_version
ss.dependency 'abseil/container/btree', abseil_version
ss.dependency 'abseil/container/flat_hash_map', abseil_version
ss.dependency 'abseil/container/flat_hash_set', abseil_version
ss.dependency 'abseil/container/inlined_vector', abseil_version
@ -240,48 +238,14 @@ Pod::Spec.new do |s|
ss.dependency 'abseil/utility/utility', abseil_version
ss.compiler_flags = '-DBORINGSSL_PREFIX=GRPC -Wno-unreachable-code -Wno-shorten-64-to-32'
ss.source_files = 'src/core/call/call_arena_allocator.cc',
'src/core/call/call_arena_allocator.h',
'src/core/call/call_destination.h',
'src/core/call/call_filters.cc',
'src/core/call/call_filters.h',
'src/core/call/call_finalization.h',
'src/core/call/call_spine.cc',
'src/core/call/call_spine.h',
'src/core/call/call_state.cc',
'src/core/call/call_state.h',
'src/core/call/client_call.cc',
'src/core/call/client_call.h',
'src/core/call/custom_metadata.h',
'src/core/call/interception_chain.cc',
'src/core/call/interception_chain.h',
'src/core/call/message.cc',
'src/core/call/message.h',
'src/core/call/metadata.cc',
'src/core/call/metadata.h',
'src/core/call/metadata_batch.cc',
'src/core/call/metadata_batch.h',
'src/core/call/metadata_compression_traits.h',
'src/core/call/metadata_info.cc',
'src/core/call/metadata_info.h',
'src/core/call/parsed_metadata.cc',
'src/core/call/parsed_metadata.h',
'src/core/call/request_buffer.cc',
ss.source_files = 'src/core/call/request_buffer.cc',
'src/core/call/request_buffer.h',
'src/core/call/security_context.cc',
'src/core/call/security_context.h',
'src/core/call/server_call.cc',
'src/core/call/server_call.h',
'src/core/call/simple_slice_based_metadata.h',
'src/core/call/status_util.cc',
'src/core/call/status_util.h',
'src/core/channelz/channel_trace.cc',
'src/core/channelz/channel_trace.h',
'src/core/channelz/channelz.cc',
'src/core/channelz/channelz.h',
'src/core/channelz/channelz_registry.cc',
'src/core/channelz/channelz_registry.h',
'src/core/channelz/ztrace_collector.h',
'src/core/client_channel/backup_poller.cc',
'src/core/client_channel/backup_poller.h',
'src/core/client_channel/client_channel.cc',
@ -333,108 +297,6 @@ Pod::Spec.new do |s|
'src/core/config/core_configuration.h',
'src/core/config/load_config.cc',
'src/core/config/load_config.h',
'src/core/credentials/call/call_credentials.h',
'src/core/credentials/call/call_creds_util.cc',
'src/core/credentials/call/call_creds_util.h',
'src/core/credentials/call/composite/composite_call_credentials.cc',
'src/core/credentials/call/composite/composite_call_credentials.h',
'src/core/credentials/call/external/aws_external_account_credentials.cc',
'src/core/credentials/call/external/aws_external_account_credentials.h',
'src/core/credentials/call/external/aws_request_signer.cc',
'src/core/credentials/call/external/aws_request_signer.h',
'src/core/credentials/call/external/external_account_credentials.cc',
'src/core/credentials/call/external/external_account_credentials.h',
'src/core/credentials/call/external/file_external_account_credentials.cc',
'src/core/credentials/call/external/file_external_account_credentials.h',
'src/core/credentials/call/external/url_external_account_credentials.cc',
'src/core/credentials/call/external/url_external_account_credentials.h',
'src/core/credentials/call/gcp_service_account_identity/gcp_service_account_identity_credentials.cc',
'src/core/credentials/call/gcp_service_account_identity/gcp_service_account_identity_credentials.h',
'src/core/credentials/call/iam/iam_credentials.cc',
'src/core/credentials/call/iam/iam_credentials.h',
'src/core/credentials/call/json_util.cc',
'src/core/credentials/call/json_util.h',
'src/core/credentials/call/jwt/json_token.cc',
'src/core/credentials/call/jwt/json_token.h',
'src/core/credentials/call/jwt/jwt_credentials.cc',
'src/core/credentials/call/jwt/jwt_credentials.h',
'src/core/credentials/call/jwt/jwt_verifier.cc',
'src/core/credentials/call/jwt/jwt_verifier.h',
'src/core/credentials/call/oauth2/oauth2_credentials.cc',
'src/core/credentials/call/oauth2/oauth2_credentials.h',
'src/core/credentials/call/plugin/plugin_credentials.cc',
'src/core/credentials/call/plugin/plugin_credentials.h',
'src/core/credentials/call/token_fetcher/token_fetcher_credentials.cc',
'src/core/credentials/call/token_fetcher/token_fetcher_credentials.h',
'src/core/credentials/transport/alts/alts_credentials.cc',
'src/core/credentials/transport/alts/alts_credentials.h',
'src/core/credentials/transport/alts/alts_security_connector.cc',
'src/core/credentials/transport/alts/alts_security_connector.h',
'src/core/credentials/transport/alts/check_gcp_environment.cc',
'src/core/credentials/transport/alts/check_gcp_environment.h',
'src/core/credentials/transport/alts/check_gcp_environment_linux.cc',
'src/core/credentials/transport/alts/check_gcp_environment_no_op.cc',
'src/core/credentials/transport/alts/check_gcp_environment_windows.cc',
'src/core/credentials/transport/alts/grpc_alts_credentials_client_options.cc',
'src/core/credentials/transport/alts/grpc_alts_credentials_options.cc',
'src/core/credentials/transport/alts/grpc_alts_credentials_options.h',
'src/core/credentials/transport/alts/grpc_alts_credentials_server_options.cc',
'src/core/credentials/transport/channel_creds_registry.h',
'src/core/credentials/transport/channel_creds_registry_init.cc',
'src/core/credentials/transport/composite/composite_channel_credentials.cc',
'src/core/credentials/transport/composite/composite_channel_credentials.h',
'src/core/credentials/transport/fake/fake_credentials.cc',
'src/core/credentials/transport/fake/fake_credentials.h',
'src/core/credentials/transport/fake/fake_security_connector.cc',
'src/core/credentials/transport/fake/fake_security_connector.h',
'src/core/credentials/transport/google_default/credentials_generic.cc',
'src/core/credentials/transport/google_default/google_default_credentials.cc',
'src/core/credentials/transport/google_default/google_default_credentials.h',
'src/core/credentials/transport/insecure/insecure_credentials.cc',
'src/core/credentials/transport/insecure/insecure_credentials.h',
'src/core/credentials/transport/insecure/insecure_security_connector.cc',
'src/core/credentials/transport/insecure/insecure_security_connector.h',
'src/core/credentials/transport/local/local_credentials.cc',
'src/core/credentials/transport/local/local_credentials.h',
'src/core/credentials/transport/local/local_security_connector.cc',
'src/core/credentials/transport/local/local_security_connector.h',
'src/core/credentials/transport/security_connector.cc',
'src/core/credentials/transport/security_connector.h',
'src/core/credentials/transport/ssl/ssl_credentials.cc',
'src/core/credentials/transport/ssl/ssl_credentials.h',
'src/core/credentials/transport/ssl/ssl_security_connector.cc',
'src/core/credentials/transport/ssl/ssl_security_connector.h',
'src/core/credentials/transport/tls/certificate_provider_factory.h',
'src/core/credentials/transport/tls/certificate_provider_registry.cc',
'src/core/credentials/transport/tls/certificate_provider_registry.h',
'src/core/credentials/transport/tls/grpc_tls_certificate_distributor.cc',
'src/core/credentials/transport/tls/grpc_tls_certificate_distributor.h',
'src/core/credentials/transport/tls/grpc_tls_certificate_match.cc',
'src/core/credentials/transport/tls/grpc_tls_certificate_provider.cc',
'src/core/credentials/transport/tls/grpc_tls_certificate_provider.h',
'src/core/credentials/transport/tls/grpc_tls_certificate_verifier.cc',
'src/core/credentials/transport/tls/grpc_tls_certificate_verifier.h',
'src/core/credentials/transport/tls/grpc_tls_credentials_options.cc',
'src/core/credentials/transport/tls/grpc_tls_credentials_options.h',
'src/core/credentials/transport/tls/grpc_tls_crl_provider.cc',
'src/core/credentials/transport/tls/grpc_tls_crl_provider.h',
'src/core/credentials/transport/tls/load_system_roots.h',
'src/core/credentials/transport/tls/load_system_roots_fallback.cc',
'src/core/credentials/transport/tls/load_system_roots_supported.cc',
'src/core/credentials/transport/tls/load_system_roots_supported.h',
'src/core/credentials/transport/tls/load_system_roots_windows.cc',
'src/core/credentials/transport/tls/ssl_utils.cc',
'src/core/credentials/transport/tls/ssl_utils.h',
'src/core/credentials/transport/tls/tls_credentials.cc',
'src/core/credentials/transport/tls/tls_credentials.h',
'src/core/credentials/transport/tls/tls_security_connector.cc',
'src/core/credentials/transport/tls/tls_security_connector.h',
'src/core/credentials/transport/tls/tls_utils.cc',
'src/core/credentials/transport/tls/tls_utils.h',
'src/core/credentials/transport/transport_credentials.cc',
'src/core/credentials/transport/transport_credentials.h',
'src/core/credentials/transport/xds/xds_credentials.cc',
'src/core/credentials/transport/xds/xds_credentials.h',
'src/core/ext/filters/backend_metrics/backend_metric_filter.cc',
'src/core/ext/filters/backend_metrics/backend_metric_filter.h',
'src/core/ext/filters/backend_metrics/backend_metric_provider.h',
@ -472,7 +334,6 @@ Pod::Spec.new do |s|
'src/core/ext/filters/stateful_session/stateful_session_service_config_parser.h',
'src/core/ext/transport/chttp2/alpn/alpn.cc',
'src/core/ext/transport/chttp2/alpn/alpn.h',
'src/core/ext/transport/chttp2/chttp2_plugin.cc',
'src/core/ext/transport/chttp2/client/chttp2_connector.cc',
'src/core/ext/transport/chttp2/client/chttp2_connector.h',
'src/core/ext/transport/chttp2/server/chttp2_server.cc',
@ -485,6 +346,7 @@ Pod::Spec.new do |s|
'src/core/ext/transport/chttp2/transport/call_tracer_wrapper.h',
'src/core/ext/transport/chttp2/transport/chttp2_transport.cc',
'src/core/ext/transport/chttp2/transport/chttp2_transport.h',
'src/core/ext/transport/chttp2/transport/context_list_entry.h',
'src/core/ext/transport/chttp2/transport/decode_huff.cc',
'src/core/ext/transport/chttp2/transport/decode_huff.h',
'src/core/ext/transport/chttp2/transport/flow_control.cc',
@ -518,12 +380,9 @@ Pod::Spec.new do |s|
'src/core/ext/transport/chttp2/transport/hpack_parser_table.h',
'src/core/ext/transport/chttp2/transport/http2_settings.cc',
'src/core/ext/transport/chttp2/transport/http2_settings.h',
'src/core/ext/transport/chttp2/transport/http2_status.h',
'src/core/ext/transport/chttp2/transport/http2_ztrace_collector.h',
'src/core/ext/transport/chttp2/transport/huffsyms.cc',
'src/core/ext/transport/chttp2/transport/huffsyms.h',
'src/core/ext/transport/chttp2/transport/internal.h',
'src/core/ext/transport/chttp2/transport/internal_channel_arg_names.h',
'src/core/ext/transport/chttp2/transport/legacy_frame.h',
'src/core/ext/transport/chttp2/transport/parsing.cc',
'src/core/ext/transport/chttp2/transport/ping_abuse_policy.cc',
@ -1352,9 +1211,6 @@ Pod::Spec.new do |s|
'src/core/ext/upbdefs-gen/xds/type/v3/range.upbdefs.h',
'src/core/ext/upbdefs-gen/xds/type/v3/typed_struct.upbdefs.c',
'src/core/ext/upbdefs-gen/xds/type/v3/typed_struct.upbdefs.h',
'src/core/filter/auth/auth_filters.h',
'src/core/filter/auth/client_auth_filter.cc',
'src/core/filter/auth/server_auth_filter.cc',
'src/core/filter/blackboard.cc',
'src/core/filter/blackboard.h',
'src/core/filter/filter_args.h',
@ -1374,7 +1230,6 @@ Pod::Spec.new do |s|
'src/core/handshaker/proxy_mapper.h',
'src/core/handshaker/proxy_mapper_registry.cc',
'src/core/handshaker/proxy_mapper_registry.h',
'src/core/handshaker/security/legacy_secure_endpoint.cc',
'src/core/handshaker/security/secure_endpoint.cc',
'src/core/handshaker/security/secure_endpoint.h',
'src/core/handshaker/security/security_handshaker.cc',
@ -1385,6 +1240,7 @@ Pod::Spec.new do |s|
'src/core/lib/address_utils/parse_address.h',
'src/core/lib/address_utils/sockaddr_utils.cc',
'src/core/lib/address_utils/sockaddr_utils.h',
'src/core/lib/channel/call_finalization.h',
'src/core/lib/channel/channel_args.cc',
'src/core/lib/channel/channel_args.h',
'src/core/lib/channel/channel_args_preconditioning.cc',
@ -1400,6 +1256,8 @@ Pod::Spec.new do |s|
'src/core/lib/channel/connected_channel.h',
'src/core/lib/channel/promise_based_filter.cc',
'src/core/lib/channel/promise_based_filter.h',
'src/core/lib/channel/status_util.cc',
'src/core/lib/channel/status_util.h',
'src/core/lib/compression/compression.cc',
'src/core/lib/compression/compression_internal.cc',
'src/core/lib/compression/compression_internal.h',
@ -1428,13 +1286,9 @@ Pod::Spec.new do |s|
'src/core/lib/event_engine/default_event_engine_factory.h',
'src/core/lib/event_engine/event_engine.cc',
'src/core/lib/event_engine/event_engine_context.h',
'src/core/lib/event_engine/extensions/blocking_dns.h',
'src/core/lib/event_engine/extensions/can_track_errors.h',
'src/core/lib/event_engine/extensions/channelz.h',
'src/core/lib/event_engine/extensions/chaotic_good_extension.h',
'src/core/lib/event_engine/extensions/iomgr_compatible.h',
'src/core/lib/event_engine/extensions/supports_fd.h',
'src/core/lib/event_engine/extensions/supports_win_sockets.h',
'src/core/lib/event_engine/extensions/tcp_trace.h',
'src/core/lib/event_engine/forkable.cc',
'src/core/lib/event_engine/forkable.h',
@ -1467,7 +1321,6 @@ Pod::Spec.new do |s|
'src/core/lib/event_engine/posix_engine/posix_engine_listener.h',
'src/core/lib/event_engine/posix_engine/posix_engine_listener_utils.cc',
'src/core/lib/event_engine/posix_engine/posix_engine_listener_utils.h',
'src/core/lib/event_engine/posix_engine/set_socket_dualstack.cc',
'src/core/lib/event_engine/posix_engine/tcp_socket_utils.cc',
'src/core/lib/event_engine/posix_engine/tcp_socket_utils.h',
'src/core/lib/event_engine/posix_engine/timer.cc',
@ -1570,6 +1423,8 @@ Pod::Spec.new do |s|
'src/core/lib/iomgr/event_engine_shims/tcp_client.h',
'src/core/lib/iomgr/exec_ctx.cc',
'src/core/lib/iomgr/exec_ctx.h',
'src/core/lib/iomgr/executor.cc',
'src/core/lib/iomgr/executor.h',
'src/core/lib/iomgr/fork_posix.cc',
'src/core/lib/iomgr/fork_windows.cc',
'src/core/lib/iomgr/internal_errqueue.cc',
@ -1726,6 +1581,110 @@ Pod::Spec.new do |s|
'src/core/lib/security/authorization/rbac_policy.h',
'src/core/lib/security/authorization/stdout_logger.cc',
'src/core/lib/security/authorization/stdout_logger.h',
'src/core/lib/security/certificate_provider/certificate_provider_factory.h',
'src/core/lib/security/certificate_provider/certificate_provider_registry.cc',
'src/core/lib/security/certificate_provider/certificate_provider_registry.h',
'src/core/lib/security/context/security_context.cc',
'src/core/lib/security/context/security_context.h',
'src/core/lib/security/credentials/alts/alts_credentials.cc',
'src/core/lib/security/credentials/alts/alts_credentials.h',
'src/core/lib/security/credentials/alts/check_gcp_environment.cc',
'src/core/lib/security/credentials/alts/check_gcp_environment.h',
'src/core/lib/security/credentials/alts/check_gcp_environment_linux.cc',
'src/core/lib/security/credentials/alts/check_gcp_environment_no_op.cc',
'src/core/lib/security/credentials/alts/check_gcp_environment_windows.cc',
'src/core/lib/security/credentials/alts/grpc_alts_credentials_client_options.cc',
'src/core/lib/security/credentials/alts/grpc_alts_credentials_options.cc',
'src/core/lib/security/credentials/alts/grpc_alts_credentials_options.h',
'src/core/lib/security/credentials/alts/grpc_alts_credentials_server_options.cc',
'src/core/lib/security/credentials/call_creds_util.cc',
'src/core/lib/security/credentials/call_creds_util.h',
'src/core/lib/security/credentials/channel_creds_registry.h',
'src/core/lib/security/credentials/channel_creds_registry_init.cc',
'src/core/lib/security/credentials/composite/composite_credentials.cc',
'src/core/lib/security/credentials/composite/composite_credentials.h',
'src/core/lib/security/credentials/credentials.cc',
'src/core/lib/security/credentials/credentials.h',
'src/core/lib/security/credentials/external/aws_external_account_credentials.cc',
'src/core/lib/security/credentials/external/aws_external_account_credentials.h',
'src/core/lib/security/credentials/external/aws_request_signer.cc',
'src/core/lib/security/credentials/external/aws_request_signer.h',
'src/core/lib/security/credentials/external/external_account_credentials.cc',
'src/core/lib/security/credentials/external/external_account_credentials.h',
'src/core/lib/security/credentials/external/file_external_account_credentials.cc',
'src/core/lib/security/credentials/external/file_external_account_credentials.h',
'src/core/lib/security/credentials/external/url_external_account_credentials.cc',
'src/core/lib/security/credentials/external/url_external_account_credentials.h',
'src/core/lib/security/credentials/fake/fake_credentials.cc',
'src/core/lib/security/credentials/fake/fake_credentials.h',
'src/core/lib/security/credentials/gcp_service_account_identity/gcp_service_account_identity_credentials.cc',
'src/core/lib/security/credentials/gcp_service_account_identity/gcp_service_account_identity_credentials.h',
'src/core/lib/security/credentials/google_default/credentials_generic.cc',
'src/core/lib/security/credentials/google_default/google_default_credentials.cc',
'src/core/lib/security/credentials/google_default/google_default_credentials.h',
'src/core/lib/security/credentials/iam/iam_credentials.cc',
'src/core/lib/security/credentials/iam/iam_credentials.h',
'src/core/lib/security/credentials/insecure/insecure_credentials.cc',
'src/core/lib/security/credentials/insecure/insecure_credentials.h',
'src/core/lib/security/credentials/jwt/json_token.cc',
'src/core/lib/security/credentials/jwt/json_token.h',
'src/core/lib/security/credentials/jwt/jwt_credentials.cc',
'src/core/lib/security/credentials/jwt/jwt_credentials.h',
'src/core/lib/security/credentials/jwt/jwt_verifier.cc',
'src/core/lib/security/credentials/jwt/jwt_verifier.h',
'src/core/lib/security/credentials/local/local_credentials.cc',
'src/core/lib/security/credentials/local/local_credentials.h',
'src/core/lib/security/credentials/oauth2/oauth2_credentials.cc',
'src/core/lib/security/credentials/oauth2/oauth2_credentials.h',
'src/core/lib/security/credentials/plugin/plugin_credentials.cc',
'src/core/lib/security/credentials/plugin/plugin_credentials.h',
'src/core/lib/security/credentials/ssl/ssl_credentials.cc',
'src/core/lib/security/credentials/ssl/ssl_credentials.h',
'src/core/lib/security/credentials/tls/grpc_tls_certificate_distributor.cc',
'src/core/lib/security/credentials/tls/grpc_tls_certificate_distributor.h',
'src/core/lib/security/credentials/tls/grpc_tls_certificate_match.cc',
'src/core/lib/security/credentials/tls/grpc_tls_certificate_provider.cc',
'src/core/lib/security/credentials/tls/grpc_tls_certificate_provider.h',
'src/core/lib/security/credentials/tls/grpc_tls_certificate_verifier.cc',
'src/core/lib/security/credentials/tls/grpc_tls_certificate_verifier.h',
'src/core/lib/security/credentials/tls/grpc_tls_credentials_options.cc',
'src/core/lib/security/credentials/tls/grpc_tls_credentials_options.h',
'src/core/lib/security/credentials/tls/grpc_tls_crl_provider.cc',
'src/core/lib/security/credentials/tls/grpc_tls_crl_provider.h',
'src/core/lib/security/credentials/tls/tls_credentials.cc',
'src/core/lib/security/credentials/tls/tls_credentials.h',
'src/core/lib/security/credentials/tls/tls_utils.cc',
'src/core/lib/security/credentials/tls/tls_utils.h',
'src/core/lib/security/credentials/token_fetcher/token_fetcher_credentials.cc',
'src/core/lib/security/credentials/token_fetcher/token_fetcher_credentials.h',
'src/core/lib/security/credentials/xds/xds_credentials.cc',
'src/core/lib/security/credentials/xds/xds_credentials.h',
'src/core/lib/security/security_connector/alts/alts_security_connector.cc',
'src/core/lib/security/security_connector/alts/alts_security_connector.h',
'src/core/lib/security/security_connector/fake/fake_security_connector.cc',
'src/core/lib/security/security_connector/fake/fake_security_connector.h',
'src/core/lib/security/security_connector/insecure/insecure_security_connector.cc',
'src/core/lib/security/security_connector/insecure/insecure_security_connector.h',
'src/core/lib/security/security_connector/load_system_roots.h',
'src/core/lib/security/security_connector/load_system_roots_fallback.cc',
'src/core/lib/security/security_connector/load_system_roots_supported.cc',
'src/core/lib/security/security_connector/load_system_roots_supported.h',
'src/core/lib/security/security_connector/load_system_roots_windows.cc',
'src/core/lib/security/security_connector/local/local_security_connector.cc',
'src/core/lib/security/security_connector/local/local_security_connector.h',
'src/core/lib/security/security_connector/security_connector.cc',
'src/core/lib/security/security_connector/security_connector.h',
'src/core/lib/security/security_connector/ssl/ssl_security_connector.cc',
'src/core/lib/security/security_connector/ssl/ssl_security_connector.h',
'src/core/lib/security/security_connector/ssl_utils.cc',
'src/core/lib/security/security_connector/ssl_utils.h',
'src/core/lib/security/security_connector/tls/tls_security_connector.cc',
'src/core/lib/security/security_connector/tls/tls_security_connector.h',
'src/core/lib/security/transport/auth_filters.h',
'src/core/lib/security/transport/client_auth_filter.cc',
'src/core/lib/security/transport/server_auth_filter.cc',
'src/core/lib/security/util/json_util.cc',
'src/core/lib/security/util/json_util.h',
'src/core/lib/slice/percent_encoding.cc',
'src/core/lib/slice/percent_encoding.h',
'src/core/lib/slice/slice.cc',
@ -1753,6 +1712,8 @@ Pod::Spec.new do |s|
'src/core/lib/surface/channel_init.h',
'src/core/lib/surface/channel_stack_type.cc',
'src/core/lib/surface/channel_stack_type.h',
'src/core/lib/surface/client_call.cc',
'src/core/lib/surface/client_call.h',
'src/core/lib/surface/completion_queue.cc',
'src/core/lib/surface/completion_queue.h',
'src/core/lib/surface/completion_queue_factory.cc',
@ -1772,17 +1733,44 @@ Pod::Spec.new do |s|
'src/core/lib/surface/legacy_channel.cc',
'src/core/lib/surface/legacy_channel.h',
'src/core/lib/surface/metadata_array.cc',
'src/core/lib/surface/server_call.cc',
'src/core/lib/surface/server_call.h',
'src/core/lib/surface/validate_metadata.cc',
'src/core/lib/surface/validate_metadata.h',
'src/core/lib/surface/version.cc',
'src/core/lib/transport/bdp_estimator.cc',
'src/core/lib/transport/bdp_estimator.h',
'src/core/lib/transport/call_arena_allocator.cc',
'src/core/lib/transport/call_arena_allocator.h',
'src/core/lib/transport/call_destination.h',
'src/core/lib/transport/call_filters.cc',
'src/core/lib/transport/call_filters.h',
'src/core/lib/transport/call_final_info.cc',
'src/core/lib/transport/call_final_info.h',
'src/core/lib/transport/call_spine.cc',
'src/core/lib/transport/call_spine.h',
'src/core/lib/transport/call_state.cc',
'src/core/lib/transport/call_state.h',
'src/core/lib/transport/connectivity_state.cc',
'src/core/lib/transport/connectivity_state.h',
'src/core/lib/transport/custom_metadata.h',
'src/core/lib/transport/error_utils.cc',
'src/core/lib/transport/error_utils.h',
'src/core/lib/transport/http2_errors.h',
'src/core/lib/transport/interception_chain.cc',
'src/core/lib/transport/interception_chain.h',
'src/core/lib/transport/message.cc',
'src/core/lib/transport/message.h',
'src/core/lib/transport/metadata.cc',
'src/core/lib/transport/metadata.h',
'src/core/lib/transport/metadata_batch.cc',
'src/core/lib/transport/metadata_batch.h',
'src/core/lib/transport/metadata_compression_traits.h',
'src/core/lib/transport/metadata_info.cc',
'src/core/lib/transport/metadata_info.h',
'src/core/lib/transport/parsed_metadata.cc',
'src/core/lib/transport/parsed_metadata.h',
'src/core/lib/transport/simple_slice_based_metadata.h',
'src/core/lib/transport/status_conversion.cc',
'src/core/lib/transport/status_conversion.h',
'src/core/lib/transport/timeout_encoding.cc',
@ -1885,7 +1873,6 @@ Pod::Spec.new do |s|
'src/core/resolver/xds/xds_dependency_manager.h',
'src/core/resolver/xds/xds_resolver.cc',
'src/core/resolver/xds/xds_resolver_attributes.h',
'src/core/server/add_port.cc',
'src/core/server/server.cc',
'src/core/server/server.h',
'src/core/server/server_call_tracer_filter.cc',
@ -1906,9 +1893,6 @@ Pod::Spec.new do |s|
'src/core/service_config/service_config_parser.h',
'src/core/telemetry/call_tracer.cc',
'src/core/telemetry/call_tracer.h',
'src/core/telemetry/context_list_entry.h',
'src/core/telemetry/default_tcp_tracer.cc',
'src/core/telemetry/default_tcp_tracer.h',
'src/core/telemetry/histogram_view.cc',
'src/core/telemetry/histogram_view.h',
'src/core/telemetry/metrics.cc',
@ -1917,13 +1901,7 @@ Pod::Spec.new do |s|
'src/core/telemetry/stats.h',
'src/core/telemetry/stats_data.cc',
'src/core/telemetry/stats_data.h',
'src/core/telemetry/tcp_tracer.cc',
'src/core/telemetry/tcp_tracer.h',
'src/core/transport/auth_context.cc',
'src/core/transport/auth_context.h',
'src/core/transport/endpoint_transport.h',
'src/core/transport/endpoint_transport_client_channel_factory.cc',
'src/core/transport/endpoint_transport_client_channel_factory.h',
'src/core/tsi/alts/crypt/aes_gcm.cc',
'src/core/tsi/alts/crypt/gsec.cc',
'src/core/tsi/alts/crypt/gsec.h',
@ -1989,7 +1967,6 @@ Pod::Spec.new do |s|
'src/core/util/backoff.cc',
'src/core/util/backoff.h',
'src/core/util/bitset.h',
'src/core/util/check_class_size.h',
'src/core/util/chunked_vector.h',
'src/core/util/construct_destruct.h',
'src/core/util/cpp_impl_of.h',
@ -2008,7 +1985,6 @@ Pod::Spec.new do |s|
'src/core/util/examine_stack.h',
'src/core/util/fork.cc',
'src/core/util/fork.h',
'src/core/util/function_signature.h',
'src/core/util/gcp_metadata_query.cc',
'src/core/util/gcp_metadata_query.h',
'src/core/util/gethostname.h',
@ -2083,8 +2059,6 @@ Pod::Spec.new do |s|
'src/core/util/ref_counted_string.cc',
'src/core/util/ref_counted_string.h',
'src/core/util/ring_buffer.h',
'src/core/util/shared_bit_gen.cc',
'src/core/util/shared_bit_gen.h',
'src/core/util/single_set_ptr.h',
'src/core/util/sorted_pack.h',
'src/core/util/spinlock.h',
@ -2301,10 +2275,10 @@ Pod::Spec.new do |s|
'third_party/upb/upb/message/copy.h',
'third_party/upb/upb/message/internal/accessors.h',
'third_party/upb/upb/message/internal/array.h',
'third_party/upb/upb/message/internal/compare_unknown.c',
'third_party/upb/upb/message/internal/compare_unknown.h',
'third_party/upb/upb/message/internal/extension.c',
'third_party/upb/upb/message/internal/extension.h',
'third_party/upb/upb/message/internal/iterator.c',
'third_party/upb/upb/message/internal/iterator.h',
'third_party/upb/upb/message/internal/map.h',
'third_party/upb/upb/message/internal/map_entry.h',
'third_party/upb/upb/message/internal/map_sorter.h',
@ -2430,8 +2404,6 @@ Pod::Spec.new do |s|
'third_party/upb/upb/wire/types.h',
'third_party/utf8_range/utf8_range.c',
'third_party/utf8_range/utf8_range.h',
'third_party/utf8_range/utf8_range_neon.inc',
'third_party/utf8_range/utf8_range_sse.inc',
'third_party/xxhash/xxhash.h',
'third_party/zlib/adler32.c',
'third_party/zlib/compress.c',
@ -2455,30 +2427,10 @@ Pod::Spec.new do |s|
'third_party/zlib/zlib.h',
'third_party/zlib/zutil.c',
'third_party/zlib/zutil.h'
ss.private_header_files = 'src/core/call/call_arena_allocator.h',
'src/core/call/call_destination.h',
'src/core/call/call_filters.h',
'src/core/call/call_finalization.h',
'src/core/call/call_spine.h',
'src/core/call/call_state.h',
'src/core/call/client_call.h',
'src/core/call/custom_metadata.h',
'src/core/call/interception_chain.h',
'src/core/call/message.h',
'src/core/call/metadata.h',
'src/core/call/metadata_batch.h',
'src/core/call/metadata_compression_traits.h',
'src/core/call/metadata_info.h',
'src/core/call/parsed_metadata.h',
'src/core/call/request_buffer.h',
'src/core/call/security_context.h',
'src/core/call/server_call.h',
'src/core/call/simple_slice_based_metadata.h',
'src/core/call/status_util.h',
ss.private_header_files = 'src/core/call/request_buffer.h',
'src/core/channelz/channel_trace.h',
'src/core/channelz/channelz.h',
'src/core/channelz/channelz_registry.h',
'src/core/channelz/ztrace_collector.h',
'src/core/client_channel/backup_poller.h',
'src/core/client_channel/client_channel.h',
'src/core/client_channel/client_channel_args.h',
@ -2506,54 +2458,6 @@ Pod::Spec.new do |s|
'src/core/config/config_vars.h',
'src/core/config/core_configuration.h',
'src/core/config/load_config.h',
'src/core/credentials/call/call_credentials.h',
'src/core/credentials/call/call_creds_util.h',
'src/core/credentials/call/composite/composite_call_credentials.h',
'src/core/credentials/call/external/aws_external_account_credentials.h',
'src/core/credentials/call/external/aws_request_signer.h',
'src/core/credentials/call/external/external_account_credentials.h',
'src/core/credentials/call/external/file_external_account_credentials.h',
'src/core/credentials/call/external/url_external_account_credentials.h',
'src/core/credentials/call/gcp_service_account_identity/gcp_service_account_identity_credentials.h',
'src/core/credentials/call/iam/iam_credentials.h',
'src/core/credentials/call/json_util.h',
'src/core/credentials/call/jwt/json_token.h',
'src/core/credentials/call/jwt/jwt_credentials.h',
'src/core/credentials/call/jwt/jwt_verifier.h',
'src/core/credentials/call/oauth2/oauth2_credentials.h',
'src/core/credentials/call/plugin/plugin_credentials.h',
'src/core/credentials/call/token_fetcher/token_fetcher_credentials.h',
'src/core/credentials/transport/alts/alts_credentials.h',
'src/core/credentials/transport/alts/alts_security_connector.h',
'src/core/credentials/transport/alts/check_gcp_environment.h',
'src/core/credentials/transport/alts/grpc_alts_credentials_options.h',
'src/core/credentials/transport/channel_creds_registry.h',
'src/core/credentials/transport/composite/composite_channel_credentials.h',
'src/core/credentials/transport/fake/fake_credentials.h',
'src/core/credentials/transport/fake/fake_security_connector.h',
'src/core/credentials/transport/google_default/google_default_credentials.h',
'src/core/credentials/transport/insecure/insecure_credentials.h',
'src/core/credentials/transport/insecure/insecure_security_connector.h',
'src/core/credentials/transport/local/local_credentials.h',
'src/core/credentials/transport/local/local_security_connector.h',
'src/core/credentials/transport/security_connector.h',
'src/core/credentials/transport/ssl/ssl_credentials.h',
'src/core/credentials/transport/ssl/ssl_security_connector.h',
'src/core/credentials/transport/tls/certificate_provider_factory.h',
'src/core/credentials/transport/tls/certificate_provider_registry.h',
'src/core/credentials/transport/tls/grpc_tls_certificate_distributor.h',
'src/core/credentials/transport/tls/grpc_tls_certificate_provider.h',
'src/core/credentials/transport/tls/grpc_tls_certificate_verifier.h',
'src/core/credentials/transport/tls/grpc_tls_credentials_options.h',
'src/core/credentials/transport/tls/grpc_tls_crl_provider.h',
'src/core/credentials/transport/tls/load_system_roots.h',
'src/core/credentials/transport/tls/load_system_roots_supported.h',
'src/core/credentials/transport/tls/ssl_utils.h',
'src/core/credentials/transport/tls/tls_credentials.h',
'src/core/credentials/transport/tls/tls_security_connector.h',
'src/core/credentials/transport/tls/tls_utils.h',
'src/core/credentials/transport/transport_credentials.h',
'src/core/credentials/transport/xds/xds_credentials.h',
'src/core/ext/filters/backend_metrics/backend_metric_filter.h',
'src/core/ext/filters/backend_metrics/backend_metric_provider.h',
'src/core/ext/filters/channel_idle/idle_filter_state.h',
@ -2578,6 +2482,7 @@ Pod::Spec.new do |s|
'src/core/ext/transport/chttp2/transport/bin_encoder.h',
'src/core/ext/transport/chttp2/transport/call_tracer_wrapper.h',
'src/core/ext/transport/chttp2/transport/chttp2_transport.h',
'src/core/ext/transport/chttp2/transport/context_list_entry.h',
'src/core/ext/transport/chttp2/transport/decode_huff.h',
'src/core/ext/transport/chttp2/transport/flow_control.h',
'src/core/ext/transport/chttp2/transport/frame.h',
@ -2595,11 +2500,8 @@ Pod::Spec.new do |s|
'src/core/ext/transport/chttp2/transport/hpack_parser.h',
'src/core/ext/transport/chttp2/transport/hpack_parser_table.h',
'src/core/ext/transport/chttp2/transport/http2_settings.h',
'src/core/ext/transport/chttp2/transport/http2_status.h',
'src/core/ext/transport/chttp2/transport/http2_ztrace_collector.h',
'src/core/ext/transport/chttp2/transport/huffsyms.h',
'src/core/ext/transport/chttp2/transport/internal.h',
'src/core/ext/transport/chttp2/transport/internal_channel_arg_names.h',
'src/core/ext/transport/chttp2/transport/legacy_frame.h',
'src/core/ext/transport/chttp2/transport/ping_abuse_policy.h',
'src/core/ext/transport/chttp2/transport/ping_callbacks.h',
@ -3097,7 +2999,6 @@ Pod::Spec.new do |s|
'src/core/ext/upbdefs-gen/xds/type/v3/cel.upbdefs.h',
'src/core/ext/upbdefs-gen/xds/type/v3/range.upbdefs.h',
'src/core/ext/upbdefs-gen/xds/type/v3/typed_struct.upbdefs.h',
'src/core/filter/auth/auth_filters.h',
'src/core/filter/blackboard.h',
'src/core/filter/filter_args.h',
'src/core/handshaker/endpoint_info/endpoint_info_handshaker.h',
@ -3114,6 +3015,7 @@ Pod::Spec.new do |s|
'src/core/handshaker/tcp_connect/tcp_connect_handshaker.h',
'src/core/lib/address_utils/parse_address.h',
'src/core/lib/address_utils/sockaddr_utils.h',
'src/core/lib/channel/call_finalization.h',
'src/core/lib/channel/channel_args.h',
'src/core/lib/channel/channel_args_preconditioning.h',
'src/core/lib/channel/channel_fwd.h',
@ -3122,6 +3024,7 @@ Pod::Spec.new do |s|
'src/core/lib/channel/channel_stack_builder_impl.h',
'src/core/lib/channel/connected_channel.h',
'src/core/lib/channel/promise_based_filter.h',
'src/core/lib/channel/status_util.h',
'src/core/lib/compression/compression_internal.h',
'src/core/lib/compression/message_compress.h',
'src/core/lib/debug/trace.h',
@ -3137,13 +3040,9 @@ Pod::Spec.new do |s|
'src/core/lib/event_engine/default_event_engine.h',
'src/core/lib/event_engine/default_event_engine_factory.h',
'src/core/lib/event_engine/event_engine_context.h',
'src/core/lib/event_engine/extensions/blocking_dns.h',
'src/core/lib/event_engine/extensions/can_track_errors.h',
'src/core/lib/event_engine/extensions/channelz.h',
'src/core/lib/event_engine/extensions/chaotic_good_extension.h',
'src/core/lib/event_engine/extensions/iomgr_compatible.h',
'src/core/lib/event_engine/extensions/supports_fd.h',
'src/core/lib/event_engine/extensions/supports_win_sockets.h',
'src/core/lib/event_engine/extensions/tcp_trace.h',
'src/core/lib/event_engine/forkable.h',
'src/core/lib/event_engine/grpc_polled_fd.h',
@ -3217,6 +3116,7 @@ Pod::Spec.new do |s|
'src/core/lib/iomgr/event_engine_shims/endpoint.h',
'src/core/lib/iomgr/event_engine_shims/tcp_client.h',
'src/core/lib/iomgr/exec_ctx.h',
'src/core/lib/iomgr/executor.h',
'src/core/lib/iomgr/internal_errqueue.h',
'src/core/lib/iomgr/iocp_windows.h',
'src/core/lib/iomgr/iomgr.h',
@ -3305,6 +3205,54 @@ Pod::Spec.new do |s|
'src/core/lib/security/authorization/matchers.h',
'src/core/lib/security/authorization/rbac_policy.h',
'src/core/lib/security/authorization/stdout_logger.h',
'src/core/lib/security/certificate_provider/certificate_provider_factory.h',
'src/core/lib/security/certificate_provider/certificate_provider_registry.h',
'src/core/lib/security/context/security_context.h',
'src/core/lib/security/credentials/alts/alts_credentials.h',
'src/core/lib/security/credentials/alts/check_gcp_environment.h',
'src/core/lib/security/credentials/alts/grpc_alts_credentials_options.h',
'src/core/lib/security/credentials/call_creds_util.h',
'src/core/lib/security/credentials/channel_creds_registry.h',
'src/core/lib/security/credentials/composite/composite_credentials.h',
'src/core/lib/security/credentials/credentials.h',
'src/core/lib/security/credentials/external/aws_external_account_credentials.h',
'src/core/lib/security/credentials/external/aws_request_signer.h',
'src/core/lib/security/credentials/external/external_account_credentials.h',
'src/core/lib/security/credentials/external/file_external_account_credentials.h',
'src/core/lib/security/credentials/external/url_external_account_credentials.h',
'src/core/lib/security/credentials/fake/fake_credentials.h',
'src/core/lib/security/credentials/gcp_service_account_identity/gcp_service_account_identity_credentials.h',
'src/core/lib/security/credentials/google_default/google_default_credentials.h',
'src/core/lib/security/credentials/iam/iam_credentials.h',
'src/core/lib/security/credentials/insecure/insecure_credentials.h',
'src/core/lib/security/credentials/jwt/json_token.h',
'src/core/lib/security/credentials/jwt/jwt_credentials.h',
'src/core/lib/security/credentials/jwt/jwt_verifier.h',
'src/core/lib/security/credentials/local/local_credentials.h',
'src/core/lib/security/credentials/oauth2/oauth2_credentials.h',
'src/core/lib/security/credentials/plugin/plugin_credentials.h',
'src/core/lib/security/credentials/ssl/ssl_credentials.h',
'src/core/lib/security/credentials/tls/grpc_tls_certificate_distributor.h',
'src/core/lib/security/credentials/tls/grpc_tls_certificate_provider.h',
'src/core/lib/security/credentials/tls/grpc_tls_certificate_verifier.h',
'src/core/lib/security/credentials/tls/grpc_tls_credentials_options.h',
'src/core/lib/security/credentials/tls/grpc_tls_crl_provider.h',
'src/core/lib/security/credentials/tls/tls_credentials.h',
'src/core/lib/security/credentials/tls/tls_utils.h',
'src/core/lib/security/credentials/token_fetcher/token_fetcher_credentials.h',
'src/core/lib/security/credentials/xds/xds_credentials.h',
'src/core/lib/security/security_connector/alts/alts_security_connector.h',
'src/core/lib/security/security_connector/fake/fake_security_connector.h',
'src/core/lib/security/security_connector/insecure/insecure_security_connector.h',
'src/core/lib/security/security_connector/load_system_roots.h',
'src/core/lib/security/security_connector/load_system_roots_supported.h',
'src/core/lib/security/security_connector/local/local_security_connector.h',
'src/core/lib/security/security_connector/security_connector.h',
'src/core/lib/security/security_connector/ssl/ssl_security_connector.h',
'src/core/lib/security/security_connector/ssl_utils.h',
'src/core/lib/security/security_connector/tls/tls_security_connector.h',
'src/core/lib/security/transport/auth_filters.h',
'src/core/lib/security/util/json_util.h',
'src/core/lib/slice/percent_encoding.h',
'src/core/lib/slice/slice.h',
'src/core/lib/slice/slice_buffer.h',
@ -3318,6 +3266,7 @@ Pod::Spec.new do |s|
'src/core/lib/surface/channel_create.h',
'src/core/lib/surface/channel_init.h',
'src/core/lib/surface/channel_stack_type.h',
'src/core/lib/surface/client_call.h',
'src/core/lib/surface/completion_queue.h',
'src/core/lib/surface/completion_queue_factory.h',
'src/core/lib/surface/connection_context.h',
@ -3327,11 +3276,27 @@ Pod::Spec.new do |s|
'src/core/lib/surface/init_internally.h',
'src/core/lib/surface/lame_client.h',
'src/core/lib/surface/legacy_channel.h',
'src/core/lib/surface/server_call.h',
'src/core/lib/surface/validate_metadata.h',
'src/core/lib/transport/bdp_estimator.h',
'src/core/lib/transport/call_arena_allocator.h',
'src/core/lib/transport/call_destination.h',
'src/core/lib/transport/call_filters.h',
'src/core/lib/transport/call_final_info.h',
'src/core/lib/transport/call_spine.h',
'src/core/lib/transport/call_state.h',
'src/core/lib/transport/connectivity_state.h',
'src/core/lib/transport/custom_metadata.h',
'src/core/lib/transport/error_utils.h',
'src/core/lib/transport/http2_errors.h',
'src/core/lib/transport/interception_chain.h',
'src/core/lib/transport/message.h',
'src/core/lib/transport/metadata.h',
'src/core/lib/transport/metadata_batch.h',
'src/core/lib/transport/metadata_compression_traits.h',
'src/core/lib/transport/metadata_info.h',
'src/core/lib/transport/parsed_metadata.h',
'src/core/lib/transport/simple_slice_based_metadata.h',
'src/core/lib/transport/status_conversion.h',
'src/core/lib/transport/timeout_encoding.h',
'src/core/lib/transport/transport.h',
@ -3392,16 +3357,11 @@ Pod::Spec.new do |s|
'src/core/service_config/service_config_impl.h',
'src/core/service_config/service_config_parser.h',
'src/core/telemetry/call_tracer.h',
'src/core/telemetry/context_list_entry.h',
'src/core/telemetry/default_tcp_tracer.h',
'src/core/telemetry/histogram_view.h',
'src/core/telemetry/metrics.h',
'src/core/telemetry/stats.h',
'src/core/telemetry/stats_data.h',
'src/core/telemetry/tcp_tracer.h',
'src/core/transport/auth_context.h',
'src/core/transport/endpoint_transport.h',
'src/core/transport/endpoint_transport_client_channel_factory.h',
'src/core/tsi/alts/crypt/gsec.h',
'src/core/tsi/alts/frame_protector/alts_counter.h',
'src/core/tsi/alts/frame_protector/alts_crypter.h',
@ -3436,7 +3396,6 @@ Pod::Spec.new do |s|
'src/core/util/avl.h',
'src/core/util/backoff.h',
'src/core/util/bitset.h',
'src/core/util/check_class_size.h',
'src/core/util/chunked_vector.h',
'src/core/util/construct_destruct.h',
'src/core/util/cpp_impl_of.h',
@ -3450,7 +3409,6 @@ Pod::Spec.new do |s|
'src/core/util/event_log.h',
'src/core/util/examine_stack.h',
'src/core/util/fork.h',
'src/core/util/function_signature.h',
'src/core/util/gcp_metadata_query.h',
'src/core/util/gethostname.h',
'src/core/util/glob.h',
@ -3487,7 +3445,6 @@ Pod::Spec.new do |s|
'src/core/util/ref_counted_ptr.h',
'src/core/util/ref_counted_string.h',
'src/core/util/ring_buffer.h',
'src/core/util/shared_bit_gen.h',
'src/core/util/single_set_ptr.h',
'src/core/util/sorted_pack.h',
'src/core/util/spinlock.h',
@ -3607,8 +3564,8 @@ Pod::Spec.new do |s|
'third_party/upb/upb/message/copy.h',
'third_party/upb/upb/message/internal/accessors.h',
'third_party/upb/upb/message/internal/array.h',
'third_party/upb/upb/message/internal/compare_unknown.h',
'third_party/upb/upb/message/internal/extension.h',
'third_party/upb/upb/message/internal/iterator.h',
'third_party/upb/upb/message/internal/map.h',
'third_party/upb/upb/message/internal/map_entry.h',
'third_party/upb/upb/message/internal/map_sorter.h',
@ -3696,8 +3653,6 @@ Pod::Spec.new do |s|
'third_party/upb/upb/wire/reader.h',
'third_party/upb/upb/wire/types.h',
'third_party/utf8_range/utf8_range.h',
'third_party/utf8_range/utf8_range_neon.inc',
'third_party/utf8_range/utf8_range_sse.inc',
'third_party/xxhash/xxhash.h',
'third_party/zlib/crc32.h',
'third_party/zlib/deflate.h',
@ -3717,6 +3672,28 @@ Pod::Spec.new do |s|
ss.dependency "#{s.name}/Implementation", version
end
s.subspec 'Cronet-Interface' do |ss|
ss.header_mappings_dir = 'include/grpc'
ss.source_files = 'include/grpc/grpc_cronet.h'
end
s.subspec 'Cronet-Implementation' do |ss|
ss.header_mappings_dir = '.'
ss.dependency "#{s.name}/Interface", version
ss.dependency "#{s.name}/Implementation", version
ss.dependency "#{s.name}/Privacy", version
ss.dependency "#{s.name}/Cronet-Interface", version
ss.source_files = 'src/core/ext/transport/cronet/client/secure/cronet_channel_create.cc',
'src/core/ext/transport/cronet/client/secure/cronet_channel_create.h',
'src/core/ext/transport/cronet/transport/cronet_status.cc',
'src/core/ext/transport/cronet/transport/cronet_status.h',
'src/core/ext/transport/cronet/transport/cronet_transport.cc',
'src/core/ext/transport/cronet/transport/cronet_transport.h',
'third_party/objective_c/Cronet/bidirectional_stream_c.h'
end
# patch include of openssl to openssl_grpc
s.prepare_command = <<-END_OF_COMMAND
set -e

View File

@ -21,7 +21,7 @@
Pod::Spec.new do |s|
s.name = 'gRPC-ProtoRPC'
version = '1.73.1'
version = '1.71.0-pre2'
s.version = version
s.summary = 'RPC library for Protocol Buffers, based on gRPC'
s.homepage = 'https://grpc.io'
@ -33,8 +33,8 @@ Pod::Spec.new do |s|
:tag => "v#{version}",
}
s.ios.deployment_target = '15.0'
s.osx.deployment_target = '11.0'
s.ios.deployment_target = '12.0'
s.osx.deployment_target = '10.14'
s.tvos.deployment_target = '13.0'
s.watchos.deployment_target = '6.0'
s.visionos.deployment_target = '1.0'
@ -55,7 +55,7 @@ Pod::Spec.new do |s|
ss.header_mappings_dir = "src/objective-c/ProtoRPC"
ss.dependency "#{s.name}/Legacy-Header", version
ss.dependency 'gRPC/Interface', version
ss.dependency 'Protobuf', '~> 4.0'
ss.dependency 'Protobuf', '~> 3.0'
ss.source_files = "src/objective-c/ProtoRPC/ProtoMethod.{h,m}",
"src/objective-c/ProtoRPC/ProtoRPC.{h,m}",
@ -68,7 +68,7 @@ Pod::Spec.new do |s|
ss.dependency "#{s.name}/Legacy-Header", version
ss.dependency 'gRPC/GRPCCore', version
ss.dependency 'gRPC-RxLibrary', version
ss.dependency 'Protobuf', '~> 4.0'
ss.dependency 'Protobuf', '~> 3.0'
ss.source_files = "src/objective-c/ProtoRPC/ProtoRPCLegacy.m",
"src/objective-c/ProtoRPC/ProtoServiceLegacy.m"

View File

@ -21,7 +21,7 @@
Pod::Spec.new do |s|
s.name = 'gRPC-RxLibrary'
version = '1.73.1'
version = '1.71.0-pre2'
s.version = version
s.summary = 'Reactive Extensions library for iOS/OSX.'
s.homepage = 'https://grpc.io'
@ -33,8 +33,8 @@ Pod::Spec.new do |s|
:tag => "v#{version}",
}
s.ios.deployment_target = '15.0'
s.osx.deployment_target = '11.0'
s.ios.deployment_target = '12.0'
s.osx.deployment_target = '10.14'
s.tvos.deployment_target = '13.0'
s.watchos.deployment_target = '6.0'
s.visionos.deployment_target = '1.0'

View File

@ -20,7 +20,7 @@
Pod::Spec.new do |s|
s.name = 'gRPC'
version = '1.73.1'
version = '1.71.0-pre2'
s.version = version
s.summary = 'gRPC client library for iOS/OSX'
s.homepage = 'https://grpc.io'
@ -45,8 +45,8 @@ Pod::Spec.new do |s|
'CLANG_CXX_LANGUAGE_STANDARD' => 'c++17',
}
s.ios.deployment_target = '15.0'
s.osx.deployment_target = '11.0'
s.ios.deployment_target = '12.0'
s.osx.deployment_target = '10.14'
s.tvos.deployment_target = '13.0'
s.watchos.deployment_target = '6.0'
s.visionos.deployment_target = '1.0'
@ -64,6 +64,7 @@ Pod::Spec.new do |s|
ss.public_header_files = "src/objective-c/GRPCClient/GRPCCall+ChannelArg.h",
"src/objective-c/GRPCClient/GRPCCall+ChannelCredentials.h",
"src/objective-c/GRPCClient/GRPCCall+Cronet.h",
"src/objective-c/GRPCClient/GRPCCall+OAuth2.h",
"src/objective-c/GRPCClient/GRPCCall+Tests.h",
"src/objective-c/GRPCClient/GRPCCallLegacy.h",
@ -71,6 +72,7 @@ Pod::Spec.new do |s|
ss.source_files = "src/objective-c/GRPCClient/GRPCCall+ChannelArg.h",
"src/objective-c/GRPCClient/GRPCCall+ChannelCredentials.h",
"src/objective-c/GRPCClient/GRPCCall+Cronet.h",
"src/objective-c/GRPCClient/GRPCCall+OAuth2.h",
"src/objective-c/GRPCClient/GRPCCall+Tests.h",
"src/objective-c/GRPCClient/GRPCCallLegacy.h",
@ -78,8 +80,8 @@ Pod::Spec.new do |s|
"src/objective-c/GRPCClient/GRPCTypes.mm"
ss.dependency "gRPC-RxLibrary/Interface", version
ss.dependency "#{s.name}/Privacy", version
s.ios.deployment_target = '15.0'
s.osx.deployment_target = '11.0'
s.ios.deployment_target = '12.0'
s.osx.deployment_target = '10.14'
s.tvos.deployment_target = '13.0'
s.watchos.deployment_target = '6.0'
s.visionos.deployment_target = '1.0'
@ -114,8 +116,8 @@ Pod::Spec.new do |s|
ss.dependency "#{s.name}/Interface-Legacy", version
ss.dependency "#{s.name}/Privacy", version
s.ios.deployment_target = '15.0'
s.osx.deployment_target = '11.0'
s.ios.deployment_target = '12.0'
s.osx.deployment_target = '10.14'
s.tvos.deployment_target = '13.0'
s.watchos.deployment_target = '6.0'
s.visionos.deployment_target = '1.0'
@ -125,6 +127,7 @@ Pod::Spec.new do |s|
ss.header_mappings_dir = 'src/objective-c/GRPCClient'
ss.public_header_files = 'src/objective-c/GRPCClient/GRPCCall+ChannelCredentials.h',
'src/objective-c/GRPCClient/GRPCCall+Cronet.h',
'src/objective-c/GRPCClient/GRPCCall+OAuth2.h',
'src/objective-c/GRPCClient/GRPCCall+Tests.h',
'src/objective-c/GRPCClient/GRPCCall+ChannelArg.h'
@ -134,6 +137,8 @@ Pod::Spec.new do |s|
'src/objective-c/GRPCClient/GRPCCall+ChannelArg.mm',
'src/objective-c/GRPCClient/GRPCCall+ChannelCredentials.h',
'src/objective-c/GRPCClient/GRPCCall+ChannelCredentials.mm',
'src/objective-c/GRPCClient/GRPCCall+Cronet.h',
'src/objective-c/GRPCClient/GRPCCall+Cronet.mm',
'src/objective-c/GRPCClient/GRPCCall+OAuth2.h',
'src/objective-c/GRPCClient/GRPCCall+OAuth2.mm',
'src/objective-c/GRPCClient/GRPCCall+Tests.h',
@ -149,19 +154,33 @@ Pod::Spec.new do |s|
ss.dependency 'gRPC-Core', version
ss.dependency 'gRPC-RxLibrary', version
s.ios.deployment_target = '15.0'
s.osx.deployment_target = '11.0'
s.ios.deployment_target = '12.0'
s.osx.deployment_target = '10.14'
s.tvos.deployment_target = '13.0'
s.watchos.deployment_target = '6.0'
s.visionos.deployment_target = '1.0'
end
s.subspec 'GRPCCoreCronet' do |ss|
ss.header_mappings_dir = 'src/objective-c/GRPCClient'
ss.source_files = 'src/objective-c/GRPCClient/GRPCCall+Cronet.h',
'src/objective-c/GRPCClient/GRPCCall+Cronet.mm',
'src/objective-c/GRPCClient/private/GRPCCore/GRPCCoreCronet/*.{h,mm}'
ss.dependency "#{s.name}/GRPCCore", version
ss.dependency "#{s.name}/Privacy", version
ss.dependency 'gRPC-Core/Cronet-Implementation', version
ss.dependency 'CronetFramework'
ss.ios.deployment_target = '12.0'
end
# CFStream is now default. Leaving this subspec only for compatibility purpose.
s.subspec 'CFStream' do |ss|
ss.dependency "#{s.name}/GRPCCore", version
s.ios.deployment_target = '15.0'
s.osx.deployment_target = '11.0'
s.ios.deployment_target = '12.0'
s.osx.deployment_target = '10.14'
s.tvos.deployment_target = '13.0'
s.watchos.deployment_target = '6.0'
s.visionos.deployment_target = '1.0'
@ -173,8 +192,8 @@ Pod::Spec.new do |s|
ss.source_files = 'src/objective-c/GRPCClient/internal_testing/*.{h,mm}'
ss.header_mappings_dir = 'src/objective-c/GRPCClient'
s.ios.deployment_target = '15.0'
s.osx.deployment_target = '11.0'
s.ios.deployment_target = '12.0'
s.osx.deployment_target = '10.14'
s.tvos.deployment_target = '13.0'
s.watchos.deployment_target = '6.0'
s.visionos.deployment_target = '1.0'

View File

@ -16,14 +16,11 @@
#include <grpc/event_engine/endpoint_config.h>
#include <grpc/event_engine/extensible.h>
#include <grpc/event_engine/internal/write_event.h>
#include <grpc/event_engine/memory_allocator.h>
#include <grpc/event_engine/port.h>
#include <grpc/event_engine/slice_buffer.h>
#include <grpc/support/port_platform.h>
#include <bitset>
#include <initializer_list>
#include <vector>
#include "absl/functional/any_invocable.h"
@ -183,26 +180,13 @@ class EventEngine : public std::enable_shared_from_this<EventEngine>,
/// EventEngine Endpoint Read API call.
///
/// Passed as argument to an Endpoint \a Read
class ReadArgs final {
public:
ReadArgs() = default;
ReadArgs(const ReadArgs&) = delete;
ReadArgs& operator=(const ReadArgs&) = delete;
ReadArgs(ReadArgs&&) = default;
ReadArgs& operator=(ReadArgs&&) = default;
struct ReadArgs {
// A suggestion to the endpoint implementation to read at-least the
// specified number of bytes over the network connection before marking
// the endpoint read operation as complete. gRPC may use this argument
// to minimize the number of endpoint read API calls over the lifetime
// of a connection.
void set_read_hint_bytes(int64_t read_hint_bytes) {
read_hint_bytes_ = read_hint_bytes;
}
int64_t read_hint_bytes() const { return read_hint_bytes_; }
private:
int64_t read_hint_bytes_ = 1;
int64_t read_hint_bytes;
};
/// Reads data from the Endpoint.
///
@ -228,110 +212,20 @@ class EventEngine : public std::enable_shared_from_this<EventEngine>,
/// statuses to \a on_read. For example, callbacks might expect to receive
/// CANCELLED on endpoint shutdown.
virtual bool Read(absl::AnyInvocable<void(absl::Status)> on_read,
SliceBuffer* buffer, ReadArgs args) = 0;
//// The set of write events that can be reported by an Endpoint.
using WriteEvent = ::grpc_event_engine::experimental::internal::WriteEvent;
/// An output WriteMetric consists of a key and a value.
/// The space of keys can be queried from the endpoint via the
/// \a AllWriteMetrics, \a GetMetricName and \a GetMetricKey APIs.
/// The value is an int64_t that is implementation-defined. Check with the
/// endpoint implementation documentation for the semantics of each metric.
struct WriteMetric {
size_t key;
int64_t value;
};
using WriteEventCallback = absl::AnyInvocable<void(
WriteEvent, absl::Time, std::vector<WriteMetric>) const>;
// A bitmask of the events that the caller is interested in.
// Each bit corresponds to an entry in WriteEvent.
using WriteEventSet = std::bitset<static_cast<int>(WriteEvent::kCount)>;
// A sink to receive write events.
// The requested metrics are the keys of the metrics that the caller is
// interested in. The on_event callback will be called on each event
// requested.
class WriteEventSink final {
public:
WriteEventSink(absl::Span<const size_t> requested_metrics,
std::initializer_list<WriteEvent> requested_events,
WriteEventCallback on_event)
: requested_metrics_(requested_metrics),
on_event_(std::move(on_event)) {
for (auto event : requested_events) {
requested_events_mask_.set(static_cast<int>(event));
}
}
absl::Span<const size_t> requested_metrics() const {
return requested_metrics_;
}
bool requested_event(WriteEvent event) const {
return requested_events_mask_.test(static_cast<int>(event));
}
WriteEventSet requested_events_mask() const {
return requested_events_mask_;
}
WriteEventCallback TakeEventCallback() { return std::move(on_event_); }
private:
absl::Span<const size_t> requested_metrics_;
WriteEventSet requested_events_mask_;
// The callback to be called on each event.
WriteEventCallback on_event_;
};
SliceBuffer* buffer, const ReadArgs* args) = 0;
/// A struct representing optional arguments that may be provided to an
/// EventEngine Endpoint Write API call.
///
/// Passed as argument to an Endpoint \a Write
class WriteArgs final {
public:
WriteArgs() = default;
WriteArgs(const WriteArgs&) = delete;
WriteArgs& operator=(const WriteArgs&) = delete;
WriteArgs(WriteArgs&&) = default;
WriteArgs& operator=(WriteArgs&&) = default;
// A sink to receive write events.
std::optional<WriteEventSink> TakeMetricsSink() {
auto sink = std::move(metrics_sink_);
metrics_sink_.reset();
return sink;
}
bool has_metrics_sink() const { return metrics_sink_.has_value(); }
void set_metrics_sink(WriteEventSink sink) {
metrics_sink_ = std::move(sink);
}
struct WriteArgs {
// Represents private information that may be passed by gRPC for
// select endpoints expected to be used only within google.
// TODO(ctiller): Remove this method once all callers are migrated to
// metrics sink.
void* GetDeprecatedAndDiscouragedGoogleSpecificPointer() {
return google_specific_;
}
void SetDeprecatedAndDiscouragedGoogleSpecificPointer(void* pointer) {
google_specific_ = pointer;
}
void* google_specific = nullptr;
// A suggestion to the endpoint implementation to group data to be written
// into frames of the specified max_frame_size. gRPC may use this
// argument to dynamically control the max sizes of frames sent to a
// receiver in response to high receiver memory pressure.
int64_t max_frame_size() const { return max_frame_size_; }
void set_max_frame_size(int64_t max_frame_size) {
max_frame_size_ = max_frame_size;
}
private:
std::optional<WriteEventSink> metrics_sink_;
void* google_specific_ = nullptr;
int64_t max_frame_size_ = 1024 * 1024;
int64_t max_frame_size;
};
/// Writes data out on the connection.
///
@ -354,22 +248,11 @@ class EventEngine : public std::enable_shared_from_this<EventEngine>,
/// statuses to \a on_writable. For example, callbacks might expect to
/// receive CANCELLED on endpoint shutdown.
virtual bool Write(absl::AnyInvocable<void(absl::Status)> on_writable,
SliceBuffer* data, WriteArgs args) = 0;
SliceBuffer* data, const WriteArgs* args) = 0;
/// Returns an address in the format described in DNSResolver. The returned
/// values are expected to remain valid for the life of the Endpoint.
virtual const ResolvedAddress& GetPeerAddress() const = 0;
virtual const ResolvedAddress& GetLocalAddress() const = 0;
/// Returns the list of write metrics that the endpoint supports.
/// The keys are used to identify the metrics in the GetMetricName and
/// GetMetricKey APIs. The current value of the metric can be queried by
/// adding a WriteEventSink to the WriteArgs of a Write call.
virtual std::vector<size_t> AllWriteMetrics() = 0;
/// Returns the name of the write metric with the given key.
/// If the key is not found, returns std::nullopt.
virtual std::optional<absl::string_view> GetMetricName(size_t key) = 0;
/// Returns the key of the write metric with the given name.
/// If the name is not found, returns std::nullopt.
virtual std::optional<size_t> GetMetricKey(absl::string_view name) = 0;
};
/// Called when a new connection is established.
@ -451,7 +334,7 @@ class EventEngine : public std::enable_shared_from_this<EventEngine>,
/// when the object is destroyed and all pending callbacks will be called
/// shortly. If cancellation races with request completion, implementations
/// may choose to either cancel or satisfy the request.
class DNSResolver : public Extensible {
class DNSResolver {
public:
/// Optional configuration for DNSResolvers.
struct ResolverOptions {

View File

@ -1,34 +0,0 @@
// Copyright 2022 gRPC authors.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
#ifndef GRPC_EVENT_ENGINE_INTERNAL_WRITE_EVENT_H
#define GRPC_EVENT_ENGINE_INTERNAL_WRITE_EVENT_H
namespace grpc_event_engine::experimental::internal {
// Use of this enum via this name is internal to gRPC.
// API users should get this enumeration via the
// EventEngine::Endpoint::WriteEvent.
enum class WriteEvent {
kSendMsg,
kScheduled,
kSent,
kAcked,
kClosed,
kCount // Must be last.
};
} // namespace grpc_event_engine::experimental::internal
#endif // GRPC_EVENT_ENGINE_INTERNAL_WRITE_EVENT_H

View File

@ -55,11 +55,11 @@ class MemoryRequest {
template <typename Sink>
friend void AbslStringify(Sink& s, const MemoryRequest& r) {
if (r.min_ == r.max_) {
s.Append(std::to_string(r.min_));
s.Append(r.min_);
} else {
s.Append(std::to_string(r.min_));
s.Append(r.min_);
s.Append("..");
s.Append(std::to_string(r.max_));
s.Append(r.max_);
}
}

View File

@ -0,0 +1,37 @@
/*
*
* Copyright 2016 gRPC authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
*/
#ifndef GRPC_GRPC_CRONET_H
#define GRPC_GRPC_CRONET_H
#include <grpc/grpc.h>
#include <grpc/support/port_platform.h>
#ifdef __cplusplus
extern "C" {
#endif
GRPCAPI grpc_channel* grpc_cronet_secure_channel_create(
void* engine, const char* target, const grpc_channel_args* args,
void* reserved);
#ifdef __cplusplus
}
#endif
#endif /* GRPC_GRPC_CRONET_H */

View File

@ -31,15 +31,13 @@
#define GRPC_ARG_SERVER_CALL_METRIC_RECORDING \
"grpc.server_call_metric_recording"
/** Request that optional features default to off (regardless of what they
usually default to) - to enable tight control over what gets enabled
Boolean valued. Defaults to false. */
usually default to) - to enable tight control over what gets enabled */
#define GRPC_ARG_MINIMAL_STACK "grpc.minimal_stack"
/** Maximum number of concurrent incoming streams to allow on a http2
connection. Int valued. Deafult to -1(indicating no explicit limit).*/
connection. Int valued. */
#define GRPC_ARG_MAX_CONCURRENT_STREAMS "grpc.max_concurrent_streams"
/** Maximum message length that the channel can receive. Int valued, bytes.
-1 means unlimited. Defaults to 4MB(4*1024*1024 bytes). -1 means unlimited.
*/
-1 means unlimited. */
#define GRPC_ARG_MAX_RECEIVE_MESSAGE_LENGTH "grpc.max_receive_message_length"
/** \deprecated For backward compatibility.
* Use GRPC_ARG_MAX_RECEIVE_MESSAGE_LENGTH instead. */
@ -49,31 +47,27 @@
#define GRPC_ARG_MAX_SEND_MESSAGE_LENGTH "grpc.max_send_message_length"
/** Maximum time that a channel may have no outstanding rpcs, after which the
* server will close the connection. Int valued, milliseconds. INT_MAX means
* unlimited. Defaults to INT_MAX. */
* unlimited. */
#define GRPC_ARG_MAX_CONNECTION_IDLE_MS "grpc.max_connection_idle_ms"
/** Maximum amount of time in milliseconds that a connection may exist before it
* will be gracefully shut down. Refer
* https://github.com/grpc/proposal/blob/master/A9-server-side-conn-mgt.md for
* more details. Int valued, defaults to INT_MAX (disabled). */
/** Maximum time that a channel may exist. Int valued, milliseconds.
* INT_MAX means unlimited. */
#define GRPC_ARG_MAX_CONNECTION_AGE_MS "grpc.max_connection_age_ms"
/** Grace period in milliseconds after connection reaches its max age for
* outstanding RPCs to complete. Int valued, defaults to INT_MAX (disabled). */
/** Grace period after the channel reaches its max age. Int valued,
milliseconds. INT_MAX means unlimited. */
#define GRPC_ARG_MAX_CONNECTION_AGE_GRACE_MS "grpc.max_connection_age_grace_ms"
/** Timeout after the last RPC finishes on the client channel at which the
* channel goes back into IDLE state. Int valued, milliseconds. INT_MAX means
* unlimited. The default value is 30 minutes and the min value is 1 second. */
#define GRPC_ARG_CLIENT_IDLE_TIMEOUT_MS "grpc.client_idle_timeout_ms"
/** Enable/disable support for per-message compression. Boolean valued. Defaults
to true, unless GRPC_ARG_MINIMAL_STACK is enabled, in which case it defaults
to false. */
/** Enable/disable support for per-message compression. Defaults to 1, unless
GRPC_ARG_MINIMAL_STACK is enabled, in which case it defaults to 0. */
#define GRPC_ARG_ENABLE_PER_MESSAGE_COMPRESSION "grpc.per_message_compression"
/** Experimental Arg. Enable/disable support for per-message decompression.
Defaults to 1. If disabled, decompression will not be performed and the
application will see the compressed message in the byte buffer. */
#define GRPC_ARG_ENABLE_PER_MESSAGE_DECOMPRESSION \
"grpc.per_message_decompression"
/** Initial stream ID for http2 transports. Int valued. Defaults to -1
indicating use of default http2 setting initial stream ID (1). */
/** Initial stream ID for http2 transports. Int valued. */
#define GRPC_ARG_HTTP2_INITIAL_SEQUENCE_NUMBER \
"grpc.http2.initial_sequence_number"
/** Amount to read ahead on individual streams. Defaults to 64kb, larger
@ -81,22 +75,17 @@
NOTE: at some point we'd like to auto-tune this, and this parameter
will become a no-op. Int valued, bytes. */
#define GRPC_ARG_HTTP2_STREAM_LOOKAHEAD_BYTES "grpc.http2.lookahead_bytes"
/** How much memory to use for hpack decoding. Int valued, bytes. Defaults to -1
indicating use of default http2 setting(4096 bytes). */
/** How much memory to use for hpack decoding. Int valued, bytes. */
#define GRPC_ARG_HTTP2_HPACK_TABLE_SIZE_DECODER \
"grpc.http2.hpack_table_size.decoder"
/** How much memory to use for hpack encoding. Int valued, bytes. Defaults to -1
indicating use of default http2 setting(4096 bytes). */
/** How much memory to use for hpack encoding. Int valued, bytes. */
#define GRPC_ARG_HTTP2_HPACK_TABLE_SIZE_ENCODER \
"grpc.http2.hpack_table_size.encoder"
/** How big a frame are we willing to receive via HTTP2.
Min 16384, max 16777215. Larger values give lower CPU usage for large
messages, but more head of line blocking for small messages. Defaults to
-1(indicating no explicit max frame size), so it will take standard http/2
specified max frame size to 16 KB. */
messages, but more head of line blocking for small messages. */
#define GRPC_ARG_HTTP2_MAX_FRAME_SIZE "grpc.http2.max_frame_size"
/** Should BDP probing be performed?
Boolean valued. Defaults to true(enabled). */
/** Should BDP probing be performed? */
#define GRPC_ARG_HTTP2_BDP_PROBE "grpc.http2.bdp_probe"
/** (DEPRECATED) Does not have any effect.
Earlier, this arg configured the minimum time between successive ping frames
@ -120,24 +109,21 @@
before the request is cancelled */
#define GRPC_ARG_SERVER_MAX_UNREQUESTED_TIME_IN_SERVER_SECONDS \
"grpc.server_max_unrequested_time_in_server"
/** Channel arg to override the http2 :scheme header. String valued. */
/** Channel arg to override the http2 :scheme header */
#define GRPC_ARG_HTTP2_SCHEME "grpc.http2_scheme"
/** How many pings can the client send before needing to send a data/header
frame? (0 indicates that an infinite number of pings can be sent without
sending a data frame or header frame).
If experiment "max_pings_wo_data_throttle" is enabled, instead of pings being
completely blocked, they are throttled.
* Integer valued. Defaults to 2. */
completely blocked, they are throttled. */
#define GRPC_ARG_HTTP2_MAX_PINGS_WITHOUT_DATA \
"grpc.http2.max_pings_without_data"
/** How many misbehaving pings the server can bear before sending goaway and
closing the transport? (0 indicates that the server can bear an infinite
number of misbehaving pings)
* Integer valued. Defaults to 2. */
number of misbehaving pings) */
#define GRPC_ARG_HTTP2_MAX_PING_STRIKES "grpc.http2.max_ping_strikes"
/** How much data are we willing to queue up per stream if
GRPC_WRITE_BUFFER_HINT is set? This is an upper bound
* Integer valued, bytes. Defaults to 65535 bytes. */
GRPC_WRITE_BUFFER_HINT is set? This is an upper bound */
#define GRPC_ARG_HTTP2_WRITE_BUFFER_SIZE "grpc.http2.write_buffer_size"
/** Should we allow receipt of true-binary data on http2 connections?
Defaults to on (1) */
@ -150,44 +136,33 @@
#define GRPC_ARG_EXPERIMENTAL_HTTP2_PREFERRED_CRYPTO_FRAME_SIZE \
"grpc.experimental.http2.enable_preferred_frame_size"
/** After a duration of this time the client/server pings its peer to see if the
transport is still alive. Int valued, milliseconds. Defaults to 7200000 (2
hours). */
transport is still alive. Int valued, milliseconds. */
#define GRPC_ARG_KEEPALIVE_TIME_MS "grpc.keepalive_time_ms"
/** After waiting for a duration of this time, if the keepalive ping sender does
not receive the ping ack, it will close the transport. Int valued,
milliseconds. Defaults to 20000 (20 seonds). */
milliseconds. */
#define GRPC_ARG_KEEPALIVE_TIMEOUT_MS "grpc.keepalive_timeout_ms"
/** Is it permissible to send keepalive pings from the client without any
outstanding streams. Int valued, 0(false)/1(true). Defaults to 0. */
outstanding streams. Int valued, 0(false)/1(true). */
#define GRPC_ARG_KEEPALIVE_PERMIT_WITHOUT_CALLS \
"grpc.keepalive_permit_without_calls"
/** Default authority to pass if none specified on call construction. A string.
* */
#define GRPC_ARG_DEFAULT_AUTHORITY "grpc.default_authority"
/** Primary user agent: goes at the start of the user-agent metadata
sent on each request. A string. Defaults to empty string(""). */
sent on each request. A string. */
#define GRPC_ARG_PRIMARY_USER_AGENT_STRING "grpc.primary_user_agent"
/** Secondary user agent: goes at the end of the user-agent metadata
sent on each request. A string. */
#define GRPC_ARG_SECONDARY_USER_AGENT_STRING "grpc.secondary_user_agent"
/** The minimum time between subsequent connection attempts, in ms. Refer to
* MIN_CONNECT_TIMEOUT from
* https://github.com/grpc/grpc/blob/master/doc/connection-backoff.md. Defaults
* to 20 seconds. */
/** The minimum time between subsequent connection attempts, in ms */
#define GRPC_ARG_MIN_RECONNECT_BACKOFF_MS "grpc.min_reconnect_backoff_ms"
/** The maximum time between subsequent connection attempts, in ms. Refer to
* MAX_BACKOFF from
* https://github.com/grpc/grpc/blob/master/doc/connection-backoff.md. Defaults
* to 120 seconds. */
/** The maximum time between subsequent connection attempts, in ms */
#define GRPC_ARG_MAX_RECONNECT_BACKOFF_MS "grpc.max_reconnect_backoff_ms"
/** The time between the first and second connection attempts, in ms. Refer to
* INITIAL_BACKOFF from
* https://github.com/grpc/grpc/blob/master/doc/connection-backoff.md. Defaults
* to 1 second. */
/** The time between the first and second connection attempts, in ms */
#define GRPC_ARG_INITIAL_RECONNECT_BACKOFF_MS \
"grpc.initial_reconnect_backoff_ms"
/** Minimum amount of time between DNS resolutions, in ms. Defaults to 30
* seconds. */
/** Minimum amount of time between DNS resolutions, in ms */
#define GRPC_ARG_DNS_MIN_TIME_BETWEEN_RESOLUTIONS_MS \
"grpc.dns_min_time_between_resolutions_ms"
/** The timeout used on servers for finishing handshaking on an incoming
@ -203,10 +178,10 @@
#define GRPC_SSL_TARGET_NAME_OVERRIDE_ARG "grpc.ssl_target_name_override"
/** If non-zero, a pointer to a session cache (a pointer of type
grpc_ssl_session_cache*). (use grpc_ssl_session_cache_arg_vtable() to fetch
an appropriate pointer arg vtable). */
an appropriate pointer arg vtable) */
#define GRPC_SSL_SESSION_CACHE_ARG "grpc.ssl_session_cache"
/** If non-zero, it will determine the maximum frame size used by TSI's frame
* protector. Defaults to zero.
* protector.
*/
#define GRPC_ARG_TSI_MAX_FRAME_SIZE "grpc.tsi.max_frame_size"
/** Maximum metadata size (soft limit), in bytes. Note this limit applies to the
@ -225,20 +200,17 @@
#define GRPC_ARG_ALLOW_REUSEPORT "grpc.so_reuseport"
/** If non-zero, a pointer to a buffer pool (a pointer of type
* grpc_resource_quota*). (use grpc_resource_quota_arg_vtable() to fetch an
* appropriate pointer arg vtable). */
* appropriate pointer arg vtable) */
#define GRPC_ARG_RESOURCE_QUOTA "grpc.resource_quota"
/** If non-zero, expand wildcard addresses to a list of local addresses. Boolean
* valued. */
/** If non-zero, expand wildcard addresses to a list of local addresses. */
#define GRPC_ARG_EXPAND_WILDCARD_ADDRS "grpc.expand_wildcard_addrs"
/** Service config data in JSON form.
This value will be ignored if the name resolver returns a service config. A
string value. */
This value will be ignored if the name resolver returns a service config. */
#define GRPC_ARG_SERVICE_CONFIG "grpc.service_config"
/** Disable looking up the service config via the name resolver. Boolean valued.
* Defaults to true. */
/** Disable looking up the service config via the name resolver. */
#define GRPC_ARG_SERVICE_CONFIG_DISABLE_RESOLUTION \
"grpc.service_config_disable_resolution"
/** LB policy name. A string value.*/
/** LB policy name. */
#define GRPC_ARG_LB_POLICY_NAME "grpc.lb_policy_name"
/** Cap for ring size in the ring_hash LB policy. The min and max ring size
values set in the LB policy config will be capped to this value.
@ -251,23 +223,24 @@
/** The maximum amount of memory used by trace events per channel trace node.
* Once the maximum is reached, subsequent events will evict the oldest events
* from the buffer. The unit for this knob is bytes. Setting it to zero causes
* channel tracing to be disabled. Defaults to (1024 * 4) bytes. */
* channel tracing to be disabled. */
#define GRPC_ARG_MAX_CHANNEL_TRACE_EVENT_MEMORY_PER_NODE \
"grpc.max_channel_trace_event_memory_per_node"
/** If non-zero, gRPC library will track stats and information at at per channel
* level. Disabling channelz naturally disables channel tracing. The default
* is for channelz to be enabled. */
#define GRPC_ARG_ENABLE_CHANNELZ "grpc.enable_channelz"
/** If non-zero, Cronet transport will coalesce packets to fewer frames
* when possible. */
#define GRPC_ARG_USE_CRONET_PACKET_COALESCING \
"grpc.use_cronet_packet_coalescing"
/** Channel arg (integer) setting how large a slice to try and read from the
wire each time recvmsg (or equivalent). Range varied from 1
to (32 * 1024 * 1024) bytes. Defaults to 8192 bytes. **/
wire each time recvmsg (or equivalent) is called **/
#define GRPC_ARG_TCP_READ_CHUNK_SIZE "grpc.experimental.tcp_read_chunk_size"
/** Note this is not a "channel arg" key. This is the default slice size to use
* when trying to read from the wire if the GRPC_ARG_TCP_READ_CHUNK_SIZE
* channel arg is unspecified. */
#define GRPC_TCP_DEFAULT_READ_SLICE_SIZE 8192
/** Minimum read chunk size defaults to 256 bytes. Range varies from 1 to (32 *
* 1024 * 1024) bytes. */
#define GRPC_ARG_TCP_MIN_READ_CHUNK_SIZE \
"grpc.experimental.tcp_min_read_chunk_size"
#define GRPC_ARG_TCP_MAX_READ_CHUNK_SIZE \
@ -286,12 +259,10 @@
issued by the tcp_write(). By default, this is set to 4. */
#define GRPC_ARG_TCP_TX_ZEROCOPY_MAX_SIMULT_SENDS \
"grpc.experimental.tcp_tx_zerocopy_max_simultaneous_sends"
/* Overrides the TCP socket receive buffer size, SO_RCVBUF.
Default value is -1(kReadBufferSizeUnset) indicating that the system will
decide the buffer size. Range varies from 0 to INT_MAX. */
/* Overrides the TCP socket receive buffer size, SO_RCVBUF. */
#define GRPC_ARG_TCP_RECEIVE_BUFFER_SIZE "grpc.tcp_receive_buffer_size"
/* Timeout in milliseconds to use for calls to the grpclb load balancer.
If 0 or unset, the balancer calls will have no deadline. Defaults to 0 ms. */
If 0 or unset, the balancer calls will have no deadline. */
#define GRPC_ARG_GRPCLB_CALL_TIMEOUT_MS "grpc.grpclb_call_timeout_ms"
/* Specifies the xDS bootstrap config as a JSON string.
FOR TESTING PURPOSES ONLY -- DO NOT USE IN PRODUCTION.
@ -306,7 +277,7 @@
"grpc.TEST_ONLY_DO_NOT_USE_IN_PROD.xds_bootstrap_config"
/* Timeout in milliseconds to wait for the serverlist from the grpclb load
balancer before using fallback backend addresses from the resolver.
If 0, enter fallback mode immediately. Default value is 10000ms. */
If 0, enter fallback mode immediately. Default value is 10000. */
#define GRPC_ARG_GRPCLB_FALLBACK_TIMEOUT_MS "grpc.grpclb_fallback_timeout_ms"
/* Experimental Arg. Channel args to be used for the control-plane channel
* created to the grpclb load balancers. This is a pointer arg whose value is a
@ -319,6 +290,9 @@
over to the next priority. Default value is 10 seconds. */
#define GRPC_ARG_PRIORITY_FAILOVER_TIMEOUT_MS \
"grpc.priority_failover_timeout_ms"
/** If non-zero, grpc server's cronet compression workaround will be enabled */
#define GRPC_ARG_WORKAROUND_CRONET_COMPRESSION \
"grpc.workaround.cronet_compression"
/** String defining the optimization target for a channel.
Can be: "latency" - attempt to minimize latency at the cost of throughput
"blend" - try to balance latency and throughput
@ -351,15 +325,13 @@
/** Channel arg that carries the bridged objective c object for custom metrics
* logging filter. */
#define GRPC_ARG_MOBILE_LOG_CONTEXT "grpc.mobile_log_context"
/** If non-zero, client authority filter is disabled for the channel.
* Boolean valued. Defaults to false. */
/** If non-zero, client authority filter is disabled for the channel */
#define GRPC_ARG_DISABLE_CLIENT_AUTHORITY_FILTER \
"grpc.disable_client_authority_filter"
/** If set to zero, disables use of http proxies. Enabled by default. */
#define GRPC_ARG_ENABLE_HTTP_PROXY "grpc.enable_http_proxy"
/** Channel arg to set http proxy per channel. If set, the channel arg
* value will be preferred over the environment variable settings. String
* value. */
* value will be preferred over the environment variable settings. */
#define GRPC_ARG_HTTP_PROXY "grpc.http_proxy"
/** Specifies an HTTP proxy to use for individual addresses.
* The proxy must be specified as an IP address, not a DNS name.
@ -375,7 +347,7 @@
agent is surfaced by default. */
#define GRPC_ARG_SURFACE_USER_AGENT "grpc.surface_user_agent"
/** If set, inhibits health checking (which may be enabled via the
* service config.). Boolean valued. Defaults to false. */
* service config.) */
#define GRPC_ARG_INHIBIT_HEALTH_CHECKING "grpc.inhibit_health_checking"
/** If enabled, the channel's DNS resolver queries for SRV records.
* This is useful only when using the "grpclb" load balancing policy,
@ -384,17 +356,17 @@
* https://github.com/grpc/proposal/blob/master/A24-lb-policy-config.md
* https://github.com/grpc/proposal/blob/master/A26-grpclb-selection.md
* Note that this works only with the "ares" DNS resolver; it isn't supported
* by the "native" DNS resolver. Boolean valued. Defaults to false. */
* by the "native" DNS resolver. */
#define GRPC_ARG_DNS_ENABLE_SRV_QUERIES "grpc.dns_enable_srv_queries"
/** If set, determines an upper bound on the number of milliseconds that the
* c-ares based DNS resolver will wait on queries before cancelling them.
* The default value is 120,000ms. Setting this to "0" will disable the
* The default value is 120,000. Setting this to "0" will disable the
* overall timeout entirely. Note that this doesn't include internal c-ares
* timeouts/backoff/retry logic, and so the actual DNS resolution may time out
* sooner than the value specified here. */
#define GRPC_ARG_DNS_ARES_QUERY_TIMEOUT_MS "grpc.dns_ares_query_timeout"
/** If set, uses a local subchannel pool within the channel. Otherwise, uses the
* global subchannel pool. Boolean valued. Defaults to false. */
* global subchannel pool. */
#define GRPC_ARG_USE_LOCAL_SUBCHANNEL_POOL "grpc.use_local_subchannel_pool"
/** gRPC Objective-C channel pooling domain string. */
#define GRPC_ARG_CHANNEL_POOL_DOMAIN "grpc.channel_pooling_domain"

View File

@ -41,9 +41,8 @@ extern "C" {
* Its value is an int from the \a grpc_compression_algorithm enum. */
#define GRPC_COMPRESSION_CHANNEL_DEFAULT_ALGORITHM \
"grpc.default_compression_algorithm"
/** Set the default compression level for the channel.
* Valid values are defined by the enum type grpc_compression_level, defaults to
* GRPC_COMPRESS_LEVEL_NONE. */
/** Default compression level for the channel.
* Its value is an int from the \a grpc_compression_level enum. */
#define GRPC_COMPRESSION_CHANNEL_DEFAULT_LEVEL "grpc.default_compression_level"
/** Compression algorithms supported by the channel.
* Its value is a bitset (an int). Bits correspond to algorithms in \a

View File

@ -73,7 +73,7 @@ struct grpc_slice {
} data;
};
#define GRPC_SLICE_BUFFER_INLINE_ELEMENTS 3
#define GRPC_SLICE_BUFFER_INLINE_ELEMENTS 6
/** Represents an expandable array of slices, to be interpreted as a
single item. */

View File

@ -22,7 +22,6 @@
#include <map>
#include <string>
#include <type_traits>
#include <utility>
#include <variant>
#include <vector>
@ -73,8 +72,27 @@ class Json {
json.value_ = NumberValue{std::move(str)};
return json;
}
template <typename T>
static std::enable_if_t<std::is_arithmetic_v<T>, Json> FromNumber(T value) {
static Json FromNumber(int32_t value) {
Json json;
json.value_ = NumberValue{absl::StrCat(value)};
return json;
}
static Json FromNumber(uint32_t value) {
Json json;
json.value_ = NumberValue{absl::StrCat(value)};
return json;
}
static Json FromNumber(int64_t value) {
Json json;
json.value_ = NumberValue{absl::StrCat(value)};
return json;
}
static Json FromNumber(uint64_t value) {
Json json;
json.value_ = NumberValue{absl::StrCat(value)};
return json;
}
static Json FromNumber(double value) {
Json json;
json.value_ = NumberValue{absl::StrCat(value)};
return json;

View File

@ -26,20 +26,17 @@
#define GRPC_DEPRECATED(reason)
#endif // __cplusplus >= 201402L
#ifndef GPR_DISABLE_ABSEIL_SYNC
/*
* Defines GPR_ABSEIL_SYNC to use synchronization features from Abseil
*
* You can opt for gRPC's native synchronization by enabling
* GPR_DISABLE_ABSEIL_SYNC. However, this flag is temporary and will be
* removed once the Abseil synchronization is stabilized.
* If you encounter any issues with this feature, please report them
* by filing a bug at https://github.com/grpc/grpc.
*/
#ifndef GPR_ABSEIL_SYNC
#if defined(__APPLE__)
// This is disabled on Apple platforms because macos/grpc_basictests_c_cpp
// fails with this. https://github.com/grpc/grpc/issues/23661
#else
#define GPR_ABSEIL_SYNC 1
#endif
#endif // GPR_ABSEIL_SYNC
#endif // GPR_DISABLE_ABSEIL_SYNC
/* Get windows.h included everywhere (we need it) */
#if defined(_WIN64) || defined(WIN64) || defined(_WIN32) || defined(WIN32)

View File

@ -23,6 +23,9 @@
* explanation and detailed descriptions of workarounds, see
* /doc/workarounds.md
*/
typedef enum { GRPC_MAX_WORKAROUND_ID } grpc_workaround_list;
typedef enum {
GRPC_WORKAROUND_ID_CRONET_COMPRESSION = 0,
GRPC_MAX_WORKAROUND_ID
} grpc_workaround_list;
#endif /* GRPC_SUPPORT_WORKAROUND_LIST_H */

View File

@ -36,12 +36,12 @@
#include <grpc/support/atm.h>
#include <grpc/support/time.h>
#include <grpcpp/impl/codegen/rpc_service_method.h>
#include <grpcpp/impl/codegen/status.h>
#include <grpcpp/impl/codegen/sync.h>
#include <grpcpp/impl/codegen/time.h>
#include <grpcpp/impl/completion_queue_tag.h>
#include <grpcpp/impl/grpc_library.h>
#include <grpcpp/impl/sync.h>
#include <grpcpp/support/status.h>
#include <list>

View File

@ -116,8 +116,8 @@ class CallbackUnaryHandler : public grpc::internal::MethodHandler {
// A callback that only contains a call to MaybeDone can be run as an
// inline callback regardless of whether or not OnDone is inlineable
// because if the actual OnDone callback needs to be scheduled, MaybeDone
// is responsible for dispatching to an EventEngine thread if needed.
// Thus, when setting up the finish_tag_, we can set its own callback to
// is responsible for dispatching to an executor thread if needed. Thus,
// when setting up the finish_tag_, we can set its own callback to
// inlineable.
finish_tag_.Set(
call_.call(),
@ -152,9 +152,9 @@ class CallbackUnaryHandler : public grpc::internal::MethodHandler {
this->Ref();
// The callback for this function should not be marked inline because it
// is directly invoking a user-controlled reaction
// (OnSendInitialMetadataDone). Thus it must be dispatched to an
// EventEngine thread. However, any OnDone needed after that can be
// inlined because it is already running on an EventEngine thread.
// (OnSendInitialMetadataDone). Thus it must be dispatched to an executor
// thread. However, any OnDone needed after that can be inlined because it
// is already running on an executor thread.
meta_tag_.Set(
call_.call(),
[this](bool ok) {
@ -340,7 +340,7 @@ class CallbackClientStreamingHandler : public grpc::internal::MethodHandler {
this->Ref();
// The callback for this function should not be inlined because it invokes
// a user-controlled reaction, but any resulting OnDone can be inlined in
// the EventEngine thread to which this callback is dispatched.
// the executor to which this callback is dispatched.
meta_tag_.Set(
call_.call(),
[this](bool ok) {
@ -380,7 +380,7 @@ class CallbackClientStreamingHandler : public grpc::internal::MethodHandler {
reactor_.store(reactor, std::memory_order_relaxed);
// The callback for this function should not be inlined because it invokes
// a user-controlled reaction, but any resulting OnDone can be inlined in
// the EventEngine thread to which this callback is dispatched.
// the executor to which this callback is dispatched.
read_tag_.Set(
call_.call(),
[this, reactor](bool ok) {
@ -544,7 +544,7 @@ class CallbackServerStreamingHandler : public grpc::internal::MethodHandler {
this->Ref();
// The callback for this function should not be inlined because it invokes
// a user-controlled reaction, but any resulting OnDone can be inlined in
// the EventEngine thread to which this callback is dispatched.
// the executor to which this callback is dispatched.
meta_tag_.Set(
call_.call(),
[this](bool ok) {
@ -607,7 +607,7 @@ class CallbackServerStreamingHandler : public grpc::internal::MethodHandler {
reactor_.store(reactor, std::memory_order_relaxed);
// The callback for this function should not be inlined because it invokes
// a user-controlled reaction, but any resulting OnDone can be inlined in
// the EventEngine thread to which this callback is dispatched.
// the executor to which this callback is dispatched.
write_tag_.Set(
call_.call(),
[this, reactor](bool ok) {
@ -756,7 +756,7 @@ class CallbackBidiHandler : public grpc::internal::MethodHandler {
this->Ref();
// The callback for this function should not be inlined because it invokes
// a user-controlled reaction, but any resulting OnDone can be inlined in
// the EventEngine thread to which this callback is dispatched.
// the executor to which this callback is dispatched.
meta_tag_.Set(
call_.call(),
[this](bool ok) {
@ -821,7 +821,7 @@ class CallbackBidiHandler : public grpc::internal::MethodHandler {
reactor_.store(reactor, std::memory_order_relaxed);
// The callbacks for these functions should not be inlined because they
// invoke user-controlled reactions, but any resulting OnDones can be
// inlined in the EventEngine thread to which a callback is dispatched.
// inlined in the executor to which a callback is dispatched.
write_tag_.Set(
call_.call(),
[this, reactor](bool ok) {

View File

@ -17,7 +17,7 @@
#include <grpc/grpc_security.h>
#include <grpc/status.h>
#include <grpcpp/support/status.h>
#include <grpcpp/impl/codegen/status.h>
#include <memory>

View File

@ -1,6 +1,6 @@
//
//
// Copyright 2025 gRPC authors.
// Copyright 2019 gRPC authors.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
@ -16,9 +16,18 @@
//
//
#ifndef GRPC_SRC_CORE_EXT_TRANSPORT_CHTTP2_TRANSPORT_INTERNAL_CHANNEL_ARG_NAMES_H
#define GRPC_SRC_CORE_EXT_TRANSPORT_CHTTP2_TRANSPORT_INTERNAL_CHANNEL_ARG_NAMES_H
#ifndef GRPCPP_SECURITY_CRONET_CREDENTIALS_H
#define GRPCPP_SECURITY_CRONET_CREDENTIALS_H
#define GRPC_ARG_PING_TIMEOUT_MS "grpc.http2.ping_timeout_ms"
#include <memory>
#endif // GRPC_SRC_CORE_EXT_TRANSPORT_CHTTP2_TRANSPORT_INTERNAL_CHANNEL_ARG_NAMES_H
namespace grpc {
class ChannelCredentials;
/// Credentials for a channel using Cronet.
std::shared_ptr<ChannelCredentials> CronetChannelCredentials(void* engine);
} // namespace grpc
#endif // GRPCPP_SECURITY_CRONET_CREDENTIALS_H

View File

@ -501,9 +501,9 @@ class ServerContextBase {
void OnCancel() override {}
void OnDone() override {}
// Override InternalInlineable for this class since its reactions are
// trivial and thus do not need to be run from the EventEngine (potentially
// triggering a thread hop). This should only be used by internal reactors
// (thus the name) and not by user application code.
// trivial and thus do not need to be run from the executor (triggering a
// thread hop). This should only be used by internal reactors (thus the
// name) and not by user application code.
bool InternalInlineable() override { return true; }
};

View File

@ -84,10 +84,8 @@ class ChannelArguments {
void SetMaxSendMessageSize(int size);
/// Set LB policy name.
/// Note that this API implicitly provides an empty config for the
/// specified LB policy, so it cannot be used for any policy with
/// required configuration parameters. For those cases, set the LB
/// policy via the service config instead.
/// Note that if the name resolver returns only balancer addresses, the
/// grpclb LB policy will be used, regardless of what is specified here.
void SetLoadBalancingPolicyName(const std::string& lb_policy_name);
/// Set service config in JSON form.

View File

@ -636,8 +636,8 @@ class ClientCallbackReaderWriterImpl
// like StartCall or RemoveHold. If this is the last operation or hold on this
// object, it will invoke the OnDone reaction. If MaybeFinish was called from
// a reaction, it can call OnDone directly. If not, it would need to schedule
// OnDone onto an EventEngine thread to avoid the possibility of deadlocking
// with any locks in the user code that invoked it.
// OnDone onto an executor thread to avoid the possibility of deadlocking with
// any locks in the user code that invoked it.
void MaybeFinish(bool from_reaction) {
if (GPR_UNLIKELY(callbacks_outstanding_.fetch_sub(
1, std::memory_order_acq_rel) == 1)) {

View File

@ -56,7 +56,7 @@ class ServerReactor {
virtual void OnCancel() = 0;
// The following is not API. It is for internal use only and specifies whether
// all reactions of this Reactor can be run without extra EventEngine
// all reactions of this Reactor can be run without an extra executor
// scheduling. This should only be used for internally-defined reactors with
// trivial reactions.
virtual bool InternalInlineable() { return false; }
@ -90,7 +90,7 @@ class ServerCallbackCall {
// advance (used for the ServerContext CompletionOp), and one for where we
// know the inlineability of the OnDone reaction. You should set the inline
// flag to true if either the Reactor is InternalInlineable() or if this
// callback is already being forced to run dispatched to an EventEngine thread
// callback is already being forced to run dispatched to an executor
// (typically because it contains additional work than just the MaybeDone).
void MaybeDone() {
@ -141,12 +141,12 @@ class ServerCallbackCall {
// ever invoked on a fully-Unref'fed ServerCallbackCall.
virtual void CallOnDone() = 0;
// If the OnDone reaction is inlineable, execute it inline. Otherwise run it
// async on EventEngine.
// If the OnDone reaction is inlineable, execute it inline. Otherwise send it
// to an executor.
void ScheduleOnDone(bool inline_ondone);
// If the OnCancel reaction is inlineable, execute it inline. Otherwise run it
// async on EventEngine.
// If the OnCancel reaction is inlineable, execute it inline. Otherwise send
// it to an executor.
void CallOnCancel(ServerReactor* reactor);
// Implement the cancellation constraint counter. Return true if OnCancel

View File

@ -19,9 +19,9 @@
#define GRPCPP_VERSION_INFO_H
#define GRPC_CPP_VERSION_MAJOR 1
#define GRPC_CPP_VERSION_MINOR 73
#define GRPC_CPP_VERSION_PATCH 1
#define GRPC_CPP_VERSION_TAG ""
#define GRPC_CPP_VERSION_STRING "1.73.1"
#define GRPC_CPP_VERSION_MINOR 71
#define GRPC_CPP_VERSION_PATCH 0
#define GRPC_CPP_VERSION_TAG "pre2"
#define GRPC_CPP_VERSION_STRING "1.71.0-pre2"
#endif // GRPCPP_VERSION_INFO_H
#endif // GRPCPP_VERSION_INFO_H

View File

@ -9,7 +9,7 @@ GRPC_IOS_BUILD_FLAGS="
CODE_SIGNING_ALLOWED=NO
ONLY_ACTIVE_ARCH=NO
ARCHS=arm64
IPHONEOS_DEPLOYMENT_TARGET=15.0
IPHONEOS_DEPLOYMENT_TARGET=12.0
"
# Xcodebuild destination for iOS

View File

@ -28,14 +28,10 @@ targets = (
'grpc_authorization_provider',
'gpr',
'upb_base_lib',
'upb_hash_lib',
'upb_lex_lib',
'upb_mem_lib',
'upb_message_lib',
'upb_mini_descriptor_lib',
'upb_mini_table_lib',
'upb_json_lib',
'upb_reflection_lib',
'upb_textformat_lib',
'upb_wire_lib',
'utf8_range_lib',
@ -57,6 +53,17 @@ extra_files = (
'src/objective-c/!ProtoCompiler-gRPCPlugin.podspec',
'src/objective-c/!ProtoCompiler.podspec',
'src/objective-c/BoringSSL-GRPC.podspec',
# cronet files
'include/grpc/grpc_cronet.h',
'src/core/ext/transport/cronet/client/secure/cronet_channel_create.cc',
'src/core/ext/transport/cronet/client/secure/cronet_channel_create.h',
'src/core/ext/transport/cronet/transport/cronet_status.cc',
'src/core/ext/transport/cronet/transport/cronet_status.h',
'src/core/ext/transport/cronet/transport/cronet_transport.cc',
'src/core/ext/transport/cronet/transport/cronet_transport.h',
'third_party/objective_c/Cronet/bidirectional_stream_c.h',
'include/grpcpp/security/cronet_credentials.h',
'src/cpp/client/cronet_credentials.cc',
# podspec files
'gRPC-C++.podspec',
'gRPC-Core.podspec',

View File

@ -17,9 +17,9 @@
#include <utility>
#include "src/core/call/call_spine.h"
#include "src/core/call/message.h"
#include "src/core/call/metadata.h"
#include "src/core/lib/transport/call_spine.h"
#include "src/core/lib/transport/message.h"
#include "src/core/lib/transport/metadata.h"
namespace grpc_core {

View File

@ -1,125 +0,0 @@
//
// Copyright 2015 gRPC authors.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
//
#include "src/core/call/security_context.h"
#include <grpc/credentials.h>
#include <grpc/grpc_security.h>
#include <grpc/support/alloc.h>
#include <grpc/support/port_platform.h>
#include <grpc/support/string_util.h>
#include <string.h>
#include <algorithm>
#include "absl/log/check.h"
#include "absl/log/log.h"
#include "src/core/credentials/call/call_credentials.h"
#include "src/core/lib/channel/channel_args.h"
#include "src/core/lib/debug/trace.h"
#include "src/core/lib/iomgr/exec_ctx.h"
#include "src/core/lib/resource_quota/arena.h"
#include "src/core/lib/surface/call.h"
#include "src/core/util/ref_counted_ptr.h"
// --- grpc_call ---
grpc_call_error grpc_call_set_credentials(grpc_call* call,
grpc_call_credentials* creds) {
grpc_core::ExecCtx exec_ctx;
grpc_client_security_context* ctx = nullptr;
GRPC_TRACE_LOG(api, INFO) << "grpc_call_set_credentials(call=" << call
<< ", creds=" << creds << ")";
if (!grpc_call_is_client(call)) {
LOG(ERROR) << "Method is client-side only.";
return GRPC_CALL_ERROR_NOT_ON_SERVER;
}
auto* arena = grpc_call_get_arena(call);
ctx = grpc_core::DownCast<grpc_client_security_context*>(
arena->GetContext<grpc_core::SecurityContext>());
if (ctx == nullptr) {
ctx = grpc_client_security_context_create(arena, creds);
arena->SetContext<grpc_core::SecurityContext>(ctx);
} else {
ctx->creds = creds != nullptr ? creds->Ref() : nullptr;
}
return GRPC_CALL_OK;
}
grpc_auth_context* grpc_call_auth_context(grpc_call* call) {
auto* sec_ctx =
grpc_call_get_arena(call)->GetContext<grpc_core::SecurityContext>();
GRPC_TRACE_LOG(api, INFO) << "grpc_call_auth_context(call=" << call << ")";
if (sec_ctx == nullptr) return nullptr;
if (grpc_call_is_client(call)) {
auto* sc = grpc_core::DownCast<grpc_client_security_context*>(sec_ctx);
if (sc->auth_context == nullptr) {
return nullptr;
} else {
return sc->auth_context
->Ref(DEBUG_LOCATION, "grpc_call_auth_context client")
.release();
}
} else {
auto* sc = grpc_core::DownCast<grpc_server_security_context*>(sec_ctx);
if (sc->auth_context == nullptr) {
return nullptr;
} else {
return sc->auth_context
->Ref(DEBUG_LOCATION, "grpc_call_auth_context server")
.release();
}
}
}
// --- grpc_client_security_context ---
grpc_client_security_context::~grpc_client_security_context() {
auth_context.reset(DEBUG_LOCATION, "client_security_context");
if (extension.instance != nullptr && extension.destroy != nullptr) {
extension.destroy(extension.instance);
}
}
grpc_client_security_context* grpc_client_security_context_create(
grpc_core::Arena* arena, grpc_call_credentials* creds) {
return arena->New<grpc_client_security_context>(
creds != nullptr ? creds->Ref() : nullptr);
}
void grpc_client_security_context_destroy(void* ctx) {
grpc_client_security_context* c =
static_cast<grpc_client_security_context*>(ctx);
c->~grpc_client_security_context();
}
// --- grpc_server_security_context ---
grpc_server_security_context::~grpc_server_security_context() {
auth_context.reset(DEBUG_LOCATION, "server_security_context");
if (extension.instance != nullptr && extension.destroy != nullptr) {
extension.destroy(extension.instance);
}
}
grpc_server_security_context* grpc_server_security_context_create(
grpc_core::Arena* arena) {
return arena->New<grpc_server_security_context>();
}
void grpc_server_security_context_destroy(void* ctx) {
grpc_server_security_context* c =
static_cast<grpc_server_security_context*>(ctx);
c->~grpc_server_security_context();
}

View File

@ -1,114 +0,0 @@
//
// Copyright 2015 gRPC authors.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
//
#ifndef GRPC_SRC_CORE_CALL_SECURITY_CONTEXT_H
#define GRPC_SRC_CORE_CALL_SECURITY_CONTEXT_H
#include <grpc/credentials.h>
#include <grpc/grpc.h>
#include <grpc/grpc_security.h>
#include <grpc/support/alloc.h>
#include <grpc/support/port_platform.h>
#include <stddef.h>
#include <memory>
#include <utility>
#include "absl/strings/string_view.h"
#include "src/core/credentials/call/call_credentials.h" // IWYU pragma: keep
#include "src/core/lib/debug/trace.h"
#include "src/core/lib/resource_quota/arena.h"
#include "src/core/lib/surface/connection_context.h"
#include "src/core/transport/auth_context.h"
#include "src/core/util/debug_location.h"
#include "src/core/util/orphanable.h"
#include "src/core/util/ref_counted.h"
#include "src/core/util/ref_counted_ptr.h"
#include "src/core/util/useful.h"
// --- grpc_security_context_extension ---
// Extension to the security context that may be set in a filter and accessed
// later by a higher level method on a grpc_call object.
struct grpc_security_context_extension {
void* instance = nullptr;
void (*destroy)(void*) = nullptr;
};
namespace grpc_core {
// TODO(roth): Consider renaming to something like CallSecurityContext
// to reflect the fact that it stores call-level security properties.
class SecurityContext {
public:
virtual ~SecurityContext() = default;
};
} // namespace grpc_core
// --- grpc_client_security_context ---
// Internal client-side security context.
struct grpc_client_security_context final : public grpc_core::SecurityContext {
explicit grpc_client_security_context(
grpc_core::RefCountedPtr<grpc_call_credentials> creds)
: creds(std::move(creds)) {}
~grpc_client_security_context() override;
grpc_core::RefCountedPtr<grpc_call_credentials> creds;
grpc_core::RefCountedPtr<grpc_auth_context> auth_context;
grpc_security_context_extension extension;
};
grpc_client_security_context* grpc_client_security_context_create(
grpc_core::Arena* arena, grpc_call_credentials* creds);
void grpc_client_security_context_destroy(void* ctx);
// --- grpc_server_security_context ---
// Internal server-side security context.
struct grpc_server_security_context final : public grpc_core::SecurityContext {
grpc_server_security_context() = default;
~grpc_server_security_context() override;
grpc_core::RefCountedPtr<grpc_auth_context> auth_context;
grpc_security_context_extension extension;
};
grpc_server_security_context* grpc_server_security_context_create(
grpc_core::Arena* arena);
void grpc_server_security_context_destroy(void* ctx);
namespace grpc_core {
template <>
struct ArenaContextType<SecurityContext> {
static void Destroy(SecurityContext* p) { p->~SecurityContext(); }
};
template <>
struct ContextSubclass<grpc_client_security_context> {
using Base = SecurityContext;
};
template <>
struct ContextSubclass<grpc_server_security_context> {
using Base = SecurityContext;
};
} // namespace grpc_core
#endif // GRPC_SRC_CORE_CALL_SECURITY_CONTEXT_H

View File

@ -29,9 +29,7 @@
#include "src/core/channelz/channelz.h"
#include "src/core/lib/slice/slice.h"
#include "src/core/lib/slice/slice_internal.h"
#include "src/core/util/ref_counted_ptr.h"
#include "src/core/util/string.h"
#include "src/core/util/sync.h"
#include "src/core/util/time.h"
namespace grpc_core {
@ -54,8 +52,41 @@ ChannelTrace::TraceEvent::TraceEvent(Severity severity, const grpc_slice& data)
ChannelTrace::TraceEvent::~TraceEvent() { CSliceUnref(data_); }
RefCountedPtr<BaseNode> ChannelTrace::TraceEvent::referenced_entity() const {
return referenced_entity_;
namespace {
const char* SeverityString(ChannelTrace::Severity severity) {
switch (severity) {
case ChannelTrace::Severity::Info:
return "CT_INFO";
case ChannelTrace::Severity::Warning:
return "CT_WARNING";
case ChannelTrace::Severity::Error:
return "CT_ERROR";
default:
GPR_UNREACHABLE_CODE(return "CT_UNKNOWN");
}
}
} // anonymous namespace
Json ChannelTrace::TraceEvent::RenderTraceEvent() const {
char* description = grpc_slice_to_c_string(data_);
Json::Object object = {
{"description", Json::FromString(description)},
{"severity", Json::FromString(SeverityString(severity_))},
{"timestamp", Json::FromString(gpr_format_timespec(timestamp_))},
};
gpr_free(description);
if (referenced_entity_ != nullptr) {
const bool is_channel =
(referenced_entity_->type() == BaseNode::EntityType::kTopLevelChannel ||
referenced_entity_->type() == BaseNode::EntityType::kInternalChannel);
object[is_channel ? "channelRef" : "subchannelRef"] = Json::FromObject({
{(is_channel ? "channelId" : "subchannelId"),
Json::FromString(absl::StrCat(referenced_entity_->uuid()))},
});
}
return Json::FromObject(std::move(object));
}
//
@ -84,8 +115,9 @@ void ChannelTrace::AddTraceEventHelper(TraceEvent* new_trace_event) {
// first event case
if (head_trace_ == nullptr) {
head_trace_ = tail_trace_ = new_trace_event;
} else {
// regular event add case
}
// regular event add case
else {
tail_trace_->set_next(new_trace_event);
tail_trace_ = tail_trace_->next();
}
@ -119,25 +151,6 @@ void ChannelTrace::AddTraceEventWithReference(
new TraceEvent(severity, data, std::move(referenced_entity)));
}
std::string ChannelTrace::TraceEvent::description() const {
char* description = grpc_slice_to_c_string(data_);
std::string s(description);
gpr_free(description);
return s;
}
void ChannelTrace::ForEachTraceEventLocked(
absl::FunctionRef<void(gpr_timespec, Severity, std::string,
RefCountedPtr<BaseNode>)>
callback) const {
TraceEvent* it = head_trace_;
while (it != nullptr) {
callback(it->timestamp(), it->severity(), it->description(),
it->referenced_entity());
it = it->next();
}
}
Json ChannelTrace::RenderJson() const {
// Tracing is disabled if max_event_memory_ == 0.
if (max_event_memory_ == 0) {
@ -153,36 +166,15 @@ Json ChannelTrace::RenderJson() const {
Json::FromString(absl::StrCat(num_events_logged_));
}
// Only add in the event list if it is non-empty.
Json::Array array;
ForEachTraceEventLocked([&array](gpr_timespec timestamp, Severity severity,
std::string description,
RefCountedPtr<BaseNode> referenced_entity) {
Json::Object object = {
{"description", Json::FromString(description)},
{"severity", Json::FromString(SeverityString(severity))},
{"timestamp", Json::FromString(gpr_format_timespec(timestamp))},
};
if (referenced_entity != nullptr) {
const bool is_channel =
(referenced_entity->type() ==
BaseNode::EntityType::kTopLevelChannel ||
referenced_entity->type() == BaseNode::EntityType::kInternalChannel);
object[is_channel ? "channelRef" : "subchannelRef"] = Json::FromObject({
{(is_channel ? "channelId" : "subchannelId"),
Json::FromString(absl::StrCat(referenced_entity->uuid()))},
});
if (head_trace_ != nullptr) {
Json::Array array;
for (TraceEvent* it = head_trace_; it != nullptr; it = it->next()) {
array.emplace_back(it->RenderTraceEvent());
}
array.emplace_back(Json::FromObject(std::move(object)));
});
if (!array.empty()) {
object["events"] = Json::FromArray(std::move(array));
}
return Json::FromObject(std::move(object));
}
std::string ChannelTrace::creation_timestamp() const {
return gpr_format_timespec(time_created_);
}
} // namespace channelz
} // namespace grpc_core

View File

@ -24,7 +24,6 @@
#include <grpc/support/time.h>
#include <stddef.h>
#include <stdint.h>
#include <sys/types.h>
#include "absl/base/thread_annotations.h"
#include "src/core/util/json/json.h"
@ -55,19 +54,6 @@ class ChannelTrace {
Error
};
static const char* SeverityString(ChannelTrace::Severity severity) {
switch (severity) {
case ChannelTrace::Severity::Info:
return "CT_INFO";
case ChannelTrace::Severity::Warning:
return "CT_WARNING";
case ChannelTrace::Severity::Error:
return "CT_ERROR";
default:
GPR_UNREACHABLE_CODE(return "CT_UNKNOWN");
}
}
// Adds a new trace event to the tracing object
//
// NOTE: each ChannelTrace tracks the memory used by its list of trace
@ -96,19 +82,6 @@ class ChannelTrace {
// object may incorporate the json before rendering.
Json RenderJson() const;
void ForEachTraceEvent(
absl::FunctionRef<void(gpr_timespec, Severity, std::string,
RefCountedPtr<BaseNode>)>
callback) const {
MutexLock lock(&mu_);
ForEachTraceEventLocked(callback);
}
std::string creation_timestamp() const;
uint64_t num_events_logged() const {
MutexLock lock(&mu_);
return num_events_logged_;
}
private:
friend size_t testing::GetSizeofTraceEvent(void);
@ -126,15 +99,15 @@ class ChannelTrace {
~TraceEvent();
// Renders the data inside of this TraceEvent into a json object. This is
// used by the ChannelTrace, when it is rendering itself.
Json RenderTraceEvent() const;
// set and get for the next_ pointer.
TraceEvent* next() const { return next_; }
void set_next(TraceEvent* next) { next_ = next; }
size_t memory_usage() const { return memory_usage_; }
gpr_timespec timestamp() const { return timestamp_; }
Severity severity() const { return severity_; }
std::string description() const;
RefCountedPtr<BaseNode> referenced_entity() const;
private:
const gpr_timespec timestamp_;
@ -148,10 +121,6 @@ class ChannelTrace {
// Internal helper to add and link in a trace event
void AddTraceEventHelper(TraceEvent* new_trace_event);
void ForEachTraceEventLocked(
absl::FunctionRef<void(gpr_timespec, Severity, std::string,
RefCountedPtr<BaseNode>)>) const
ABSL_EXCLUSIVE_LOCKS_REQUIRED(mu_);
const size_t max_event_memory_;
const gpr_timespec time_created_;

View File

@ -25,10 +25,6 @@
#include <algorithm>
#include <atomic>
#include <cstdint>
#include <initializer_list>
#include <limits>
#include <string>
#include <tuple>
#include "absl/log/check.h"
#include "absl/status/statusor.h"
@ -43,123 +39,12 @@
#include "src/core/lib/transport/connectivity_state.h"
#include "src/core/util/json/json_writer.h"
#include "src/core/util/string.h"
#include "src/core/util/time.h"
#include "src/core/util/uri.h"
#include "src/core/util/useful.h"
namespace grpc_core {
namespace channelz {
//
// DataSink
//
namespace {
class ChildObjectCollector {
public:
void Add(RefCountedPtr<BaseNode> node) {
child_objects_[node->type()].insert(node->uuid());
}
void Add(std::vector<RefCountedPtr<BaseNode>> nodes) {
for (auto& node : nodes) Add(std::move(node));
}
// Calls AddAdditionalInfo to export the collected child objects.
void Finalize(DataSink& sink) {
if (child_objects_.empty()) return;
Json::Object subobjects;
for (const auto& [type, child_objects] : child_objects_) {
std::string key;
switch (type) {
case BaseNode::EntityType::kTopLevelChannel:
case BaseNode::EntityType::kSubchannel:
case BaseNode::EntityType::kListenSocket:
case BaseNode::EntityType::kServer:
case BaseNode::EntityType::kInternalChannel: {
LOG(ERROR)
<< "Nodes of type " << BaseNode::EntityTypeString(type)
<< " not supported for child object collection in DataSink";
continue;
}
case BaseNode::EntityType::kSocket:
key = "subSockets";
break;
case BaseNode::EntityType::kCall:
key = "calls";
break;
}
Json::Array uuids;
uuids.reserve(child_objects.size());
for (int64_t uuid : child_objects) {
uuids.push_back(Json::FromNumber(uuid));
}
subobjects[key] = Json::FromArray(std::move(uuids));
}
sink.AddAdditionalInfo("childObjects", std::move(subobjects));
}
private:
std::map<BaseNode::EntityType, std::set<int64_t>> child_objects_;
};
class JsonDataSink final : public DataSink {
public:
explicit JsonDataSink(Json::Object& output) : output_(output) {
CHECK(output_.find("additionalInfo") == output_.end());
}
~JsonDataSink() {
collector_.Finalize(*this);
if (additional_info_ != nullptr) {
output_["additionalInfo"] =
Json::FromObject(std::move(*additional_info_));
}
}
void AddAdditionalInfo(absl::string_view name,
Json::Object additional_info) override {
if (additional_info_ == nullptr) {
additional_info_ = std::make_unique<Json::Object>();
}
additional_info_->emplace(name,
Json::FromObject(std::move(additional_info)));
}
void AddChildObjects(
std::vector<RefCountedPtr<BaseNode>> child_objects) override {
collector_.Add(std::move(child_objects));
}
private:
Json::Object& output_;
std::unique_ptr<Json::Object> additional_info_;
ChildObjectCollector collector_;
};
class ExplicitJsonDataSink final : public DataSink {
public:
void AddAdditionalInfo(absl::string_view name,
Json::Object additional_info) override {
additional_info_.emplace(name,
Json::FromObject(std::move(additional_info)));
}
void AddChildObjects(
std::vector<RefCountedPtr<BaseNode>> child_objects) override {
collector_.Add(std::move(child_objects));
}
Json::Object Finalize() {
collector_.Finalize(*this);
return std::move(additional_info_);
}
private:
Json::Object additional_info_;
ChildObjectCollector collector_;
};
} // namespace
//
// BaseNode
//
@ -170,95 +55,13 @@ BaseNode::BaseNode(EntityType type, std::string name)
ChannelzRegistry::Register(this);
}
void BaseNode::Orphaned() { ChannelzRegistry::Unregister(this); }
intptr_t BaseNode::UuidSlow() { return ChannelzRegistry::NumberNode(this); }
BaseNode::~BaseNode() { ChannelzRegistry::Unregister(uuid_); }
std::string BaseNode::RenderJsonString() {
Json json = RenderJson();
return JsonDump(json);
}
void BaseNode::PopulateJsonFromDataSources(Json::Object& json) {
JsonDataSink sink(json);
MutexLock lock(&data_sources_mu_);
for (DataSource* data_source : data_sources_) {
data_source->AddData(sink);
}
}
Json::Object BaseNode::AdditionalInfo() {
ExplicitJsonDataSink sink;
MutexLock lock(&data_sources_mu_);
for (DataSource* data_source : data_sources_) {
data_source->AddData(sink);
}
return sink.Finalize();
}
void BaseNode::RunZTrace(
absl::string_view name, Timestamp deadline,
std::map<std::string, std::string> args,
std::shared_ptr<grpc_event_engine::experimental::EventEngine> event_engine,
absl::AnyInvocable<void(Json)> callback) {
// Limit deadline to help contain potential resource exhaustion due to
// tracing.
deadline = std::min(deadline, Timestamp::Now() + Duration::Minutes(10));
auto fail = [&callback, event_engine](absl::Status status) {
event_engine->Run(
[callback = std::move(callback), status = std::move(status)]() mutable {
Json::Object object;
object["status"] = Json::FromString(status.ToString());
callback(Json::FromObject(std::move(object)));
});
};
std::unique_ptr<ZTrace> ztrace;
{
MutexLock lock(&data_sources_mu_);
for (auto* data_source : data_sources_) {
if (auto found_ztrace = data_source->GetZTrace(name);
found_ztrace != nullptr) {
if (ztrace == nullptr) {
ztrace = std::move(found_ztrace);
} else {
fail(absl::InternalError(
absl::StrCat("Ambiguous ztrace handler: ", name)));
return;
}
}
}
}
if (ztrace == nullptr) {
fail(absl::NotFoundError(absl::StrCat("ztrace not found: ", name)));
return;
}
ztrace->Run(deadline, std::move(args), event_engine, std::move(callback));
}
//
// DataSource
//
DataSource::DataSource(RefCountedPtr<BaseNode> node) : node_(std::move(node)) {
if (node_ == nullptr) return;
MutexLock lock(&node_->data_sources_mu_);
node_->data_sources_.push_back(this);
}
DataSource::~DataSource() {
DCHECK(node_ == nullptr) << "DataSource must be ResetDataSource()'d in the "
"most derived class before destruction";
}
void DataSource::ResetDataSource() {
RefCountedPtr<BaseNode> node = std::move(node_);
if (node == nullptr) return;
MutexLock lock(&node->data_sources_mu_);
node->data_sources_.erase(
std::remove(node->data_sources_.begin(), node->data_sources_.end(), this),
node->data_sources_.end());
}
//
// CallCountingHelper
//
@ -277,21 +80,24 @@ void CallCountingHelper::RecordCallSucceeded() {
calls_succeeded_.fetch_add(1, std::memory_order_relaxed);
}
//
// CallCounts
//
void CallCounts::PopulateJson(Json::Object& json) const {
void CallCountingHelper::PopulateCallCounts(Json::Object* json) {
auto calls_started = calls_started_.load(std::memory_order_relaxed);
auto calls_succeeded = calls_succeeded_.load(std::memory_order_relaxed);
auto calls_failed = calls_failed_.load(std::memory_order_relaxed);
auto last_call_started_cycle =
last_call_started_cycle_.load(std::memory_order_relaxed);
if (calls_started != 0) {
json["callsStarted"] = Json::FromString(absl::StrCat(calls_started));
json["lastCallStartedTimestamp"] =
Json::FromString(last_call_started_timestamp());
(*json)["callsStarted"] = Json::FromString(absl::StrCat(calls_started));
gpr_timespec ts = gpr_convert_clock_type(
gpr_cycle_counter_to_time(last_call_started_cycle), GPR_CLOCK_REALTIME);
(*json)["lastCallStartedTimestamp"] =
Json::FromString(gpr_format_timespec(ts));
}
if (calls_succeeded != 0) {
json["callsSucceeded"] = Json::FromString(absl::StrCat(calls_succeeded));
(*json)["callsSucceeded"] = Json::FromString(absl::StrCat(calls_succeeded));
}
if (calls_failed != 0) {
json["callsFailed"] = Json::FromString(absl::StrCat(calls_failed));
(*json)["callsFailed"] = Json::FromString(absl::StrCat(calls_failed));
}
}
@ -315,20 +121,33 @@ void PerCpuCallCountingHelper::RecordCallSucceeded() {
std::memory_order_relaxed);
}
CallCounts PerCpuCallCountingHelper::GetCallCounts() const {
CallCounts call_counts;
void PerCpuCallCountingHelper::PopulateCallCounts(Json::Object* json) {
int64_t calls_started = 0;
int64_t calls_succeeded = 0;
int64_t calls_failed = 0;
gpr_cycle_counter last_call_started_cycle = 0;
for (const auto& cpu : per_cpu_data_) {
call_counts.calls_started +=
cpu.calls_started.load(std::memory_order_relaxed);
call_counts.calls_succeeded +=
cpu.calls_succeeded.load(std::memory_order_relaxed);
call_counts.calls_failed +=
cpu.calls_failed.load(std::memory_order_relaxed);
call_counts.last_call_started_cycle =
std::max(call_counts.last_call_started_cycle,
calls_started += cpu.calls_started.load(std::memory_order_relaxed);
calls_succeeded += cpu.calls_succeeded.load(std::memory_order_relaxed);
calls_failed += cpu.calls_failed.load(std::memory_order_relaxed);
last_call_started_cycle =
std::max(last_call_started_cycle,
cpu.last_call_started_cycle.load(std::memory_order_relaxed));
}
return call_counts;
if (calls_started != 0) {
(*json)["callsStarted"] = Json::FromString(absl::StrCat(calls_started));
gpr_timespec ts = gpr_convert_clock_type(
gpr_cycle_counter_to_time(last_call_started_cycle), GPR_CLOCK_REALTIME);
(*json)["lastCallStartedTimestamp"] =
Json::FromString(gpr_format_timespec(ts));
}
if (calls_succeeded != 0) {
(*json)["callsSucceeded"] = Json::FromString(absl::StrCat(calls_succeeded));
}
if (calls_failed != 0) {
(*json)["callsFailed"] = Json::FromString(absl::StrCat(calls_failed));
}
}
//
@ -360,48 +179,18 @@ const char* ChannelNode::GetChannelConnectivityStateChangeString(
GPR_UNREACHABLE_CODE(return "UNKNOWN");
}
namespace {
std::set<intptr_t> ChildIdSet(const BaseNode* parent,
BaseNode::EntityType type) {
std::set<intptr_t> ids;
auto [children, _] = ChannelzRegistry::GetChildrenOfType(
0, parent, type, std::numeric_limits<size_t>::max());
for (const auto& node : children) {
ids.insert(node->uuid());
}
return ids;
}
} // namespace
std::set<intptr_t> ChannelNode::child_channels() const {
return ChildIdSet(this, BaseNode::EntityType::kInternalChannel);
}
std::set<intptr_t> ChannelNode::child_subchannels() const {
return ChildIdSet(this, BaseNode::EntityType::kSubchannel);
}
std::optional<std::string> ChannelNode::connectivity_state() {
Json ChannelNode::RenderJson() {
Json::Object data = {
{"target", Json::FromString(target_)},
};
// Connectivity state.
// If low-order bit is on, then the field is set.
int state_field = connectivity_state_.load(std::memory_order_relaxed);
if ((state_field & 1) != 0) {
grpc_connectivity_state state =
static_cast<grpc_connectivity_state>(state_field >> 1);
return ConnectivityStateName(state);
}
return std::nullopt;
}
Json ChannelNode::RenderJson() {
Json::Object data = {
{"target", Json::FromString(target_)},
};
if (auto cs = connectivity_state(); cs.has_value()) {
data["state"] = Json::FromObject({
{"state", Json::FromString(cs.value())},
{"state", Json::FromString(ConnectivityStateName(state))},
});
}
// Fill in the channel trace if applicable.
@ -410,7 +199,7 @@ Json ChannelNode::RenderJson() {
data["trace"] = std::move(trace_json);
}
// Ask CallCountingHelper to populate call count data.
call_counter_.GetCallCounts().PopulateJson(data);
call_counter_.PopulateCallCounts(&data);
// Construct outer object.
Json::Object json = {
{"ref", Json::FromObject({
@ -421,25 +210,23 @@ Json ChannelNode::RenderJson() {
// Template method. Child classes may override this to add their specific
// functionality.
PopulateChildRefs(&json);
PopulateJsonFromDataSources(json);
return Json::FromObject(std::move(json));
}
void ChannelNode::PopulateChildRefs(Json::Object* json) {
auto child_subchannels = this->child_subchannels();
auto child_channels = this->child_channels();
if (!child_subchannels.empty()) {
MutexLock lock(&child_mu_);
if (!child_subchannels_.empty()) {
Json::Array array;
for (intptr_t subchannel_uuid : child_subchannels) {
for (intptr_t subchannel_uuid : child_subchannels_) {
array.emplace_back(Json::FromObject({
{"subchannelId", Json::FromString(absl::StrCat(subchannel_uuid))},
}));
}
(*json)["subchannelRef"] = Json::FromArray(std::move(array));
}
if (!child_channels.empty()) {
if (!child_channels_.empty()) {
Json::Array array;
for (intptr_t channel_uuid : child_channels) {
for (intptr_t channel_uuid : child_channels_) {
array.emplace_back(Json::FromObject({
{"channelId", Json::FromString(absl::StrCat(channel_uuid))},
}));
@ -454,6 +241,26 @@ void ChannelNode::SetConnectivityState(grpc_connectivity_state state) {
connectivity_state_.store(state_field, std::memory_order_relaxed);
}
void ChannelNode::AddChildChannel(intptr_t child_uuid) {
MutexLock lock(&child_mu_);
child_channels_.insert(child_uuid);
}
void ChannelNode::RemoveChildChannel(intptr_t child_uuid) {
MutexLock lock(&child_mu_);
child_channels_.erase(child_uuid);
}
void ChannelNode::AddChildSubchannel(intptr_t child_uuid) {
MutexLock lock(&child_mu_);
child_subchannels_.insert(child_uuid);
}
void ChannelNode::RemoveChildSubchannel(intptr_t child_uuid) {
MutexLock lock(&child_mu_);
child_subchannels_.erase(child_uuid);
}
//
// SubchannelNode
//
@ -475,17 +282,13 @@ void SubchannelNode::SetChildSocket(RefCountedPtr<SocketNode> socket) {
child_socket_ = std::move(socket);
}
std::string SubchannelNode::connectivity_state() const {
grpc_connectivity_state state =
connectivity_state_.load(std::memory_order_relaxed);
return ConnectivityStateName(state);
}
Json SubchannelNode::RenderJson() {
// Create and fill the data child.
grpc_connectivity_state state =
connectivity_state_.load(std::memory_order_relaxed);
Json::Object data = {
{"state", Json::FromObject({
{"state", Json::FromString(connectivity_state())},
{"state", Json::FromString(ConnectivityStateName(state))},
})},
{"target", Json::FromString(target_)},
};
@ -495,7 +298,7 @@ Json SubchannelNode::RenderJson() {
data["trace"] = std::move(trace_json);
}
// Ask CallCountingHelper to populate call count data.
call_counter_.GetCallCounts().PopulateJson(data);
call_counter_.PopulateCallCounts(&data);
// Construct top-level object.
Json::Object object{
{"ref", Json::FromObject({
@ -517,8 +320,7 @@ Json SubchannelNode::RenderJson() {
}),
});
}
PopulateJsonFromDataSources(object);
return Json::FromObject(std::move(object));
return Json::FromObject(object);
}
//
@ -530,25 +332,51 @@ ServerNode::ServerNode(size_t channel_tracer_max_nodes)
ServerNode::~ServerNode() {}
void ServerNode::AddChildSocket(RefCountedPtr<SocketNode> node) {
MutexLock lock(&child_mu_);
child_sockets_.insert(std::pair(node->uuid(), std::move(node)));
}
void ServerNode::RemoveChildSocket(intptr_t child_uuid) {
MutexLock lock(&child_mu_);
child_sockets_.erase(child_uuid);
}
void ServerNode::AddChildListenSocket(RefCountedPtr<ListenSocketNode> node) {
MutexLock lock(&child_mu_);
child_listen_sockets_.insert(std::pair(node->uuid(), std::move(node)));
}
void ServerNode::RemoveChildListenSocket(intptr_t child_uuid) {
MutexLock lock(&child_mu_);
child_listen_sockets_.erase(child_uuid);
}
std::string ServerNode::RenderServerSockets(intptr_t start_socket_id,
intptr_t max_results) {
CHECK_GE(start_socket_id, 0);
CHECK_GE(max_results, 0);
// If user does not set max_results, we choose 500.
if (max_results == 0) max_results = 500;
size_t pagination_limit = max_results == 0 ? 500 : max_results;
Json::Object object;
auto [children, end] = ChannelzRegistry::GetChildrenOfType(
start_socket_id, this, BaseNode::EntityType::kSocket, max_results);
// Create list of socket refs.
Json::Array array;
for (const auto& child : children) {
array.emplace_back(Json::FromObject({
{"socketId", Json::FromString(absl::StrCat(child->uuid()))},
{"name", Json::FromString(child->name())},
}));
{
MutexLock lock(&child_mu_);
size_t sockets_rendered = 0;
// Create list of socket refs.
Json::Array array;
auto it = child_sockets_.lower_bound(start_socket_id);
for (; it != child_sockets_.end() && sockets_rendered < pagination_limit;
++it, ++sockets_rendered) {
array.emplace_back(Json::FromObject({
{"socketId", Json::FromString(absl::StrCat(it->first))},
{"name", Json::FromString(it->second->name())},
}));
}
object["socketRef"] = Json::FromArray(std::move(array));
if (it == child_sockets_.end()) {
object["end"] = Json::FromBool(true);
}
}
object["socketRef"] = Json::FromArray(std::move(array));
if (end) object["end"] = Json::FromBool(true);
return JsonDump(Json::FromObject(std::move(object)));
}
@ -560,7 +388,7 @@ Json ServerNode::RenderJson() {
data["trace"] = std::move(trace_json);
}
// Ask CallCountingHelper to populate call count data.
call_counter_.GetCallCounts().PopulateJson(data);
call_counter_.PopulateCallCounts(&data);
// Construct top-level object.
Json::Object object = {
{"ref", Json::FromObject({
@ -569,47 +397,22 @@ Json ServerNode::RenderJson() {
{"data", Json::FromObject(std::move(data))},
};
// Render listen sockets.
auto [children, _] = ChannelzRegistry::GetChildrenOfType(
0, this, BaseNode::EntityType::kListenSocket,
std::numeric_limits<size_t>::max());
if (!children.empty()) {
Json::Array array;
for (const auto& child : children) {
array.emplace_back(Json::FromObject({
{"socketId", Json::FromString(absl::StrCat(child->uuid()))},
{"name", Json::FromString(child->name())},
}));
{
MutexLock lock(&child_mu_);
if (!child_listen_sockets_.empty()) {
Json::Array array;
for (const auto& it : child_listen_sockets_) {
array.emplace_back(Json::FromObject({
{"socketId", Json::FromString(absl::StrCat(it.first))},
{"name", Json::FromString(it.second->name())},
}));
}
object["listenSocket"] = Json::FromArray(std::move(array));
}
object["listenSocket"] = Json::FromArray(std::move(array));
}
PopulateJsonFromDataSources(object);
return Json::FromObject(std::move(object));
}
std::map<intptr_t, RefCountedPtr<ListenSocketNode>>
ServerNode::child_listen_sockets() const {
std::map<intptr_t, RefCountedPtr<ListenSocketNode>> result;
auto [children, _] = ChannelzRegistry::GetChildrenOfType(
0, this, BaseNode::EntityType::kListenSocket,
std::numeric_limits<size_t>::max());
for (const auto& child : children) {
result[child->uuid()] = child->RefAsSubclass<ListenSocketNode>();
}
return result;
}
std::map<intptr_t, RefCountedPtr<SocketNode>> ServerNode::child_sockets()
const {
std::map<intptr_t, RefCountedPtr<SocketNode>> result;
auto [children, _] = ChannelzRegistry::GetChildrenOfType(
0, this, BaseNode::EntityType::kSocket,
std::numeric_limits<size_t>::max());
for (const auto& child : children) {
result[child->uuid()] = child->RefAsSubclass<SocketNode>();
}
return result;
}
//
// SocketNode::Security::Tls
//
@ -841,7 +644,6 @@ Json SocketNode::RenderJson() {
}
PopulateSocketAddressJson(&object, "remote", remote_.c_str());
PopulateSocketAddressJson(&object, "local", local_.c_str());
PopulateJsonFromDataSources(object);
return Json::FromObject(std::move(object));
}
@ -850,7 +652,7 @@ Json SocketNode::RenderJson() {
//
ListenSocketNode::ListenSocketNode(std::string local_addr, std::string name)
: BaseNode(EntityType::kListenSocket, std::move(name)),
: BaseNode(EntityType::kSocket, std::move(name)),
local_addr_(std::move(local_addr)) {}
Json ListenSocketNode::RenderJson() {
@ -861,21 +663,6 @@ Json ListenSocketNode::RenderJson() {
})},
};
PopulateSocketAddressJson(&object, "local", local_addr_.c_str());
PopulateJsonFromDataSources(object);
return Json::FromObject(std::move(object));
}
//
// CallNode
//
Json CallNode::RenderJson() {
Json::Object object = {
{"ref", Json::FromObject({
{"callId", Json::FromString(absl::StrCat(uuid()))},
})},
};
PopulateJsonFromDataSources(object);
return Json::FromObject(std::move(object));
}

View File

@ -27,7 +27,6 @@
#include <atomic>
#include <cstdint>
#include <initializer_list>
#include <map>
#include <optional>
#include <set>
@ -35,29 +34,18 @@
#include <utility>
#include "absl/base/thread_annotations.h"
#include "absl/container/flat_hash_set.h"
#include "absl/container/inlined_vector.h"
#include "absl/strings/string_view.h"
#include "src/core/channelz/channel_trace.h"
#include "src/core/lib/channel/channel_args.h"
#include "src/core/util/dual_ref_counted.h"
#include "src/core/util/json/json.h"
#include "src/core/util/per_cpu.h"
#include "src/core/util/ref_counted.h"
#include "src/core/util/ref_counted_ptr.h"
#include "src/core/util/string.h"
#include "src/core/util/sync.h"
#include "src/core/util/time.h"
#include "src/core/util/time_precise.h"
#include "src/core/util/useful.h"
// Channel arg key for channelz node.
#define GRPC_ARG_CHANNELZ_CHANNEL_NODE \
"grpc.internal.no_subchannel.channelz_channel_node"
// Channel arg key for the containing base node
#define GRPC_ARG_CHANNELZ_CONTAINING_BASE_NODE \
"grpc.internal.no_subchannel.channelz_containing_base_node"
#define GRPC_ARG_CHANNELZ_CHANNEL_NODE "grpc.internal.channelz_channel_node"
// Channel arg key for indicating an internal channel.
#define GRPC_ARG_CHANNELZ_IS_INTERNAL_CHANNEL \
@ -79,8 +67,6 @@ namespace channelz {
class SocketNode;
class ListenSocketNode;
class DataSource;
class ZTrace;
namespace testing {
class CallCountingHelperPeer;
@ -88,7 +74,7 @@ class SubchannelNodePeer;
} // namespace testing
// base class for all channelz entities
class BaseNode : public DualRefCounted<BaseNode> {
class BaseNode : public RefCounted<BaseNode> {
public:
// There are only four high level channelz entities. However, to support
// GetTopChannelsRequest, we split the Channel entity into two different
@ -98,58 +84,14 @@ class BaseNode : public DualRefCounted<BaseNode> {
kInternalChannel,
kSubchannel,
kServer,
kListenSocket,
kSocket,
kCall,
};
static absl::string_view EntityTypeString(EntityType type) {
switch (type) {
case EntityType::kTopLevelChannel:
return "top_level_channel";
case EntityType::kInternalChannel:
return "internal_channel";
case EntityType::kSubchannel:
return "subchannel";
case EntityType::kServer:
return "server";
case EntityType::kListenSocket:
return "listen_socket";
case EntityType::kSocket:
return "socket";
case EntityType::kCall:
return "call";
}
return "unknown";
}
protected:
BaseNode(EntityType type, std::string name);
public:
void Orphaned() override;
bool HasParent(const BaseNode* parent) const {
MutexLock lock(&parent_mu_);
return parents_.find(parent) != parents_.end();
}
void AddParent(BaseNode* parent) {
MutexLock lock(&parent_mu_);
parents_.insert(parent->WeakRef());
}
void RemoveParent(BaseNode* parent) {
MutexLock lock(&parent_mu_);
parents_.erase(parent);
}
static absl::string_view ChannelArgName() {
return GRPC_ARG_CHANNELZ_CONTAINING_BASE_NODE;
}
static int ChannelArgsCompare(const BaseNode* a, const BaseNode* b) {
return QsortCompare(a, b);
}
~BaseNode() override;
// All children must implement this function.
virtual Json RenderJson() = 0;
@ -159,107 +101,15 @@ class BaseNode : public DualRefCounted<BaseNode> {
std::string RenderJsonString();
EntityType type() const { return type_; }
intptr_t uuid() {
const intptr_t id = uuid_.load(std::memory_order_relaxed);
if (id > 0) return id;
return UuidSlow();
}
intptr_t uuid() const { return uuid_; }
const std::string& name() const { return name_; }
void RunZTrace(absl::string_view name, Timestamp deadline,
std::map<std::string, std::string> args,
std::shared_ptr<grpc_event_engine::experimental::EventEngine>
event_engine,
absl::AnyInvocable<void(Json output)> callback);
Json::Object AdditionalInfo();
protected:
void PopulateJsonFromDataSources(Json::Object& json);
private:
// to allow the ChannelzRegistry to set uuid_ under its lock.
friend class ChannelzRegistry;
// allow data source to register/unregister itself
friend class DataSource;
using ParentSet = absl::flat_hash_set<WeakRefCountedPtr<BaseNode>,
WeakRefCountedPtrHash<BaseNode>,
WeakRefCountedPtrEq<BaseNode>>;
intptr_t UuidSlow();
const EntityType type_;
uint64_t orphaned_index_ = 0; // updated by registry
std::atomic<intptr_t> uuid_;
intptr_t uuid_;
std::string name_;
Mutex data_sources_mu_;
absl::InlinedVector<DataSource*, 3> data_sources_
ABSL_GUARDED_BY(data_sources_mu_);
BaseNode* prev_; // updated by registry
BaseNode* next_; // updated by registry
mutable Mutex parent_mu_;
ParentSet parents_ ABSL_GUARDED_BY(parent_mu_);
};
class ZTrace {
public:
virtual ~ZTrace() = default;
virtual void Run(Timestamp deadline, std::map<std::string, std::string> args,
std::shared_ptr<grpc_event_engine::experimental::EventEngine>
event_engine,
absl::AnyInvocable<void(Json)>) = 0;
};
class DataSink {
public:
virtual void AddAdditionalInfo(absl::string_view name,
Json::Object additional_info) = 0;
virtual void AddChildObjects(
std::vector<RefCountedPtr<BaseNode>> children) = 0;
protected:
~DataSink() = default;
};
class DataSource {
public:
explicit DataSource(RefCountedPtr<BaseNode> node);
// Add any relevant json fragments to the output.
// This method must not cause the DataSource to be deleted, or else there will
// be a deadlock.
virtual void AddData(DataSink&) {}
// If this data source exports some ztrace, return it here.
virtual std::unique_ptr<ZTrace> GetZTrace(absl::string_view /*name*/) {
return nullptr;
}
protected:
~DataSource();
RefCountedPtr<BaseNode> channelz_node() { return node_; }
// This method must be called in the most derived class's destructor.
// It removes this data source from the node's list of data sources.
// If it is not called, then the AddData() function pointer may be invalid
// when the node is queried.
void ResetDataSource();
private:
RefCountedPtr<BaseNode> node_;
};
struct CallCounts {
int64_t calls_started = 0;
int64_t calls_succeeded = 0;
int64_t calls_failed = 0;
gpr_cycle_counter last_call_started_cycle = 0;
std::string last_call_started_timestamp() const {
return gpr_format_timespec(
gpr_cycle_counter_to_time(last_call_started_cycle));
}
void PopulateJson(Json::Object& json) const;
};
// This class is a helper class for channelz entities that deal with Channels,
@ -274,14 +124,8 @@ class CallCountingHelper final {
void RecordCallFailed();
void RecordCallSucceeded();
CallCounts GetCallCounts() const {
return {
calls_started_.load(std::memory_order_relaxed),
calls_succeeded_.load(std::memory_order_relaxed),
calls_failed_.load(std::memory_order_relaxed),
last_call_started_cycle_.load(std::memory_order_relaxed),
};
}
// Common rendering of the call count data and last_call_started_timestamp.
void PopulateCallCounts(Json::Object* json);
private:
// testing peer friend.
@ -299,7 +143,8 @@ class PerCpuCallCountingHelper final {
void RecordCallFailed();
void RecordCallSucceeded();
CallCounts GetCallCounts() const;
// Common rendering of the call count data and last_call_started_timestamp.
void PopulateCallCounts(Json::Object* json);
private:
// testing peer friend.
@ -322,11 +167,6 @@ class ChannelNode final : public BaseNode {
ChannelNode(std::string target, size_t channel_tracer_max_nodes,
bool is_internal_channel);
void Orphaned() override {
channel_args_ = ChannelArgs();
BaseNode::Orphaned();
}
static absl::string_view ChannelArgName() {
return GRPC_ARG_CHANNELZ_CHANNEL_NODE;
}
@ -350,22 +190,21 @@ class ChannelNode final : public BaseNode {
trace_.AddTraceEventWithReference(severity, data,
std::move(referenced_channel));
}
void SetChannelArgs(const ChannelArgs& channel_args) {
channel_args_ = channel_args;
}
void RecordCallStarted() { call_counter_.RecordCallStarted(); }
void RecordCallFailed() { call_counter_.RecordCallFailed(); }
void RecordCallSucceeded() { call_counter_.RecordCallSucceeded(); }
void SetConnectivityState(grpc_connectivity_state state);
const std::string& target() const { return target_; }
std::optional<std::string> connectivity_state();
CallCounts GetCallCounts() const { return call_counter_.GetCallCounts(); }
std::set<intptr_t> child_channels() const;
std::set<intptr_t> child_subchannels() const;
const ChannelTrace& trace() const { return trace_; }
const ChannelArgs& channel_args() const { return channel_args_; }
// TODO(roth): take in a RefCountedPtr to the child channel so we can retrieve
// the human-readable name.
void AddChildChannel(intptr_t child_uuid);
void RemoveChildChannel(intptr_t child_uuid);
// TODO(roth): take in a RefCountedPtr to the child subchannel so we can
// retrieve the human-readable name.
void AddChildSubchannel(intptr_t child_uuid);
void RemoveChildSubchannel(intptr_t child_uuid);
private:
void PopulateChildRefs(Json::Object* json);
@ -373,13 +212,14 @@ class ChannelNode final : public BaseNode {
std::string target_;
CallCountingHelper call_counter_;
ChannelTrace trace_;
// TODO(ctiller): keeping channel args here can create odd circular references
// that are hard to reason about. Consider moving this to a DataSource.
ChannelArgs channel_args_;
// Least significant bit indicates whether the value is set. Remaining
// bits are a grpc_connectivity_state value.
std::atomic<int> connectivity_state_{0};
Mutex child_mu_; // Guards sets below.
std::set<intptr_t> child_channels_;
std::set<intptr_t> child_subchannels_;
};
// Handles channelz bookkeeping for subchannels
@ -388,11 +228,6 @@ class SubchannelNode final : public BaseNode {
SubchannelNode(std::string target_address, size_t channel_tracer_max_nodes);
~SubchannelNode() override;
void Orphaned() override {
channel_args_ = ChannelArgs();
BaseNode::Orphaned();
}
// Sets the subchannel's connectivity state without health checking.
void UpdateConnectivityState(grpc_connectivity_state state);
@ -407,9 +242,6 @@ class SubchannelNode final : public BaseNode {
void AddTraceEvent(ChannelTrace::Severity severity, const grpc_slice& data) {
trace_.AddTraceEvent(severity, data);
}
void SetChannelArgs(const ChannelArgs& channel_args) {
channel_args_ = channel_args;
}
void AddTraceEventWithReference(ChannelTrace::Severity severity,
const grpc_slice& data,
RefCountedPtr<BaseNode> referenced_channel) {
@ -420,29 +252,16 @@ class SubchannelNode final : public BaseNode {
void RecordCallFailed() { call_counter_.RecordCallFailed(); }
void RecordCallSucceeded() { call_counter_.RecordCallSucceeded(); }
const std::string& target() const { return target_; }
std::string connectivity_state() const;
CallCounts GetCallCounts() const { return call_counter_.GetCallCounts(); }
RefCountedPtr<SocketNode> child_socket() const {
MutexLock lock(&socket_mu_);
return child_socket_;
}
const ChannelTrace& trace() const { return trace_; }
const ChannelArgs& channel_args() const { return channel_args_; }
private:
// Allows the channel trace test to access trace_.
friend class testing::SubchannelNodePeer;
std::atomic<grpc_connectivity_state> connectivity_state_{GRPC_CHANNEL_IDLE};
mutable Mutex socket_mu_;
Mutex socket_mu_;
RefCountedPtr<SocketNode> child_socket_ ABSL_GUARDED_BY(socket_mu_);
std::string target_;
CallCountingHelper call_counter_;
ChannelTrace trace_;
// TODO(ctiller): keeping channel args here can create odd circular references
// that are hard to reason about. Consider moving this to a DataSource.
ChannelArgs channel_args_;
};
// Handles channelz bookkeeping for servers
@ -452,16 +271,19 @@ class ServerNode final : public BaseNode {
~ServerNode() override;
void Orphaned() override {
channel_args_ = ChannelArgs();
BaseNode::Orphaned();
}
Json RenderJson() override;
std::string RenderServerSockets(intptr_t start_socket_id,
intptr_t max_results);
void AddChildSocket(RefCountedPtr<SocketNode> node);
void RemoveChildSocket(intptr_t child_uuid);
void AddChildListenSocket(RefCountedPtr<ListenSocketNode> node);
void RemoveChildListenSocket(intptr_t child_uuid);
// proxy methods to composed classes.
void AddTraceEvent(ChannelTrace::Severity severity, const grpc_slice& data) {
trace_.AddTraceEvent(severity, data);
@ -472,28 +294,16 @@ class ServerNode final : public BaseNode {
trace_.AddTraceEventWithReference(severity, data,
std::move(referenced_channel));
}
void SetChannelArgs(const ChannelArgs& channel_args) {
channel_args_ = channel_args;
}
void RecordCallStarted() { call_counter_.RecordCallStarted(); }
void RecordCallFailed() { call_counter_.RecordCallFailed(); }
void RecordCallSucceeded() { call_counter_.RecordCallSucceeded(); }
CallCounts GetCallCounts() const { return call_counter_.GetCallCounts(); }
std::map<intptr_t, RefCountedPtr<ListenSocketNode>> child_listen_sockets()
const;
std::map<intptr_t, RefCountedPtr<SocketNode>> child_sockets() const;
const ChannelTrace& trace() const { return trace_; }
const ChannelArgs& channel_args() const { return channel_args_; }
private:
PerCpuCallCountingHelper call_counter_;
ChannelTrace trace_;
// TODO(ctiller): keeping channel args here can create odd circular references
// that are hard to reason about. Consider moving this to a DataSource.
ChannelArgs channel_args_;
Mutex child_mu_; // Guards child maps below.
std::map<intptr_t, RefCountedPtr<SocketNode>> child_sockets_;
std::map<intptr_t, RefCountedPtr<ListenSocketNode>> child_listen_sockets_;
};
#define GRPC_ARG_CHANNELZ_SECURITY "grpc.internal.channelz_security"
@ -558,51 +368,7 @@ class SocketNode final : public BaseNode {
const std::string& remote() { return remote_; }
int64_t streams_started() const {
return streams_started_.load(std::memory_order_relaxed);
}
int64_t streams_succeeded() const {
return streams_succeeded_.load(std::memory_order_relaxed);
}
int64_t streams_failed() const {
return streams_failed_.load(std::memory_order_relaxed);
}
int64_t messages_sent() const {
return messages_sent_.load(std::memory_order_relaxed);
}
int64_t messages_received() const {
return messages_received_.load(std::memory_order_relaxed);
}
int64_t keepalives_sent() const {
return keepalives_sent_.load(std::memory_order_relaxed);
}
auto last_local_stream_created_timestamp() const {
return CycleCounterToTimestamp(
last_local_stream_created_cycle_.load(std::memory_order_relaxed));
}
auto last_remote_stream_created_timestamp() const {
return CycleCounterToTimestamp(
last_remote_stream_created_cycle_.load(std::memory_order_relaxed));
}
auto last_message_sent_timestamp() const {
return CycleCounterToTimestamp(
last_message_sent_cycle_.load(std::memory_order_relaxed));
}
auto last_message_received_timestamp() const {
return CycleCounterToTimestamp(
last_message_received_cycle_.load(std::memory_order_relaxed));
}
const std::string& local() const { return local_; }
const std::string& remote() const { return remote_; }
RefCountedPtr<Security> security() const { return security_; }
private:
std::optional<std::string> CycleCounterToTimestamp(
gpr_cycle_counter cycle_counter) const {
return gpr_format_timespec(gpr_cycle_counter_to_time(cycle_counter));
}
std::atomic<int64_t> streams_started_{0};
std::atomic<int64_t> streams_succeeded_{0};
std::atomic<int64_t> streams_failed_{0};
@ -630,14 +396,6 @@ class ListenSocketNode final : public BaseNode {
std::string local_addr_;
};
class CallNode final : public BaseNode {
public:
explicit CallNode(std::string name)
: BaseNode(EntityType::kCall, std::move(name)) {}
Json RenderJson() override;
};
} // namespace channelz
} // namespace grpc_core

View File

@ -24,356 +24,154 @@
#include <grpc/support/string_util.h>
#include <algorithm>
#include <atomic>
#include <cstdint>
#include <cstring>
#include <memory>
#include <optional>
#include <string>
#include <utility>
#include <vector>
#include "absl/log/check.h"
#include "absl/log/log.h"
#include "src/core/channelz/channelz.h"
#include "src/core/config/config_vars.h"
#include "src/core/lib/iomgr/exec_ctx.h"
#include "src/core/util/json/json.h"
#include "src/core/util/json/json_reader.h"
#include "src/core/util/json/json_writer.h"
#include "src/core/util/shared_bit_gen.h"
#include "src/core/util/sync.h"
namespace grpc_core {
namespace channelz {
namespace {
template <typename T>
std::string RenderArray(std::tuple<T, bool> values_and_end,
const std::string& key) {
auto& [values, end] = values_and_end;
Json::Object object;
if (!values.empty()) {
// Create list of channels.
Json::Array array;
for (size_t i = 0; i < values.size(); ++i) {
array.emplace_back(values[i]->RenderJson());
}
object[key] = Json::FromArray(std::move(array));
}
if (end) {
object["end"] = Json::FromBool(true);
}
return JsonDump(Json::FromObject(std::move(object)));
}
Json RemoveAdditionalInfo(const Json& json) {
switch (json.type()) {
case Json::Type::kArray: {
Json::Array out;
for (const auto& node : json.array()) {
out.emplace_back(RemoveAdditionalInfo(node));
}
return Json::FromArray(std::move(out));
} break;
case Json::Type::kObject: {
Json::Object out;
for (const auto& [key, value] : json.object()) {
if (key == "additionalInfo") continue;
out[key] = RemoveAdditionalInfo(value);
}
return Json::FromObject(std::move(out));
} break;
default:
return json;
}
}
const int kPaginationLimit = 100;
// TODO(ctiller): Temporary hack to remove fields that are objectionable to the
// protobuf parser (because we've not published them in protobuf yet).
char* ApplyHacks(const std::string& json_str) {
return gpr_strdup(StripAdditionalInfoFromJson(json_str).c_str());
}
} // namespace
std::string StripAdditionalInfoFromJson(absl::string_view json_str) {
auto json = JsonParse(json_str);
if (!json.ok()) return gpr_strdup(std::string(json_str).c_str());
return JsonDump(RemoveAdditionalInfo(*json));
}
} // anonymous namespace
ChannelzRegistry* ChannelzRegistry::Default() {
static ChannelzRegistry* singleton = new ChannelzRegistry();
return singleton;
}
std::vector<WeakRefCountedPtr<BaseNode>>
ChannelzRegistry::InternalGetAllEntities() {
return std::get<0>(QueryNodes(
0, [](const BaseNode*) { return true; },
std::numeric_limits<size_t>::max()));
}
void ChannelzRegistry::InternalLogAllEntities() {
for (const auto& p : InternalGetAllEntities()) {
std::string json = p->RenderJsonString();
LOG(INFO) << json;
}
}
std::string ChannelzRegistry::GetTopChannelsJson(intptr_t start_channel_id) {
return RenderArray(GetTopChannels(start_channel_id), "channel");
}
std::string ChannelzRegistry::GetServersJson(intptr_t start_server_id) {
return RenderArray(GetServers(start_server_id), "server");
}
void ChannelzRegistry::InternalRegister(BaseNode* node) {
DCHECK_EQ(node->uuid_, -1);
const size_t node_shard_index = NodeShardIndex(node);
NodeShard& node_shard = node_shards_[node_shard_index];
MutexLock lock(&node_shard.mu);
node_shard.nursery.AddToHead(node);
MutexLock lock(&mu_);
node->uuid_ = ++uuid_generator_;
node_map_[node->uuid_] = node;
}
void ChannelzRegistry::InternalUnregister(BaseNode* node) {
const size_t node_shard_index = NodeShardIndex(node);
NodeShard& node_shard = node_shards_[node_shard_index];
node_shard.mu.Lock();
CHECK_EQ(node->orphaned_index_, 0u);
intptr_t uuid = node->uuid_.load(std::memory_order_relaxed);
NodeList& remove_list = uuid == -1 ? node_shard.nursery : node_shard.numbered;
remove_list.Remove(node);
if (max_orphaned_per_shard_ == 0) {
// We are not tracking orphaned nodes... remove from the index
// if necessary, then exit out.
node_shard.mu.Unlock();
if (uuid != -1) {
MutexLock lock(&index_mu_);
index_.erase(uuid);
}
return;
}
NodeList& add_list =
uuid != -1 ? node_shard.orphaned_numbered : node_shard.orphaned;
// Ref counting: once a node becomes orphaned we add a single weak ref to it.
// We hold that ref until it gets garbage collected later.
node->WeakRef().release();
node->orphaned_index_ = node_shard.next_orphan_index;
CHECK_GT(node->orphaned_index_, 0u);
++node_shard.next_orphan_index;
add_list.AddToHead(node);
if (node_shard.TotalOrphaned() <= max_orphaned_per_shard_) {
// Below recycling thresholds: just exit out
node_shard.mu.Unlock();
return;
}
CHECK_EQ(node_shard.TotalOrphaned(), max_orphaned_per_shard_ + 1);
NodeList* gc_list;
// choose the oldest node to evict, regardless of numbered or not
if (node_shard.orphaned.tail == nullptr) {
CHECK_NE(node_shard.orphaned_numbered.tail, nullptr);
gc_list = &node_shard.orphaned_numbered;
} else if (node_shard.orphaned_numbered.tail == nullptr) {
gc_list = &node_shard.orphaned;
} else if (node_shard.orphaned.tail->orphaned_index_ <
node_shard.orphaned_numbered.tail->orphaned_index_) {
gc_list = &node_shard.orphaned;
} else {
gc_list = &node_shard.orphaned_numbered;
}
auto* n = gc_list->tail;
CHECK_GT(n->orphaned_index_, 0u);
gc_list->Remove(n);
// Note: we capture the reference to n previously added here, and release
// it when this smart pointer is destroyed, outside of any locks.
WeakRefCountedPtr<BaseNode> gcd_node(n);
node_shard.mu.Unlock();
if (gc_list == &node_shard.orphaned_numbered) {
MutexLock lock(&index_mu_);
intptr_t uuid = n->uuid_.load(std::memory_order_relaxed);
index_.erase(uuid);
}
void ChannelzRegistry::InternalUnregister(intptr_t uuid) {
CHECK_GE(uuid, 1);
MutexLock lock(&mu_);
CHECK(uuid <= uuid_generator_);
node_map_.erase(uuid);
}
void ChannelzRegistry::LoadConfig() {
const auto max_orphaned = ConfigVars::Get().ChannelzMaxOrphanedNodes();
if (max_orphaned == 0) {
max_orphaned_per_shard_ = 0;
} else {
max_orphaned_per_shard_ = std::max<int>(max_orphaned / kNodeShards, 1);
RefCountedPtr<BaseNode> ChannelzRegistry::InternalGet(intptr_t uuid) {
MutexLock lock(&mu_);
if (uuid < 1 || uuid > uuid_generator_) {
return nullptr;
}
auto it = node_map_.find(uuid);
if (it == node_map_.end()) return nullptr;
// Found node. Return only if its refcount is not zero (i.e., when we
// know that there is no other thread about to destroy it).
BaseNode* node = it->second;
return node->RefIfNonZero();
}
std::tuple<std::vector<WeakRefCountedPtr<BaseNode>>, bool>
ChannelzRegistry::QueryNodes(
intptr_t start_node, absl::FunctionRef<bool(const BaseNode*)> discriminator,
size_t max_results) {
// Mitigate drain hotspotting by randomizing the drain order each query.
std::vector<size_t> nursery_visitation_order;
for (size_t i = 0; i < kNodeShards; ++i) {
nursery_visitation_order.push_back(i);
}
absl::c_shuffle(nursery_visitation_order, SharedBitGen());
// In the iteration below, even once we have max_results nodes, we need
// to find the next node in order to know if we've hit the end. If we get
// through the loop without returning, then we return end=true. But if we
// find a node to add after we already have max_results nodes, then we
// return with end=false before exiting the loop. However, in the latter
// case, we will have already increased the ref count of the next node,
// so we need to unref it, but we can't do that while holding the lock.
// So instead, we store it in node_after_end, which will be unreffed
// after releasing the lock.
WeakRefCountedPtr<BaseNode> node_after_end;
std::vector<WeakRefCountedPtr<BaseNode>> result;
MutexLock index_lock(&index_mu_);
for (auto it = index_.lower_bound(start_node); it != index_.end(); ++it) {
BaseNode* node = it->second;
if (!discriminator(node)) continue;
auto node_ref = node->WeakRefIfNonZero();
if (node_ref == nullptr) continue;
if (result.size() == max_results) {
node_after_end = std::move(node_ref);
return std::tuple(std::move(result), false);
}
result.emplace_back(std::move(node_ref));
}
for (auto nursery_index : nursery_visitation_order) {
NodeShard& node_shard = node_shards_[nursery_index];
MutexLock shard_lock(&node_shard.mu);
for (auto [nursery, numbered] :
{std::pair(&node_shard.nursery, &node_shard.numbered),
std::pair(&node_shard.orphaned, &node_shard.orphaned_numbered)}) {
if (nursery->head == nullptr) continue;
BaseNode* n = nursery->head;
while (n != nullptr) {
if (!discriminator(n)) {
n = n->next_;
continue;
std::string ChannelzRegistry::InternalGetTopChannels(
intptr_t start_channel_id) {
std::vector<RefCountedPtr<BaseNode>> top_level_channels;
RefCountedPtr<BaseNode> node_after_pagination_limit;
{
MutexLock lock(&mu_);
for (auto it = node_map_.lower_bound(start_channel_id);
it != node_map_.end(); ++it) {
BaseNode* node = it->second;
RefCountedPtr<BaseNode> node_ref;
if (node->type() == BaseNode::EntityType::kTopLevelChannel &&
(node_ref = node->RefIfNonZero()) != nullptr) {
// Check if we are over pagination limit to determine if we need to set
// the "end" element. If we don't go through this block, we know that
// when the loop terminates, we have <= to kPaginationLimit.
// Note that because we have already increased this node's
// refcount, we need to decrease it, but we can't unref while
// holding the lock, because this may lead to a deadlock.
if (top_level_channels.size() == kPaginationLimit) {
node_after_pagination_limit = std::move(node_ref);
break;
}
auto node_ref = n->WeakRefIfNonZero();
if (node_ref == nullptr) {
n = n->next_;
continue;
}
BaseNode* next = n->next_;
nursery->Remove(n);
numbered->AddToHead(n);
n->uuid_ = uuid_generator_;
++uuid_generator_;
index_.emplace(n->uuid_, n);
if (n->uuid_ >= start_node) {
if (result.size() == max_results) {
node_after_end = std::move(node_ref);
return std::tuple(std::move(result), false);
}
result.emplace_back(std::move(node_ref));
}
n = next;
top_level_channels.emplace_back(std::move(node_ref));
}
}
}
CHECK(node_after_end == nullptr);
return std::tuple(std::move(result), true);
}
WeakRefCountedPtr<BaseNode> ChannelzRegistry::InternalGet(intptr_t uuid) {
MutexLock index_lock(&index_mu_);
auto it = index_.find(uuid);
if (it == index_.end()) return nullptr;
BaseNode* node = it->second;
return node->WeakRefIfNonZero();
}
intptr_t ChannelzRegistry::InternalNumberNode(BaseNode* node) {
// node must be strongly owned still
node->AssertStronglyOwned();
const size_t node_shard_index = NodeShardIndex(node);
NodeShard& node_shard = node_shards_[node_shard_index];
MutexLock index_lock(&index_mu_);
MutexLock lock(&node_shard.mu);
intptr_t uuid = node->uuid_.load(std::memory_order_relaxed);
if (uuid != -1) return uuid;
uuid = uuid_generator_;
++uuid_generator_;
node->uuid_ = uuid;
if (node->orphaned_index_ > 0) {
node_shard.orphaned.Remove(node);
node_shard.orphaned_numbered.AddToHead(node);
} else {
node_shard.nursery.Remove(node);
node_shard.numbered.AddToHead(node);
}
index_.emplace(uuid, node);
return uuid;
}
bool ChannelzRegistry::NodeList::Holds(BaseNode* node) const {
BaseNode* n = head;
while (n != nullptr) {
if (n == node) return true;
n = n->next_;
}
return false;
}
void ChannelzRegistry::NodeList::AddToHead(BaseNode* node) {
DCHECK(!Holds(node));
++count;
if (head != nullptr) head->prev_ = node;
node->next_ = head;
node->prev_ = nullptr;
head = node;
if (tail == nullptr) tail = node;
DCHECK(Holds(node));
}
void ChannelzRegistry::NodeList::Remove(BaseNode* node) {
DCHECK(Holds(node));
DCHECK_GT(count, 0u);
--count;
if (node->prev_ == nullptr) {
head = node->next_;
if (head == nullptr) {
DCHECK_EQ(count, 0u);
tail = nullptr;
DCHECK(!Holds(node));
return;
Json::Object object;
if (!top_level_channels.empty()) {
// Create list of channels.
Json::Array array;
for (size_t i = 0; i < top_level_channels.size(); ++i) {
array.emplace_back(top_level_channels[i]->RenderJson());
}
} else {
node->prev_->next_ = node->next_;
object["channel"] = Json::FromArray(std::move(array));
}
if (node->next_ == nullptr) {
tail = node->prev_;
} else {
node->next_->prev_ = node->prev_;
if (node_after_pagination_limit == nullptr) {
object["end"] = Json::FromBool(true);
}
DCHECK(!Holds(node));
return JsonDump(Json::FromObject(std::move(object)));
}
void ChannelzRegistry::TestOnlyReset() {
auto* p = Default();
p->uuid_generator_ = 1;
p->LoadConfig();
std::vector<WeakRefCountedPtr<BaseNode>> free_nodes;
for (size_t i = 0; i < kNodeShards; i++) {
MutexLock lock(&p->node_shards_[i].mu);
CHECK(p->node_shards_[i].nursery.head == nullptr);
CHECK(p->node_shards_[i].numbered.head == nullptr);
while (p->node_shards_[i].orphaned.head != nullptr) {
free_nodes.emplace_back(p->node_shards_[i].orphaned.head);
p->node_shards_[i].orphaned.Remove(p->node_shards_[i].orphaned.head);
}
while (p->node_shards_[i].orphaned_numbered.head != nullptr) {
free_nodes.emplace_back(p->node_shards_[i].orphaned_numbered.head);
p->node_shards_[i].orphaned_numbered.Remove(
p->node_shards_[i].orphaned_numbered.head);
std::string ChannelzRegistry::InternalGetServers(intptr_t start_server_id) {
std::vector<RefCountedPtr<BaseNode>> servers;
RefCountedPtr<BaseNode> node_after_pagination_limit;
{
MutexLock lock(&mu_);
for (auto it = node_map_.lower_bound(start_server_id);
it != node_map_.end(); ++it) {
BaseNode* node = it->second;
RefCountedPtr<BaseNode> node_ref;
if (node->type() == BaseNode::EntityType::kServer &&
(node_ref = node->RefIfNonZero()) != nullptr) {
// Check if we are over pagination limit to determine if we need to set
// the "end" element. If we don't go through this block, we know that
// when the loop terminates, we have <= to kPaginationLimit.
// Note that because we have already increased this node's
// refcount, we need to decrease it, but we can't unref while
// holding the lock, because this may lead to a deadlock.
if (servers.size() == kPaginationLimit) {
node_after_pagination_limit = std::move(node_ref);
break;
}
servers.emplace_back(std::move(node_ref));
}
}
}
std::vector<NodeShard> replace_node_shards(kNodeShards);
replace_node_shards.swap(p->node_shards_);
MutexLock lock(&p->index_mu_);
p->index_.clear();
Json::Object object;
if (!servers.empty()) {
// Create list of servers.
Json::Array array;
for (size_t i = 0; i < servers.size(); ++i) {
array.emplace_back(servers[i]->RenderJson());
}
object["server"] = Json::FromArray(std::move(array));
}
if (node_after_pagination_limit == nullptr) {
object["end"] = Json::FromBool(true);
}
return JsonDump(Json::FromObject(std::move(object)));
}
void ChannelzRegistry::InternalLogAllEntities() {
std::vector<RefCountedPtr<BaseNode>> nodes;
{
MutexLock lock(&mu_);
for (auto& p : node_map_) {
RefCountedPtr<BaseNode> node = p.second->RefIfNonZero();
if (node != nullptr) {
nodes.emplace_back(std::move(node));
}
}
}
for (size_t i = 0; i < nodes.size(); ++i) {
std::string json = nodes[i]->RenderJsonString();
LOG(INFO) << json;
}
}
} // namespace channelz
@ -381,22 +179,21 @@ void ChannelzRegistry::TestOnlyReset() {
char* grpc_channelz_get_top_channels(intptr_t start_channel_id) {
grpc_core::ExecCtx exec_ctx;
return grpc_core::channelz::ApplyHacks(
grpc_core::channelz::ChannelzRegistry::GetTopChannelsJson(
start_channel_id)
return gpr_strdup(
grpc_core::channelz::ChannelzRegistry::GetTopChannels(start_channel_id)
.c_str());
}
char* grpc_channelz_get_servers(intptr_t start_server_id) {
grpc_core::ExecCtx exec_ctx;
return grpc_core::channelz::ApplyHacks(
grpc_core::channelz::ChannelzRegistry::GetServersJson(start_server_id)
return gpr_strdup(
grpc_core::channelz::ChannelzRegistry::GetServers(start_server_id)
.c_str());
}
char* grpc_channelz_get_server(intptr_t server_id) {
grpc_core::ExecCtx exec_ctx;
grpc_core::WeakRefCountedPtr<grpc_core::channelz::BaseNode> server_node =
grpc_core::RefCountedPtr<grpc_core::channelz::BaseNode> server_node =
grpc_core::channelz::ChannelzRegistry::Get(server_id);
if (server_node == nullptr ||
server_node->type() !=
@ -406,7 +203,7 @@ char* grpc_channelz_get_server(intptr_t server_id) {
grpc_core::Json json = grpc_core::Json::FromObject({
{"server", server_node->RenderJson()},
});
return grpc_core::channelz::ApplyHacks(grpc_core::JsonDump(json).c_str());
return gpr_strdup(grpc_core::JsonDump(json).c_str());
}
char* grpc_channelz_get_server_sockets(intptr_t server_id,
@ -414,7 +211,7 @@ char* grpc_channelz_get_server_sockets(intptr_t server_id,
intptr_t max_results) {
grpc_core::ExecCtx exec_ctx;
// Validate inputs before handing them of to the renderer.
grpc_core::WeakRefCountedPtr<grpc_core::channelz::BaseNode> base_node =
grpc_core::RefCountedPtr<grpc_core::channelz::BaseNode> base_node =
grpc_core::channelz::ChannelzRegistry::Get(server_id);
if (base_node == nullptr ||
base_node->type() != grpc_core::channelz::BaseNode::EntityType::kServer ||
@ -425,13 +222,13 @@ char* grpc_channelz_get_server_sockets(intptr_t server_id,
// actually a server node.
grpc_core::channelz::ServerNode* server_node =
static_cast<grpc_core::channelz::ServerNode*>(base_node.get());
return grpc_core::channelz::ApplyHacks(
return gpr_strdup(
server_node->RenderServerSockets(start_socket_id, max_results).c_str());
}
char* grpc_channelz_get_channel(intptr_t channel_id) {
grpc_core::ExecCtx exec_ctx;
grpc_core::WeakRefCountedPtr<grpc_core::channelz::BaseNode> channel_node =
grpc_core::RefCountedPtr<grpc_core::channelz::BaseNode> channel_node =
grpc_core::channelz::ChannelzRegistry::Get(channel_id);
if (channel_node == nullptr ||
(channel_node->type() !=
@ -443,12 +240,12 @@ char* grpc_channelz_get_channel(intptr_t channel_id) {
grpc_core::Json json = grpc_core::Json::FromObject({
{"channel", channel_node->RenderJson()},
});
return grpc_core::channelz::ApplyHacks(grpc_core::JsonDump(json).c_str());
return gpr_strdup(grpc_core::JsonDump(json).c_str());
}
char* grpc_channelz_get_subchannel(intptr_t subchannel_id) {
grpc_core::ExecCtx exec_ctx;
grpc_core::WeakRefCountedPtr<grpc_core::channelz::BaseNode> subchannel_node =
grpc_core::RefCountedPtr<grpc_core::channelz::BaseNode> subchannel_node =
grpc_core::channelz::ChannelzRegistry::Get(subchannel_id);
if (subchannel_node == nullptr ||
subchannel_node->type() !=
@ -458,22 +255,20 @@ char* grpc_channelz_get_subchannel(intptr_t subchannel_id) {
grpc_core::Json json = grpc_core::Json::FromObject({
{"subchannel", subchannel_node->RenderJson()},
});
return grpc_core::channelz::ApplyHacks(grpc_core::JsonDump(json).c_str());
return gpr_strdup(grpc_core::JsonDump(json).c_str());
}
char* grpc_channelz_get_socket(intptr_t socket_id) {
grpc_core::ExecCtx exec_ctx;
grpc_core::WeakRefCountedPtr<grpc_core::channelz::BaseNode> socket_node =
grpc_core::RefCountedPtr<grpc_core::channelz::BaseNode> socket_node =
grpc_core::channelz::ChannelzRegistry::Get(socket_id);
if (socket_node == nullptr ||
(socket_node->type() !=
grpc_core::channelz::BaseNode::EntityType::kSocket &&
socket_node->type() !=
grpc_core::channelz::BaseNode::EntityType::kListenSocket)) {
socket_node->type() !=
grpc_core::channelz::BaseNode::EntityType::kSocket) {
return nullptr;
}
grpc_core::Json json = grpc_core::Json::FromObject({
{"socket", socket_node->RenderJson()},
});
return grpc_core::channelz::ApplyHacks(grpc_core::JsonDump(json).c_str());
return gpr_strdup(grpc_core::JsonDump(json).c_str());
}

View File

@ -25,10 +25,8 @@
#include <map>
#include <string>
#include "absl/container/btree_map.h"
#include "absl/functional/function_ref.h"
#include "absl/base/thread_annotations.h"
#include "src/core/channelz/channelz.h"
#include "src/core/util/json/json_writer.h"
#include "src/core/util/ref_counted_ptr.h"
#include "src/core/util/sync.h"
@ -42,134 +40,36 @@ class ChannelzRegistry final {
static void Register(BaseNode* node) {
return Default()->InternalRegister(node);
}
static void Unregister(BaseNode* node) {
Default()->InternalUnregister(node);
}
static WeakRefCountedPtr<BaseNode> Get(intptr_t uuid) {
static void Unregister(intptr_t uuid) { Default()->InternalUnregister(uuid); }
static RefCountedPtr<BaseNode> Get(intptr_t uuid) {
return Default()->InternalGet(uuid);
}
static intptr_t NumberNode(BaseNode* node) {
return Default()->InternalNumberNode(node);
}
static WeakRefCountedPtr<SubchannelNode> GetSubchannel(intptr_t uuid) {
return Default()
->InternalGetTyped<SubchannelNode, BaseNode::EntityType::kSubchannel>(
uuid);
}
static WeakRefCountedPtr<ChannelNode> GetChannel(intptr_t uuid) {
auto node = Default()->InternalGet(uuid);
if (node == nullptr) return nullptr;
if (node->type() == BaseNode::EntityType::kTopLevelChannel) {
return node->WeakRefAsSubclass<ChannelNode>();
}
if (node->type() == BaseNode::EntityType::kInternalChannel) {
return node->WeakRefAsSubclass<ChannelNode>();
}
return nullptr;
}
static WeakRefCountedPtr<ServerNode> GetServer(intptr_t uuid) {
return Default()
->InternalGetTyped<ServerNode, BaseNode::EntityType::kServer>(uuid);
}
static WeakRefCountedPtr<SocketNode> GetSocket(intptr_t uuid) {
return Default()
->InternalGetTyped<SocketNode, BaseNode::EntityType::kSocket>(uuid);
}
// Returns the allocated JSON string that represents the proto
// GetTopChannelsResponse as per channelz.proto.
static auto GetTopChannels(intptr_t start_channel_id) {
return Default()
->InternalGetObjects<ChannelNode,
BaseNode::EntityType::kTopLevelChannel>(
start_channel_id);
static std::string GetTopChannels(intptr_t start_channel_id) {
return Default()->InternalGetTopChannels(start_channel_id);
}
static std::string GetTopChannelsJson(intptr_t start_channel_id);
static std::string GetServersJson(intptr_t start_server_id);
// Returns the allocated JSON string that represents the proto
// GetServersResponse as per channelz.proto.
static auto GetServers(intptr_t start_server_id) {
return Default()
->InternalGetObjects<ServerNode, BaseNode::EntityType::kServer>(
start_server_id);
}
static std::tuple<std::vector<WeakRefCountedPtr<BaseNode>>, bool>
GetChildrenOfType(intptr_t start_node, const BaseNode* parent,
BaseNode::EntityType type, size_t max_results) {
return Default()->InternalGetChildrenOfType(start_node, parent, type,
max_results);
static std::string GetServers(intptr_t start_server_id) {
return Default()->InternalGetServers(start_server_id);
}
// Test only helper function to dump the JSON representation to std out.
// This can aid in debugging channelz code.
static void LogAllEntities() { Default()->InternalLogAllEntities(); }
static std::vector<WeakRefCountedPtr<BaseNode>> GetAllEntities() {
return Default()->InternalGetAllEntities();
}
// Test only helper function to reset to initial state.
static void TestOnlyReset();
static void TestOnlyReset() {
auto* p = Default();
MutexLock lock(&p->mu_);
p->node_map_.clear();
p->uuid_generator_ = 0;
}
private:
ChannelzRegistry() { LoadConfig(); }
void LoadConfig();
// Takes a callable F: (WeakRefCountedPtr<BaseNode>) -> bool, and returns
// a (BaseNode*) -> bool that filters unreffed objects and returns true.
// The ref must be unreffed outside the NodeMapInterface iteration.
template <typename F>
static auto CollectReferences(F fn) {
return [fn = std::move(fn)](BaseNode* n) {
auto node = n->RefIfNonZero();
if (node == nullptr) return true;
return fn(std::move(node));
};
}
struct NodeList {
BaseNode* head = nullptr;
BaseNode* tail = nullptr;
size_t count = 0;
bool Holds(BaseNode* node) const;
void AddToHead(BaseNode* node);
void Remove(BaseNode* node);
};
// Nodes traverse through up to four lists, depending on
// whether they have a uuid (this is becoming numbered),
// and whether they have been orphaned or not.
// The lists help us find un-numbered nodes when needed for
// queries, and the oldest orphaned node when needed for
// garbage collection.
// Nodes are organized into shards based on their pointer
// address. A shard tracks the four lists of nodes
// independently - we strive to have no cross-talk between
// shards as these are very global objects.
struct alignas(GPR_CACHELINE_SIZE) NodeShard {
Mutex mu;
// Nursery nodes have no uuid and are not orphaned.
NodeList nursery ABSL_GUARDED_BY(mu);
// Numbered nodes have been assigned a uuid, and are not orphaned.
NodeList numbered ABSL_GUARDED_BY(mu);
// Orphaned nodes have no uuid, but have been orphaned.
NodeList orphaned ABSL_GUARDED_BY(mu);
// Finally, orphaned numbered nodes are orphaned, and have been assigned a
// uuid.
NodeList orphaned_numbered ABSL_GUARDED_BY(mu);
uint64_t next_orphan_index ABSL_GUARDED_BY(mu) = 1;
size_t TotalOrphaned() ABSL_EXCLUSIVE_LOCKS_REQUIRED(mu) {
return orphaned.count + orphaned_numbered.count;
}
};
// Returned the singleton instance of ChannelzRegistry;
static ChannelzRegistry* Default();
@ -178,81 +78,23 @@ class ChannelzRegistry final {
// globally unregisters the object that is associated to uuid. Also does
// sanity check that an object doesn't try to unregister the wrong type.
void InternalUnregister(BaseNode* node);
intptr_t InternalNumberNode(BaseNode* node);
void InternalUnregister(intptr_t uuid);
// if object with uuid has previously been registered as the correct type,
// returns the void* associated with that uuid. Else returns nullptr.
WeakRefCountedPtr<BaseNode> InternalGet(intptr_t uuid);
RefCountedPtr<BaseNode> InternalGet(intptr_t uuid);
// Generic query over nodes.
// This function takes care of all the gnarly locking, and allows high level
// code to request a start node and maximum number of results (for pagination
// purposes).
// `discriminator` allows callers to choose which nodes will be returned - if
// it returns true, the node is included in the result.
// `discriminator` *MUST NOT* ref the node, nor call into ChannelzRegistry via
// any code path (locks are held during the call).
std::tuple<std::vector<WeakRefCountedPtr<BaseNode>>, bool> QueryNodes(
intptr_t start_node,
absl::FunctionRef<bool(const BaseNode*)> discriminator,
size_t max_results);
std::tuple<std::vector<WeakRefCountedPtr<BaseNode>>, bool>
InternalGetChildrenOfType(intptr_t start_node, const BaseNode* parent,
BaseNode::EntityType type, size_t max_results) {
return QueryNodes(
start_node,
[type, parent](const BaseNode* n) {
return n->type() == type && n->HasParent(parent);
},
max_results);
}
template <typename T, BaseNode::EntityType entity_type>
WeakRefCountedPtr<T> InternalGetTyped(intptr_t uuid) {
WeakRefCountedPtr<BaseNode> node = InternalGet(uuid);
if (node == nullptr || node->type() != entity_type) {
return nullptr;
}
return node->WeakRefAsSubclass<T>();
}
template <typename T, BaseNode::EntityType entity_type>
std::tuple<std::vector<WeakRefCountedPtr<T>>, bool> InternalGetObjects(
intptr_t start_id) {
const int kPaginationLimit = 100;
std::vector<WeakRefCountedPtr<T>> top_level_channels;
const auto [nodes, end] = QueryNodes(
start_id,
[](const BaseNode* node) { return node->type() == entity_type; },
kPaginationLimit);
for (const auto& p : nodes) {
top_level_channels.emplace_back(p->template WeakRefAsSubclass<T>());
}
return std::tuple(std::move(top_level_channels), end);
}
std::string InternalGetTopChannels(intptr_t start_channel_id);
std::string InternalGetServers(intptr_t start_server_id);
void InternalLogAllEntities();
std::vector<WeakRefCountedPtr<BaseNode>> InternalGetAllEntities();
static constexpr size_t kNodeShards = 63;
size_t NodeShardIndex(BaseNode* node) {
return absl::HashOf(node) % kNodeShards;
}
int64_t uuid_generator_{1};
std::vector<NodeShard> node_shards_{kNodeShards};
Mutex index_mu_;
absl::btree_map<intptr_t, BaseNode*> index_ ABSL_GUARDED_BY(index_mu_);
size_t max_orphaned_per_shard_;
// protects members
Mutex mu_;
std::map<intptr_t, BaseNode*> node_map_ ABSL_GUARDED_BY(mu_);
intptr_t uuid_generator_ ABSL_GUARDED_BY(mu_) = 0;
};
// `additionalInfo` section is not yet in the protobuf format, so we
// provide a utility to strip it for compatibility.
std::string StripAdditionalInfoFromJson(absl::string_view json);
} // namespace channelz
} // namespace grpc_core

View File

@ -1,315 +0,0 @@
// Copyright 2025 gRPC authors.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
#ifndef GRPC_SRC_CORE_CHANNELZ_ZTRACE_COLLECTOR_H
#define GRPC_SRC_CORE_CHANNELZ_ZTRACE_COLLECTOR_H
#include <grpc/support/time.h>
#include <memory>
#include <tuple>
#include <vector>
#include "absl/container/flat_hash_set.h"
#include "src/core/channelz/channelz.h"
#include "src/core/lib/debug/trace.h"
#include "src/core/util/json/json_writer.h"
#include "src/core/util/single_set_ptr.h"
#include "src/core/util/string.h"
#include "src/core/util/sync.h"
#include "src/core/util/time.h"
#ifdef GRPC_NO_ZTRACE
namespace grpc_core::channelz {
namespace ztrace_collector_detail {
class ZTraceImpl final : public ZTrace {
public:
explicit ZTraceImpl() {}
void Run(Timestamp deadline, std::map<std::string, std::string> args,
std::shared_ptr<grpc_event_engine::experimental::EventEngine>
event_engine,
absl::AnyInvocable<void(Json)> callback) override {
event_engine->Run([callback = std::move(callback)]() mutable {
callback(Json::FromBool(false));
});
}
};
class StubImpl {
public:
template <typename T>
void Append(const T&) {}
std::unique_ptr<ZTrace> MakeZTrace() {
return std::make_unique<ZTraceImpl>();
}
};
} // namespace ztrace_collector_detail
template <typename...>
class ZTraceCollector : public ztrace_collector_detail::StubImpl {};
} // namespace grpc_core::channelz
#else
namespace grpc_core::channelz {
namespace ztrace_collector_detail {
template <typename T>
using Collection = std::deque<std::pair<gpr_cycle_counter, T> >;
template <typename T>
void AppendResults(const Collection<T>& data, Json::Array& results) {
for (const auto& value : data) {
Json::Object object;
object["timestamp"] =
Json::FromString(gpr_format_timespec(gpr_convert_clock_type(
gpr_cycle_counter_to_time(value.first), GPR_CLOCK_REALTIME)));
value.second.RenderJson(object);
results.emplace_back(Json::FromObject(std::move(object)));
}
}
template <typename Needle, typename... Haystack>
constexpr bool kIsElement = false;
template <typename Needle, typename... Haystack>
constexpr bool kIsElement<Needle, Needle, Haystack...> = true;
template <typename Needle, typename H, typename... Haystack>
constexpr bool kIsElement<Needle, H, Haystack...> =
kIsElement<Needle, Haystack...>;
} // namespace ztrace_collector_detail
inline std::optional<int64_t> IntFromArgs(
const std::map<std::string, std::string>& args, const std::string& name) {
auto it = args.find(name);
if (it == args.end()) return std::nullopt;
int64_t out;
if (!absl::SimpleAtoi(it->second, &out)) return std::nullopt;
return out;
}
// Generic collector infrastructure for ztrace queries.
// Abstracts away most of the ztrace requirements in an efficient manner,
// allowing system authors to concentrate on emitting useful data.
// If no trace is performed, overhead is one pointer and one relaxed atomic read
// per trace event.
//
// Two kinds of objects are required:
// 1. A `Config`
// - This type should be constructible with a std::map<std::string,
// std::string>
// and provides overall query configuration - the map can be used to pull
// predicates from the calling system.
// - Needs a `bool Finishes(T)` method for each Data type (see 2).
// This allows the config to terminate a query in the event of reaching
// some configured predicate.
// 2. N `Data` types
// - One for each kind of data captured in the trace
// - Allows avoiding e.g. variant<> data types; these are inefficient
// in this context because they force every recorded entry to use the
// same number of bytes whilst pending.
template <typename Config, typename... Data>
class ZTraceCollector {
public:
template <typename X>
void Append(X producer_or_value) {
GRPC_TRACE_LOG(ztrace, INFO) << "ZTRACE[" << this << "]: " << [&]() {
Json::Object obj;
if constexpr (ztrace_collector_detail::kIsElement<X, Data...>) {
producer_or_value.RenderJson(obj);
} else {
producer_or_value().RenderJson(obj);
}
return JsonDump(Json::FromObject(std::move(obj)));
}();
if (!impl_.is_set()) return;
if constexpr (ztrace_collector_detail::kIsElement<X, Data...>) {
AppendValue(std::move(producer_or_value));
} else {
AppendValue(producer_or_value());
}
}
std::unique_ptr<ZTrace> MakeZTrace() {
return std::make_unique<ZTraceImpl>(impl_.GetOrCreate());
}
private:
template <typename T>
using Collection = ztrace_collector_detail::Collection<T>;
struct Instance : public RefCounted<Instance> {
Instance(std::map<std::string, std::string> args,
std::shared_ptr<grpc_event_engine::experimental::EventEngine>
event_engine,
absl::AnyInvocable<void(Json)> done)
: memory_cap_(IntFromArgs(args, "memory_cap").value_or(1024 * 1024)),
config(args),
event_engine(std::move(event_engine)),
done(std::move(done)) {}
using Collections = std::tuple<Collection<Data>...>;
struct RemoveMostRecentState {
void (*enact)(Instance*) = nullptr;
gpr_cycle_counter most_recent =
std::numeric_limits<gpr_cycle_counter>::max();
};
template <typename T>
void Append(std::pair<gpr_cycle_counter, T> value) {
memory_used_ += value.second.MemoryUsage();
while (memory_used_ > memory_cap_) RemoveMostRecent();
std::get<Collection<T> >(data).push_back(std::move(value));
}
void RemoveMostRecent() {
RemoveMostRecentState state;
(UpdateRemoveMostRecentState<Data>(&state), ...);
CHECK(state.enact != nullptr);
state.enact(this);
++items_removed_;
}
template <typename T>
void UpdateRemoveMostRecentState(RemoveMostRecentState* state) {
auto& collection = std::get<Collection<T> >(data);
if (collection.empty()) return;
if (state->enact == nullptr ||
collection.front().first < state->most_recent) {
state->enact = +[](Instance* instance) {
auto& collection = std::get<Collection<T> >(instance->data);
const size_t ent_usage = collection.front().second.MemoryUsage();
CHECK_GE(instance->memory_used_, ent_usage);
instance->memory_used_ -= ent_usage;
collection.pop_front();
};
state->most_recent = collection.front().first;
}
}
void Finish(absl::Status status) {
event_engine->Run([data = std::move(data), done = std::move(done),
status = std::move(status), memory_used = memory_used_,
items_removed = items_removed_]() mutable {
Json::Array entries;
(ztrace_collector_detail::AppendResults(
std::get<Collection<Data> >(data), entries),
...);
Json::Object result;
result["entries"] = Json::FromArray(entries);
result["status"] = Json::FromString(status.ToString());
result["memory_used"] =
Json::FromNumber(static_cast<uint64_t>(memory_used));
result["items_removed"] = Json::FromNumber(items_removed);
done(Json::FromObject(std::move(result)));
});
}
size_t memory_used_ = 0;
size_t memory_cap_ = 0;
uint64_t items_removed_ = 0;
Config config;
const Timestamp start_time = Timestamp::Now();
std::shared_ptr<grpc_event_engine::experimental::EventEngine> event_engine;
grpc_event_engine::experimental::EventEngine::TaskHandle task_handle{
grpc_event_engine::experimental::EventEngine::TaskHandle::kInvalid};
Collections data;
absl::AnyInvocable<void(Json)> done;
};
struct Impl : public RefCounted<Impl> {
Mutex mu;
absl::flat_hash_set<RefCountedPtr<Instance> > instances ABSL_GUARDED_BY(mu);
};
class ZTraceImpl final : public ZTrace {
public:
explicit ZTraceImpl(RefCountedPtr<Impl> impl) : impl_(std::move(impl)) {}
void Run(Timestamp deadline, std::map<std::string, std::string> args,
std::shared_ptr<grpc_event_engine::experimental::EventEngine>
event_engine,
absl::AnyInvocable<void(Json)> callback) override {
auto instance = MakeRefCounted<Instance>(std::move(args), event_engine,
std::move(callback));
auto impl = std::move(impl_);
RefCountedPtr<Instance> oldest_instance;
MutexLock lock(&impl->mu);
if (impl->instances.size() > 20) {
// Eject oldest running trace
Timestamp oldest_time = Timestamp::InfFuture();
for (auto& instance : impl->instances) {
if (instance->start_time < oldest_time) {
oldest_time = instance->start_time;
oldest_instance = instance;
}
}
CHECK(oldest_instance != nullptr);
impl->instances.erase(oldest_instance);
oldest_instance->Finish(
absl::ResourceExhaustedError("Too many concurrent ztrace queries"));
}
instance->task_handle = event_engine->RunAfter(
deadline - Timestamp::Now(), [instance, impl]() {
bool finish;
{
MutexLock lock(&impl->mu);
finish = impl->instances.erase(instance);
}
if (finish) instance->Finish(absl::DeadlineExceededError(""));
});
impl->instances.insert(instance);
}
private:
RefCountedPtr<Impl> impl_;
};
template <typename T>
void AppendValue(T&& data) {
auto value = std::pair(gpr_get_cycle_counter(), std::forward<T>(data));
auto* impl = impl_.Get();
{
MutexLock lock(&impl->mu);
switch (impl->instances.size()) {
case 0:
return;
case 1: {
auto& instances = impl->instances;
auto& instance = *instances.begin();
const bool finishes = instance->config.Finishes(value.second);
instance->Append(std::move(value));
if (finishes) {
instance->Finish(absl::OkStatus());
instances.clear();
}
} break;
default: {
std::vector<RefCountedPtr<Instance> > finished;
for (auto& instance : impl->instances) {
const bool finishes = instance->config.Finishes(value.second);
instance->Append(value);
if (finishes) {
finished.push_back(instance);
}
}
for (const auto& instance : finished) {
instance->Finish(absl::OkStatus());
impl->instances.erase(instance);
}
}
}
}
}
SingleSetRefCountedPtr<Impl> impl_;
};
} // namespace grpc_core::channelz
#endif // GRPC_NO_ZTRACE
#endif // GRPC_SRC_CORE_CHANNELZ_ZTRACE_COLLECTOR_H

View File

@ -62,15 +62,10 @@ static grpc_core::Duration g_poll_interval =
static bool g_backup_polling_disabled;
void grpc_client_channel_global_init_backup_polling() {
#ifndef GRPC_DO_NOT_INSTANTIATE_POSIX_POLLER
// Disable backup polling if EventEngine is used everywhere.
g_backup_polling_disabled = grpc_core::IsEventEngineClientEnabled() &&
grpc_core::IsEventEngineListenerEnabled() &&
grpc_core::IsEventEngineDnsEnabled();
#else
// EventEngine polling not supported, keep using the backup poller.
g_backup_polling_disabled = false;
#endif
if (g_backup_polling_disabled) {
return;
}
@ -160,21 +155,11 @@ static void g_poller_init_locked() {
}
}
static bool g_can_poll_in_background() {
#ifndef GRPC_DO_NOT_INSTANTIATE_POSIX_POLLER
return grpc_iomgr_run_in_background();
#else
// No iomgr "event_engines" (not to be confused with the new EventEngine)
// are able to run in backgroung.
return false;
#endif
}
void grpc_client_channel_start_backup_polling(
grpc_pollset_set* interested_parties) {
if (g_backup_polling_disabled ||
g_poll_interval == grpc_core::Duration::Zero() ||
g_can_poll_in_background()) {
grpc_iomgr_run_in_background()) {
return;
}
gpr_mu_lock(&g_poller_mu);
@ -194,7 +179,7 @@ void grpc_client_channel_stop_backup_polling(
grpc_pollset_set* interested_parties) {
if (g_backup_polling_disabled ||
g_poll_interval == grpc_core::Duration::Zero() ||
g_can_poll_in_background()) {
grpc_iomgr_run_in_background()) {
return;
}
grpc_pollset_set_del_pollset(interested_parties, g_poller->pollset);

View File

@ -45,10 +45,6 @@
#include "absl/strings/str_cat.h"
#include "absl/strings/str_join.h"
#include "absl/strings/string_view.h"
#include "src/core/call/call_spine.h"
#include "src/core/call/client_call.h"
#include "src/core/call/metadata_batch.h"
#include "src/core/call/status_util.h"
#include "src/core/client_channel/client_channel_internal.h"
#include "src/core/client_channel/client_channel_service_config.h"
#include "src/core/client_channel/config_selector.h"
@ -59,10 +55,10 @@
#include "src/core/client_channel/subchannel.h"
#include "src/core/client_channel/subchannel_interface_internal.h"
#include "src/core/config/core_configuration.h"
#include "src/core/credentials/transport/transport_credentials.h"
#include "src/core/ext/filters/channel_idle/legacy_channel_idle_filter.h"
#include "src/core/lib/address_utils/sockaddr_utils.h"
#include "src/core/lib/channel/channel_args.h"
#include "src/core/lib/channel/status_util.h"
#include "src/core/lib/debug/trace.h"
#include "src/core/lib/event_engine/channel_args_endpoint_config.h"
#include "src/core/lib/iomgr/resolved_address.h"
@ -74,12 +70,16 @@
#include "src/core/lib/promise/sleep.h"
#include "src/core/lib/promise/try_seq.h"
#include "src/core/lib/resource_quota/arena.h"
#include "src/core/lib/security/credentials/credentials.h"
#include "src/core/lib/slice/slice.h"
#include "src/core/lib/slice/slice_internal.h"
#include "src/core/lib/surface/call.h"
#include "src/core/lib/surface/channel.h"
#include "src/core/lib/surface/client_call.h"
#include "src/core/lib/surface/completion_queue.h"
#include "src/core/lib/transport/call_spine.h"
#include "src/core/lib/transport/connectivity_state.h"
#include "src/core/lib/transport/metadata_batch.h"
#include "src/core/load_balancing/child_policy_handler.h"
#include "src/core/load_balancing/lb_policy.h"
#include "src/core/load_balancing/lb_policy_registry.h"
@ -228,19 +228,21 @@ class ClientChannel::SubchannelWrapper::WatcherWrapper
subchannel_wrapper_.reset(DEBUG_LOCATION, "WatcherWrapper");
}
void OnConnectivityStateChange(grpc_connectivity_state state,
const absl::Status& status) override {
void OnConnectivityStateChange(
RefCountedPtr<ConnectivityStateWatcherInterface> self,
grpc_connectivity_state state, const absl::Status& status) override {
GRPC_TRACE_LOG(client_channel, INFO)
<< "client_channel=" << subchannel_wrapper_->client_channel_.get()
<< ": connectivity change for subchannel wrapper "
<< subchannel_wrapper_.get() << " subchannel "
<< subchannel_wrapper_->subchannel_.get()
<< "; hopping into work_serializer";
auto self = RefAsSubclass<WatcherWrapper>();
self.release(); // Held by callback.
subchannel_wrapper_->client_channel_->work_serializer_->Run(
[self, state, status]() ABSL_EXCLUSIVE_LOCKS_REQUIRED(
*self->subchannel_wrapper_->client_channel_->work_serializer_) {
self->ApplyUpdateInControlPlaneWorkSerializer(state, status);
[this, state, status]() ABSL_EXCLUSIVE_LOCKS_REQUIRED(
*subchannel_wrapper_->client_channel_->work_serializer_) {
ApplyUpdateInControlPlaneWorkSerializer(state, status);
Unref();
});
}
@ -322,7 +324,8 @@ ClientChannel::SubchannelWrapper::SubchannelWrapper(
auto it =
client_channel_->subchannel_refcount_map_.find(subchannel_.get());
if (it == client_channel_->subchannel_refcount_map_.end()) {
subchannel_node->AddParent(client_channel_->channelz_node_);
client_channel_->channelz_node_->AddChildSubchannel(
subchannel_node->uuid());
it = client_channel_->subchannel_refcount_map_
.emplace(subchannel_.get(), 0)
.first;
@ -357,8 +360,8 @@ void ClientChannel::SubchannelWrapper::Orphaned() {
CHECK(it != self->client_channel_->subchannel_refcount_map_.end());
--it->second;
if (it->second == 0) {
subchannel_node->RemoveParent(
self->client_channel_->channelz_node_);
self->client_channel_->channelz_node_->RemoveChildSubchannel(
subchannel_node->uuid());
self->client_channel_->subchannel_refcount_map_.erase(it);
}
}
@ -492,7 +495,7 @@ class ClientChannel::ClientChannelControlHelper
}
GlobalStatsPluginRegistry::StatsPluginGroup& GetStatsPluginGroup() override {
return *client_channel_->stats_plugin_group_;
return client_channel_->stats_plugin_group_;
}
void AddTraceEvent(TraceSeverity severity, absl::string_view message) override
@ -527,11 +530,7 @@ RefCountedPtr<SubchannelPoolInterface> GetSubchannelPool(
if (args.GetBool(GRPC_ARG_USE_LOCAL_SUBCHANNEL_POOL).value_or(false)) {
return MakeRefCounted<LocalSubchannelPool>();
}
if (IsShardGlobalConnectionPoolEnabled()) {
return GlobalSubchannelPool::instance();
} else {
return LegacyGlobalSubchannelPool::instance();
}
return GlobalSubchannelPool::instance();
}
} // namespace
@ -588,7 +587,6 @@ absl::StatusOr<RefCountedPtr<Channel>> ClientChannel::Create(
}
namespace {
std::string GetDefaultAuthorityFromChannelArgs(const ChannelArgs& channel_args,
absl::string_view target) {
std::optional<std::string> default_authority =
@ -600,18 +598,6 @@ std::string GetDefaultAuthorityFromChannelArgs(const ChannelArgs& channel_args,
return std::move(*default_authority);
}
}
std::shared_ptr<GlobalStatsPluginRegistry::StatsPluginGroup>
GetStatsPluginGroupFromChannelArgs(const ChannelArgs& channel_args,
absl::string_view target,
absl::string_view default_authority) {
grpc_event_engine::experimental::ChannelArgsEndpointConfig endpoint_config(
channel_args);
experimental::StatsPluginChannelScope scope(target, default_authority,
endpoint_config);
return GlobalStatsPluginRegistry::GetStatsPluginsForChannel(scope);
}
} // namespace
ClientChannel::ClientChannel(
@ -620,17 +606,15 @@ ClientChannel::ClientChannel(
ClientChannelFactory* client_channel_factory,
CallDestinationFactory* call_destination_factory)
: Channel(std::move(target), channel_args),
default_authority_(
GetDefaultAuthorityFromChannelArgs(channel_args, this->target())),
stats_plugin_group_(GetStatsPluginGroupFromChannelArgs(
channel_args, this->target(), default_authority_)),
channel_args_(channel_args.SetObject(stats_plugin_group_)),
channel_args_(std::move(channel_args)),
event_engine_(channel_args_.GetObjectRef<EventEngine>()),
uri_to_resolve_(std::move(uri_to_resolve)),
service_config_parser_index_(
internal::ClientChannelServiceConfigParser::ParserIndex()),
default_service_config_(std::move(default_service_config)),
client_channel_factory_(client_channel_factory),
default_authority_(
GetDefaultAuthorityFromChannelArgs(channel_args_, this->target())),
channelz_node_(channel_args_.GetObject<channelz::ChannelNode>()),
idle_timeout_(GetClientIdleTimeout(channel_args_)),
resolver_data_for_calls_(ResolverDataForCalls{}),
@ -650,6 +634,13 @@ ClientChannel::ClientChannel(
} else {
keepalive_time_ = -1; // unset
}
// Get stats plugins for channel.
grpc_event_engine::experimental::ChannelArgsEndpointConfig endpoint_config(
channel_args_);
experimental::StatsPluginChannelScope scope(
this->target(), default_authority_, endpoint_config);
stats_plugin_group_ =
GlobalStatsPluginRegistry::GetStatsPluginsForChannel(scope);
}
ClientChannel::~ClientChannel() {
@ -702,7 +693,6 @@ class ExternalStateWatcher : public RefCounted<ExternalStateWatcher> {
grpc_connectivity_state last_observed_state,
Timestamp deadline)
: channel_(std::move(channel)), cq_(cq), tag_(tag) {
grpc_cq_begin_op(cq, tag);
MutexLock lock(&mu_);
// Start watch. This inherits the ref from creation.
auto watcher =
@ -782,14 +772,17 @@ void ClientChannel::WatchConnectivityState(grpc_connectivity_state state,
}
void ClientChannel::AddConnectivityWatcher(
grpc_connectivity_state initial_state,
OrphanablePtr<AsyncConnectivityStateWatcherInterface> watcher) {
auto self = RefAsSubclass<ClientChannel>();
work_serializer_->Run(
[self, initial_state, watcher = std::move(watcher)]()
ABSL_EXCLUSIVE_LOCKS_REQUIRED(*self->work_serializer_) mutable {
self->state_tracker_.AddWatcher(initial_state, std::move(watcher));
});
grpc_connectivity_state,
OrphanablePtr<AsyncConnectivityStateWatcherInterface>) {
Crash("not implemented");
// TODO(ctiller): to make this work, need to change WorkSerializer to use
// absl::AnyInvocable<> instead of std::function<>
// work_serializer_->Run(
// [self = RefAsSubclass<ClientChannel>(), initial_state,
// watcher = std::move(watcher)]()
// ABSL_EXCLUSIVE_LOCKS_REQUIRED(*work_serializer_) {
// self->state_tracker_.AddWatcher(initial_state, std::move(watcher));
// });
}
void ClientChannel::RemoveConnectivityWatcher(
@ -1319,13 +1312,11 @@ void ClientChannel::UpdateStateLocked(grpc_connectivity_state state,
state_tracker_.SetState(state, status, reason);
if (channelz_node_ != nullptr) {
channelz_node_->SetConnectivityState(state);
std::string trace =
channelz::ChannelNode::GetChannelConnectivityStateChangeString(state);
if (!status.ok() || state == GRPC_CHANNEL_TRANSIENT_FAILURE) {
absl::StrAppend(&trace, " status:", status.ToString());
}
channelz_node_->AddTraceEvent(channelz::ChannelTrace::Severity::Info,
grpc_slice_from_cpp_string(std::move(trace)));
channelz_node_->AddTraceEvent(
channelz::ChannelTrace::Severity::Info,
grpc_slice_from_static_string(
channelz::ChannelNode::GetChannelConnectivityStateChangeString(
state)));
}
}

View File

@ -22,7 +22,6 @@
#include "absl/status/status.h"
#include "absl/status/statusor.h"
#include "absl/strings/string_view.h"
#include "src/core/call/metadata.h"
#include "src/core/client_channel/client_channel_factory.h"
#include "src/core/client_channel/config_selector.h"
#include "src/core/client_channel/subchannel.h"
@ -30,6 +29,7 @@
#include "src/core/filter/blackboard.h"
#include "src/core/lib/promise/observable.h"
#include "src/core/lib/surface/channel.h"
#include "src/core/lib/transport/metadata.h"
#include "src/core/load_balancing/lb_policy.h"
#include "src/core/resolver/resolver.h"
#include "src/core/service_config/service_config.h"
@ -170,9 +170,6 @@ class ClientChannel : public Channel {
ConfigSelector& config_selector,
ClientMetadata& client_initial_metadata) const;
const std::string default_authority_;
const std::shared_ptr<GlobalStatsPluginRegistry::StatsPluginGroup>
stats_plugin_group_;
const ChannelArgs channel_args_;
const std::shared_ptr<grpc_event_engine::experimental::EventEngine>
event_engine_;
@ -180,7 +177,9 @@ class ClientChannel : public Channel {
const size_t service_config_parser_index_;
const RefCountedPtr<ServiceConfig> default_service_config_;
ClientChannelFactory* const client_channel_factory_;
const std::string default_authority_;
channelz::ChannelNode* const channelz_node_;
GlobalStatsPluginRegistry::StatsPluginGroup stats_plugin_group_;
//
// Idleness state.

View File

@ -47,8 +47,6 @@
#include "absl/strings/str_cat.h"
#include "absl/strings/str_join.h"
#include "absl/strings/string_view.h"
#include "src/core/call/metadata_batch.h"
#include "src/core/call/status_util.h"
#include "src/core/channelz/channel_trace.h"
#include "src/core/client_channel/backup_poller.h"
#include "src/core/client_channel/client_channel_internal.h"
@ -62,11 +60,11 @@
#include "src/core/client_channel/subchannel.h"
#include "src/core/client_channel/subchannel_interface_internal.h"
#include "src/core/config/core_configuration.h"
#include "src/core/credentials/transport/transport_credentials.h"
#include "src/core/handshaker/proxy_mapper_registry.h"
#include "src/core/lib/address_utils/sockaddr_utils.h"
#include "src/core/lib/channel/channel_args.h"
#include "src/core/lib/channel/channel_stack.h"
#include "src/core/lib/channel/status_util.h"
#include "src/core/lib/debug/trace.h"
#include "src/core/lib/experiments/experiments.h"
#include "src/core/lib/iomgr/exec_ctx.h"
@ -81,11 +79,13 @@
#include "src/core/lib/promise/poll.h"
#include "src/core/lib/promise/promise.h"
#include "src/core/lib/promise/try_seq.h"
#include "src/core/lib/security/credentials/credentials.h"
#include "src/core/lib/slice/slice.h"
#include "src/core/lib/slice/slice_internal.h"
#include "src/core/lib/surface/call.h"
#include "src/core/lib/transport/connectivity_state.h"
#include "src/core/lib/transport/error_utils.h"
#include "src/core/lib/transport/metadata_batch.h"
#include "src/core/load_balancing/backend_metric_parser.h"
#include "src/core/load_balancing/child_policy_handler.h"
#include "src/core/load_balancing/lb_policy_registry.h"
@ -268,6 +268,7 @@ class ClientChannelFilter::FilterBasedCallData final
static void RecvTrailingMetadataReadyForConfigSelectorCommitCallback(
void* arg, grpc_error_handle error);
grpc_slice path_; // Request path.
gpr_cycle_counter call_start_time_;
Timestamp deadline_;
@ -397,6 +398,7 @@ class DynamicTerminationFilter::CallData final {
auto* chand = static_cast<DynamicTerminationFilter*>(elem->channel_data);
ClientChannelFilter* client_channel = chand->chand_;
grpc_call_element_args args = {calld->owning_call_, nullptr,
calld->path_,
/*start_time=*/0, calld->deadline_,
calld->arena_, calld->call_combiner_};
auto* service_config_call_data = GetServiceConfigCallData(calld->arena_);
@ -411,11 +413,15 @@ class DynamicTerminationFilter::CallData final {
private:
explicit CallData(const grpc_call_element_args& args)
: deadline_(args.deadline),
: path_(CSliceRef(args.path)),
deadline_(args.deadline),
arena_(args.arena),
owning_call_(args.call_stack),
call_combiner_(args.call_combiner) {}
~CallData() { CSliceUnref(path_); }
grpc_slice path_; // Request path.
Timestamp deadline_;
Arena* arena_;
grpc_call_stack* owning_call_;
@ -501,7 +507,7 @@ class ClientChannelFilter::SubchannelWrapper final
if (subchannel_node != nullptr) {
auto it = chand_->subchannel_refcount_map_.find(subchannel_.get());
if (it == chand_->subchannel_refcount_map_.end()) {
subchannel_node->AddParent(chand_->channelz_node_);
chand_->channelz_node_->AddChildSubchannel(subchannel_node->uuid());
it = chand_->subchannel_refcount_map_.emplace(subchannel_.get(), 0)
.first;
}
@ -533,7 +539,8 @@ class ClientChannelFilter::SubchannelWrapper final
CHECK(it != chand_->subchannel_refcount_map_.end());
--it->second;
if (it->second == 0) {
subchannel_node->RemoveParent(chand_->channelz_node_);
chand_->channelz_node_->RemoveChildSubchannel(
subchannel_node->uuid());
chand_->subchannel_refcount_map_.erase(it);
}
}
@ -616,18 +623,20 @@ class ClientChannelFilter::SubchannelWrapper final
parent_.reset(DEBUG_LOCATION, "WatcherWrapper");
}
void OnConnectivityStateChange(grpc_connectivity_state state,
const absl::Status& status) override {
void OnConnectivityStateChange(
RefCountedPtr<ConnectivityStateWatcherInterface> self,
grpc_connectivity_state state, const absl::Status& status) override {
GRPC_TRACE_LOG(client_channel, INFO)
<< "chand=" << parent_->chand_
<< ": connectivity change for subchannel wrapper " << parent_.get()
<< " subchannel " << parent_->subchannel_.get()
<< "hopping into work_serializer";
auto self = RefAsSubclass<WatcherWrapper>();
self.release(); // Held by callback.
parent_->chand_->work_serializer_->Run(
[self, state, status]() ABSL_EXCLUSIVE_LOCKS_REQUIRED(
*self->parent_->chand_->work_serializer_) {
self->ApplyUpdateInControlPlaneWorkSerializer(state, status);
[this, state, status]() ABSL_EXCLUSIVE_LOCKS_REQUIRED(
*parent_->chand_->work_serializer_) {
ApplyUpdateInControlPlaneWorkSerializer(state, status);
Unref();
});
}
@ -977,7 +986,7 @@ class ClientChannelFilter::ClientChannelControlHelper final
}
GlobalStatsPluginRegistry::StatsPluginGroup& GetStatsPluginGroup() override {
return **chand_->owning_stack_->stats_plugin_group;
return *chand_->owning_stack_->stats_plugin_group;
}
void AddTraceEvent(TraceSeverity severity, absl::string_view message) override
@ -1026,11 +1035,7 @@ RefCountedPtr<SubchannelPoolInterface> GetSubchannelPool(
if (args.GetBool(GRPC_ARG_USE_LOCAL_SUBCHANNEL_POOL).value_or(false)) {
return MakeRefCounted<LocalSubchannelPool>();
}
if (IsShardGlobalConnectionPoolEnabled()) {
return GlobalSubchannelPool::instance();
} else {
return LegacyGlobalSubchannelPool::instance();
}
return GlobalSubchannelPool::instance();
}
} // namespace
@ -1552,13 +1557,11 @@ void ClientChannelFilter::UpdateStateLocked(grpc_connectivity_state state,
state_tracker_.SetState(state, status, reason);
if (channelz_node_ != nullptr) {
channelz_node_->SetConnectivityState(state);
std::string trace =
channelz::ChannelNode::GetChannelConnectivityStateChangeString(state);
if (!status.ok() || state == GRPC_CHANNEL_TRANSIENT_FAILURE) {
absl::StrAppend(&trace, " status:", status.ToString());
}
channelz_node_->AddTraceEvent(channelz::ChannelTrace::Severity::Info,
grpc_slice_from_cpp_string(std::move(trace)));
channelz_node_->AddTraceEvent(
channelz::ChannelTrace::Severity::Info,
grpc_slice_from_static_string(
channelz::ChannelNode::GetChannelConnectivityStateChangeString(
state)));
}
}
@ -1925,7 +1928,8 @@ bool ClientChannelFilter::CallData::CheckResolutionLocked(
ClientChannelFilter::FilterBasedCallData::FilterBasedCallData(
grpc_call_element* elem, const grpc_call_element_args& args)
: call_start_time_(args.start_time),
: path_(CSliceRef(args.path)),
call_start_time_(args.start_time),
deadline_(args.deadline),
arena_(args.arena),
elem_(elem),
@ -1936,6 +1940,7 @@ ClientChannelFilter::FilterBasedCallData::FilterBasedCallData(
}
ClientChannelFilter::FilterBasedCallData::~FilterBasedCallData() {
CSliceUnref(path_);
// Make sure there are no remaining pending batches.
for (size_t i = 0; i < GPR_ARRAY_SIZE(pending_batches_); ++i) {
CHECK_EQ(pending_batches_[i], nullptr);
@ -2247,9 +2252,9 @@ void ClientChannelFilter::FilterBasedCallData::RetryCheckResolutionLocked() {
}
void ClientChannelFilter::FilterBasedCallData::CreateDynamicCall() {
DynamicFilters::Call::Args args = {dynamic_filters(), pollent_,
call_start_time_, deadline_,
arena(), call_combiner()};
DynamicFilters::Call::Args args = {dynamic_filters(), pollent_, path_,
call_start_time_, deadline_, arena(),
call_combiner()};
grpc_error_handle error;
DynamicFilters* channel_stack = args.channel_stack.get();
GRPC_TRACE_LOG(client_channel_call, INFO)
@ -2431,7 +2436,9 @@ void ClientChannelFilter::LoadBalancedCall::RecordCallCompletion(
void ClientChannelFilter::LoadBalancedCall::RecordLatency() {
// Compute latency and report it to the tracer.
if (call_attempt_tracer() != nullptr) {
call_attempt_tracer()->RecordEnd();
gpr_timespec latency =
gpr_cycle_counter_sub(gpr_get_cycle_counter(), lb_call_start_time_);
call_attempt_tracer()->RecordEnd(latency);
}
}
@ -3035,8 +3042,10 @@ void ClientChannelFilter::FilterBasedLoadBalancedCall::RetryPickLocked() {
}
void ClientChannelFilter::FilterBasedLoadBalancedCall::CreateSubchannelCall() {
Slice* path = send_initial_metadata()->get_pointer(HttpPathMetadata());
CHECK_NE(path, nullptr);
SubchannelCall::Args call_args = {
connected_subchannel()->Ref(), pollent_, /*start_time=*/0,
connected_subchannel()->Ref(), pollent_, path->Ref(), /*start_time=*/0,
arena()->GetContext<Call>()->deadline(),
// TODO(roth): When we implement hedging support, we will probably
// need to use a separate call arena for each subchannel call.

View File

@ -34,7 +34,6 @@
#include "absl/functional/any_invocable.h"
#include "absl/status/status.h"
#include "absl/strings/string_view.h"
#include "src/core/call/metadata_batch.h"
#include "src/core/channelz/channelz.h"
#include "src/core/client_channel/client_channel_args.h"
#include "src/core/client_channel/client_channel_factory.h"
@ -54,6 +53,7 @@
#include "src/core/lib/resource_quota/arena.h"
#include "src/core/lib/slice/slice.h"
#include "src/core/lib/transport/connectivity_state.h"
#include "src/core/lib/transport/metadata_batch.h"
#include "src/core/lib/transport/transport.h"
#include "src/core/load_balancing/backend_metric_data.h"
#include "src/core/load_balancing/lb_policy.h"
@ -438,6 +438,8 @@ class ClientChannelFilter::LoadBalancedCall
absl::AnyInvocable<void()> on_commit_;
gpr_cycle_counter lb_call_start_time_ = gpr_get_cycle_counter();
RefCountedPtr<ConnectedSubchannel> connected_subchannel_;
const BackendMetricData* backend_metric_data_ = nullptr;
std::unique_ptr<LoadBalancingPolicy::SubchannelCallTrackerInterface>

View File

@ -23,8 +23,8 @@
#include "absl/functional/any_invocable.h"
#include "absl/log/check.h"
#include "src/core/call/call_destination.h"
#include "src/core/lib/resource_quota/arena.h"
#include "src/core/lib/transport/call_destination.h"
#include "src/core/load_balancing/lb_policy.h"
#include "src/core/service_config/service_config_call_data.h"
#include "src/core/telemetry/call_tracer.h"

View File

@ -27,12 +27,12 @@
#include "absl/log/check.h"
#include "absl/status/status.h"
#include "absl/strings/string_view.h"
#include "src/core/call/interception_chain.h"
#include "src/core/call/metadata_batch.h"
#include "src/core/client_channel/client_channel_internal.h"
#include "src/core/lib/channel/channel_fwd.h"
#include "src/core/lib/resource_quota/arena.h"
#include "src/core/lib/slice/slice.h"
#include "src/core/lib/transport/interception_chain.h"
#include "src/core/lib/transport/metadata_batch.h"
#include "src/core/service_config/service_config.h"
#include "src/core/util/ref_counted.h"
#include "src/core/util/ref_counted_ptr.h"

View File

@ -53,6 +53,8 @@ class SubchannelConnector : public InternallyRefCounted<SubchannelConnector> {
Transport* transport = nullptr;
// Channel args to be passed to filters.
ChannelArgs channel_args;
// Channelz socket node of the connected transport, if any.
RefCountedPtr<channelz::SocketNode> socket_node;
void Reset() {
if (transport != nullptr) {
@ -60,6 +62,7 @@ class SubchannelConnector : public InternallyRefCounted<SubchannelConnector> {
transport = nullptr;
}
channel_args = ChannelArgs();
socket_node.reset();
}
};

View File

@ -14,11 +14,11 @@
#include "src/core/client_channel/direct_channel.h"
#include "src/core/call/client_call.h"
#include "src/core/call/interception_chain.h"
#include "src/core/config/core_configuration.h"
#include "src/core/lib/event_engine/event_engine_context.h"
#include "src/core/lib/surface/channel_stack_type.h"
#include "src/core/lib/surface/client_call.h"
#include "src/core/lib/transport/interception_chain.h"
#include "src/core/util/orphanable.h"
namespace grpc_core {

View File

@ -55,6 +55,7 @@ DynamicFilters::Call::Call(Args args, grpc_error_handle* error)
const grpc_call_element_args call_args = {
call_stack, // call_stack
nullptr, // server_transport_data
args.path, // path
args.start_time, // start_time
args.deadline, // deadline
args.arena, // arena

View File

@ -49,6 +49,7 @@ class DynamicFilters final : public RefCounted<DynamicFilters> {
struct Args {
RefCountedPtr<DynamicFilters> channel_stack;
grpc_polling_entity* pollent;
grpc_slice path;
gpr_cycle_counter start_time;
Timestamp deadline;
Arena* arena;

View File

@ -26,13 +26,12 @@
namespace grpc_core {
RefCountedPtr<LegacyGlobalSubchannelPool>
LegacyGlobalSubchannelPool::instance() {
static LegacyGlobalSubchannelPool* p = new LegacyGlobalSubchannelPool();
return p->RefAsSubclass<LegacyGlobalSubchannelPool>();
RefCountedPtr<GlobalSubchannelPool> GlobalSubchannelPool::instance() {
static GlobalSubchannelPool* p = new GlobalSubchannelPool();
return p->RefAsSubclass<GlobalSubchannelPool>();
}
RefCountedPtr<Subchannel> LegacyGlobalSubchannelPool::RegisterSubchannel(
RefCountedPtr<Subchannel> GlobalSubchannelPool::RegisterSubchannel(
const SubchannelKey& key, RefCountedPtr<Subchannel> constructed) {
MutexLock lock(&mu_);
auto it = subchannel_map_.find(key);
@ -44,8 +43,8 @@ RefCountedPtr<Subchannel> LegacyGlobalSubchannelPool::RegisterSubchannel(
return constructed;
}
void LegacyGlobalSubchannelPool::UnregisterSubchannel(const SubchannelKey& key,
Subchannel* subchannel) {
void GlobalSubchannelPool::UnregisterSubchannel(const SubchannelKey& key,
Subchannel* subchannel) {
MutexLock lock(&mu_);
auto it = subchannel_map_.find(key);
// delete only if key hasn't been re-registered to a different subchannel
@ -55,7 +54,7 @@ void LegacyGlobalSubchannelPool::UnregisterSubchannel(const SubchannelKey& key,
}
}
RefCountedPtr<Subchannel> LegacyGlobalSubchannelPool::FindSubchannel(
RefCountedPtr<Subchannel> GlobalSubchannelPool::FindSubchannel(
const SubchannelKey& key) {
MutexLock lock(&mu_);
auto it = subchannel_map_.find(key);
@ -63,64 +62,4 @@ RefCountedPtr<Subchannel> LegacyGlobalSubchannelPool::FindSubchannel(
return it->second->RefIfNonZero();
}
RefCountedPtr<GlobalSubchannelPool> GlobalSubchannelPool::instance() {
static GlobalSubchannelPool* p = new GlobalSubchannelPool();
return p->RefAsSubclass<GlobalSubchannelPool>();
}
RefCountedPtr<Subchannel> GlobalSubchannelPool::RegisterSubchannel(
const SubchannelKey& key, RefCountedPtr<Subchannel> constructed) {
auto shard_index = ShardIndex(key);
auto& write_shard = write_shards_[shard_index];
auto& read_shard = read_shards_[shard_index];
SubchannelMap old_map1;
SubchannelMap old_map2;
MutexLock lock(&write_shard.mu);
auto* existing = write_shard.map.Lookup(key);
if (existing != nullptr) return (*existing)->RefIfNonZero();
old_map1 = std::exchange(write_shard.map,
write_shard.map.Add(key, constructed->WeakRef()));
MutexLock lock_read(&read_shard.mu);
old_map2 = std::exchange(read_shard.map, write_shard.map);
return constructed;
}
void GlobalSubchannelPool::UnregisterSubchannel(const SubchannelKey& key,
Subchannel* subchannel) {
auto shard_index = ShardIndex(key);
auto& write_shard = write_shards_[shard_index];
auto& read_shard = read_shards_[shard_index];
SubchannelMap old_map1;
SubchannelMap old_map2;
MutexLock lock(&write_shard.mu);
auto* existing = write_shard.map.Lookup(key);
// delete only if key hasn't been re-registered to a different subchannel
// between strong-unreffing and unregistration of subchannel.
if (existing == nullptr || existing->get() != subchannel) return;
old_map1 = std::exchange(write_shard.map, write_shard.map.Remove(key));
MutexLock lock_read(&read_shard.mu);
old_map2 = std::exchange(read_shard.map, write_shard.map);
}
RefCountedPtr<Subchannel> GlobalSubchannelPool::FindSubchannel(
const SubchannelKey& key) {
auto shard_index = ShardIndex(key);
auto& read_shard = read_shards_[shard_index];
read_shard.mu.Lock();
auto map = read_shard.map;
read_shard.mu.Unlock();
auto* subchannel = map.Lookup(key);
if (subchannel == nullptr) return nullptr;
return (*subchannel)->RefIfNonZero();
}
size_t GlobalSubchannelPool::ShardIndex(const SubchannelKey& key) {
absl::string_view addr(key.address().addr, key.address().len);
return absl::HashOf(addr) % kShards;
}
GlobalSubchannelPool::GlobalSubchannelPool() = default;
GlobalSubchannelPool::~GlobalSubchannelPool() = default;
} // namespace grpc_core

View File

@ -32,10 +32,10 @@ namespace grpc_core {
// The global subchannel pool. It shares subchannels among channels. There
// should be only one instance of this class.
class LegacyGlobalSubchannelPool final : public SubchannelPoolInterface {
class GlobalSubchannelPool final : public SubchannelPoolInterface {
public:
// Gets the singleton instance.
static RefCountedPtr<LegacyGlobalSubchannelPool> instance();
static RefCountedPtr<GlobalSubchannelPool> instance();
// Implements interface methods.
RefCountedPtr<Subchannel> RegisterSubchannel(
@ -48,8 +48,8 @@ class LegacyGlobalSubchannelPool final : public SubchannelPoolInterface {
ABSL_LOCKS_EXCLUDED(mu_);
private:
LegacyGlobalSubchannelPool() {}
~LegacyGlobalSubchannelPool() override {}
GlobalSubchannelPool() {}
~GlobalSubchannelPool() override {}
// A map from subchannel key to subchannel.
std::map<SubchannelKey, Subchannel*> subchannel_map_ ABSL_GUARDED_BY(mu_);
@ -57,39 +57,6 @@ class LegacyGlobalSubchannelPool final : public SubchannelPoolInterface {
Mutex mu_;
};
// The global subchannel pool. It shares subchannels among channels. There
// should be only one instance of this class.
class GlobalSubchannelPool final : public SubchannelPoolInterface {
public:
// Gets the singleton instance.
static RefCountedPtr<GlobalSubchannelPool> instance();
// Implements interface methods.
RefCountedPtr<Subchannel> RegisterSubchannel(
const SubchannelKey& key, RefCountedPtr<Subchannel> constructed) override;
void UnregisterSubchannel(const SubchannelKey& key,
Subchannel* subchannel) override;
RefCountedPtr<Subchannel> FindSubchannel(const SubchannelKey& key) override;
private:
GlobalSubchannelPool();
~GlobalSubchannelPool() override;
static const size_t kShards = 127;
using SubchannelMap = AVL<SubchannelKey, WeakRefCountedPtr<Subchannel>>;
struct LockedMap {
Mutex mu;
SubchannelMap map ABSL_GUARDED_BY(mu);
};
using ShardedMap = std::array<LockedMap, kShards>;
static size_t ShardIndex(const SubchannelKey& key);
ShardedMap write_shards_;
ShardedMap read_shards_;
};
} // namespace grpc_core
#endif // GRPC_SRC_CORE_CLIENT_CHANNEL_GLOBAL_SUBCHANNEL_POOL_H

View File

@ -22,7 +22,7 @@
#include <vector>
#include "absl/strings/string_view.h"
#include "src/core/call/metadata_batch.h"
#include "src/core/lib/transport/metadata_batch.h"
#include "src/core/load_balancing/lb_policy.h"
namespace grpc_core {

View File

@ -15,12 +15,12 @@
#include "src/core/client_channel/load_balanced_call_destination.h"
#include "absl/log/log.h"
#include "src/core/call/status_util.h"
#include "src/core/client_channel/client_channel.h"
#include "src/core/client_channel/client_channel_internal.h"
#include "src/core/client_channel/lb_metadata.h"
#include "src/core/client_channel/subchannel.h"
#include "src/core/config/core_configuration.h"
#include "src/core/lib/channel/status_util.h"
#include "src/core/lib/promise/loop.h"
#include "src/core/telemetry/call_tracer.h"

View File

@ -16,9 +16,9 @@
#define GRPC_SRC_CORE_CLIENT_CHANNEL_LOAD_BALANCED_CALL_DESTINATION_H
#include "absl/functional/any_invocable.h"
#include "src/core/call/call_destination.h"
#include "src/core/client_channel/client_channel.h"
#include "src/core/lib/promise/context.h"
#include "src/core/lib/transport/call_destination.h"
#include "src/core/load_balancing/lb_policy.h"
namespace grpc_core {

View File

@ -24,12 +24,11 @@
#include "absl/log/log.h"
#include "absl/status/status.h"
#include "absl/strings/str_cat.h"
#include "src/core/call/metadata_batch.h"
#include "src/core/call/status_util.h"
#include "src/core/client_channel/client_channel_internal.h"
#include "src/core/client_channel/retry_service_config.h"
#include "src/core/client_channel/retry_throttle.h"
#include "src/core/lib/channel/channel_stack.h"
#include "src/core/lib/channel/status_util.h"
#include "src/core/lib/debug/trace.h"
#include "src/core/lib/iomgr/call_combiner.h"
#include "src/core/lib/iomgr/closure.h"
@ -40,6 +39,7 @@
#include "src/core/lib/slice/slice.h"
#include "src/core/lib/slice/slice_buffer.h"
#include "src/core/lib/transport/error_utils.h"
#include "src/core/lib/transport/metadata_batch.h"
#include "src/core/lib/transport/transport.h"
#include "src/core/util/backoff.h"
#include "src/core/util/construct_destruct.h"
@ -53,8 +53,6 @@
namespace grpc_core {
using TaskHandle = grpc_event_engine::experimental::EventEngine::TaskHandle;
//
// RetryFilter::LegacyCallData::CallStackDestructionBarrier
//
@ -222,7 +220,7 @@ void RetryFilter::LegacyCallData::CallAttempt::MaybeSwitchToFastPath() {
// If we've already switched to fast path, there's nothing to do here.
if (calld_->committed_call_ != nullptr) return;
// If the perAttemptRecvTimeout timer is pending, we can't switch yet.
if (per_attempt_recv_timer_handle_ != TaskHandle::kInvalid) return;
if (per_attempt_recv_timer_handle_.has_value()) return;
// If there are still send ops to replay, we can't switch yet.
if (HaveSendOpsToReplay()) return;
// If we started an internal batch for recv_trailing_metadata but have not
@ -645,33 +643,31 @@ void RetryFilter::LegacyCallData::CallAttempt::OnPerAttemptRecvTimerLocked(
<< "chand=" << calld->chand_ << " calld=" << calld
<< " attempt=" << call_attempt
<< ": perAttemptRecvTimeout timer fired: error=" << StatusToString(error)
<< ", per_attempt_recv_timer_handle_ is valid ="
<< (call_attempt->per_attempt_recv_timer_handle_ != TaskHandle::kInvalid);
<< ", per_attempt_recv_timer_handle_.has_value()="
<< call_attempt->per_attempt_recv_timer_handle_.has_value();
CallCombinerClosureList closures;
if (call_attempt->per_attempt_recv_timer_handle_ != TaskHandle::kInvalid) {
call_attempt->per_attempt_recv_timer_handle_ = TaskHandle::kInvalid;
// Cancel this attempt.
// TODO(roth): When implementing hedging, we should not cancel the
// current attempt.
call_attempt->MaybeAddBatchForCancelOp(
grpc_error_set_int(
GRPC_ERROR_CREATE("retry perAttemptRecvTimeout exceeded"),
StatusIntProperty::kRpcStatus, GRPC_STATUS_CANCELLED),
&closures);
// Check whether we should retry.
if (call_attempt->ShouldRetry(/*status=*/std::nullopt,
/*server_pushback_ms=*/std::nullopt)) {
// Mark current attempt as abandoned.
call_attempt->Abandon();
// We are retrying. Start backoff timer.
calld->StartRetryTimer(/*server_pushback=*/std::nullopt);
} else {
// Not retrying, so commit the call.
calld->RetryCommit(call_attempt);
// If retry state is no longer needed, switch to fast path for
// subsequent batches.
call_attempt->MaybeSwitchToFastPath();
}
call_attempt->per_attempt_recv_timer_handle_.reset();
// Cancel this attempt.
// TODO(roth): When implementing hedging, we should not cancel the
// current attempt.
call_attempt->MaybeAddBatchForCancelOp(
grpc_error_set_int(
GRPC_ERROR_CREATE("retry perAttemptRecvTimeout exceeded"),
StatusIntProperty::kRpcStatus, GRPC_STATUS_CANCELLED),
&closures);
// Check whether we should retry.
if (call_attempt->ShouldRetry(/*status=*/std::nullopt,
/*server_pushback_ms=*/std::nullopt)) {
// Mark current attempt as abandoned.
call_attempt->Abandon();
// We are retrying. Start backoff timer.
calld->StartRetryTimer(/*server_pushback=*/std::nullopt);
} else {
// Not retrying, so commit the call.
calld->RetryCommit(call_attempt);
// If retry state is no longer needed, switch to fast path for
// subsequent batches.
call_attempt->MaybeSwitchToFastPath();
}
closures.RunClosures(calld->call_combiner_);
call_attempt->Unref(DEBUG_LOCATION, "OnPerAttemptRecvTimer");
@ -680,16 +676,16 @@ void RetryFilter::LegacyCallData::CallAttempt::OnPerAttemptRecvTimerLocked(
void RetryFilter::LegacyCallData::CallAttempt::
MaybeCancelPerAttemptRecvTimer() {
if (per_attempt_recv_timer_handle_ != TaskHandle::kInvalid) {
if (per_attempt_recv_timer_handle_.has_value()) {
GRPC_TRACE_LOG(retry, INFO)
<< "chand=" << calld_->chand_ << " calld=" << calld_
<< " attempt=" << this << ": cancelling perAttemptRecvTimeout timer";
if (calld_->chand_->event_engine()->Cancel(
per_attempt_recv_timer_handle_)) {
*per_attempt_recv_timer_handle_)) {
Unref(DEBUG_LOCATION, "OnPerAttemptRecvTimer");
GRPC_CALL_STACK_UNREF(calld_->owning_call_, "OnPerAttemptRecvTimer");
}
per_attempt_recv_timer_handle_ = TaskHandle::kInvalid;
per_attempt_recv_timer_handle_.reset();
}
}
@ -1485,6 +1481,7 @@ RetryFilter::LegacyCallData::LegacyCallData(RetryFilter* chand,
.set_max_backoff(retry_policy_ == nullptr
? Duration::Zero()
: retry_policy_->max_backoff())),
path_(CSliceRef(args.path)),
deadline_(args.deadline),
arena_(args.arena),
owning_call_(args.call_stack),
@ -1500,6 +1497,7 @@ RetryFilter::LegacyCallData::LegacyCallData(RetryFilter* chand,
RetryFilter::LegacyCallData::~LegacyCallData() {
FreeAllCachedSendOpData();
CSliceUnref(path_);
// Make sure there are no remaining pending batches.
for (size_t i = 0; i < GPR_ARRAY_SIZE(pending_batches_); ++i) {
CHECK_EQ(pending_batches_[i].batch, nullptr);
@ -1552,13 +1550,13 @@ void RetryFilter::LegacyCallData::StartTransportStreamOpBatch(
return;
}
// Cancel retry timer if needed.
if (retry_timer_handle_ != TaskHandle::kInvalid) {
if (retry_timer_handle_.has_value()) {
GRPC_TRACE_LOG(retry, INFO) << "chand=" << chand_ << " calld=" << this
<< ": cancelling retry timer";
if (chand_->event_engine()->Cancel(retry_timer_handle_)) {
if (chand_->event_engine()->Cancel(*retry_timer_handle_)) {
GRPC_CALL_STACK_UNREF(owning_call_, "OnRetryTimer");
}
retry_timer_handle_ = TaskHandle::kInvalid;
retry_timer_handle_.reset();
FreeAllCachedSendOpData();
}
// We have no call attempt, so there's nowhere to send the cancellation
@ -1572,7 +1570,7 @@ void RetryFilter::LegacyCallData::StartTransportStreamOpBatch(
PendingBatch* pending = PendingBatchesAdd(batch);
// If the timer is pending, yield the call combiner and wait for it to
// run, since we don't want to start another call attempt until it does.
if (retry_timer_handle_ != TaskHandle::kInvalid) {
if (retry_timer_handle_.has_value()) {
GRPC_CALL_COMBINER_STOP(call_combiner_,
"added pending batch while retry timer pending");
return;
@ -1629,9 +1627,9 @@ void RetryFilter::LegacyCallData::StartTransportStreamOpBatch(
OrphanablePtr<ClientChannelFilter::FilterBasedLoadBalancedCall>
RetryFilter::LegacyCallData::CreateLoadBalancedCall(
absl::AnyInvocable<void()> on_commit, bool is_transparent_retry) {
grpc_call_element_args args = {owning_call_, nullptr,
/*start_time=*/0, deadline_,
arena_, call_combiner_};
grpc_call_element_args args = {owning_call_, nullptr, path_,
/*start_time=*/0, deadline_, arena_,
call_combiner_};
return chand_->client_channel()->CreateLoadBalancedCall(
args, pollent_,
// This callback holds a ref to the CallStackDestructionBarrier
@ -1914,8 +1912,8 @@ void RetryFilter::LegacyCallData::OnRetryTimer() {
void RetryFilter::LegacyCallData::OnRetryTimerLocked(
void* arg, grpc_error_handle /*error*/) {
auto* calld = static_cast<RetryFilter::LegacyCallData*>(arg);
if (calld->retry_timer_handle_ != TaskHandle::kInvalid) {
calld->retry_timer_handle_ = TaskHandle::kInvalid;
if (calld->retry_timer_handle_.has_value()) {
calld->retry_timer_handle_.reset();
calld->CreateCallAttempt(/*is_transparent_retry=*/false);
}
GRPC_CALL_STACK_UNREF(calld->owning_call_, "OnRetryTimer");

View File

@ -27,7 +27,6 @@
#include "absl/container/inlined_vector.h"
#include "absl/functional/any_invocable.h"
#include "src/core/call/metadata_batch.h"
#include "src/core/client_channel/client_channel_filter.h"
#include "src/core/client_channel/retry_filter.h"
#include "src/core/client_channel/retry_service_config.h"
@ -40,6 +39,7 @@
#include "src/core/lib/iomgr/polling_entity.h"
#include "src/core/lib/resource_quota/arena.h"
#include "src/core/lib/slice/slice_buffer.h"
#include "src/core/lib/transport/metadata_batch.h"
#include "src/core/lib/transport/transport.h"
#include "src/core/util/backoff.h"
#include "src/core/util/debug_location.h"
@ -256,9 +256,8 @@ class RetryFilter::LegacyCallData final {
bool lb_call_committed_ = false;
grpc_closure on_per_attempt_recv_timer_;
grpc_event_engine::experimental::EventEngine::TaskHandle
per_attempt_recv_timer_handle_ =
grpc_event_engine::experimental::EventEngine::TaskHandle::kInvalid;
std::optional<grpc_event_engine::experimental::EventEngine::TaskHandle>
per_attempt_recv_timer_handle_;
// BatchData.batch.payload points to this.
grpc_transport_stream_op_batch_payload batch_payload_;
@ -374,6 +373,7 @@ class RetryFilter::LegacyCallData final {
const internal::RetryMethodConfig* retry_policy_ = nullptr;
BackOff retry_backoff_;
grpc_slice path_; // Request path.
Timestamp deadline_;
Arena* arena_;
grpc_call_stack* owning_call_;
@ -410,8 +410,8 @@ class RetryFilter::LegacyCallData final {
bool retry_codepath_started_ : 1;
bool sent_transparent_retry_not_seen_by_server_ : 1;
int num_attempts_completed_ = 0;
grpc_event_engine::experimental::EventEngine::TaskHandle retry_timer_handle_ =
grpc_event_engine::experimental::EventEngine::TaskHandle::kInvalid;
std::optional<grpc_event_engine::experimental::EventEngine::TaskHandle>
retry_timer_handle_;
grpc_closure retry_closure_;
// Cached data for retrying send ops.

View File

@ -15,12 +15,12 @@
#ifndef GRPC_SRC_CORE_CLIENT_CHANNEL_RETRY_INTERCEPTOR_H
#define GRPC_SRC_CORE_CLIENT_CHANNEL_RETRY_INTERCEPTOR_H
#include "src/core/call/interception_chain.h"
#include "src/core/call/request_buffer.h"
#include "src/core/client_channel/client_channel_args.h"
#include "src/core/client_channel/retry_service_config.h"
#include "src/core/client_channel/retry_throttle.h"
#include "src/core/filter/filter_args.h"
#include "src/core/lib/transport/interception_chain.h"
#include "src/core/util/backoff.h"
namespace grpc_core {

View File

@ -30,9 +30,9 @@
#include "absl/log/log.h"
#include "absl/strings/numbers.h"
#include "absl/strings/str_cat.h"
#include "src/core/call/status_util.h"
#include "src/core/config/core_configuration.h"
#include "src/core/lib/channel/channel_args.h"
#include "src/core/lib/channel/status_util.h"
#include "src/core/util/json/json_channel_args.h"
// As per the retry design, we do not allow more than 5 retry attempts.

View File

@ -25,9 +25,9 @@
#include <optional>
#include "absl/strings/string_view.h"
#include "src/core/call/status_util.h"
#include "src/core/config/core_configuration.h"
#include "src/core/lib/channel/channel_args.h"
#include "src/core/lib/channel/status_util.h"
#include "src/core/service_config/service_config_parser.h"
#include "src/core/util/json/json.h"
#include "src/core/util/json/json_args.h"

View File

@ -49,12 +49,32 @@ T ClampedAdd(std::atomic<T>& value, T delta, T min, T max) {
// ServerRetryThrottleData
//
ServerRetryThrottleData::ServerRetryThrottleData(uintptr_t max_milli_tokens,
uintptr_t milli_token_ratio,
uintptr_t milli_tokens)
ServerRetryThrottleData::ServerRetryThrottleData(
uintptr_t max_milli_tokens, uintptr_t milli_token_ratio,
ServerRetryThrottleData* old_throttle_data)
: max_milli_tokens_(max_milli_tokens),
milli_token_ratio_(milli_token_ratio),
milli_tokens_(milli_tokens) {}
milli_token_ratio_(milli_token_ratio) {
uintptr_t initial_milli_tokens = max_milli_tokens;
// If there was a pre-existing entry for this server name, initialize
// the token count by scaling proportionately to the old data. This
// ensures that if we're already throttling retries on the old scale,
// we will start out doing the same thing on the new one.
if (old_throttle_data != nullptr) {
double token_fraction =
static_cast<double>(
old_throttle_data->milli_tokens_.load(std::memory_order_relaxed)) /
static_cast<double>(old_throttle_data->max_milli_tokens_);
initial_milli_tokens =
static_cast<uintptr_t>(token_fraction * max_milli_tokens);
}
milli_tokens_.store(initial_milli_tokens, std::memory_order_relaxed);
// If there was a pre-existing entry, mark it as stale and give it a
// pointer to the new entry, which is its replacement.
if (old_throttle_data != nullptr) {
Ref().release(); // Ref held by pre-existing entry.
old_throttle_data->replacement_.store(this, std::memory_order_release);
}
}
ServerRetryThrottleData::~ServerRetryThrottleData() {
ServerRetryThrottleData* replacement =
@ -64,11 +84,6 @@ ServerRetryThrottleData::~ServerRetryThrottleData() {
}
}
void ServerRetryThrottleData::SetReplacement(
RefCountedPtr<ServerRetryThrottleData> replacement) {
replacement_.store(replacement.release(), std::memory_order_release);
}
void ServerRetryThrottleData::GetReplacementThrottleDataIfNeeded(
ServerRetryThrottleData** throttle_data) {
while (true) {
@ -118,31 +133,20 @@ RefCountedPtr<ServerRetryThrottleData> ServerRetryThrottleMap::GetDataForServer(
const std::string& server_name, uintptr_t max_milli_tokens,
uintptr_t milli_token_ratio) {
MutexLock lock(&mu_);
auto& throttle_data = map_[server_name];
auto it = map_.find(server_name);
ServerRetryThrottleData* throttle_data =
it == map_.end() ? nullptr : it->second.get();
if (throttle_data == nullptr ||
throttle_data->max_milli_tokens() != max_milli_tokens ||
throttle_data->milli_token_ratio() != milli_token_ratio) {
// Entry not found, or found with old parameters. Create a new one.
auto old_throttle_data = std::move(throttle_data);
uintptr_t initial_milli_tokens = max_milli_tokens;
// If there was a pre-existing entry for this server name, initialize
// the token count by scaling proportionately to the old data. This
// ensures that if we're already throttling retries on the old scale,
// we will start out doing the same thing on the new one.
if (old_throttle_data != nullptr) {
double token_fraction =
static_cast<double>(old_throttle_data->milli_tokens()) /
static_cast<double>(old_throttle_data->max_milli_tokens());
initial_milli_tokens =
static_cast<uintptr_t>(token_fraction * max_milli_tokens);
}
throttle_data = MakeRefCounted<ServerRetryThrottleData>(
max_milli_tokens, milli_token_ratio, initial_milli_tokens);
if (old_throttle_data != nullptr) {
old_throttle_data->SetReplacement(throttle_data);
}
it = map_.emplace(server_name,
MakeRefCounted<ServerRetryThrottleData>(
max_milli_tokens, milli_token_ratio, throttle_data))
.first;
throttle_data = it->second.get();
}
return throttle_data;
return throttle_data->Ref();
}
} // namespace internal

View File

@ -34,14 +34,13 @@
namespace grpc_core {
namespace internal {
class ServerRetryThrottleMap;
/// Tracks retry throttling data for an individual server name.
class ServerRetryThrottleData final
: public RefCounted<ServerRetryThrottleData> {
public:
ServerRetryThrottleData(uintptr_t max_milli_tokens,
uintptr_t milli_token_ratio, uintptr_t milli_tokens);
uintptr_t milli_token_ratio,
ServerRetryThrottleData* old_throttle_data);
~ServerRetryThrottleData() override;
/// Records a failure. Returns true if it's okay to send a retry.
@ -52,15 +51,8 @@ class ServerRetryThrottleData final
uintptr_t max_milli_tokens() const { return max_milli_tokens_; }
uintptr_t milli_token_ratio() const { return milli_token_ratio_; }
intptr_t milli_tokens() const {
return milli_tokens_.load(std::memory_order_relaxed);
}
private:
friend ServerRetryThrottleMap;
void SetReplacement(RefCountedPtr<ServerRetryThrottleData> replacement);
void GetReplacementThrottleDataIfNeeded(
ServerRetryThrottleData** throttle_data);

View File

@ -35,7 +35,6 @@
#include "absl/strings/cord.h"
#include "absl/strings/str_cat.h"
#include "absl/strings/string_view.h"
#include "src/core/call/interception_chain.h"
#include "src/core/channelz/channel_trace.h"
#include "src/core/channelz/channelz.h"
#include "src/core/client_channel/client_channel_internal.h"
@ -58,6 +57,7 @@
#include "src/core/lib/surface/init_internally.h"
#include "src/core/lib/transport/connectivity_state.h"
#include "src/core/lib/transport/error_utils.h"
#include "src/core/lib/transport/interception_chain.h"
#include "src/core/lib/transport/transport.h"
#include "src/core/telemetry/stats.h"
#include "src/core/telemetry/stats_data.h"
@ -244,12 +244,13 @@ SubchannelCall::SubchannelCall(Args args, grpc_error_handle* error)
deadline_(args.deadline) {
grpc_call_stack* callstk = SUBCHANNEL_CALL_TO_CALL_STACK(this);
const grpc_call_element_args call_args = {
callstk, // call_stack
nullptr, // server_transport_data
args.start_time, // start_time
args.deadline, // deadline
args.arena, // arena
args.call_combiner // call_combiner
callstk, // call_stack
nullptr, // server_transport_data
args.path.c_slice(), // path
args.start_time, // start_time
args.deadline, // deadline
args.arena, // arena
args.call_combiner // call_combiner
};
*error = grpc_call_stack_init(connected_subchannel_->channel_stack(), 1,
SubchannelCall::Destroy, this, &call_args);
@ -452,8 +453,10 @@ void Subchannel::ConnectivityStateWatcherList::RemoveWatcherLocked(
void Subchannel::ConnectivityStateWatcherList::NotifyLocked(
grpc_connectivity_state state, const absl::Status& status) {
for (const auto& watcher : watchers_) {
subchannel_->work_serializer_.Run([watcher, state, status]() {
watcher->OnConnectivityStateChange(state, status);
subchannel_->work_serializer_.Run([watcher = watcher->Ref(), state,
status]() mutable {
auto* watcher_ptr = watcher.get();
watcher_ptr->OnConnectivityStateChange(std::move(watcher), state, status);
});
}
}
@ -549,8 +552,6 @@ Subchannel::Subchannel(SubchannelKey key,
channelz_node_->AddTraceEvent(
channelz::ChannelTrace::Severity::Info,
grpc_slice_from_static_string("subchannel created"));
channelz_node_->SetChannelArgs(args_);
args_ = args_.SetObject<channelz::BaseNode>(channelz_node_);
}
}
@ -612,8 +613,10 @@ void Subchannel::WatchConnectivityState(
grpc_pollset_set_add_pollset_set(pollset_set_, interested_parties);
}
work_serializer_.Run(
[watcher, state = state_, status = status_]() {
watcher->OnConnectivityStateChange(state, status);
[watcher = watcher->Ref(), state = state_, status = status_]() mutable {
auto* watcher_ptr = watcher.get();
watcher_ptr->OnConnectivityStateChange(std::move(watcher), state,
status);
},
DEBUG_LOCATION);
watcher_list_.AddWatcherLocked(std::move(watcher));
@ -790,7 +793,7 @@ void Subchannel::OnConnectingFinishedLocked(grpc_error_handle error) {
}
bool Subchannel::PublishTransportLocked() {
auto socket_node = connecting_result_.transport->GetSocketNode();
auto socket_node = std::move(connecting_result_.socket_node);
if (connecting_result_.transport->filter_stack_transport() != nullptr) {
// Construct channel stack.
// Builder takes ownership of transport.

View File

@ -29,7 +29,6 @@
#include "absl/base/thread_annotations.h"
#include "absl/container/flat_hash_set.h"
#include "absl/status/status.h"
#include "src/core/call/metadata_batch.h"
#include "src/core/client_channel/connector.h"
#include "src/core/client_channel/subchannel_pool_interface.h"
#include "src/core/lib/address_utils/sockaddr_utils.h"
@ -45,6 +44,7 @@
#include "src/core/lib/resource_quota/arena.h"
#include "src/core/lib/slice/slice.h"
#include "src/core/lib/transport/connectivity_state.h"
#include "src/core/lib/transport/metadata_batch.h"
#include "src/core/lib/transport/transport.h"
#include "src/core/util/backoff.h"
#include "src/core/util/debug_location.h"
@ -95,6 +95,7 @@ class SubchannelCall final {
struct Args {
RefCountedPtr<ConnectedSubchannel> connected_subchannel;
grpc_polling_entity* pollent;
Slice path;
gpr_cycle_counter start_time;
Timestamp deadline;
Arena* arena;
@ -168,8 +169,14 @@ class Subchannel final : public DualRefCounted<Subchannel> {
// Invoked whenever the subchannel's connectivity state changes.
// There will be only one invocation of this method on a given watcher
// instance at any given time.
virtual void OnConnectivityStateChange(grpc_connectivity_state state,
const absl::Status& status) = 0;
// A ref to the watcher is passed in here so that the implementation
// can unref it in the appropriate synchronization context (e.g.,
// inside a WorkSerializer).
// TODO(roth): Figure out a cleaner way to guarantee that the ref is
// released in the right context.
virtual void OnConnectivityStateChange(
RefCountedPtr<ConnectivityStateWatcherInterface> self,
grpc_connectivity_state state, const absl::Status& status) = 0;
virtual grpc_pollset_set* interested_parties() = 0;
};

View File

@ -38,12 +38,13 @@ SubchannelKey::SubchannelKey(const grpc_resolved_address& address,
const ChannelArgs& args)
: address_(address), args_(args) {}
int SubchannelKey::Compare(const SubchannelKey& other) const {
if (address_.len < other.address_.len) return -1;
if (address_.len > other.address_.len) return 1;
bool SubchannelKey::operator<(const SubchannelKey& other) const {
if (address_.len < other.address_.len) return true;
if (address_.len > other.address_.len) return false;
int r = memcmp(address_.addr, other.address_.addr, address_.len);
if (r != 0) return r;
return QsortCompare(args_, other.args_);
if (r < 0) return true;
if (r > 0) return false;
return args_ < other.args();
}
std::string SubchannelKey::ToString() const {

View File

@ -45,17 +45,7 @@ class SubchannelKey final {
SubchannelKey(SubchannelKey&& other) noexcept = default;
SubchannelKey& operator=(SubchannelKey&& other) noexcept = default;
bool operator<(const SubchannelKey& other) const {
return Compare(other) < 0;
}
bool operator>(const SubchannelKey& other) const {
return Compare(other) > 0;
}
bool operator==(const SubchannelKey& other) const {
return Compare(other) == 0;
}
int Compare(const SubchannelKey& other) const;
bool operator<(const SubchannelKey& other) const;
const grpc_resolved_address& address() const { return address_; }
const ChannelArgs& args() const { return args_; }

View File

@ -130,7 +130,7 @@ void SubchannelStreamClient::StartRetryTimerLocked() {
const Duration timeout = retry_backoff_.NextAttemptDelay();
if (GPR_UNLIKELY(tracer_ != nullptr)) {
LOG(INFO) << tracer_ << " " << this
<< ": SubchannelStreamClient call lost...";
<< ": SubchannelStreamClient health check call lost...";
if (timeout > Duration::Zero()) {
LOG(INFO) << tracer_ << " " << this << ": ... will retry in "
<< timeout.millis() << "ms.";
@ -139,10 +139,10 @@ void SubchannelStreamClient::StartRetryTimerLocked() {
}
}
retry_timer_handle_ = event_engine_->RunAfter(
timeout, [self = Ref(DEBUG_LOCATION, "retry_timer")]() mutable {
timeout, [self = Ref(DEBUG_LOCATION, "health_retry_timer")]() mutable {
ExecCtx exec_ctx;
self->OnRetryTimer();
self.reset(DEBUG_LOCATION, "retry_timer");
self.reset(DEBUG_LOCATION, "health_retry_timer");
});
}
@ -152,7 +152,7 @@ void SubchannelStreamClient::OnRetryTimer() {
call_state_ == nullptr) {
if (GPR_UNLIKELY(tracer_ != nullptr)) {
LOG(INFO) << tracer_ << " " << this
<< ": SubchannelStreamClient restarting call";
<< ": SubchannelStreamClient restarting health check call";
}
StartCallLocked();
}
@ -164,9 +164,9 @@ void SubchannelStreamClient::OnRetryTimer() {
//
SubchannelStreamClient::CallState::CallState(
RefCountedPtr<SubchannelStreamClient> subchannel_stream_client,
RefCountedPtr<SubchannelStreamClient> health_check_client,
grpc_pollset_set* interested_parties)
: subchannel_stream_client_(std::move(subchannel_stream_client)),
: subchannel_stream_client_(std::move(health_check_client)),
pollent_(grpc_polling_entity_create_from_pollset_set(interested_parties)),
arena_(subchannel_stream_client_->call_allocator_->MakeArena()) {}
@ -192,6 +192,7 @@ void SubchannelStreamClient::CallState::StartCallLocked() {
SubchannelCall::Args args = {
subchannel_stream_client_->connected_subchannel_,
&pollent_,
Slice::FromStaticString("/grpc.health.v1.Health/Watch"),
gpr_get_cycle_counter(), // start_time
Timestamp::InfFuture(), // deadline
arena_.get(),
@ -298,7 +299,7 @@ void SubchannelStreamClient::CallState::AfterCallStackDestruction(
void SubchannelStreamClient::CallState::OnCancelComplete(
void* arg, grpc_error_handle /*error*/) {
auto* self = static_cast<SubchannelStreamClient::CallState*>(arg);
GRPC_CALL_COMBINER_STOP(&self->call_combiner_, "cancel_batch");
GRPC_CALL_COMBINER_STOP(&self->call_combiner_, "health_cancel");
self->call_->Unref(DEBUG_LOCATION, "cancel");
}
@ -321,7 +322,7 @@ void SubchannelStreamClient::CallState::Cancel() {
GRPC_CALL_COMBINER_START(
&call_combiner_,
GRPC_CLOSURE_CREATE(StartCancel, this, grpc_schedule_on_exec_ctx),
absl::OkStatus(), "cancel_batch");
absl::OkStatus(), "health_cancel");
}
}
@ -405,22 +406,18 @@ void SubchannelStreamClient::CallState::RecvTrailingMetadataReady(
LOG(INFO) << self->subchannel_stream_client_->tracer_ << " "
<< self->subchannel_stream_client_.get()
<< ": SubchannelStreamClient CallState " << self
<< ": call failed with status " << status;
<< ": health watch failed with status " << status;
}
// Clean up.
self->recv_trailing_metadata_.Clear();
// Report call end.
// Note: We hold a ref to the SubchannelStreamClient here to ensure
// that it lives long enough for us to release the mutex, since the
// call to CallEndedLocked() may release the last ref.
auto subchannel_stream_client = self->subchannel_stream_client_->Ref();
MutexLock lock(&self->subchannel_stream_client_->mu_);
if (self->subchannel_stream_client_->event_handler_ != nullptr) {
self->subchannel_stream_client_->event_handler_
->RecvTrailingMetadataReadyLocked(self->subchannel_stream_client_.get(),
status);
}
// For status UNIMPLEMENTED, give up.
// For status UNIMPLEMENTED, give up and assume always healthy.
self->CallEndedLocked(/*retry=*/status != GRPC_STATUS_UNIMPLEMENTED);
}

View File

@ -30,7 +30,6 @@
#include "absl/base/thread_annotations.h"
#include "absl/status/status.h"
#include "absl/strings/string_view.h"
#include "src/core/call/metadata_batch.h"
#include "src/core/client_channel/subchannel.h"
#include "src/core/lib/iomgr/call_combiner.h"
#include "src/core/lib/iomgr/closure.h"
@ -41,6 +40,7 @@
#include "src/core/lib/resource_quota/memory_quota.h"
#include "src/core/lib/slice/slice.h"
#include "src/core/lib/slice/slice_buffer.h"
#include "src/core/lib/transport/metadata_batch.h"
#include "src/core/lib/transport/transport.h"
#include "src/core/util/backoff.h"
#include "src/core/util/orphanable.h"
@ -202,7 +202,7 @@ class SubchannelStreamClient final
Mutex mu_;
std::unique_ptr<CallEventHandler> event_handler_ ABSL_GUARDED_BY(mu_);
// The data associated with the current call. It holds a ref
// The data associated with the current health check call. It holds a ref
// to this SubchannelStreamClient object.
OrphanablePtr<CallState> call_state_ ABSL_GUARDED_BY(mu_);

View File

@ -76,11 +76,6 @@ ABSL_FLAG(absl::optional<bool>, grpc_cpp_experimental_disable_reflection, {},
"EXPERIMENTAL. Only respected when there is a dependency on "
":grpc++_reflection. If true, no reflection server will be "
"automatically added.");
ABSL_FLAG(
absl::optional<int32_t>, grpc_channelz_max_orphaned_nodes, {},
"EXPERIMENTAL: If non-zero, extend the lifetime of channelz nodes past the "
"underlying object lifetime, up to this many nodes. The value may be "
"adjusted slightly to account for implementation limits.");
namespace grpc_core {
@ -89,10 +84,6 @@ ConfigVars::ConfigVars(const Overrides& overrides)
LoadConfig(FLAGS_grpc_client_channel_backup_poll_interval_ms,
"GRPC_CLIENT_CHANNEL_BACKUP_POLL_INTERVAL_MS",
overrides.client_channel_backup_poll_interval_ms, 5000)),
channelz_max_orphaned_nodes_(
LoadConfig(FLAGS_grpc_channelz_max_orphaned_nodes,
"GRPC_CHANNELZ_MAX_ORPHANED_NODES",
overrides.channelz_max_orphaned_nodes, 0)),
enable_fork_support_(LoadConfig(
FLAGS_grpc_enable_fork_support, "GRPC_ENABLE_FORK_SUPPORT",
overrides.enable_fork_support, GRPC_ENABLE_FORK_SUPPORT_DEFAULT)),
@ -155,8 +146,7 @@ std::string ConfigVars::ToString() const {
", not_use_system_ssl_roots: ", NotUseSystemSslRoots() ? "true" : "false",
", ssl_cipher_suites: ", "\"", absl::CEscape(SslCipherSuites()), "\"",
", cpp_experimental_disable_reflection: ",
CppExperimentalDisableReflection() ? "true" : "false",
", channelz_max_orphaned_nodes: ", ChannelzMaxOrphanedNodes());
CppExperimentalDisableReflection() ? "true" : "false");
}
} // namespace grpc_core

View File

@ -35,7 +35,6 @@ class GPR_DLL ConfigVars {
public:
struct Overrides {
absl::optional<int32_t> client_channel_backup_poll_interval_ms;
absl::optional<int32_t> channelz_max_orphaned_nodes;
absl::optional<bool> enable_fork_support;
absl::optional<bool> abort_on_leaks;
absl::optional<bool> not_use_system_ssl_roots;
@ -105,19 +104,12 @@ class GPR_DLL ConfigVars {
bool CppExperimentalDisableReflection() const {
return cpp_experimental_disable_reflection_;
}
// EXPERIMENTAL: If non-zero, extend the lifetime of channelz nodes past the
// underlying object lifetime, up to this many nodes. The value may be
// adjusted slightly to account for implementation limits.
int32_t ChannelzMaxOrphanedNodes() const {
return channelz_max_orphaned_nodes_;
}
private:
explicit ConfigVars(const Overrides& overrides);
static const ConfigVars& Load();
static std::atomic<ConfigVars*> config_vars_;
int32_t client_channel_backup_poll_interval_ms_;
int32_t channelz_max_orphaned_nodes_;
bool enable_fork_support_;
bool abort_on_leaks_;
bool not_use_system_ssl_roots_;

View File

@ -25,10 +25,8 @@
namespace grpc_core {
std::atomic<CoreConfiguration*> CoreConfiguration::config_{nullptr};
std::atomic<CoreConfiguration::RegisteredBuilder*>
CoreConfiguration::builders_[static_cast<size_t>(BuilderScope::kCount)]{
nullptr, nullptr};
std::atomic<bool> CoreConfiguration::has_config_ever_been_produced_{false};
std::atomic<CoreConfiguration::RegisteredBuilder*> CoreConfiguration::builders_{
nullptr};
void (*CoreConfiguration::default_builder_)(CoreConfiguration::Builder*);
CoreConfiguration::Builder::Builder() = default;
@ -48,31 +46,18 @@ CoreConfiguration::CoreConfiguration(Builder* builder)
lb_policy_registry_(builder->lb_policy_registry_.Build()),
proxy_mapper_registry_(builder->proxy_mapper_registry_.Build()),
certificate_provider_registry_(
builder->certificate_provider_registry_.Build()),
endpoint_transport_registry_(
builder->endpoint_transport_registry_.Build()) {}
builder->certificate_provider_registry_.Build()) {}
void CoreConfiguration::RegisterBuilder(
BuilderScope scope, absl::AnyInvocable<void(Builder*)> builder,
SourceLocation whence) {
absl::AnyInvocable<void(Builder*)> builder) {
CHECK(config_.load(std::memory_order_relaxed) == nullptr)
<< "CoreConfiguration was already instantiated before builder "
"registration was completed";
if (scope == BuilderScope::kPersistent) {
CHECK(!has_config_ever_been_produced_.load(std::memory_order_relaxed))
<< "Persistent builders cannot be registered after the first "
"CoreConfiguration has been produced";
}
CHECK_NE(scope, BuilderScope::kCount);
auto& head = builders_[static_cast<size_t>(scope)];
RegisteredBuilder* n = new RegisteredBuilder();
VLOG(4) << "Registering " << scope << " builder from " << whence.file() << ":"
<< whence.line();
n->builder = std::move(builder);
n->whence = whence;
n->next = head.load(std::memory_order_relaxed);
while (!head.compare_exchange_weak(n->next, n, std::memory_order_acq_rel,
std::memory_order_relaxed)) {
n->next = builders_.load(std::memory_order_relaxed);
while (!builders_.compare_exchange_weak(n->next, n, std::memory_order_acq_rel,
std::memory_order_relaxed)) {
}
CHECK(config_.load(std::memory_order_relaxed) == nullptr)
<< "CoreConfiguration was already instantiated before builder "
@ -80,7 +65,6 @@ void CoreConfiguration::RegisterBuilder(
}
const CoreConfiguration& CoreConfiguration::BuildNewAndMaybeSet() {
has_config_ever_been_produced_.store(true, std::memory_order_relaxed);
// Construct builder, pass it up to code that knows about build configuration
Builder builder;
// The linked list of builders stores things in reverse registration order.
@ -88,21 +72,13 @@ const CoreConfiguration& CoreConfiguration::BuildNewAndMaybeSet() {
// actually need to run things in forward registration order, so we iterate
// once over the linked list to build a vector of builders, and then iterate
// over said vector in reverse to actually run the builders.
// Note that we also iterate scopes in reverse order here too, so that when
// we run the builders in the reverse generated order we'll actually run
// persistent builders before ephemeral ones.
std::vector<RegisteredBuilder*> registered_builders;
for (auto scope : {BuilderScope::kEphemeral, BuilderScope::kPersistent}) {
for (RegisteredBuilder* b = builders_[static_cast<size_t>(scope)].load(
std::memory_order_acquire);
b != nullptr; b = b->next) {
registered_builders.push_back(b);
}
for (RegisteredBuilder* b = builders_.load(std::memory_order_acquire);
b != nullptr; b = b->next) {
registered_builders.push_back(b);
}
for (auto it = registered_builders.rbegin(); it != registered_builders.rend();
++it) {
VLOG(4) << "Running builder from " << (*it)->whence.file() << ":"
<< (*it)->whence.line();
(*it)->builder(&builder);
}
// Finally, call the built in configuration builder.
@ -124,8 +100,7 @@ const CoreConfiguration& CoreConfiguration::BuildNewAndMaybeSet() {
void CoreConfiguration::Reset() {
delete config_.exchange(nullptr, std::memory_order_acquire);
RegisteredBuilder* builder =
builders_[static_cast<size_t>(BuilderScope::kEphemeral)].exchange(
nullptr, std::memory_order_acquire);
builders_.exchange(nullptr, std::memory_order_acquire);
while (builder != nullptr) {
RegisteredBuilder* next = builder->next;
delete builder;
@ -133,18 +108,4 @@ void CoreConfiguration::Reset() {
}
}
void CoreConfiguration::
ResetEverythingIncludingPersistentBuildersAbsolutelyNotRecommended() {
has_config_ever_been_produced_.store(false, std::memory_order_relaxed);
RegisteredBuilder* builder =
builders_[static_cast<size_t>(BuilderScope::kPersistent)].exchange(
nullptr, std::memory_order_acquire);
while (builder != nullptr) {
RegisteredBuilder* next = builder->next;
delete builder;
builder = next;
}
Reset();
}
} // namespace grpc_core

View File

@ -16,23 +16,20 @@
#define GRPC_SRC_CORE_CONFIG_CORE_CONFIGURATION_H
#include <grpc/support/port_platform.h>
#include <sys/stat.h>
#include <atomic>
#include "absl/functional/any_invocable.h"
#include "absl/log/check.h"
#include "src/core/credentials/transport/channel_creds_registry.h"
#include "src/core/credentials/transport/tls/certificate_provider_registry.h"
#include "src/core/handshaker/handshaker_registry.h"
#include "src/core/handshaker/proxy_mapper_registry.h"
#include "src/core/lib/channel/channel_args_preconditioning.h"
#include "src/core/lib/security/certificate_provider/certificate_provider_registry.h"
#include "src/core/lib/security/credentials/channel_creds_registry.h"
#include "src/core/lib/surface/channel_init.h"
#include "src/core/load_balancing/lb_policy_registry.h"
#include "src/core/resolver/resolver_registry.h"
#include "src/core/service_config/service_config_parser.h"
#include "src/core/transport/endpoint_transport.h"
#include "src/core/util/debug_location.h"
namespace grpc_core {
@ -43,27 +40,6 @@ class GRPC_DLL CoreConfiguration {
CoreConfiguration(const CoreConfiguration&) = delete;
CoreConfiguration& operator=(const CoreConfiguration&) = delete;
// BulderScope is used to indicate whether a builder is persistent - these
// are builders that are used every time the configuration is built, or
// ephemeral - each time the configuration is built these are thrown away.
//
// Considerations for choosing persistent vs ephemeral:
// - For testing we want ephemeral builders, so the next test can throw away
// configuration.
// - For adapting gRPC to different environments we typically want persistent
// builders.
// - However, if the adaption should run only once per process, then
// ephemeral is better.
//
// Builders are instantiated in scope order - persistent first, ephemeral
// second.
enum class BuilderScope {
kPersistent,
kEphemeral,
// Must be last, do not use as a scope.
kCount,
};
// Builder is passed to plugins, etc... at initialization time to collect
// their configuration and assemble the published CoreConfiguration.
class Builder {
@ -102,10 +78,6 @@ class GRPC_DLL CoreConfiguration {
return &certificate_provider_registry_;
}
EndpointTransportRegistry::Builder* endpoint_transport_registry() {
return &endpoint_transport_registry_;
}
private:
friend class CoreConfiguration;
@ -118,7 +90,6 @@ class GRPC_DLL CoreConfiguration {
LoadBalancingPolicyRegistry::Builder lb_policy_registry_;
ProxyMapperRegistry::Builder proxy_mapper_registry_;
CertificateProviderRegistry::Builder certificate_provider_registry_;
EndpointTransportRegistry::Builder endpoint_transport_registry_;
Builder();
CoreConfiguration* Build();
@ -128,7 +99,6 @@ class GRPC_DLL CoreConfiguration {
struct RegisteredBuilder {
absl::AnyInvocable<void(Builder*)> builder;
RegisteredBuilder* next;
SourceLocation whence;
};
// Temporarily replaces core configuration with what is built from the
@ -151,10 +121,8 @@ class GRPC_DLL CoreConfiguration {
// Backup current core configuration and replace/reset.
config_restore_ =
CoreConfiguration::config_.exchange(p, std::memory_order_acquire);
builders_restore_ =
CoreConfiguration::builders_[static_cast<size_t>(
BuilderScope::kEphemeral)]
.exchange(nullptr, std::memory_order_acquire);
builders_restore_ = CoreConfiguration::builders_.exchange(
nullptr, std::memory_order_acquire);
}
~WithSubstituteBuilder() {
@ -162,10 +130,8 @@ class GRPC_DLL CoreConfiguration {
Reset();
CHECK(CoreConfiguration::config_.exchange(
config_restore_, std::memory_order_acquire) == nullptr);
CHECK(CoreConfiguration::builders_[static_cast<size_t>(
BuilderScope::kEphemeral)]
.exchange(builders_restore_, std::memory_order_acquire) ==
nullptr);
CHECK(CoreConfiguration::builders_.exchange(
builders_restore_, std::memory_order_acquire) == nullptr);
}
private:
@ -187,34 +153,13 @@ class GRPC_DLL CoreConfiguration {
// Attach a registration function globally.
// Each registration function is called *in addition to*
// BuildCoreConfiguration for the default core configuration.
static void RegisterBuilder(BuilderScope scope,
absl::AnyInvocable<void(Builder*)> builder,
SourceLocation whence);
static void RegisterPersistentBuilder(
absl::AnyInvocable<void(Builder*)> builder, SourceLocation whence = {}) {
RegisterBuilder(BuilderScope::kPersistent, std::move(builder), whence);
}
static void RegisterEphemeralBuilder(
absl::AnyInvocable<void(Builder*)> builder, SourceLocation whence = {}) {
RegisterBuilder(BuilderScope::kEphemeral, std::move(builder), whence);
}
static void RegisterBuilder(absl::AnyInvocable<void(Builder*)> builder);
// Drop the core configuration. Users must ensure no other threads are
// accessing the configuration.
// Clears any dynamically registered ephemeral builders.
// Clears any dynamically registered builders.
static void Reset();
// Reset, but also reset persistent builders. This is not recommended, but
// is useful for tests that assume exactly the default open source
// configuration when running in other environments.
//
// TODO(ctiller, roth, yashkt): Remove the need for this method, and then
// move the legacy plugin registration mechanism to be a persistent builder.
static void
ResetEverythingIncludingPersistentBuildersAbsolutelyNotRecommended();
// Helper for tests: Reset the configuration, build a special one, run some
// code, and then reset the configuration again.
// Templatized to be sure no codegen in normal builds.
@ -261,10 +206,6 @@ class GRPC_DLL CoreConfiguration {
return certificate_provider_registry_;
}
const EndpointTransportRegistry& endpoint_transport_registry() const {
return endpoint_transport_registry_;
}
static void SetDefaultBuilder(void (*builder)(CoreConfiguration::Builder*)) {
default_builder_ = builder;
}
@ -278,13 +219,8 @@ class GRPC_DLL CoreConfiguration {
// The configuration
static std::atomic<CoreConfiguration*> config_;
// Has a configuration *ever* been produced - we verify this is false for
// persistent builders so that we can prove consistency build to build for
// these.
static std::atomic<bool> has_config_ever_been_produced_;
// Extra registered builders
static std::atomic<RegisteredBuilder*>
builders_[static_cast<size_t>(BuilderScope::kCount)];
static std::atomic<RegisteredBuilder*> builders_;
// Default builder
static void (*default_builder_)(CoreConfiguration::Builder*);
@ -297,26 +233,8 @@ class GRPC_DLL CoreConfiguration {
LoadBalancingPolicyRegistry lb_policy_registry_;
ProxyMapperRegistry proxy_mapper_registry_;
CertificateProviderRegistry certificate_provider_registry_;
EndpointTransportRegistry endpoint_transport_registry_;
};
template <typename Sink>
void AbslStringify(Sink& sink, CoreConfiguration::BuilderScope scope) {
switch (scope) {
case CoreConfiguration::BuilderScope::kPersistent:
sink.Append("Persistent");
break;
case CoreConfiguration::BuilderScope::kEphemeral:
sink.Append("Ephemeral");
break;
case CoreConfiguration::BuilderScope::kCount:
sink.Append("Count(");
sink.Append(std::to_string(static_cast<size_t>(scope)));
sink.Append(")");
break;
}
}
extern void BuildCoreConfiguration(CoreConfiguration::Builder* builder);
} // namespace grpc_core

View File

@ -1,157 +0,0 @@
//
// Copyright 2015 gRPC authors.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
//
#ifndef GRPC_SRC_CORE_CREDENTIALS_CALL_CALL_CREDENTIALS_H
#define GRPC_SRC_CORE_CREDENTIALS_CALL_CALL_CREDENTIALS_H
#include <grpc/credentials.h>
#include <grpc/grpc.h>
#include <grpc/grpc_security.h>
#include <grpc/grpc_security_constants.h>
#include <grpc/impl/grpc_types.h>
#include <grpc/support/port_platform.h>
#include <string>
#include <utility>
#include <vector>
#include "absl/log/check.h"
#include "absl/status/statusor.h"
#include "absl/strings/string_view.h"
#include "src/core/credentials/transport/security_connector.h"
#include "src/core/lib/channel/channel_args.h"
#include "src/core/lib/promise/arena_promise.h"
#include "src/core/lib/slice/slice.h"
#include "src/core/lib/transport/transport.h"
#include "src/core/transport/auth_context.h"
#include "src/core/util/crash.h"
#include "src/core/util/ref_counted.h"
#include "src/core/util/ref_counted_ptr.h"
#include "src/core/util/unique_type_name.h"
// --- Constants. ---
typedef enum {
GRPC_CREDENTIALS_OK = 0,
GRPC_CREDENTIALS_ERROR
} grpc_credentials_status;
#define GRPC_AUTHORIZATION_METADATA_KEY "authorization"
#define GRPC_IAM_AUTHORIZATION_TOKEN_METADATA_KEY \
"x-goog-iam-authorization-token"
#define GRPC_IAM_AUTHORITY_SELECTOR_METADATA_KEY "x-goog-iam-authority-selector"
#define GRPC_SECURE_TOKEN_REFRESH_THRESHOLD_SECS 60
#define GRPC_COMPUTE_ENGINE_METADATA_HOST "metadata.google.internal."
#define GRPC_COMPUTE_ENGINE_METADATA_TOKEN_PATH \
"/computeMetadata/v1/instance/service-accounts/default/token"
#define GRPC_GOOGLE_OAUTH2_SERVICE_HOST "oauth2.googleapis.com"
#define GRPC_GOOGLE_OAUTH2_SERVICE_TOKEN_PATH "/token"
#define GRPC_SERVICE_ACCOUNT_POST_BODY_PREFIX \
"grant_type=urn%3Aietf%3Aparams%3Aoauth%3Agrant-type%3Ajwt-bearer&" \
"assertion="
#define GRPC_REFRESH_TOKEN_POST_BODY_FORMAT_STRING \
"client_id=%s&client_secret=%s&refresh_token=%s&grant_type=refresh_token"
// --- Google utils ---
// It is the caller's responsibility to gpr_free the result if not NULL.
std::string grpc_get_well_known_google_credentials_file_path(void);
// Implementation function for the different platforms.
std::string grpc_get_well_known_google_credentials_file_path_impl(void);
// Override for testing only. Not thread-safe
typedef std::string (*grpc_well_known_credentials_path_getter)(void);
void grpc_override_well_known_credentials_path_getter(
grpc_well_known_credentials_path_getter getter);
// --- grpc_core::CredentialsMetadataArray. ---
namespace grpc_core {
using CredentialsMetadataArray = std::vector<std::pair<Slice, Slice>>;
}
// --- grpc_call_credentials. ---
// This type is forward declared as a C struct and we cannot define it as a
// class. Otherwise, compiler will complain about type mismatch due to
// -Wmismatched-tags.
struct grpc_call_credentials
: public grpc_core::DualRefCounted<grpc_call_credentials> {
public:
// TODO(roth): Consider whether security connector actually needs to
// be part of this interface. Currently, it is here only for the
// url_scheme() method, which we might be able to instead add as an
// auth context property.
struct GetRequestMetadataArgs {
grpc_core::RefCountedPtr<grpc_channel_security_connector>
security_connector;
grpc_core::RefCountedPtr<grpc_auth_context> auth_context;
};
// The pointer value \a type is used to uniquely identify a creds
// implementation for down-casting purposes. Every creds implementation should
// use a unique string instance, which should be returned by all instances of
// that creds implementation.
explicit grpc_call_credentials(
grpc_security_level min_security_level = GRPC_PRIVACY_AND_INTEGRITY)
: min_security_level_(min_security_level) {}
~grpc_call_credentials() override = default;
virtual grpc_core::ArenaPromise<
absl::StatusOr<grpc_core::ClientMetadataHandle>>
GetRequestMetadata(grpc_core::ClientMetadataHandle initial_metadata,
const GetRequestMetadataArgs* args) = 0;
virtual grpc_security_level min_security_level() const {
return min_security_level_;
}
// Compares this grpc_call_credentials object with \a other.
// If this method returns 0, it means that gRPC can treat the two call
// credentials as effectively the same..
int cmp(const grpc_call_credentials* other) const {
CHECK_NE(other, nullptr);
int r = type().Compare(other->type());
if (r != 0) return r;
return cmp_impl(other);
}
virtual std::string debug_string() {
return "grpc_call_credentials did not provide debug string";
}
// The pointer value \a type is used to uniquely identify a creds
// implementation for down-casting purposes. Every creds implementation should
// use a unique string instance, which should be returned by all instances of
// that creds implementation.
virtual grpc_core::UniqueTypeName type() const = 0;
private:
// Implementation for `cmp` method intended to be overridden by subclasses.
// Only invoked if `type()` and `other->type()` point to the same string.
virtual int cmp_impl(const grpc_call_credentials* other) const = 0;
const grpc_security_level min_security_level_;
};
#endif // GRPC_SRC_CORE_CREDENTIALS_CALL_CALL_CREDENTIALS_H

View File

@ -1,82 +0,0 @@
//
//
// Copyright 2015 gRPC authors.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
//
//
#ifndef GRPC_SRC_CORE_CREDENTIALS_CALL_COMPOSITE_COMPOSITE_CALL_CREDENTIALS_H
#define GRPC_SRC_CORE_CREDENTIALS_CALL_COMPOSITE_COMPOSITE_CALL_CREDENTIALS_H
#include <grpc/credentials.h>
#include <grpc/grpc.h>
#include <grpc/grpc_security.h>
#include <grpc/grpc_security_constants.h>
#include <algorithm>
#include <string>
#include <utility>
#include <vector>
#include "absl/status/statusor.h"
#include "src/core/credentials/call/call_credentials.h"
#include "src/core/credentials/transport/security_connector.h"
#include "src/core/lib/channel/channel_args.h"
#include "src/core/lib/promise/arena_promise.h"
#include "src/core/lib/transport/transport.h"
#include "src/core/util/ref_counted_ptr.h"
#include "src/core/util/unique_type_name.h"
#include "src/core/util/useful.h"
class grpc_composite_call_credentials : public grpc_call_credentials {
public:
using CallCredentialsList =
std::vector<grpc_core::RefCountedPtr<grpc_call_credentials>>;
grpc_composite_call_credentials(
grpc_core::RefCountedPtr<grpc_call_credentials> creds1,
grpc_core::RefCountedPtr<grpc_call_credentials> creds2);
~grpc_composite_call_credentials() override = default;
void Orphaned() override { inner_.clear(); }
grpc_core::ArenaPromise<absl::StatusOr<grpc_core::ClientMetadataHandle>>
GetRequestMetadata(grpc_core::ClientMetadataHandle initial_metadata,
const GetRequestMetadataArgs* args) override;
grpc_security_level min_security_level() const override {
return min_security_level_;
}
const CallCredentialsList& inner() const { return inner_; }
std::string debug_string() override;
static grpc_core::UniqueTypeName Type();
grpc_core::UniqueTypeName type() const override { return Type(); }
private:
int cmp_impl(const grpc_call_credentials* other) const override {
// TODO(yashykt): Check if we can do something better here
return grpc_core::QsortCompare(
static_cast<const grpc_call_credentials*>(this), other);
}
void push_to_inner(grpc_core::RefCountedPtr<grpc_call_credentials> creds,
bool is_composite);
grpc_security_level min_security_level_;
CallCredentialsList inner_;
};
#endif // GRPC_SRC_CORE_CREDENTIALS_CALL_COMPOSITE_COMPOSITE_CALL_CREDENTIALS_H

View File

@ -1,68 +0,0 @@
//
// Copyright 2015-2016 gRPC authors.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
//
#include "src/core/credentials/transport/composite/composite_channel_credentials.h"
#include <grpc/support/port_platform.h>
#include <cstring>
#include <memory>
#include <vector>
#include "absl/log/check.h"
#include "absl/strings/str_cat.h"
#include "absl/strings/str_join.h"
#include "src/core/call/metadata_batch.h"
#include "src/core/credentials/call/composite/composite_call_credentials.h"
#include "src/core/lib/debug/trace.h"
#include "src/core/lib/promise/try_seq.h"
#include "src/core/util/ref_counted_ptr.h"
grpc_core::UniqueTypeName grpc_composite_channel_credentials::Type() {
static grpc_core::UniqueTypeName::Factory kFactory("Composite");
return kFactory.Create();
}
grpc_core::RefCountedPtr<grpc_channel_security_connector>
grpc_composite_channel_credentials::create_security_connector(
grpc_core::RefCountedPtr<grpc_call_credentials> call_creds,
const char* target, grpc_core::ChannelArgs* args) {
CHECK(inner_creds_ != nullptr);
CHECK(call_creds_ != nullptr);
// If we are passed a call_creds, create a call composite to pass it
// downstream.
if (call_creds != nullptr) {
return inner_creds_->create_security_connector(
grpc_core::MakeRefCounted<grpc_composite_call_credentials>(
call_creds_, std::move(call_creds)),
target, args);
} else {
return inner_creds_->create_security_connector(call_creds_, target, args);
}
}
grpc_channel_credentials* grpc_composite_channel_credentials_create(
grpc_channel_credentials* channel_creds, grpc_call_credentials* call_creds,
void* reserved) {
CHECK(channel_creds != nullptr && call_creds != nullptr &&
reserved == nullptr);
GRPC_TRACE_LOG(api, INFO)
<< "grpc_composite_channel_credentials_create(channel_creds="
<< channel_creds << ", call_creds=" << call_creds
<< ", reserved=" << reserved << ")";
return new grpc_composite_channel_credentials(channel_creds->Ref(),
call_creds->Ref());
}

View File

@ -26,7 +26,6 @@
#include "absl/log/log.h"
#include "absl/strings/string_view.h"
#include "src/core/call/metadata_batch.h"
#include "src/core/config/core_configuration.h"
#include "src/core/lib/channel/channel_stack.h"
#include "src/core/lib/channel/promise_based_filter.h"
@ -36,6 +35,7 @@
#include "src/core/lib/promise/map.h"
#include "src/core/lib/slice/slice.h"
#include "src/core/lib/surface/channel_stack_type.h"
#include "src/core/lib/transport/metadata_batch.h"
#include "src/core/load_balancing/backend_metric_data.h"
#include "src/core/util/latent_see.h"
#include "upb/base/string_view.h"

View File

@ -28,9 +28,7 @@
#include "absl/meta/type_traits.h"
#include "absl/random/random.h"
#include "absl/status/statusor.h"
#include "src/core/call/metadata_batch.h"
#include "src/core/config/core_configuration.h"
#include "src/core/ext/transport/chttp2/transport/http2_status.h"
#include "src/core/lib/channel/channel_args.h"
#include "src/core/lib/channel/promise_based_filter.h"
#include "src/core/lib/debug/trace.h"
@ -46,24 +44,23 @@
#include "src/core/lib/promise/try_seq.h"
#include "src/core/lib/resource_quota/arena.h"
#include "src/core/lib/surface/channel_stack_type.h"
#include "src/core/lib/transport/http2_errors.h"
#include "src/core/lib/transport/metadata_batch.h"
#include "src/core/util/debug_location.h"
#include "src/core/util/no_destruct.h"
#include "src/core/util/orphanable.h"
#include "src/core/util/per_cpu.h"
#include "src/core/util/shared_bit_gen.h"
#include "src/core/util/status_helper.h"
#include "src/core/util/sync.h"
namespace grpc_core {
using http2::Http2ErrorCode;
namespace {
constexpr Duration kDefaultIdleTimeout = Duration::Minutes(30);
// If these settings change, make sure that we are not sending a GOAWAY for
// inproc transport, since a GOAWAY to inproc ends up destroying the
// transport.
// inproc transport, since a GOAWAY to inproc ends up destroying the transport.
const auto kDefaultMaxConnectionAge = Duration::Infinity();
const auto kDefaultMaxConnectionAgeGrace = Duration::Infinity();
const auto kDefaultMaxConnectionIdle = Duration::Infinity();
@ -108,11 +105,9 @@ struct LegacyMaxAgeFilter::Config {
return absl::Uniform(bit_gen, min, max);
}
};
const double multiplier = []() {
SharedBitGen g;
return absl::Uniform(g, 1.0 - kMaxConnectionAgeJitter,
1.0 + kMaxConnectionAgeJitter);
}();
static NoDestruct<PerCpu<BitGen>> bit_gen(PerCpuOptions().SetMaxShards(8));
const double multiplier = bit_gen->this_cpu().MakeUniformDouble(
1.0 - kMaxConnectionAgeJitter, 1.0 + kMaxConnectionAgeJitter);
// GRPC_MILLIS_INF_FUTURE - 0.5 converts the value to float, so that result
// will not be cast to int implicitly before the comparison.
return Config{args_max_age * multiplier, args_max_idle * multiplier,
@ -189,8 +184,7 @@ void LegacyMaxAgeFilter::PostInit() {
grpc_transport_op* op = grpc_make_transport_op(nullptr);
op->goaway_error = grpc_error_set_int(
GRPC_ERROR_CREATE("max_age"),
StatusIntProperty::kHttp2Error,
static_cast<intptr_t>(Http2ErrorCode::kNoError));
StatusIntProperty::kHttp2Error, GRPC_HTTP2_NO_ERROR);
grpc_channel_element* elem =
grpc_channel_stack_element(channel_stack, 0);
elem->filter->start_transport_op(elem, op);

View File

@ -35,15 +35,15 @@
#include "absl/strings/numbers.h"
#include "absl/strings/str_cat.h"
#include "absl/strings/string_view.h"
#include "src/core/call/metadata_batch.h"
#include "src/core/call/status_util.h"
#include "src/core/config/core_configuration.h"
#include "src/core/ext/filters/fault_injection/fault_injection_service_config_parser.h"
#include "src/core/lib/channel/channel_stack.h"
#include "src/core/lib/channel/status_util.h"
#include "src/core/lib/debug/trace.h"
#include "src/core/lib/promise/context.h"
#include "src/core/lib/promise/sleep.h"
#include "src/core/lib/promise/try_seq.h"
#include "src/core/lib/transport/metadata_batch.h"
#include "src/core/lib/transport/transport.h"
#include "src/core/service_config/service_config_call_data.h"
#include "src/core/util/time.h"

View File

@ -21,8 +21,8 @@
#include <optional>
#include <vector>
#include "src/core/call/status_util.h"
#include "src/core/lib/channel/channel_args.h"
#include "src/core/lib/channel/status_util.h"
namespace grpc_core {

View File

@ -22,13 +22,13 @@
#include "absl/log/check.h"
#include "absl/strings/str_cat.h"
#include "src/core/call/security_context.h"
#include "src/core/config/core_configuration.h"
#include "src/core/credentials/call/gcp_service_account_identity/gcp_service_account_identity_credentials.h"
#include "src/core/ext/filters/gcp_authentication/gcp_authentication_service_config_parser.h"
#include "src/core/lib/channel/channel_stack.h"
#include "src/core/lib/promise/context.h"
#include "src/core/lib/resource_quota/arena.h"
#include "src/core/lib/security/context/security_context.h"
#include "src/core/lib/security/credentials/gcp_service_account_identity/gcp_service_account_identity_credentials.h"
#include "src/core/lib/transport/transport.h"
#include "src/core/resolver/xds/xds_resolver_attributes.h"
#include "src/core/service_config/service_config.h"

View File

@ -23,12 +23,12 @@
#include "absl/status/status.h"
#include "absl/status/statusor.h"
#include "absl/strings/string_view.h"
#include "src/core/credentials/call/call_credentials.h"
#include "src/core/ext/filters/gcp_authentication/gcp_authentication_service_config_parser.h"
#include "src/core/filter/blackboard.h"
#include "src/core/lib/channel/channel_args.h"
#include "src/core/lib/channel/channel_fwd.h"
#include "src/core/lib/channel/promise_based_filter.h"
#include "src/core/lib/security/credentials/credentials.h"
#include "src/core/lib/transport/transport.h"
#include "src/core/resolver/xds/xds_config.h"
#include "src/core/util/lru_cache.h"

View File

@ -21,11 +21,11 @@
#include <grpc/support/port_platform.h>
#include "absl/status/statusor.h"
#include "src/core/call/metadata_batch.h"
#include "src/core/lib/channel/channel_args.h"
#include "src/core/lib/channel/channel_fwd.h"
#include "src/core/lib/channel/promise_based_filter.h"
#include "src/core/lib/slice/slice.h"
#include "src/core/lib/transport/metadata_batch.h"
#include "src/core/lib/transport/transport.h"
namespace grpc_core {

View File

@ -27,11 +27,11 @@
#include "absl/status/status.h"
#include "absl/strings/string_view.h"
#include "src/core/call/metadata_batch.h"
#include "src/core/config/core_configuration.h"
#include "src/core/filter/auth/auth_filters.h"
#include "src/core/lib/channel/channel_stack.h"
#include "src/core/lib/security/transport/auth_filters.h"
#include "src/core/lib/surface/channel_stack_type.h"
#include "src/core/lib/transport/metadata_batch.h"
#include "src/core/util/latent_see.h"
namespace grpc_core {

View File

@ -30,7 +30,6 @@
#include "absl/status/status.h"
#include "absl/strings/str_cat.h"
#include "absl/strings/str_format.h"
#include "src/core/call/metadata_batch.h"
#include "src/core/ext/filters/message_size/message_size_filter.h"
#include "src/core/lib/channel/channel_args.h"
#include "src/core/lib/channel/channel_stack.h"
@ -46,6 +45,7 @@
#include "src/core/lib/resource_quota/arena.h"
#include "src/core/lib/slice/slice_buffer.h"
#include "src/core/lib/surface/call.h"
#include "src/core/lib/transport/metadata_batch.h"
#include "src/core/lib/transport/transport.h"
#include "src/core/telemetry/call_tracer.h"
#include "src/core/util/latent_see.h"

View File

@ -28,12 +28,12 @@
#include "absl/status/statusor.h"
#include "absl/strings/string_view.h"
#include "src/core/call/metadata_batch.h"
#include "src/core/lib/channel/channel_args.h"
#include "src/core/lib/channel/channel_fwd.h"
#include "src/core/lib/channel/promise_based_filter.h"
#include "src/core/lib/compression/compression_internal.h"
#include "src/core/lib/promise/arena_promise.h"
#include "src/core/lib/transport/metadata_batch.h"
#include "src/core/lib/transport/transport.h"
namespace grpc_core {
@ -91,20 +91,6 @@ class ChannelCompression {
bool is_client, MessageHandle message, DecompressArgs args,
CallTracerInterface* call_tracer) const;
Json::Object ToJsonObject() const {
Json::Object object;
if (max_recv_size_.has_value()) {
object["maxRecvSize"] = Json::FromNumber(*max_recv_size_);
}
object["defaultCompressionAlgorithm"] = Json::FromString(
CompressionAlgorithmAsString(default_compression_algorithm_));
object["enabledCompressionAlgorithms"] = Json::FromString(
std::string(enabled_compression_algorithms_.ToString()));
object["enableCompression"] = Json::FromBool(enable_compression_);
object["enableDecompression"] = Json::FromBool(enable_decompression_);
return object;
}
private:
// Max receive message length, if set.
std::optional<uint32_t> max_recv_size_;
@ -120,8 +106,7 @@ class ChannelCompression {
};
class ClientCompressionFilter final
: public ImplementChannelFilter<ClientCompressionFilter>,
public channelz::DataSource {
: public ImplementChannelFilter<ClientCompressionFilter> {
public:
static const grpc_channel_filter kFilter;
@ -131,14 +116,7 @@ class ClientCompressionFilter final
const ChannelArgs& args, ChannelFilter::Args filter_args);
explicit ClientCompressionFilter(const ChannelArgs& args)
: channelz::DataSource(args.GetObjectRef<channelz::BaseNode>()),
compression_engine_(args) {}
~ClientCompressionFilter() override { ResetDataSource(); }
void AddData(channelz::DataSink& sink) override {
sink.AddAdditionalInfo("clientCompressionFilter",
compression_engine_.ToJsonObject());
}
: compression_engine_(args) {}
// Construct a promise for one call.
class Call {
@ -170,8 +148,7 @@ class ClientCompressionFilter final
};
class ServerCompressionFilter final
: public ImplementChannelFilter<ServerCompressionFilter>,
public channelz::DataSource {
: public ImplementChannelFilter<ServerCompressionFilter> {
public:
static const grpc_channel_filter kFilter;
@ -181,14 +158,7 @@ class ServerCompressionFilter final
const ChannelArgs& args, ChannelFilter::Args filter_args);
explicit ServerCompressionFilter(const ChannelArgs& args)
: channelz::DataSource(args.GetObjectRef<channelz::BaseNode>()),
compression_engine_(args) {}
~ServerCompressionFilter() override { ResetDataSource(); }
void AddData(channelz::DataSink& sink) override {
sink.AddAdditionalInfo("serverCompressionFilter",
compression_engine_.ToJsonObject());
}
: compression_engine_(args) {}
// Construct a promise for one call.
class Call {

View File

@ -30,7 +30,6 @@
#include "absl/base/attributes.h"
#include "absl/log/log.h"
#include "absl/strings/string_view.h"
#include "src/core/call/metadata_batch.h"
#include "src/core/lib/channel/channel_args.h"
#include "src/core/lib/channel/channel_stack.h"
#include "src/core/lib/debug/trace.h"
@ -43,6 +42,7 @@
#include "src/core/lib/resource_quota/arena.h"
#include "src/core/lib/slice/percent_encoding.h"
#include "src/core/lib/slice/slice.h"
#include "src/core/lib/transport/metadata_batch.h"
#include "src/core/util/latent_see.h"
namespace grpc_core {
@ -153,7 +153,7 @@ void HttpServerFilter::Call::OnServerTrailingMetadata(ServerMetadata& md) {
absl::StatusOr<std::unique_ptr<HttpServerFilter>> HttpServerFilter::Create(
const ChannelArgs& args, ChannelFilter::Args) {
return std::make_unique<HttpServerFilter>(
args, args.GetBool(GRPC_ARG_SURFACE_USER_AGENT).value_or(true),
args.GetBool(GRPC_ARG_SURFACE_USER_AGENT).value_or(true),
args.GetBool(
GRPC_ARG_DO_NOT_USE_UNLESS_YOU_HAVE_PERMISSION_FROM_GRPC_TEAM_ALLOW_BROKEN_PUT_REQUESTS)
.value_or(false));

View File

@ -31,8 +31,7 @@
namespace grpc_core {
// Processes metadata on the server side for HTTP2 transports
class HttpServerFilter : public ImplementChannelFilter<HttpServerFilter>,
public channelz::DataSource {
class HttpServerFilter : public ImplementChannelFilter<HttpServerFilter> {
public:
static const grpc_channel_filter kFilter;
@ -41,19 +40,9 @@ class HttpServerFilter : public ImplementChannelFilter<HttpServerFilter>,
static absl::StatusOr<std::unique_ptr<HttpServerFilter>> Create(
const ChannelArgs& args, ChannelFilter::Args filter_args);
HttpServerFilter(const ChannelArgs& args, bool surface_user_agent,
bool allow_put_requests)
: channelz::DataSource(args.GetObjectRef<channelz::BaseNode>()),
surface_user_agent_(surface_user_agent),
HttpServerFilter(bool surface_user_agent, bool allow_put_requests)
: surface_user_agent_(surface_user_agent),
allow_put_requests_(allow_put_requests) {}
~HttpServerFilter() override { ResetDataSource(); }
void AddData(channelz::DataSink& sink) override {
Json::Object object;
object["surfaceUserAgent"] = Json::FromBool(surface_user_agent_);
object["allowPutRequests"] = Json::FromBool(allow_put_requests_);
sink.AddAdditionalInfo("httpServerFilter", object);
}
class Call {
public:

View File

@ -26,7 +26,6 @@
#include "absl/log/log.h"
#include "absl/strings/str_format.h"
#include "src/core/call/metadata_batch.h"
#include "src/core/config/core_configuration.h"
#include "src/core/lib/channel/channel_args.h"
#include "src/core/lib/channel/channel_stack.h"
@ -39,6 +38,7 @@
#include "src/core/lib/slice/slice.h"
#include "src/core/lib/slice/slice_buffer.h"
#include "src/core/lib/surface/channel_stack_type.h"
#include "src/core/lib/transport/metadata_batch.h"
#include "src/core/lib/transport/transport.h"
#include "src/core/service_config/service_config_call_data.h"
#include "src/core/util/latent_see.h"

View File

@ -24,7 +24,6 @@
#include <utility>
#include "absl/status/status.h"
#include "src/core/call/metadata_batch.h"
#include "src/core/config/core_configuration.h"
#include "src/core/ext/filters/rbac/rbac_service_config_parser.h"
#include "src/core/lib/channel/channel_args.h"
@ -34,9 +33,10 @@
#include "src/core/lib/promise/promise.h"
#include "src/core/lib/security/authorization/authorization_engine.h"
#include "src/core/lib/security/authorization/grpc_authorization_engine.h"
#include "src/core/lib/security/context/security_context.h"
#include "src/core/lib/transport/metadata_batch.h"
#include "src/core/lib/transport/transport.h"
#include "src/core/service_config/service_config_call_data.h"
#include "src/core/transport/auth_context.h"
#include "src/core/util/latent_see.h"
namespace grpc_core {

View File

@ -35,7 +35,6 @@
#include "absl/strings/str_split.h"
#include "absl/strings/string_view.h"
#include "absl/strings/strip.h"
#include "src/core/call/metadata_batch.h"
#include "src/core/config/core_configuration.h"
#include "src/core/ext/filters/stateful_session/stateful_session_service_config_parser.h"
#include "src/core/lib/channel/channel_stack.h"
@ -45,6 +44,7 @@
#include "src/core/lib/promise/pipe.h"
#include "src/core/lib/resource_quota/arena.h"
#include "src/core/lib/slice/slice.h"
#include "src/core/lib/transport/metadata_batch.h"
#include "src/core/lib/transport/transport.h"
#include "src/core/resolver/xds/xds_resolver_attributes.h"
#include "src/core/service_config/service_config_call_data.h"

View File

@ -1,40 +0,0 @@
// Copyright 2025 gRPC authors.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
#include "src/core/config/core_configuration.h"
#include "src/core/ext/transport/chttp2/client/chttp2_connector.h"
#include "src/core/ext/transport/chttp2/server/chttp2_server.h"
#include "src/core/transport/endpoint_transport.h"
namespace grpc_core {
namespace {
class Chttp2Transport final : public EndpointTransport {
public:
absl::StatusOr<grpc_channel*> ChannelCreate(
std::string target, const ChannelArgs& args) override {
return CreateHttp2Channel(target, args);
}
absl::StatusOr<int> AddPort(Server* server, std::string addr,
const ChannelArgs& args) override {
return Chttp2ServerAddPort(server, addr.c_str(), args);
}
};
} // namespace
void RegisterChttp2Transport(CoreConfiguration::Builder* builder) {
builder->endpoint_transport_registry()->RegisterTransport(
"h2", std::make_unique<Chttp2Transport>());
}
} // namespace grpc_core

View File

@ -43,9 +43,6 @@
#include "src/core/client_channel/connector.h"
#include "src/core/client_channel/subchannel.h"
#include "src/core/config/core_configuration.h"
#include "src/core/credentials/transport/insecure/insecure_credentials.h"
#include "src/core/credentials/transport/security_connector.h"
#include "src/core/credentials/transport/transport_credentials.h"
#include "src/core/ext/transport/chttp2/transport/chttp2_transport.h"
#include "src/core/handshaker/handshaker.h"
#include "src/core/handshaker/handshaker_registry.h"
@ -58,13 +55,15 @@
#include "src/core/lib/iomgr/endpoint.h"
#include "src/core/lib/iomgr/exec_ctx.h"
#include "src/core/lib/iomgr/resolved_address.h"
#include "src/core/lib/security/credentials/credentials.h"
#include "src/core/lib/security/credentials/insecure/insecure_credentials.h"
#include "src/core/lib/security/security_connector/security_connector.h"
#include "src/core/lib/surface/channel.h"
#include "src/core/lib/surface/channel_create.h"
#include "src/core/lib/surface/channel_stack_type.h"
#include "src/core/lib/transport/error_utils.h"
#include "src/core/lib/transport/transport.h"
#include "src/core/resolver/resolver_registry.h"
#include "src/core/transport/endpoint_transport_client_channel_factory.h"
#include "src/core/util/debug_location.h"
#include "src/core/util/orphanable.h"
#include "src/core/util/status_helper.h"
@ -146,6 +145,8 @@ void Chttp2Connector::OnHandshakeDone(absl::StatusOr<HandshakerArgs*> result) {
result_->transport = grpc_create_chttp2_transport(
(*result)->args, std::move((*result)->endpoint), true);
CHECK_NE(result_->transport, nullptr);
result_->socket_node =
grpc_chttp2_transport_get_socket_node(result_->transport);
result_->channel_args = std::move((*result)->args);
Ref().release(); // Ref held by OnReceiveSettings()
GRPC_CLOSURE_INIT(&on_receive_settings_, OnReceiveSettings, this,
@ -224,21 +225,121 @@ void Chttp2Connector::MaybeNotify(grpc_error_handle error) {
}
}
absl::StatusOr<grpc_channel*> CreateHttp2Channel(std::string target,
const ChannelArgs& args) {
auto r = ChannelCreate(
target,
args.SetObject(EndpointTransportClientChannelFactory<Chttp2Connector>()),
GRPC_CLIENT_CHANNEL, nullptr);
if (r.ok()) {
return r->release()->c_ptr();
} else {
return r.status();
namespace {
class Chttp2SecureClientChannelFactory : public ClientChannelFactory {
public:
RefCountedPtr<Subchannel> CreateSubchannel(
const grpc_resolved_address& address, const ChannelArgs& args) override {
absl::StatusOr<ChannelArgs> new_args = GetSecureNamingChannelArgs(args);
if (!new_args.ok()) {
LOG(ERROR) << "Failed to create channel args during subchannel creation: "
<< new_args.status() << "; Got args: " << args.ToString();
return nullptr;
}
RefCountedPtr<Subchannel> s = Subchannel::Create(
MakeOrphanable<Chttp2Connector>(), address, *new_args);
return s;
}
private:
static absl::StatusOr<ChannelArgs> GetSecureNamingChannelArgs(
ChannelArgs args) {
auto* channel_credentials = args.GetObject<grpc_channel_credentials>();
if (channel_credentials == nullptr) {
return absl::InternalError("channel credentials missing for channel");
}
// Make sure security connector does not already exist in args.
if (args.Contains(GRPC_ARG_SECURITY_CONNECTOR)) {
return absl::InternalError(
"security connector already present in channel args.");
}
// Find the authority to use in the security connector.
std::optional<std::string> authority =
args.GetOwnedString(GRPC_ARG_DEFAULT_AUTHORITY);
if (!authority.has_value()) {
return absl::InternalError("authority not present in channel args");
}
// Create the security connector using the credentials and target name.
RefCountedPtr<grpc_channel_security_connector>
subchannel_security_connector =
channel_credentials->create_security_connector(
/*call_creds=*/nullptr, authority->c_str(), &args);
if (subchannel_security_connector == nullptr) {
return absl::InternalError(absl::StrFormat(
"Failed to create subchannel for secure name '%s'", *authority));
}
return args.SetObject(std::move(subchannel_security_connector));
}
};
absl::StatusOr<RefCountedPtr<Channel>> CreateChannel(const char* target,
const ChannelArgs& args) {
if (target == nullptr) {
LOG(ERROR) << "cannot create channel with NULL target name";
return absl::InvalidArgumentError("channel target is NULL");
}
return ChannelCreate(target, args, GRPC_CLIENT_CHANNEL, nullptr);
}
} // namespace
} // namespace grpc_core
namespace {
grpc_core::Chttp2SecureClientChannelFactory* g_factory;
gpr_once g_factory_once = GPR_ONCE_INIT;
void FactoryInit() {
g_factory = new grpc_core::Chttp2SecureClientChannelFactory();
}
} // namespace
// Create a client channel:
// Asynchronously: - resolve target
// - connect to it (trying alternatives as presented)
// - perform handshakes
grpc_channel* grpc_channel_create(const char* target,
grpc_channel_credentials* creds,
const grpc_channel_args* c_args) {
grpc_core::ExecCtx exec_ctx;
GRPC_TRACE_LOG(api, INFO)
<< "grpc_channel_create(target=" << target << ", creds=" << (void*)creds
<< ", args=" << (void*)c_args << ")";
grpc_channel* channel = nullptr;
grpc_error_handle error;
if (creds != nullptr) {
// Add channel args containing the client channel factory and channel
// credentials.
gpr_once_init(&g_factory_once, FactoryInit);
grpc_core::ChannelArgs args =
creds->update_arguments(grpc_core::CoreConfiguration::Get()
.channel_args_preconditioning()
.PreconditionChannelArgs(c_args)
.SetObject(creds->Ref())
.SetObject(g_factory));
// Create channel.
auto r = grpc_core::CreateChannel(target, args);
if (r.ok()) {
channel = r->release()->c_ptr();
} else {
error = absl_status_to_grpc_error(r.status());
}
}
if (channel == nullptr) {
intptr_t integer;
grpc_status_code status = GRPC_STATUS_INTERNAL;
if (grpc_error_get_int(error, grpc_core::StatusIntProperty::kRpcStatus,
&integer)) {
status = static_cast<grpc_status_code>(integer);
}
channel = grpc_lame_client_channel_create(
target, status, "Failed to create client channel");
}
return channel;
}
#ifdef GPR_SUPPORT_CHANNELS_FROM_FD
grpc_channel* grpc_channel_create_from_fd(const char* target, int fd,
grpc_channel_credentials* creds,

View File

@ -72,9 +72,6 @@ class Chttp2Connector : public SubchannelConnector {
RefCountedPtr<HandshakeManager> handshake_mgr_;
};
absl::StatusOr<grpc_channel*> CreateHttp2Channel(std::string target,
const ChannelArgs& args);
} // namespace grpc_core
#endif // GRPC_SRC_CORE_EXT_TRANSPORT_CHTTP2_CLIENT_CHTTP2_CONNECTOR_H

File diff suppressed because it is too large Load Diff

View File

@ -19,7 +19,6 @@
#ifndef GRPC_SRC_CORE_EXT_TRANSPORT_CHTTP2_SERVER_CHTTP2_SERVER_H
#define GRPC_SRC_CORE_EXT_TRANSPORT_CHTTP2_SERVER_CHTTP2_SERVER_H
#include <grpc/byte_buffer.h>
#include <grpc/event_engine/event_engine.h>
#include <grpc/passive_listener.h>
#include <grpc/support/port_platform.h>
@ -36,10 +35,7 @@ namespace grpc_core {
struct AcceptorDeleter {
void operator()(grpc_tcp_server_acceptor* acceptor) const {
if (acceptor != nullptr) {
grpc_byte_buffer_destroy(acceptor->pending_data);
gpr_free(acceptor);
}
gpr_free(acceptor);
}
};
@ -51,7 +47,7 @@ class ActiveConnectionTestPeer;
class HandshakingStateTestPeer;
} // namespace testing
// New ChttpServerListener
// New ChttpServerListener used if experiment "server_listener" is enabled
class NewChttp2ServerListener : public Server::ListenerInterface {
public:
using AcceptorPtr =
@ -255,10 +251,6 @@ class PassiveListenerImpl final : public PassiveListener {
};
} // namespace experimental
absl::StatusOr<int> Chttp2ServerAddPort(Server* server, const char* addr,
const ChannelArgs& args);
} // namespace grpc_core
#endif // GRPC_SRC_CORE_EXT_TRANSPORT_CHTTP2_SERVER_CHTTP2_SERVER_H

View File

@ -30,7 +30,7 @@ void Chttp2CallTracerWrapper::RecordIncomingBytes(
stream_->stats.incoming.header_bytes += transport_byte_size.header_bytes;
// Update new API.
if (!IsCallTracerInTransportEnabled()) return;
auto* call_tracer = stream_->call_tracer;
auto* call_tracer = stream_->CallTracer();
if (call_tracer != nullptr) {
call_tracer->RecordIncomingBytes(transport_byte_size);
}
@ -44,7 +44,7 @@ void Chttp2CallTracerWrapper::RecordOutgoingBytes(
stream_->stats.outgoing.header_bytes +=
transport_byte_size.header_bytes; // Update new API.
if (!IsCallTracerInTransportEnabled()) return;
auto* call_tracer = stream_->call_tracer;
auto* call_tracer = stream_->CallTracer();
if (call_tracer != nullptr) {
call_tracer->RecordOutgoingBytes(transport_byte_size);
}

View File

@ -54,7 +54,9 @@ class Chttp2CallTracerWrapper final : public CallTracerInterface {
void RecordReceivedDecompressedMessage(
const Message& /*recv_decompressed_message*/) override {}
void RecordCancel(grpc_error_handle /*cancel_error*/) override {}
std::shared_ptr<TcpCallTracer> StartNewTcpTrace() override { return nullptr; }
std::shared_ptr<TcpTracerInterface> StartNewTcpTrace() override {
return nullptr;
}
void RecordAnnotation(absl::string_view /*annotation*/) override {}
void RecordAnnotation(const Annotation& /*annotation*/) override {}
std::string TraceId() override { return ""; }

View File

@ -55,10 +55,9 @@
#include "absl/strings/str_cat.h"
#include "absl/strings/str_format.h"
#include "absl/strings/string_view.h"
#include "src/core/call/metadata_batch.h"
#include "src/core/call/metadata_info.h"
#include "src/core/config/config_vars.h"
#include "src/core/ext/transport/chttp2/transport/call_tracer_wrapper.h"
#include "src/core/ext/transport/chttp2/transport/context_list_entry.h"
#include "src/core/ext/transport/chttp2/transport/flow_control.h"
#include "src/core/ext/transport/chttp2/transport/frame_data.h"
#include "src/core/ext/transport/chttp2/transport/frame_goaway.h"
@ -66,7 +65,6 @@
#include "src/core/ext/transport/chttp2/transport/frame_security.h"
#include "src/core/ext/transport/chttp2/transport/hpack_encoder.h"
#include "src/core/ext/transport/chttp2/transport/http2_settings.h"
#include "src/core/ext/transport/chttp2/transport/http2_status.h"
#include "src/core/ext/transport/chttp2/transport/internal.h"
#include "src/core/ext/transport/chttp2/transport/legacy_frame.h"
#include "src/core/ext/transport/chttp2/transport/ping_abuse_policy.h"
@ -76,7 +74,6 @@
#include "src/core/ext/transport/chttp2/transport/varint.h"
#include "src/core/ext/transport/chttp2/transport/write_size_policy.h"
#include "src/core/lib/channel/channel_args.h"
#include "src/core/lib/event_engine/extensions/channelz.h"
#include "src/core/lib/event_engine/extensions/tcp_trace.h"
#include "src/core/lib/event_engine/query_extensions.h"
#include "src/core/lib/experiments/experiments.h"
@ -98,28 +95,26 @@
#include "src/core/lib/transport/bdp_estimator.h"
#include "src/core/lib/transport/connectivity_state.h"
#include "src/core/lib/transport/error_utils.h"
#include "src/core/lib/transport/http2_errors.h"
#include "src/core/lib/transport/metadata_batch.h"
#include "src/core/lib/transport/metadata_info.h"
#include "src/core/lib/transport/status_conversion.h"
#include "src/core/lib/transport/transport.h"
#include "src/core/lib/transport/transport_framing_endpoint_extension.h"
#include "src/core/telemetry/call_tracer.h"
#include "src/core/telemetry/context_list_entry.h"
#include "src/core/telemetry/default_tcp_tracer.h"
#include "src/core/telemetry/stats.h"
#include "src/core/telemetry/stats_data.h"
#include "src/core/telemetry/tcp_tracer.h"
#include "src/core/util/bitset.h"
#include "src/core/util/crash.h"
#include "src/core/util/debug_location.h"
#include "src/core/util/http_client/parser.h"
#include "src/core/util/notification.h"
#include "src/core/util/ref_counted.h"
#include "src/core/util/shared_bit_gen.h"
#include "src/core/util/status_helper.h"
#include "src/core/util/string.h"
#include "src/core/util/time.h"
#include "src/core/util/useful.h"
using grpc_core::Json;
#define DEFAULT_CONNECTION_WINDOW_TARGET (1024 * 1024)
#define MAX_WINDOW 0x7fffffffu
#define MAX_WRITE_BUFFER_SIZE (64 * 1024 * 1024)
@ -231,7 +226,26 @@ namespace {
using EventEngine = ::grpc_event_engine::experimental::EventEngine;
using TaskHandle = ::grpc_event_engine::experimental::EventEngine::TaskHandle;
using grpc_core::http2::Http2ErrorCode;
grpc_core::CallTracerAnnotationInterface* ParentCallTracerIfSampled(
grpc_chttp2_stream* s) {
auto* parent_call_tracer =
s->arena->GetContext<grpc_core::CallTracerAnnotationInterface>();
if (parent_call_tracer == nullptr || !parent_call_tracer->IsSampled()) {
return nullptr;
}
return parent_call_tracer;
}
std::shared_ptr<grpc_core::TcpTracerInterface> TcpTracerIfSampled(
grpc_chttp2_stream* s) {
auto* call_attempt_tracer =
s->arena->GetContext<grpc_core::CallTracerInterface>();
if (call_attempt_tracer == nullptr || !call_attempt_tracer->IsSampled()) {
return nullptr;
}
return call_attempt_tracer->StartNewTcpTrace();
}
grpc_core::WriteTimestampsCallback g_write_timestamps_callback = nullptr;
grpc_core::CopyContextFn g_get_copied_context_fn = nullptr;
@ -394,10 +408,6 @@ grpc_chttp2_transport::~grpc_chttp2_transport() {
}
}
using grpc_event_engine::experimental::ChannelzExtension;
using grpc_event_engine::experimental::QueryExtension;
using grpc_event_engine::experimental::TcpTraceExtension;
static void read_channel_args(grpc_chttp2_transport* t,
const grpc_core::ChannelArgs& channel_args,
const bool is_client) {
@ -482,15 +492,6 @@ static void read_channel_args(grpc_chttp2_transport* t,
t->peer_string.as_string_view()),
channel_args
.GetObjectRef<grpc_core::channelz::SocketNode::Security>());
// Checks channelz_socket, so must be initialized after.
t->channelz_data_source =
std::make_unique<grpc_chttp2_transport::ChannelzDataSource>(t);
auto epte = QueryExtension<ChannelzExtension>(
grpc_event_engine::experimental::grpc_get_wrapped_event_engine_endpoint(
t->ep.get()));
if (epte != nullptr) {
epte->SetSocketNode(t->channelz_socket);
}
}
t->ack_pings = channel_args.GetBool("grpc.http2.ack_pings").value_or(true);
@ -580,95 +581,6 @@ static void init_keepalive_pings_if_enabled_locked(
}
}
void grpc_chttp2_transport::ChannelzDataSource::AddData(
grpc_core::channelz::DataSink& sink) {
grpc_core::Notification n;
transport_->event_engine->Run([t = transport_->Ref(), &n, &sink]() {
grpc_core::ExecCtx exec_ctx;
t->combiner->Run(
grpc_core::NewClosure([t, &n, &sink](grpc_error_handle) {
Json::Object http2_info;
http2_info["flowControl"] =
Json::FromObject(t->flow_control.stats().ToJsonObject());
Json::Object misc;
misc["maxRequestsPerRead"] =
Json::FromNumber(static_cast<int64_t>(t->max_requests_per_read));
misc["nextStreamId"] = Json::FromNumber(t->next_stream_id);
misc["lastNewStreamId"] = Json::FromNumber(t->last_new_stream_id);
misc["numIncomingStreamsBeforeSettingsAck"] =
Json::FromNumber(t->num_incoming_streams_before_settings_ack);
misc["pingAckCount"] =
Json::FromNumber(static_cast<int64_t>(t->ping_ack_count));
misc["allowTarpit"] = Json::FromBool(t->allow_tarpit);
if (t->allow_tarpit) {
misc["minTarpitDurationMs"] =
Json::FromNumber(t->min_tarpit_duration_ms);
misc["maxTarpitDurationMs"] =
Json::FromNumber(t->max_tarpit_duration_ms);
}
misc["keepaliveTime"] =
Json::FromString(t->keepalive_time.ToJsonString());
misc["nextAdjustedKeepaliveTimestamp"] =
Json::FromString((t->next_adjusted_keepalive_timestamp -
grpc_core::Timestamp::Now())
.ToJsonString());
misc["numMessagesInNextWrite"] =
Json::FromNumber(t->num_messages_in_next_write);
misc["numPendingInducedFrames"] =
Json::FromNumber(t->num_pending_induced_frames);
misc["writeBufferSize"] = Json::FromNumber(t->write_buffer_size);
misc["readingPausedOnPendingInducedFrames"] =
Json::FromBool(t->reading_paused_on_pending_induced_frames);
misc["enablePreferredRxCryptoFrameAdvertisement"] =
Json::FromBool(t->enable_preferred_rx_crypto_frame_advertisement);
misc["keepalivePermitWithoutCalls"] =
Json::FromBool(t->keepalive_permit_without_calls);
misc["bdpPingBlocked"] = Json::FromBool(t->bdp_ping_blocked);
misc["bdpPingStarted"] = Json::FromBool(t->bdp_ping_started);
misc["ackPings"] = Json::FromBool(t->ack_pings);
misc["keepaliveIncomingDataWanted"] =
Json::FromBool(t->keepalive_incoming_data_wanted);
misc["maxConcurrentStreamsOverloadProtection"] =
Json::FromBool(t->max_concurrent_streams_overload_protection);
misc["maxConcurrentStreamsRejectOnClient"] =
Json::FromBool(t->max_concurrent_streams_reject_on_client);
misc["pingOnRstStreamPercent"] =
Json::FromNumber(t->ping_on_rst_stream_percent);
misc["lastWindowUpdateAge"] = Json::FromString(
(grpc_core::Timestamp::Now() - t->last_window_update_time)
.ToJsonString());
http2_info["misc"] = Json::FromObject(std::move(misc));
http2_info["settings"] = Json::FromObject(t->settings.ToJsonObject());
sink.AddAdditionalInfo("http2", std::move(http2_info));
std::vector<grpc_core::RefCountedPtr<grpc_core::channelz::BaseNode>>
children;
children.reserve(t->stream_map.size());
for (auto [id, stream] : t->stream_map) {
if (stream->channelz_call_node == nullptr) {
stream->channelz_call_node =
grpc_core::MakeRefCounted<grpc_core::channelz::CallNode>(
absl::StrCat("chttp2 ",
t->is_client ? "client" : "server",
" stream ", stream->id));
}
children.push_back(stream->channelz_call_node);
}
sink.AddChildObjects(std::move(children));
n.Notify();
}),
absl::OkStatus());
});
n.WaitForNotification();
}
std::unique_ptr<grpc_core::channelz::ZTrace>
grpc_chttp2_transport::ChannelzDataSource::GetZTrace(absl::string_view name) {
if (name == "transport_frames") {
return transport_->http2_ztrace_collector.MakeZTrace();
}
return grpc_core::channelz::DataSource::GetZTrace(name);
}
// TODO(alishananda): add unit testing as part of chttp2 promise conversion work
void grpc_chttp2_transport::WriteSecurityFrame(grpc_core::SliceBuffer* data) {
grpc_core::ExecCtx exec_ctx;
@ -699,6 +611,9 @@ void grpc_chttp2_transport::WriteSecurityFrameLocked(
grpc_chttp2_initiate_write(this, GRPC_CHTTP2_INITIATE_WRITE_SEND_MESSAGE);
}
using grpc_event_engine::experimental::QueryExtension;
using grpc_event_engine::experimental::TcpTraceExtension;
grpc_chttp2_transport::grpc_chttp2_transport(
const grpc_core::ChannelArgs& channel_args,
grpc_core::OrphanablePtr<grpc_endpoint> endpoint, const bool is_client)
@ -734,9 +649,7 @@ grpc_chttp2_transport::grpc_chttp2_transport(
grpc_event_engine::experimental::grpc_get_wrapped_event_engine_endpoint(
ep.get()));
if (epte != nullptr) {
epte->SetTcpTracer(std::make_shared<grpc_core::DefaultTcpTracer>(
channel_args.GetObjectRef<
grpc_core::GlobalStatsPluginRegistry::StatsPluginGroup>()));
epte->InitializeAndReturnTcpTracer();
}
}
@ -811,7 +724,11 @@ static void destroy_transport_locked(void* tp, grpc_error_handle /*error*/) {
grpc_core::RefCountedPtr<grpc_chttp2_transport> t(
static_cast<grpc_chttp2_transport*>(tp));
t->destroying = 1;
close_transport_locked(t.get(), GRPC_ERROR_CREATE("Transport destroyed"));
close_transport_locked(
t.get(),
grpc_error_set_int(GRPC_ERROR_CREATE("Transport destroyed"),
grpc_core::StatusIntProperty::kOccurredDuringWrite,
t->write_state));
t->memory_owner.Reset();
}
@ -943,8 +860,7 @@ grpc_chttp2_stream::grpc_chttp2_stream(grpc_chttp2_transport* t,
}()),
arena(arena),
flow_control(&t->flow_control),
call_tracer_wrapper(this),
call_tracer(arena->GetContext<grpc_core::CallTracerInterface>()) {
call_tracer_wrapper(this) {
t->streams_allocated.fetch_add(1, std::memory_order_relaxed);
if (server_data) {
id = static_cast<uint32_t>(reinterpret_cast<uintptr_t>(server_data));
@ -1185,8 +1101,6 @@ static void write_action(grpc_chttp2_transport* t) {
<< (t->is_client ? "CLIENT" : "SERVER") << "[" << t << "]: Write "
<< t->outbuf.Length() << " bytes";
t->write_size_policy.BeginWrite(t->outbuf.Length());
t->http2_ztrace_collector.Append(grpc_core::H2BeginEndpointWrite{
static_cast<uint32_t>(t->outbuf.Length())});
grpc_endpoint_write(t->ep.get(), t->outbuf.c_slice_buffer(),
grpc_core::InitTransportClosure<write_action_end>(
t->Ref(), &t->write_action_end_locked),
@ -1283,7 +1197,7 @@ void grpc_chttp2_add_incoming_goaway(grpc_chttp2_transport* t,
<< last_stream_id;
// We want to log this irrespective of whether http tracing is enabled if we
// received a GOAWAY with a non NO_ERROR code.
if (goaway_error != static_cast<int>(Http2ErrorCode::kNoError)) {
if (goaway_error != GRPC_HTTP2_NO_ERROR) {
LOG(INFO) << t->peer_string.as_string_view() << ": Got goaway ["
<< goaway_error
<< "] err=" << grpc_core::StatusToString(t->goaway_error);
@ -1310,8 +1224,7 @@ void grpc_chttp2_add_incoming_goaway(grpc_chttp2_transport* t,
// that is enabled by default and double the configured KEEPALIVE_TIME used
// for new connections on that channel.
if (GPR_UNLIKELY(t->is_client &&
goaway_error ==
static_cast<int>(Http2ErrorCode::kEnhanceYourCalm) &&
goaway_error == GRPC_HTTP2_ENHANCE_YOUR_CALM &&
goaway_text == "too_many_pings")) {
LOG(ERROR) << t->peer_string.as_string_view()
<< ": Received a GOAWAY with error code ENHANCE_YOUR_CALM and "
@ -1468,12 +1381,23 @@ static void log_metadata(const grpc_metadata_batch* md_batch, uint32_t id,
}
static void trace_annotations(grpc_chttp2_stream* s) {
if (s->call_tracer != nullptr && s->call_tracer->IsSampled()) {
s->call_tracer->RecordAnnotation(
grpc_core::HttpAnnotation(grpc_core::HttpAnnotation::Type::kStart,
gpr_now(GPR_CLOCK_REALTIME))
.Add(s->t->flow_control.stats())
.Add(s->flow_control.stats()));
if (!grpc_core::IsCallTracerTransportFixEnabled()) {
if (s->parent_call_tracer != nullptr) {
s->parent_call_tracer->RecordAnnotation(
grpc_core::HttpAnnotation(grpc_core::HttpAnnotation::Type::kStart,
gpr_now(GPR_CLOCK_REALTIME))
.Add(s->t->flow_control.stats())
.Add(s->flow_control.stats()));
}
} else {
auto* call_tracer = s->CallTracer();
if (call_tracer != nullptr && call_tracer->IsSampled()) {
call_tracer->RecordAnnotation(
grpc_core::HttpAnnotation(grpc_core::HttpAnnotation::Type::kStart,
gpr_now(GPR_CLOCK_REALTIME))
.Add(s->t->flow_control.stats())
.Add(s->flow_control.stats()));
}
}
}
@ -1722,13 +1646,17 @@ static void perform_stream_op_locked(void* stream_op,
grpc_chttp2_transport* t = s->t.get();
s->traced = op->is_traced;
// Some server filters populate CallTracerInterface in the context only after
// reading initial metadata. (Client-side population is done by
// client_channel filter.)
if (!t->is_client && !grpc_core::IsCallTracerInTransportEnabled() &&
op->send_initial_metadata) {
if (!grpc_core::IsCallTracerTransportFixEnabled()) {
s->parent_call_tracer = ParentCallTracerIfSampled(s);
}
// TODO(yashykt): Remove call_tracer field after transition to call v3. (See
// https://github.com/grpc/grpc/pull/38729 for more information.) On the
// client, the call attempt tracer will be available for use when the
// send_initial_metadata op arrives.
if (s->t->is_client && op->send_initial_metadata) {
s->call_tracer = s->arena->GetContext<grpc_core::CallTracerInterface>();
}
s->tcp_tracer = TcpTracerIfSampled(s);
if (GRPC_TRACE_FLAG_ENABLED(http)) {
LOG(INFO) << "perform_stream_op_locked[s=" << s << "; op=" << op
<< "]: " << grpc_transport_stream_op_batch_string(op, false)
@ -1919,10 +1847,9 @@ void grpc_chttp2_keepalive_timeout(
<< ": Keepalive timeout. Closing transport.";
send_goaway(
t.get(),
grpc_error_set_int(
GRPC_ERROR_CREATE("keepalive_timeout"),
grpc_core::StatusIntProperty::kHttp2Error,
static_cast<intptr_t>(Http2ErrorCode::kEnhanceYourCalm)),
grpc_error_set_int(GRPC_ERROR_CREATE("keepalive_timeout"),
grpc_core::StatusIntProperty::kHttp2Error,
GRPC_HTTP2_ENHANCE_YOUR_CALM),
/*immediate_disconnect_hint=*/true);
close_transport_locked(
t.get(),
@ -1941,10 +1868,9 @@ void grpc_chttp2_ping_timeout(
<< ": Ping timeout. Closing transport.";
send_goaway(
t.get(),
grpc_error_set_int(
GRPC_ERROR_CREATE("ping_timeout"),
grpc_core::StatusIntProperty::kHttp2Error,
static_cast<intptr_t>(Http2ErrorCode::kEnhanceYourCalm)),
grpc_error_set_int(GRPC_ERROR_CREATE("ping_timeout"),
grpc_core::StatusIntProperty::kHttp2Error,
GRPC_HTTP2_ENHANCE_YOUR_CALM),
/*immediate_disconnect_hint=*/true);
close_transport_locked(
t.get(),
@ -1963,10 +1889,9 @@ void grpc_chttp2_settings_timeout(
<< ": Settings timeout. Closing transport.";
send_goaway(
t.get(),
grpc_error_set_int(
GRPC_ERROR_CREATE("settings_timeout"),
grpc_core::StatusIntProperty::kHttp2Error,
static_cast<intptr_t>(Http2ErrorCode::kSettingsTimeout)),
grpc_error_set_int(GRPC_ERROR_CREATE("settings_timeout"),
grpc_core::StatusIntProperty::kHttp2Error,
GRPC_HTTP2_SETTINGS_TIMEOUT),
/*immediate_disconnect_hint=*/true);
close_transport_locked(
t.get(),
@ -2005,8 +1930,7 @@ class GracefulGoaway : public grpc_core::RefCounted<GracefulGoaway> {
// Graceful GOAWAYs require a NO_ERROR error code
grpc_chttp2_goaway_append(
(1u << 31) - 1, 0 /*NO_ERROR*/,
grpc_core::Slice::FromCopiedString(message_).TakeCSlice(), &t->qbuf,
&t->http2_ztrace_collector);
grpc_core::Slice::FromCopiedString(message_).TakeCSlice(), &t->qbuf);
t->keepalive_timeout =
std::min(t->keepalive_timeout, grpc_core::Duration::Seconds(20));
t->ping_timeout =
@ -2040,8 +1964,7 @@ class GracefulGoaway : public grpc_core::RefCounted<GracefulGoaway> {
t_->sent_goaway_state = GRPC_CHTTP2_FINAL_GOAWAY_SEND_SCHEDULED;
grpc_chttp2_goaway_append(
t_->last_new_stream_id, 0 /*NO_ERROR*/,
grpc_core::Slice::FromCopiedString(message_).TakeCSlice(), &t_->qbuf,
&t_->http2_ztrace_collector);
grpc_core::Slice::FromCopiedString(message_).TakeCSlice(), &t_->qbuf);
grpc_chttp2_initiate_write(t_.get(),
GRPC_CHTTP2_INITIATE_WRITE_GOAWAY_SENT);
}
@ -2068,7 +1991,7 @@ class GracefulGoaway : public grpc_core::RefCounted<GracefulGoaway> {
static void send_goaway(grpc_chttp2_transport* t, grpc_error_handle error,
const bool immediate_disconnect_hint) {
Http2ErrorCode http_error;
grpc_http2_error_code http_error;
std::string message;
grpc_error_get_status(error, grpc_core::Timestamp::InfFuture(), nullptr,
&message, &http_error, nullptr);
@ -2087,10 +2010,9 @@ static void send_goaway(grpc_chttp2_transport* t, grpc_error_handle error,
<< ": Sending goaway last_new_stream_id=" << t->last_new_stream_id
<< " err=" << grpc_core::StatusToString(error);
t->sent_goaway_state = GRPC_CHTTP2_FINAL_GOAWAY_SEND_SCHEDULED;
grpc_chttp2_goaway_append(t->last_new_stream_id,
static_cast<uint32_t>(http_error),
grpc_slice_from_cpp_string(std::move(message)),
&t->qbuf, &t->http2_ztrace_collector);
grpc_chttp2_goaway_append(
t->last_new_stream_id, static_cast<uint32_t>(http_error),
grpc_slice_from_cpp_string(std::move(message)), &t->qbuf);
} else {
// Final GOAWAY has already been sent.
}
@ -2099,10 +2021,9 @@ static void send_goaway(grpc_chttp2_transport* t, grpc_error_handle error,
void grpc_chttp2_exceeded_ping_strikes(grpc_chttp2_transport* t) {
send_goaway(t,
grpc_error_set_int(
GRPC_ERROR_CREATE("too_many_pings"),
grpc_core::StatusIntProperty::kHttp2Error,
static_cast<intptr_t>(Http2ErrorCode::kEnhanceYourCalm)),
grpc_error_set_int(GRPC_ERROR_CREATE("too_many_pings"),
grpc_core::StatusIntProperty::kHttp2Error,
GRPC_HTTP2_ENHANCE_YOUR_CALM),
/*immediate_disconnect_hint=*/true);
// The transport will be closed after the write is done
close_transport_locked(
@ -2344,7 +2265,7 @@ namespace {
Duration TarpitDuration(grpc_chttp2_transport* t) {
return Duration::Milliseconds(absl::LogUniform<int>(
SharedBitGen(), t->min_tarpit_duration_ms, t->max_tarpit_duration_ms));
absl::BitGen(), t->min_tarpit_duration_ms, t->max_tarpit_duration_ms));
}
template <typename F>
@ -2385,25 +2306,14 @@ void grpc_chttp2_cancel_stream(grpc_chttp2_transport* t, grpc_chttp2_stream* s,
}
if (!s->read_closed || !s->write_closed) {
if (s->id != 0) {
Http2ErrorCode http_error;
grpc_http2_error_code http_error;
grpc_error_get_status(due_to_error, s->deadline, nullptr, nullptr,
&http_error, nullptr);
grpc_core::MaybeTarpit(
t, tarpit,
// Capture the individual fields of the stream by value, since the
// stream state might have been deleted by the time we run the lambda.
[id = s->id, sent_initial_metadata = s->sent_initial_metadata,
http_error,
[id = s->id, http_error,
remove_stream_handle = grpc_chttp2_mark_stream_closed(
t, s, 1, 1, due_to_error)](grpc_chttp2_transport* t) {
// Do not send RST_STREAM from the client for a stream that hasn't
// sent headers yet (still in "idle" state). Note that since we have
// marked the stream closed above, we won't be writing to it
// anymore.
if (grpc_core::IsRstStreamFixEnabled() && t->is_client &&
!sent_initial_metadata) {
return;
}
grpc_chttp2_add_rst_stream_to_next_write(
t, id, static_cast<uint32_t>(http_error), nullptr);
grpc_chttp2_initiate_write(t,
@ -2731,8 +2641,8 @@ static void close_from_api(grpc_chttp2_transport* t, grpc_chttp2_stream* s,
grpc_slice_buffer_add(&t->qbuf,
grpc_slice_from_cpp_string(std::move(message)));
grpc_chttp2_reset_ping_clock(t);
grpc_chttp2_add_rst_stream_to_next_write(
t, id, static_cast<intptr_t>(Http2ErrorCode::kNoError), nullptr);
grpc_chttp2_add_rst_stream_to_next_write(t, id, GRPC_HTTP2_NO_ERROR,
nullptr);
grpc_chttp2_initiate_write(t,
GRPC_CHTTP2_INITIATE_WRITE_CLOSE_FROM_API);
@ -2947,7 +2857,9 @@ static void read_action_locked(
}
grpc_error_handle err = error;
if (!err.ok()) {
err = GRPC_ERROR_CREATE_REFERENCING("Endpoint read failed", &err, 1);
err = grpc_error_set_int(
GRPC_ERROR_CREATE_REFERENCING("Endpoint read failed", &err, 1),
grpc_core::StatusIntProperty::kOccurredDuringWrite, t->write_state);
}
std::swap(err, error);
read_action_parse_loop_locked(std::move(t), std::move(err));
@ -3306,10 +3218,9 @@ static void benign_reclaimer_locked(
<< "HTTP2: " << t->peer_string.as_string_view()
<< " - send goaway to free memory";
send_goaway(t.get(),
grpc_error_set_int(
GRPC_ERROR_CREATE("Buffers full"),
grpc_core::StatusIntProperty::kHttp2Error,
static_cast<intptr_t>(Http2ErrorCode::kEnhanceYourCalm)),
grpc_error_set_int(GRPC_ERROR_CREATE("Buffers full"),
grpc_core::StatusIntProperty::kHttp2Error,
GRPC_HTTP2_ENHANCE_YOUR_CALM),
/*immediate_disconnect_hint=*/true);
} else if (error.ok() && GRPC_TRACE_FLAG_ENABLED(resource_quota)) {
LOG(INFO) << "HTTP2: " << t->peer_string.as_string_view()
@ -3335,10 +3246,9 @@ static void destructive_reclaimer_locked(
grpc_core::global_stats().IncrementRqCallsDropped();
grpc_chttp2_cancel_stream(
t.get(), s,
grpc_error_set_int(
GRPC_ERROR_CREATE("Buffers full"),
grpc_core::StatusIntProperty::kHttp2Error,
static_cast<intptr_t>(Http2ErrorCode::kEnhanceYourCalm)),
grpc_error_set_int(GRPC_ERROR_CREATE("Buffers full"),
grpc_core::StatusIntProperty::kHttp2Error,
GRPC_HTTP2_ENHANCE_YOUR_CALM),
false);
if (!t->stream_map.empty()) {
// Since we cancel one stream per destructive reclamation, if
@ -3421,6 +3331,13 @@ absl::string_view grpc_chttp2_transport::GetTransportName() const {
return "chttp2";
}
grpc_core::RefCountedPtr<grpc_core::channelz::SocketNode>
grpc_chttp2_transport_get_socket_node(grpc_core::Transport* transport) {
grpc_chttp2_transport* t =
reinterpret_cast<grpc_chttp2_transport*>(transport);
return t->channelz_socket;
}
grpc_core::Transport* grpc_create_chttp2_transport(
const grpc_core::ChannelArgs& channel_args,
grpc_core::OrphanablePtr<grpc_endpoint> ep, const bool is_client) {

View File

@ -46,6 +46,9 @@ grpc_core::Transport* grpc_create_chttp2_transport(
const grpc_core::ChannelArgs& channel_args,
grpc_core::OrphanablePtr<grpc_endpoint> ep, bool is_client);
grpc_core::RefCountedPtr<grpc_core::channelz::SocketNode>
grpc_chttp2_transport_get_socket_node(grpc_core::Transport* transport);
/// Takes ownership of \a read_buffer, which (if non-NULL) contains
/// leftover bytes previously read from the endpoint (e.g., by handshakers).
/// If non-null, \a notify_on_receive_settings will be scheduled when

View File

@ -16,8 +16,8 @@
//
//
#ifndef GRPC_SRC_CORE_TELEMETRY_CONTEXT_LIST_ENTRY_H
#define GRPC_SRC_CORE_TELEMETRY_CONTEXT_LIST_ENTRY_H
#ifndef GRPC_SRC_CORE_EXT_TRANSPORT_CHTTP2_TRANSPORT_CONTEXT_LIST_ENTRY_H
#define GRPC_SRC_CORE_EXT_TRANSPORT_CHTTP2_TRANSPORT_CONTEXT_LIST_ENTRY_H
#include <grpc/support/port_platform.h>
#include <stddef.h>
@ -42,7 +42,7 @@ class ContextListEntry {
ContextListEntry(void* context, int64_t outbuf_offset,
int64_t num_traced_bytes, size_t byte_offset,
size_t stream_index,
std::shared_ptr<TcpCallTracer> tcp_tracer)
std::shared_ptr<TcpTracerInterface> tcp_tracer)
: trace_context_(context),
outbuf_offset_(outbuf_offset),
num_traced_bytes_in_chunk_(num_traced_bytes),
@ -57,7 +57,7 @@ class ContextListEntry {
int64_t NumTracedBytesInChunk() { return num_traced_bytes_in_chunk_; }
size_t ByteOffsetInStream() { return byte_offset_in_stream_; }
size_t StreamIndex() { return stream_index_; }
std::shared_ptr<TcpCallTracer> ReleaseTcpTracer() {
std::shared_ptr<TcpTracerInterface> ReleaseTcpTracer() {
return std::move(tcp_tracer_);
}
@ -72,11 +72,11 @@ class ContextListEntry {
// Index of the current chunk in the RPC stream.
// Set to zero for the first chunk of the RPC stream.
size_t stream_index_;
std::shared_ptr<TcpCallTracer> tcp_tracer_;
std::shared_ptr<TcpTracerInterface> tcp_tracer_;
};
/// A list of RPC Contexts
typedef std::vector<ContextListEntry> ContextList;
} // namespace grpc_core
#endif // GRPC_SRC_CORE_TELEMETRY_CONTEXT_LIST_ENTRY_H
#endif // GRPC_SRC_CORE_EXT_TRANSPORT_CHTTP2_TRANSPORT_CONTEXT_LIST_ENTRY_H

View File

@ -302,24 +302,6 @@ class TransportFlowControl final {
double bdp_bw_est;
std::string ToString() const;
Json::Object ToJsonObject() {
Json::Object object;
object["targetWindow"] = Json::FromNumber(target_window);
object["targetFrameSize"] = Json::FromNumber(target_frame_size);
object["targetPreferredRxCryptoFrameSize"] =
Json::FromNumber(target_preferred_rx_crypto_frame_size);
object["ackedInitWindow"] = Json::FromNumber(acked_init_window);
object["queuedInitWindow"] = Json::FromNumber(queued_init_window);
object["sentInitWindow"] = Json::FromNumber(sent_init_window);
object["remoteWindow"] = Json::FromNumber(remote_window);
object["announcedWindow"] = Json::FromNumber(announced_window);
object["announcedStreamTotalOverIncomingWindow"] =
Json::FromNumber(announced_stream_total_over_incoming_window);
object["bdpAccumulator"] = Json::FromNumber(bdp_accumulator);
object["bdpEstimate"] = Json::FromNumber(bdp_estimate);
object["bdpBwEst"] = Json::FromNumber(bdp_bw_est);
return object;
}
};
Stats stats() const {

Some files were not shown because too many files have changed in this diff Show More