grpc 1.19.0 → 1.20.0.pre1

Sign up to get free protection for your applications and to get access to all the features.

Potentially problematic release.


This version of grpc might be problematic. Click here for more details.

Files changed (224) hide show
  1. checksums.yaml +4 -4
  2. data/Makefile +4131 -7903
  3. data/include/grpc/grpc.h +11 -6
  4. data/include/grpc/grpc_security.h +51 -9
  5. data/include/grpc/impl/codegen/byte_buffer.h +13 -0
  6. data/include/grpc/impl/codegen/grpc_types.h +4 -0
  7. data/include/grpc/impl/codegen/port_platform.h +37 -6
  8. data/include/grpc/impl/codegen/sync_posix.h +18 -0
  9. data/src/core/ext/filters/client_channel/client_channel.cc +560 -236
  10. data/src/core/ext/filters/client_channel/client_channel_channelz.h +2 -2
  11. data/src/core/ext/filters/client_channel/client_channel_factory.cc +22 -34
  12. data/src/core/ext/filters/client_channel/client_channel_factory.h +19 -38
  13. data/src/core/ext/filters/client_channel/global_subchannel_pool.cc +7 -4
  14. data/src/core/ext/filters/client_channel/http_connect_handshaker.cc +2 -2
  15. data/src/core/ext/filters/client_channel/lb_policy.cc +105 -28
  16. data/src/core/ext/filters/client_channel/lb_policy.h +259 -141
  17. data/src/core/ext/filters/client_channel/lb_policy/grpclb/client_load_reporting_filter.cc +29 -32
  18. data/src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb.cc +789 -803
  19. data/src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb_channel.h +3 -1
  20. data/src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb_channel_secure.cc +2 -6
  21. data/src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb_client_stats.cc +1 -1
  22. data/src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb_client_stats.h +7 -1
  23. data/src/core/ext/filters/client_channel/lb_policy/grpclb/load_balancer_api.cc +8 -8
  24. data/src/core/ext/filters/client_channel/lb_policy/grpclb/load_balancer_api.h +2 -2
  25. data/src/core/ext/filters/client_channel/lb_policy/pick_first/pick_first.cc +127 -219
  26. data/src/core/ext/filters/client_channel/lb_policy/round_robin/round_robin.cc +103 -282
  27. data/src/core/ext/filters/client_channel/lb_policy/subchannel_list.h +4 -10
  28. data/src/core/ext/filters/client_channel/lb_policy/xds/xds.cc +709 -906
  29. data/src/core/ext/filters/client_channel/lb_policy/xds/xds_channel_secure.cc +0 -43
  30. data/src/core/ext/filters/client_channel/lb_policy/xds/xds_load_balancer_api.cc +8 -8
  31. data/src/core/ext/filters/client_channel/lb_policy/xds/xds_load_balancer_api.h +2 -2
  32. data/src/core/ext/filters/client_channel/lb_policy_factory.h +1 -6
  33. data/src/core/ext/filters/client_channel/resolver.cc +54 -1
  34. data/src/core/ext/filters/client_channel/resolver.h +51 -22
  35. data/src/core/ext/filters/client_channel/resolver/dns/c_ares/dns_resolver_ares.cc +34 -86
  36. data/src/core/ext/filters/client_channel/resolver/dns/c_ares/grpc_ares_wrapper.cc +29 -41
  37. data/src/core/ext/filters/client_channel/resolver/dns/native/dns_resolver.cc +32 -78
  38. data/src/core/ext/filters/client_channel/resolver/fake/fake_resolver.cc +109 -72
  39. data/src/core/ext/filters/client_channel/resolver/fake/fake_resolver.h +13 -8
  40. data/src/core/ext/filters/client_channel/resolver/sockaddr/sockaddr_resolver.cc +28 -63
  41. data/src/core/ext/filters/client_channel/resolver_factory.h +3 -1
  42. data/src/core/ext/filters/client_channel/resolver_registry.cc +5 -2
  43. data/src/core/ext/filters/client_channel/resolver_registry.h +5 -4
  44. data/src/core/ext/filters/client_channel/resolver_result_parsing.cc +69 -49
  45. data/src/core/ext/filters/client_channel/resolver_result_parsing.h +11 -8
  46. data/src/core/ext/filters/client_channel/resolving_lb_policy.cc +568 -0
  47. data/src/core/ext/filters/client_channel/resolving_lb_policy.h +141 -0
  48. data/src/core/ext/filters/client_channel/server_address.cc +0 -48
  49. data/src/core/ext/filters/client_channel/server_address.h +0 -10
  50. data/src/core/{lib/transport → ext/filters/client_channel}/service_config.cc +10 -5
  51. data/src/core/{lib/transport → ext/filters/client_channel}/service_config.h +16 -12
  52. data/src/core/ext/filters/client_channel/subchannel.cc +11 -16
  53. data/src/core/ext/filters/client_channel/subchannel.h +3 -0
  54. data/src/core/ext/filters/max_age/max_age_filter.cc +4 -1
  55. data/src/core/ext/filters/message_size/message_size_filter.cc +2 -2
  56. data/src/core/ext/transport/chttp2/client/insecure/channel_create.cc +45 -45
  57. data/src/core/ext/transport/chttp2/client/secure/secure_channel_create.cc +133 -134
  58. data/src/core/ext/transport/chttp2/transport/bin_decoder.cc +4 -4
  59. data/src/core/ext/transport/chttp2/transport/bin_decoder.h +4 -4
  60. data/src/core/ext/transport/chttp2/transport/bin_encoder.cc +7 -6
  61. data/src/core/ext/transport/chttp2/transport/bin_encoder.h +4 -3
  62. data/src/core/ext/transport/chttp2/transport/chttp2_transport.cc +37 -29
  63. data/src/core/ext/transport/chttp2/transport/flow_control.cc +1 -1
  64. data/src/core/ext/transport/chttp2/transport/frame_data.cc +2 -1
  65. data/src/core/ext/transport/chttp2/transport/frame_data.h +1 -1
  66. data/src/core/ext/transport/chttp2/transport/frame_goaway.cc +6 -5
  67. data/src/core/ext/transport/chttp2/transport/frame_goaway.h +3 -2
  68. data/src/core/ext/transport/chttp2/transport/frame_ping.cc +5 -4
  69. data/src/core/ext/transport/chttp2/transport/frame_ping.h +1 -1
  70. data/src/core/ext/transport/chttp2/transport/frame_rst_stream.cc +5 -4
  71. data/src/core/ext/transport/chttp2/transport/frame_rst_stream.h +2 -1
  72. data/src/core/ext/transport/chttp2/transport/frame_settings.cc +2 -1
  73. data/src/core/ext/transport/chttp2/transport/frame_settings.h +2 -1
  74. data/src/core/ext/transport/chttp2/transport/frame_window_update.cc +4 -4
  75. data/src/core/ext/transport/chttp2/transport/frame_window_update.h +1 -1
  76. data/src/core/ext/transport/chttp2/transport/hpack_parser.cc +7 -6
  77. data/src/core/ext/transport/chttp2/transport/hpack_parser.h +3 -2
  78. data/src/core/ext/transport/chttp2/transport/incoming_metadata.cc +9 -5
  79. data/src/core/ext/transport/chttp2/transport/incoming_metadata.h +6 -1
  80. data/src/core/ext/transport/chttp2/transport/internal.h +5 -4
  81. data/src/core/ext/transport/chttp2/transport/parsing.cc +9 -9
  82. data/src/core/ext/transport/chttp2/transport/writing.cc +1 -1
  83. data/src/core/ext/transport/inproc/inproc_transport.cc +8 -0
  84. data/src/core/lib/channel/channel_args.cc +2 -0
  85. data/src/core/lib/channel/channel_args.h +3 -0
  86. data/src/core/lib/channel/channel_stack.h +1 -1
  87. data/src/core/lib/channel/channel_trace.cc +4 -4
  88. data/src/core/lib/channel/channel_trace.h +4 -4
  89. data/src/core/lib/channel/channelz.cc +32 -19
  90. data/src/core/lib/channel/channelz.h +4 -4
  91. data/src/core/lib/channel/channelz_registry.cc +1 -1
  92. data/src/core/lib/channel/context.h +0 -3
  93. data/src/core/lib/channel/handshaker_registry.cc +7 -3
  94. data/src/core/lib/compression/algorithm_metadata.h +3 -3
  95. data/src/core/lib/compression/compression.cc +1 -1
  96. data/src/core/lib/compression/compression_internal.cc +2 -2
  97. data/src/core/lib/compression/stream_compression_gzip.cc +1 -1
  98. data/src/core/lib/debug/trace.h +2 -1
  99. data/src/core/lib/gpr/cpu_posix.cc +5 -3
  100. data/src/core/lib/gpr/sync_posix.cc +65 -4
  101. data/src/core/lib/gprpp/atomic.h +75 -5
  102. data/src/core/lib/gprpp/fork.cc +0 -2
  103. data/src/core/lib/gprpp/orphanable.h +3 -2
  104. data/src/core/lib/gprpp/ref_counted.h +9 -11
  105. data/src/core/lib/gprpp/thd.h +42 -7
  106. data/src/core/lib/gprpp/thd_posix.cc +31 -13
  107. data/src/core/lib/gprpp/thd_windows.cc +47 -34
  108. data/src/core/lib/http/httpcli.cc +3 -2
  109. data/src/core/lib/http/httpcli_security_connector.cc +0 -1
  110. data/src/core/lib/http/parser.cc +2 -1
  111. data/src/core/lib/http/parser.h +2 -1
  112. data/src/core/lib/iomgr/buffer_list.h +1 -1
  113. data/src/core/lib/iomgr/endpoint.cc +2 -2
  114. data/src/core/lib/iomgr/endpoint.h +3 -2
  115. data/src/core/lib/iomgr/error.cc +9 -9
  116. data/src/core/lib/iomgr/error.h +4 -3
  117. data/src/core/lib/iomgr/ev_epoll1_linux.cc +6 -0
  118. data/src/core/lib/iomgr/ev_epollex_linux.cc +14 -9
  119. data/src/core/lib/iomgr/ev_poll_posix.cc +7 -481
  120. data/src/core/lib/iomgr/ev_posix.cc +7 -3
  121. data/src/core/lib/iomgr/ev_posix.h +8 -0
  122. data/src/core/lib/iomgr/executor.cc +13 -0
  123. data/src/core/lib/iomgr/executor.h +2 -1
  124. data/src/core/lib/iomgr/internal_errqueue.cc +2 -4
  125. data/src/core/lib/iomgr/iomgr.cc +5 -0
  126. data/src/core/lib/iomgr/iomgr.h +7 -0
  127. data/src/core/lib/iomgr/iomgr_custom.cc +9 -2
  128. data/src/core/lib/iomgr/iomgr_internal.cc +6 -0
  129. data/src/core/lib/iomgr/iomgr_internal.h +9 -1
  130. data/src/core/lib/iomgr/iomgr_posix.cc +10 -2
  131. data/src/core/lib/iomgr/iomgr_windows.cc +10 -2
  132. data/src/core/lib/iomgr/port.h +19 -0
  133. data/src/core/lib/iomgr/tcp_client_windows.cc +6 -4
  134. data/src/core/lib/iomgr/tcp_custom.cc +1 -1
  135. data/src/core/lib/iomgr/tcp_posix.cc +158 -54
  136. data/src/core/lib/iomgr/tcp_windows.cc +1 -1
  137. data/src/core/lib/iomgr/wakeup_fd_posix.cc +1 -19
  138. data/src/core/lib/security/credentials/jwt/jwt_verifier.cc +10 -6
  139. data/src/core/lib/security/credentials/jwt/jwt_verifier.h +2 -1
  140. data/src/core/lib/security/credentials/tls/grpc_tls_credentials_options.h +3 -6
  141. data/src/core/lib/security/credentials/tls/spiffe_credentials.cc +129 -0
  142. data/src/core/lib/security/credentials/tls/spiffe_credentials.h +62 -0
  143. data/src/core/lib/security/security_connector/fake/fake_security_connector.cc +7 -2
  144. data/src/core/lib/security/security_connector/ssl/ssl_security_connector.cc +28 -17
  145. data/src/core/lib/security/security_connector/ssl_utils.cc +134 -0
  146. data/src/core/lib/security/security_connector/ssl_utils.h +32 -0
  147. data/src/core/lib/security/security_connector/tls/spiffe_security_connector.cc +426 -0
  148. data/src/core/lib/security/security_connector/tls/spiffe_security_connector.h +122 -0
  149. data/src/core/lib/security/transport/auth_filters.h +2 -2
  150. data/src/core/lib/security/transport/client_auth_filter.cc +35 -39
  151. data/src/core/lib/security/transport/secure_endpoint.cc +2 -2
  152. data/src/core/lib/security/transport/security_handshaker.cc +4 -3
  153. data/src/core/lib/slice/percent_encoding.cc +3 -3
  154. data/src/core/lib/slice/percent_encoding.h +3 -3
  155. data/src/core/lib/slice/slice.cc +27 -30
  156. data/src/core/lib/slice/slice_hash_table.h +2 -2
  157. data/src/core/lib/slice/slice_intern.cc +1 -1
  158. data/src/core/lib/slice/slice_internal.h +14 -3
  159. data/src/core/lib/slice/slice_weak_hash_table.h +4 -4
  160. data/src/core/lib/surface/byte_buffer_reader.cc +17 -0
  161. data/src/core/lib/surface/call.cc +8 -3
  162. data/src/core/lib/surface/completion_queue.cc +134 -148
  163. data/src/core/lib/surface/init.cc +78 -30
  164. data/src/core/lib/surface/init.h +1 -0
  165. data/src/core/lib/surface/lame_client.cc +4 -6
  166. data/src/core/lib/surface/version.cc +1 -1
  167. data/src/core/lib/transport/metadata.cc +66 -33
  168. data/src/core/lib/transport/metadata_batch.cc +1 -1
  169. data/src/core/lib/transport/metadata_batch.h +1 -1
  170. data/src/core/lib/transport/timeout_encoding.cc +1 -1
  171. data/src/core/lib/transport/timeout_encoding.h +1 -1
  172. data/src/core/lib/transport/transport.h +4 -3
  173. data/src/core/tsi/alts/handshaker/alts_handshaker_client.cc +3 -3
  174. data/src/core/tsi/alts/handshaker/alts_handshaker_client.h +1 -1
  175. data/src/core/tsi/alts/handshaker/transport_security_common_api.cc +4 -3
  176. data/src/core/tsi/alts/handshaker/transport_security_common_api.h +1 -1
  177. data/src/core/tsi/alts/zero_copy_frame_protector/alts_zero_copy_grpc_protector.cc +1 -1
  178. data/src/core/tsi/ssl_transport_security.cc +1 -5
  179. data/src/core/tsi/ssl_transport_security.h +24 -4
  180. data/src/ruby/bin/math_pb.rb +18 -16
  181. data/src/ruby/ext/grpc/rb_grpc_imports.generated.c +4 -0
  182. data/src/ruby/ext/grpc/rb_grpc_imports.generated.h +6 -0
  183. data/src/ruby/lib/grpc/generic/rpc_server.rb +1 -1
  184. data/src/ruby/lib/grpc/version.rb +1 -1
  185. data/src/ruby/pb/README.md +1 -1
  186. data/src/ruby/pb/grpc/health/v1/health_pb.rb +13 -10
  187. data/src/ruby/pb/grpc/health/v1/health_services_pb.rb +18 -0
  188. data/src/ruby/pb/src/proto/grpc/testing/empty_pb.rb +3 -1
  189. data/src/ruby/pb/src/proto/grpc/testing/messages_pb.rb +58 -56
  190. data/src/ruby/pb/src/proto/grpc/testing/test_pb.rb +2 -0
  191. data/third_party/cares/cares/ares.h +12 -0
  192. data/third_party/cares/cares/ares_create_query.c +5 -1
  193. data/third_party/cares/cares/ares_data.c +74 -73
  194. data/third_party/cares/cares/ares_destroy.c +6 -1
  195. data/third_party/cares/cares/ares_gethostbyaddr.c +5 -5
  196. data/third_party/cares/cares/ares_gethostbyname.c +15 -4
  197. data/third_party/cares/cares/ares_getnameinfo.c +11 -0
  198. data/third_party/cares/cares/ares_init.c +274 -173
  199. data/third_party/cares/cares/ares_library_init.c +21 -3
  200. data/third_party/cares/cares/ares_options.c +6 -2
  201. data/third_party/cares/cares/ares_parse_naptr_reply.c +7 -6
  202. data/third_party/cares/cares/ares_parse_ptr_reply.c +4 -2
  203. data/third_party/cares/cares/ares_platform.c +7 -0
  204. data/third_party/cares/cares/ares_private.h +19 -11
  205. data/third_party/cares/cares/ares_process.c +27 -2
  206. data/third_party/cares/cares/ares_rules.h +1 -1
  207. data/third_party/cares/cares/ares_search.c +7 -0
  208. data/third_party/cares/cares/ares_send.c +6 -0
  209. data/third_party/cares/cares/ares_strsplit.c +174 -0
  210. data/third_party/cares/cares/ares_strsplit.h +43 -0
  211. data/third_party/cares/cares/ares_version.h +4 -4
  212. data/third_party/cares/cares/config-win32.h +1 -1
  213. data/third_party/cares/cares/inet_ntop.c +2 -3
  214. data/third_party/cares/config_darwin/ares_config.h +3 -0
  215. data/third_party/cares/config_freebsd/ares_config.h +3 -0
  216. data/third_party/cares/config_linux/ares_config.h +3 -0
  217. data/third_party/cares/config_openbsd/ares_config.h +3 -0
  218. metadata +39 -37
  219. data/src/core/ext/filters/client_channel/request_routing.cc +0 -946
  220. data/src/core/ext/filters/client_channel/request_routing.h +0 -181
  221. data/src/core/lib/gprpp/atomic_with_atm.h +0 -57
  222. data/src/core/lib/gprpp/atomic_with_std.h +0 -35
  223. data/src/core/lib/iomgr/wakeup_fd_cv.cc +0 -107
  224. data/src/core/lib/iomgr/wakeup_fd_cv.h +0 -69
@@ -0,0 +1,568 @@
1
+ /*
2
+ *
3
+ * Copyright 2015 gRPC authors.
4
+ *
5
+ * Licensed under the Apache License, Version 2.0 (the "License");
6
+ * you may not use this file except in compliance with the License.
7
+ * You may obtain a copy of the License at
8
+ *
9
+ * http://www.apache.org/licenses/LICENSE-2.0
10
+ *
11
+ * Unless required by applicable law or agreed to in writing, software
12
+ * distributed under the License is distributed on an "AS IS" BASIS,
13
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14
+ * See the License for the specific language governing permissions and
15
+ * limitations under the License.
16
+ *
17
+ */
18
+
19
+ #include <grpc/support/port_platform.h>
20
+
21
+ #include "src/core/ext/filters/client_channel/resolving_lb_policy.h"
22
+
23
+ #include <inttypes.h>
24
+ #include <limits.h>
25
+ #include <stdbool.h>
26
+ #include <stdio.h>
27
+ #include <string.h>
28
+
29
+ #include <grpc/support/alloc.h>
30
+ #include <grpc/support/log.h>
31
+ #include <grpc/support/string_util.h>
32
+ #include <grpc/support/sync.h>
33
+
34
+ #include "src/core/ext/filters/client_channel/backup_poller.h"
35
+ #include "src/core/ext/filters/client_channel/http_connect_handshaker.h"
36
+ #include "src/core/ext/filters/client_channel/lb_policy_registry.h"
37
+ #include "src/core/ext/filters/client_channel/proxy_mapper_registry.h"
38
+ #include "src/core/ext/filters/client_channel/resolver_registry.h"
39
+ #include "src/core/ext/filters/client_channel/retry_throttle.h"
40
+ #include "src/core/ext/filters/client_channel/server_address.h"
41
+ #include "src/core/ext/filters/client_channel/service_config.h"
42
+ #include "src/core/ext/filters/client_channel/subchannel.h"
43
+ #include "src/core/ext/filters/deadline/deadline_filter.h"
44
+ #include "src/core/lib/backoff/backoff.h"
45
+ #include "src/core/lib/channel/channel_args.h"
46
+ #include "src/core/lib/channel/connected_channel.h"
47
+ #include "src/core/lib/channel/status_util.h"
48
+ #include "src/core/lib/gpr/string.h"
49
+ #include "src/core/lib/gprpp/inlined_vector.h"
50
+ #include "src/core/lib/gprpp/manual_constructor.h"
51
+ #include "src/core/lib/gprpp/mutex_lock.h"
52
+ #include "src/core/lib/iomgr/combiner.h"
53
+ #include "src/core/lib/iomgr/iomgr.h"
54
+ #include "src/core/lib/iomgr/polling_entity.h"
55
+ #include "src/core/lib/profiling/timers.h"
56
+ #include "src/core/lib/slice/slice_internal.h"
57
+ #include "src/core/lib/slice/slice_string_helpers.h"
58
+ #include "src/core/lib/surface/channel.h"
59
+ #include "src/core/lib/transport/connectivity_state.h"
60
+ #include "src/core/lib/transport/error_utils.h"
61
+ #include "src/core/lib/transport/metadata.h"
62
+ #include "src/core/lib/transport/metadata_batch.h"
63
+ #include "src/core/lib/transport/static_metadata.h"
64
+ #include "src/core/lib/transport/status_metadata.h"
65
+
66
+ namespace grpc_core {
67
+
68
+ //
69
+ // ResolvingLoadBalancingPolicy::ResolverResultHandler
70
+ //
71
+
72
+ class ResolvingLoadBalancingPolicy::ResolverResultHandler
73
+ : public Resolver::ResultHandler {
74
+ public:
75
+ explicit ResolverResultHandler(
76
+ RefCountedPtr<ResolvingLoadBalancingPolicy> parent)
77
+ : parent_(std::move(parent)) {}
78
+
79
+ ~ResolverResultHandler() {
80
+ if (parent_->tracer_->enabled()) {
81
+ gpr_log(GPR_INFO, "resolving_lb=%p: resolver shutdown complete",
82
+ parent_.get());
83
+ }
84
+ }
85
+
86
+ void ReturnResult(Resolver::Result result) override {
87
+ parent_->OnResolverResultChangedLocked(std::move(result));
88
+ }
89
+
90
+ void ReturnError(grpc_error* error) override {
91
+ parent_->OnResolverError(error);
92
+ }
93
+
94
+ private:
95
+ RefCountedPtr<ResolvingLoadBalancingPolicy> parent_;
96
+ };
97
+
98
+ //
99
+ // ResolvingLoadBalancingPolicy::ResolvingControlHelper
100
+ //
101
+
102
+ class ResolvingLoadBalancingPolicy::ResolvingControlHelper
103
+ : public LoadBalancingPolicy::ChannelControlHelper {
104
+ public:
105
+ explicit ResolvingControlHelper(
106
+ RefCountedPtr<ResolvingLoadBalancingPolicy> parent)
107
+ : parent_(std::move(parent)) {}
108
+
109
+ Subchannel* CreateSubchannel(const grpc_channel_args& args) override {
110
+ if (parent_->resolver_ == nullptr) return nullptr; // Shutting down.
111
+ if (!CalledByCurrentChild() && !CalledByPendingChild()) return nullptr;
112
+ return parent_->channel_control_helper()->CreateSubchannel(args);
113
+ }
114
+
115
+ grpc_channel* CreateChannel(const char* target,
116
+ const grpc_channel_args& args) override {
117
+ if (parent_->resolver_ == nullptr) return nullptr; // Shutting down.
118
+ if (!CalledByCurrentChild() && !CalledByPendingChild()) return nullptr;
119
+ return parent_->channel_control_helper()->CreateChannel(target, args);
120
+ }
121
+
122
+ void UpdateState(grpc_connectivity_state state, grpc_error* state_error,
123
+ UniquePtr<SubchannelPicker> picker) override {
124
+ if (parent_->resolver_ == nullptr) {
125
+ // shutting down.
126
+ GRPC_ERROR_UNREF(state_error);
127
+ return;
128
+ }
129
+ // If this request is from the pending child policy, ignore it until
130
+ // it reports READY, at which point we swap it into place.
131
+ if (CalledByPendingChild()) {
132
+ if (parent_->tracer_->enabled()) {
133
+ gpr_log(GPR_INFO,
134
+ "resolving_lb=%p helper=%p: pending child policy %p reports "
135
+ "state=%s",
136
+ parent_.get(), this, child_,
137
+ grpc_connectivity_state_name(state));
138
+ }
139
+ if (state != GRPC_CHANNEL_READY) {
140
+ GRPC_ERROR_UNREF(state_error);
141
+ return;
142
+ }
143
+ grpc_pollset_set_del_pollset_set(
144
+ parent_->lb_policy_->interested_parties(),
145
+ parent_->interested_parties());
146
+ MutexLock lock(&parent_->lb_policy_mu_);
147
+ parent_->lb_policy_ = std::move(parent_->pending_lb_policy_);
148
+ } else if (!CalledByCurrentChild()) {
149
+ // This request is from an outdated child, so ignore it.
150
+ GRPC_ERROR_UNREF(state_error);
151
+ return;
152
+ }
153
+ parent_->channel_control_helper()->UpdateState(state, state_error,
154
+ std::move(picker));
155
+ }
156
+
157
+ void RequestReresolution() override {
158
+ // If there is a pending child policy, ignore re-resolution requests
159
+ // from the current child policy (or any outdated child).
160
+ if (parent_->pending_lb_policy_ != nullptr && !CalledByPendingChild()) {
161
+ return;
162
+ }
163
+ if (parent_->tracer_->enabled()) {
164
+ gpr_log(GPR_INFO, "resolving_lb=%p: started name re-resolving",
165
+ parent_.get());
166
+ }
167
+ if (parent_->resolver_ != nullptr) {
168
+ parent_->resolver_->RequestReresolutionLocked();
169
+ }
170
+ }
171
+
172
+ void set_child(LoadBalancingPolicy* child) { child_ = child; }
173
+
174
+ private:
175
+ bool CalledByPendingChild() const {
176
+ GPR_ASSERT(child_ != nullptr);
177
+ return child_ == parent_->pending_lb_policy_.get();
178
+ }
179
+
180
+ bool CalledByCurrentChild() const {
181
+ GPR_ASSERT(child_ != nullptr);
182
+ return child_ == parent_->lb_policy_.get();
183
+ };
184
+
185
+ RefCountedPtr<ResolvingLoadBalancingPolicy> parent_;
186
+ LoadBalancingPolicy* child_ = nullptr;
187
+ };
188
+
189
+ //
190
+ // ResolvingLoadBalancingPolicy
191
+ //
192
+
193
+ ResolvingLoadBalancingPolicy::ResolvingLoadBalancingPolicy(
194
+ Args args, TraceFlag* tracer, UniquePtr<char> target_uri,
195
+ UniquePtr<char> child_policy_name, RefCountedPtr<Config> child_lb_config,
196
+ grpc_error** error)
197
+ : LoadBalancingPolicy(std::move(args)),
198
+ tracer_(tracer),
199
+ target_uri_(std::move(target_uri)),
200
+ child_policy_name_(std::move(child_policy_name)),
201
+ child_lb_config_(std::move(child_lb_config)) {
202
+ GPR_ASSERT(child_policy_name_ != nullptr);
203
+ // Don't fetch service config, since this ctor is for use in nested LB
204
+ // policies, not at the top level, and we only fetch the service
205
+ // config at the top level.
206
+ grpc_arg arg = grpc_channel_arg_integer_create(
207
+ const_cast<char*>(GRPC_ARG_SERVICE_CONFIG_DISABLE_RESOLUTION), 0);
208
+ grpc_channel_args* new_args =
209
+ grpc_channel_args_copy_and_add(args.args, &arg, 1);
210
+ *error = Init(*new_args);
211
+ grpc_channel_args_destroy(new_args);
212
+ }
213
+
214
+ ResolvingLoadBalancingPolicy::ResolvingLoadBalancingPolicy(
215
+ Args args, TraceFlag* tracer, UniquePtr<char> target_uri,
216
+ ProcessResolverResultCallback process_resolver_result,
217
+ void* process_resolver_result_user_data, grpc_error** error)
218
+ : LoadBalancingPolicy(std::move(args)),
219
+ tracer_(tracer),
220
+ target_uri_(std::move(target_uri)),
221
+ process_resolver_result_(process_resolver_result),
222
+ process_resolver_result_user_data_(process_resolver_result_user_data) {
223
+ GPR_ASSERT(process_resolver_result != nullptr);
224
+ gpr_mu_init(&lb_policy_mu_);
225
+ *error = Init(*args.args);
226
+ }
227
+
228
+ grpc_error* ResolvingLoadBalancingPolicy::Init(const grpc_channel_args& args) {
229
+ resolver_ = ResolverRegistry::CreateResolver(
230
+ target_uri_.get(), &args, interested_parties(), combiner(),
231
+ UniquePtr<Resolver::ResultHandler>(New<ResolverResultHandler>(Ref())));
232
+ if (resolver_ == nullptr) {
233
+ return GRPC_ERROR_CREATE_FROM_STATIC_STRING("resolver creation failed");
234
+ }
235
+ // Return our picker to the channel.
236
+ channel_control_helper()->UpdateState(
237
+ GRPC_CHANNEL_IDLE, GRPC_ERROR_NONE,
238
+ UniquePtr<SubchannelPicker>(New<QueuePicker>(Ref())));
239
+ return GRPC_ERROR_NONE;
240
+ }
241
+
242
+ ResolvingLoadBalancingPolicy::~ResolvingLoadBalancingPolicy() {
243
+ GPR_ASSERT(resolver_ == nullptr);
244
+ GPR_ASSERT(lb_policy_ == nullptr);
245
+ gpr_mu_destroy(&lb_policy_mu_);
246
+ }
247
+
248
+ void ResolvingLoadBalancingPolicy::ShutdownLocked() {
249
+ if (resolver_ != nullptr) {
250
+ resolver_.reset();
251
+ MutexLock lock(&lb_policy_mu_);
252
+ if (lb_policy_ != nullptr) {
253
+ if (tracer_->enabled()) {
254
+ gpr_log(GPR_INFO, "resolving_lb=%p: shutting down lb_policy=%p", this,
255
+ lb_policy_.get());
256
+ }
257
+ grpc_pollset_set_del_pollset_set(lb_policy_->interested_parties(),
258
+ interested_parties());
259
+ lb_policy_.reset();
260
+ }
261
+ if (pending_lb_policy_ != nullptr) {
262
+ if (tracer_->enabled()) {
263
+ gpr_log(GPR_INFO, "resolving_lb=%p: shutting down pending lb_policy=%p",
264
+ this, pending_lb_policy_.get());
265
+ }
266
+ grpc_pollset_set_del_pollset_set(pending_lb_policy_->interested_parties(),
267
+ interested_parties());
268
+ pending_lb_policy_.reset();
269
+ }
270
+ }
271
+ }
272
+
273
+ void ResolvingLoadBalancingPolicy::ExitIdleLocked() {
274
+ if (lb_policy_ != nullptr) {
275
+ lb_policy_->ExitIdleLocked();
276
+ if (pending_lb_policy_ != nullptr) pending_lb_policy_->ExitIdleLocked();
277
+ } else {
278
+ if (!started_resolving_ && resolver_ != nullptr) {
279
+ StartResolvingLocked();
280
+ }
281
+ }
282
+ }
283
+
284
+ void ResolvingLoadBalancingPolicy::ResetBackoffLocked() {
285
+ if (resolver_ != nullptr) {
286
+ resolver_->ResetBackoffLocked();
287
+ resolver_->RequestReresolutionLocked();
288
+ }
289
+ if (lb_policy_ != nullptr) lb_policy_->ResetBackoffLocked();
290
+ if (pending_lb_policy_ != nullptr) pending_lb_policy_->ResetBackoffLocked();
291
+ }
292
+
293
+ void ResolvingLoadBalancingPolicy::FillChildRefsForChannelz(
294
+ channelz::ChildRefsList* child_subchannels,
295
+ channelz::ChildRefsList* child_channels) {
296
+ // Delegate to the lb_policy_ to fill the children subchannels.
297
+ // This must be done holding lb_policy_mu_, since this method does not
298
+ // run in the combiner.
299
+ MutexLock lock(&lb_policy_mu_);
300
+ if (lb_policy_ != nullptr) {
301
+ lb_policy_->FillChildRefsForChannelz(child_subchannels, child_channels);
302
+ }
303
+ if (pending_lb_policy_ != nullptr) {
304
+ pending_lb_policy_->FillChildRefsForChannelz(child_subchannels,
305
+ child_channels);
306
+ }
307
+ }
308
+
309
+ void ResolvingLoadBalancingPolicy::StartResolvingLocked() {
310
+ if (tracer_->enabled()) {
311
+ gpr_log(GPR_INFO, "resolving_lb=%p: starting name resolution", this);
312
+ }
313
+ GPR_ASSERT(!started_resolving_);
314
+ started_resolving_ = true;
315
+ channel_control_helper()->UpdateState(
316
+ GRPC_CHANNEL_CONNECTING, GRPC_ERROR_NONE,
317
+ UniquePtr<SubchannelPicker>(New<QueuePicker>(Ref())));
318
+ resolver_->StartLocked();
319
+ }
320
+
321
+ void ResolvingLoadBalancingPolicy::OnResolverError(grpc_error* error) {
322
+ if (resolver_ == nullptr) {
323
+ GRPC_ERROR_UNREF(error);
324
+ return;
325
+ }
326
+ if (tracer_->enabled()) {
327
+ gpr_log(GPR_INFO, "resolving_lb=%p: resolver transient failure: %s", this,
328
+ grpc_error_string(error));
329
+ }
330
+ // If we already have an LB policy from a previous resolution
331
+ // result, then we continue to let it set the connectivity state.
332
+ // Otherwise, we go into TRANSIENT_FAILURE.
333
+ if (lb_policy_ == nullptr) {
334
+ grpc_error* state_error = GRPC_ERROR_CREATE_REFERENCING_FROM_STATIC_STRING(
335
+ "Resolver transient failure", &error, 1);
336
+ channel_control_helper()->UpdateState(
337
+ GRPC_CHANNEL_TRANSIENT_FAILURE, GRPC_ERROR_REF(state_error),
338
+ UniquePtr<SubchannelPicker>(New<TransientFailurePicker>(state_error)));
339
+ }
340
+ GRPC_ERROR_UNREF(error);
341
+ }
342
+
343
+ void ResolvingLoadBalancingPolicy::CreateOrUpdateLbPolicyLocked(
344
+ const char* lb_policy_name, RefCountedPtr<Config> lb_policy_config,
345
+ Resolver::Result result, TraceStringVector* trace_strings) {
346
+ // If the child policy name changes, we need to create a new child
347
+ // policy. When this happens, we leave child_policy_ as-is and store
348
+ // the new child policy in pending_child_policy_. Once the new child
349
+ // policy transitions into state READY, we swap it into child_policy_,
350
+ // replacing the original child policy. So pending_child_policy_ is
351
+ // non-null only between when we apply an update that changes the child
352
+ // policy name and when the new child reports state READY.
353
+ //
354
+ // Updates can arrive at any point during this transition. We always
355
+ // apply updates relative to the most recently created child policy,
356
+ // even if the most recent one is still in pending_child_policy_. This
357
+ // is true both when applying the updates to an existing child policy
358
+ // and when determining whether we need to create a new policy.
359
+ //
360
+ // As a result of this, there are several cases to consider here:
361
+ //
362
+ // 1. We have no existing child policy (i.e., we have started up but
363
+ // have not yet received a serverlist from the balancer or gone
364
+ // into fallback mode; in this case, both child_policy_ and
365
+ // pending_child_policy_ are null). In this case, we create a
366
+ // new child policy and store it in child_policy_.
367
+ //
368
+ // 2. We have an existing child policy and have no pending child policy
369
+ // from a previous update (i.e., either there has not been a
370
+ // previous update that changed the policy name, or we have already
371
+ // finished swapping in the new policy; in this case, child_policy_
372
+ // is non-null but pending_child_policy_ is null). In this case:
373
+ // a. If child_policy_->name() equals child_policy_name, then we
374
+ // update the existing child policy.
375
+ // b. If child_policy_->name() does not equal child_policy_name,
376
+ // we create a new policy. The policy will be stored in
377
+ // pending_child_policy_ and will later be swapped into
378
+ // child_policy_ by the helper when the new child transitions
379
+ // into state READY.
380
+ //
381
+ // 3. We have an existing child policy and have a pending child policy
382
+ // from a previous update (i.e., a previous update set
383
+ // pending_child_policy_ as per case 2b above and that policy has
384
+ // not yet transitioned into state READY and been swapped into
385
+ // child_policy_; in this case, both child_policy_ and
386
+ // pending_child_policy_ are non-null). In this case:
387
+ // a. If pending_child_policy_->name() equals child_policy_name,
388
+ // then we update the existing pending child policy.
389
+ // b. If pending_child_policy->name() does not equal
390
+ // child_policy_name, then we create a new policy. The new
391
+ // policy is stored in pending_child_policy_ (replacing the one
392
+ // that was there before, which will be immediately shut down)
393
+ // and will later be swapped into child_policy_ by the helper
394
+ // when the new child transitions into state READY.
395
+ const bool create_policy =
396
+ // case 1
397
+ lb_policy_ == nullptr ||
398
+ // case 2b
399
+ (pending_lb_policy_ == nullptr &&
400
+ strcmp(lb_policy_->name(), lb_policy_name) != 0) ||
401
+ // case 3b
402
+ (pending_lb_policy_ != nullptr &&
403
+ strcmp(pending_lb_policy_->name(), lb_policy_name) != 0);
404
+ LoadBalancingPolicy* policy_to_update = nullptr;
405
+ if (create_policy) {
406
+ // Cases 1, 2b, and 3b: create a new child policy.
407
+ // If lb_policy_ is null, we set it (case 1), else we set
408
+ // pending_lb_policy_ (cases 2b and 3b).
409
+ if (tracer_->enabled()) {
410
+ gpr_log(GPR_INFO, "resolving_lb=%p: Creating new %schild policy %s", this,
411
+ lb_policy_ == nullptr ? "" : "pending ", lb_policy_name);
412
+ }
413
+ auto new_policy =
414
+ CreateLbPolicyLocked(lb_policy_name, *result.args, trace_strings);
415
+ auto& lb_policy = lb_policy_ == nullptr ? lb_policy_ : pending_lb_policy_;
416
+ {
417
+ MutexLock lock(&lb_policy_mu_);
418
+ lb_policy = std::move(new_policy);
419
+ }
420
+ policy_to_update = lb_policy.get();
421
+ } else {
422
+ // Cases 2a and 3a: update an existing policy.
423
+ // If we have a pending child policy, send the update to the pending
424
+ // policy (case 3a), else send it to the current policy (case 2a).
425
+ policy_to_update = pending_lb_policy_ != nullptr ? pending_lb_policy_.get()
426
+ : lb_policy_.get();
427
+ }
428
+ GPR_ASSERT(policy_to_update != nullptr);
429
+ // Update the policy.
430
+ if (tracer_->enabled()) {
431
+ gpr_log(GPR_INFO, "resolving_lb=%p: Updating %schild policy %p", this,
432
+ policy_to_update == pending_lb_policy_.get() ? "pending " : "",
433
+ policy_to_update);
434
+ }
435
+ UpdateArgs update_args;
436
+ update_args.addresses = std::move(result.addresses);
437
+ update_args.config = std::move(lb_policy_config);
438
+ // TODO(roth): Once channel args is converted to C++, use std::move() here.
439
+ update_args.args = result.args;
440
+ result.args = nullptr;
441
+ policy_to_update->UpdateLocked(std::move(update_args));
442
+ }
443
+
444
+ // Creates a new LB policy.
445
+ // Updates trace_strings to indicate what was done.
446
+ OrphanablePtr<LoadBalancingPolicy>
447
+ ResolvingLoadBalancingPolicy::CreateLbPolicyLocked(
448
+ const char* lb_policy_name, const grpc_channel_args& args,
449
+ TraceStringVector* trace_strings) {
450
+ ResolvingControlHelper* helper = New<ResolvingControlHelper>(Ref());
451
+ LoadBalancingPolicy::Args lb_policy_args;
452
+ lb_policy_args.combiner = combiner();
453
+ lb_policy_args.channel_control_helper =
454
+ UniquePtr<ChannelControlHelper>(helper);
455
+ lb_policy_args.args = &args;
456
+ OrphanablePtr<LoadBalancingPolicy> lb_policy =
457
+ LoadBalancingPolicyRegistry::CreateLoadBalancingPolicy(
458
+ lb_policy_name, std::move(lb_policy_args));
459
+ if (GPR_UNLIKELY(lb_policy == nullptr)) {
460
+ gpr_log(GPR_ERROR, "could not create LB policy \"%s\"", lb_policy_name);
461
+ if (channelz_node() != nullptr) {
462
+ char* str;
463
+ gpr_asprintf(&str, "Could not create LB policy \"%s\"", lb_policy_name);
464
+ trace_strings->push_back(str);
465
+ }
466
+ return nullptr;
467
+ }
468
+ helper->set_child(lb_policy.get());
469
+ if (tracer_->enabled()) {
470
+ gpr_log(GPR_INFO, "resolving_lb=%p: created new LB policy \"%s\" (%p)",
471
+ this, lb_policy_name, lb_policy.get());
472
+ }
473
+ if (channelz_node() != nullptr) {
474
+ char* str;
475
+ gpr_asprintf(&str, "Created new LB policy \"%s\"", lb_policy_name);
476
+ trace_strings->push_back(str);
477
+ }
478
+ // Propagate channelz node.
479
+ auto* channelz = channelz_node();
480
+ if (channelz != nullptr) {
481
+ lb_policy->set_channelz_node(channelz->Ref());
482
+ }
483
+ grpc_pollset_set_add_pollset_set(lb_policy->interested_parties(),
484
+ interested_parties());
485
+ return lb_policy;
486
+ }
487
+
488
+ void ResolvingLoadBalancingPolicy::MaybeAddTraceMessagesForAddressChangesLocked(
489
+ bool resolution_contains_addresses, TraceStringVector* trace_strings) {
490
+ if (!resolution_contains_addresses &&
491
+ previous_resolution_contained_addresses_) {
492
+ trace_strings->push_back(gpr_strdup("Address list became empty"));
493
+ } else if (resolution_contains_addresses &&
494
+ !previous_resolution_contained_addresses_) {
495
+ trace_strings->push_back(gpr_strdup("Address list became non-empty"));
496
+ }
497
+ previous_resolution_contained_addresses_ = resolution_contains_addresses;
498
+ }
499
+
500
+ void ResolvingLoadBalancingPolicy::ConcatenateAndAddChannelTraceLocked(
501
+ TraceStringVector* trace_strings) const {
502
+ if (!trace_strings->empty()) {
503
+ gpr_strvec v;
504
+ gpr_strvec_init(&v);
505
+ gpr_strvec_add(&v, gpr_strdup("Resolution event: "));
506
+ bool is_first = 1;
507
+ for (size_t i = 0; i < trace_strings->size(); ++i) {
508
+ if (!is_first) gpr_strvec_add(&v, gpr_strdup(", "));
509
+ is_first = false;
510
+ gpr_strvec_add(&v, (*trace_strings)[i]);
511
+ }
512
+ char* flat;
513
+ size_t flat_len = 0;
514
+ flat = gpr_strvec_flatten(&v, &flat_len);
515
+ channelz_node()->AddTraceEvent(channelz::ChannelTrace::Severity::Info,
516
+ grpc_slice_new(flat, flat_len, gpr_free));
517
+ gpr_strvec_destroy(&v);
518
+ }
519
+ }
520
+
521
+ void ResolvingLoadBalancingPolicy::OnResolverResultChangedLocked(
522
+ Resolver::Result result) {
523
+ // Handle race conditions.
524
+ if (resolver_ == nullptr) return;
525
+ if (tracer_->enabled()) {
526
+ gpr_log(GPR_INFO, "resolving_lb=%p: got resolver result", this);
527
+ }
528
+ // We only want to trace the address resolution in the follow cases:
529
+ // (a) Address resolution resulted in service config change.
530
+ // (b) Address resolution that causes number of backends to go from
531
+ // zero to non-zero.
532
+ // (c) Address resolution that causes number of backends to go from
533
+ // non-zero to zero.
534
+ // (d) Address resolution that causes a new LB policy to be created.
535
+ //
536
+ // We track a list of strings to eventually be concatenated and traced.
537
+ TraceStringVector trace_strings;
538
+ const bool resolution_contains_addresses = result.addresses.size() > 0;
539
+ // Process the resolver result.
540
+ const char* lb_policy_name = nullptr;
541
+ RefCountedPtr<Config> lb_policy_config;
542
+ bool service_config_changed = false;
543
+ if (process_resolver_result_ != nullptr) {
544
+ service_config_changed =
545
+ process_resolver_result_(process_resolver_result_user_data_, &result,
546
+ &lb_policy_name, &lb_policy_config);
547
+ } else {
548
+ lb_policy_name = child_policy_name_.get();
549
+ lb_policy_config = child_lb_config_;
550
+ }
551
+ GPR_ASSERT(lb_policy_name != nullptr);
552
+ // Create or update LB policy, as needed.
553
+ CreateOrUpdateLbPolicyLocked(lb_policy_name, std::move(lb_policy_config),
554
+ std::move(result), &trace_strings);
555
+ // Add channel trace event.
556
+ if (channelz_node() != nullptr) {
557
+ if (service_config_changed) {
558
+ // TODO(ncteisen): might be worth somehow including a snippet of the
559
+ // config in the trace, at the risk of bloating the trace logs.
560
+ trace_strings.push_back(gpr_strdup("Service config changed"));
561
+ }
562
+ MaybeAddTraceMessagesForAddressChangesLocked(resolution_contains_addresses,
563
+ &trace_strings);
564
+ ConcatenateAndAddChannelTraceLocked(&trace_strings);
565
+ }
566
+ }
567
+
568
+ } // namespace grpc_core