diff --git a/.gitignore b/.gitignore
index bd9a5139fe2..383fc25b360 100644
--- a/.gitignore
+++ b/.gitignore
@@ -136,7 +136,7 @@ bm_diff_old/
bm_*.json
# cmake build files
-/cmake/build
+**/cmake/build/
# Visual Studio Code artifacts
.vscode/*
diff --git a/BUILD b/BUILD
index 992d1d403cc..81de8203a03 100644
--- a/BUILD
+++ b/BUILD
@@ -319,8 +319,9 @@ grpc_cc_library(
deps = [
"grpc_common",
"grpc_lb_policy_cds",
+ "grpc_lb_policy_eds",
"grpc_lb_policy_grpclb",
- "grpc_lb_policy_xds",
+ "grpc_lb_policy_lrs",
"grpc_resolver_xds",
],
)
@@ -337,8 +338,9 @@ grpc_cc_library(
deps = [
"grpc_common",
"grpc_lb_policy_cds_secure",
+ "grpc_lb_policy_eds_secure",
"grpc_lb_policy_grpclb_secure",
- "grpc_lb_policy_xds_secure",
+ "grpc_lb_policy_lrs_secure",
"grpc_resolver_xds_secure",
"grpc_secure",
"grpc_transport_chttp2_client_secure",
@@ -1023,7 +1025,9 @@ grpc_cc_library(
"grpc_deadline_filter",
"grpc_client_authority_filter",
"grpc_lb_policy_pick_first",
+ "grpc_lb_policy_priority",
"grpc_lb_policy_round_robin",
+ "grpc_lb_policy_weighted_target",
"grpc_client_idle_filter",
"grpc_max_age_filter",
"grpc_message_size_filter",
@@ -1357,41 +1361,75 @@ grpc_cc_library(
)
grpc_cc_library(
- name = "grpc_lb_policy_xds",
+ name = "grpc_lb_policy_cds",
srcs = [
- "src/core/ext/filters/client_channel/lb_policy/xds/xds.cc",
+ "src/core/ext/filters/client_channel/lb_policy/xds/cds.cc",
+ ],
+ language = "c++",
+ deps = [
+ "grpc_base",
+ "grpc_client_channel",
+ "grpc_xds_client",
+ ],
+)
+
+grpc_cc_library(
+ name = "grpc_lb_policy_cds_secure",
+ srcs = [
+ "src/core/ext/filters/client_channel/lb_policy/xds/cds.cc",
+ ],
+ language = "c++",
+ deps = [
+ "grpc_base",
+ "grpc_client_channel",
+ "grpc_xds_client_secure",
+ ],
+)
+
+grpc_cc_library(
+ name = "grpc_lb_policy_eds",
+ srcs = [
+ "src/core/ext/filters/client_channel/lb_policy/xds/eds.cc",
],
hdrs = [
"src/core/ext/filters/client_channel/lb_policy/xds/xds.h",
],
+ external_deps = [
+ "absl/strings",
+ ],
language = "c++",
deps = [
"grpc_base",
"grpc_client_channel",
+ "grpc_lb_address_filtering",
"grpc_xds_client",
],
)
grpc_cc_library(
- name = "grpc_lb_policy_xds_secure",
+ name = "grpc_lb_policy_eds_secure",
srcs = [
- "src/core/ext/filters/client_channel/lb_policy/xds/xds.cc",
+ "src/core/ext/filters/client_channel/lb_policy/xds/eds.cc",
],
hdrs = [
"src/core/ext/filters/client_channel/lb_policy/xds/xds.h",
],
+ external_deps = [
+ "absl/strings",
+ ],
language = "c++",
deps = [
"grpc_base",
"grpc_client_channel",
+ "grpc_lb_address_filtering",
"grpc_xds_client_secure",
],
)
grpc_cc_library(
- name = "grpc_lb_policy_cds",
+ name = "grpc_lb_policy_lrs",
srcs = [
- "src/core/ext/filters/client_channel/lb_policy/xds/cds.cc",
+ "src/core/ext/filters/client_channel/lb_policy/xds/lrs.cc",
],
language = "c++",
deps = [
@@ -1402,9 +1440,9 @@ grpc_cc_library(
)
grpc_cc_library(
- name = "grpc_lb_policy_cds_secure",
+ name = "grpc_lb_policy_lrs_secure",
srcs = [
- "src/core/ext/filters/client_channel/lb_policy/xds/cds.cc",
+ "src/core/ext/filters/client_channel/lb_policy/xds/lrs.cc",
],
language = "c++",
deps = [
@@ -1414,6 +1452,24 @@ grpc_cc_library(
],
)
+grpc_cc_library(
+ name = "grpc_lb_address_filtering",
+ srcs = [
+ "src/core/ext/filters/client_channel/lb_policy/address_filtering.cc",
+ ],
+ hdrs = [
+ "src/core/ext/filters/client_channel/lb_policy/address_filtering.h",
+ ],
+ external_deps = [
+ "absl/strings",
+ ],
+ language = "c++",
+ deps = [
+ "grpc_base",
+ "grpc_client_channel",
+ ],
+)
+
grpc_cc_library(
name = "grpc_lb_subchannel_list",
hdrs = [
@@ -1452,6 +1508,35 @@ grpc_cc_library(
],
)
+grpc_cc_library(
+ name = "grpc_lb_policy_priority",
+ srcs = [
+ "src/core/ext/filters/client_channel/lb_policy/priority/priority.cc",
+ ],
+ external_deps = [
+ "absl/strings",
+ ],
+ language = "c++",
+ deps = [
+ "grpc_base",
+ "grpc_client_channel",
+ "grpc_lb_address_filtering",
+ ],
+)
+
+grpc_cc_library(
+ name = "grpc_lb_policy_weighted_target",
+ srcs = [
+ "src/core/ext/filters/client_channel/lb_policy/weighted_target/weighted_target.cc",
+ ],
+ language = "c++",
+ deps = [
+ "grpc_base",
+ "grpc_client_channel",
+ "grpc_lb_address_filtering",
+ ],
+)
+
grpc_cc_library(
name = "lb_server_load_reporting_filter",
srcs = [
diff --git a/BUILD.gn b/BUILD.gn
index 306f2bfa6d8..129ad2b2639 100644
--- a/BUILD.gn
+++ b/BUILD.gn
@@ -223,6 +223,8 @@ config("grpc_config") {
"src/core/ext/filters/client_channel/http_proxy.h",
"src/core/ext/filters/client_channel/lb_policy.cc",
"src/core/ext/filters/client_channel/lb_policy.h",
+ "src/core/ext/filters/client_channel/lb_policy/address_filtering.cc",
+ "src/core/ext/filters/client_channel/lb_policy/address_filtering.h",
"src/core/ext/filters/client_channel/lb_policy/child_policy_handler.cc",
"src/core/ext/filters/client_channel/lb_policy/child_policy_handler.h",
"src/core/ext/filters/client_channel/lb_policy/grpclb/client_load_reporting_filter.cc",
@@ -238,10 +240,13 @@ config("grpc_config") {
"src/core/ext/filters/client_channel/lb_policy/grpclb/load_balancer_api.cc",
"src/core/ext/filters/client_channel/lb_policy/grpclb/load_balancer_api.h",
"src/core/ext/filters/client_channel/lb_policy/pick_first/pick_first.cc",
+ "src/core/ext/filters/client_channel/lb_policy/priority/priority.cc",
"src/core/ext/filters/client_channel/lb_policy/round_robin/round_robin.cc",
"src/core/ext/filters/client_channel/lb_policy/subchannel_list.h",
+ "src/core/ext/filters/client_channel/lb_policy/weighted_target/weighted_target.cc",
"src/core/ext/filters/client_channel/lb_policy/xds/cds.cc",
- "src/core/ext/filters/client_channel/lb_policy/xds/xds.cc",
+ "src/core/ext/filters/client_channel/lb_policy/xds/eds.cc",
+ "src/core/ext/filters/client_channel/lb_policy/xds/lrs.cc",
"src/core/ext/filters/client_channel/lb_policy/xds/xds.h",
"src/core/ext/filters/client_channel/lb_policy_factory.h",
"src/core/ext/filters/client_channel/lb_policy_registry.cc",
@@ -962,6 +967,7 @@ config("grpc_config") {
":address_sorting",
":upb",
":absl/types:optional",
+ ":absl/strings:strings",
":absl/container:inlined_vector",
"//third_party/cares",
":address_sorting",
diff --git a/CMakeLists.txt b/CMakeLists.txt
index 4496b174ba6..27bf340b65a 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -1315,6 +1315,7 @@ add_library(grpc
src/core/ext/filters/client_channel/http_connect_handshaker.cc
src/core/ext/filters/client_channel/http_proxy.cc
src/core/ext/filters/client_channel/lb_policy.cc
+ src/core/ext/filters/client_channel/lb_policy/address_filtering.cc
src/core/ext/filters/client_channel/lb_policy/child_policy_handler.cc
src/core/ext/filters/client_channel/lb_policy/grpclb/client_load_reporting_filter.cc
src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb.cc
@@ -1323,9 +1324,12 @@ add_library(grpc
src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb_client_stats.cc
src/core/ext/filters/client_channel/lb_policy/grpclb/load_balancer_api.cc
src/core/ext/filters/client_channel/lb_policy/pick_first/pick_first.cc
+ src/core/ext/filters/client_channel/lb_policy/priority/priority.cc
src/core/ext/filters/client_channel/lb_policy/round_robin/round_robin.cc
+ src/core/ext/filters/client_channel/lb_policy/weighted_target/weighted_target.cc
src/core/ext/filters/client_channel/lb_policy/xds/cds.cc
- src/core/ext/filters/client_channel/lb_policy/xds/xds.cc
+ src/core/ext/filters/client_channel/lb_policy/xds/eds.cc
+ src/core/ext/filters/client_channel/lb_policy/xds/lrs.cc
src/core/ext/filters/client_channel/lb_policy_registry.cc
src/core/ext/filters/client_channel/local_subchannel_pool.cc
src/core/ext/filters/client_channel/parse_address.cc
@@ -1743,6 +1747,7 @@ target_link_libraries(grpc
address_sorting
upb
absl::optional
+ absl::strings
absl::inlined_vector
)
if(_gRPC_PLATFORM_IOS OR _gRPC_PLATFORM_MAC)
@@ -1969,6 +1974,7 @@ add_library(grpc_unsecure
src/core/ext/filters/client_channel/http_connect_handshaker.cc
src/core/ext/filters/client_channel/http_proxy.cc
src/core/ext/filters/client_channel/lb_policy.cc
+ src/core/ext/filters/client_channel/lb_policy/address_filtering.cc
src/core/ext/filters/client_channel/lb_policy/child_policy_handler.cc
src/core/ext/filters/client_channel/lb_policy/grpclb/client_load_reporting_filter.cc
src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb.cc
@@ -1977,9 +1983,12 @@ add_library(grpc_unsecure
src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb_client_stats.cc
src/core/ext/filters/client_channel/lb_policy/grpclb/load_balancer_api.cc
src/core/ext/filters/client_channel/lb_policy/pick_first/pick_first.cc
+ src/core/ext/filters/client_channel/lb_policy/priority/priority.cc
src/core/ext/filters/client_channel/lb_policy/round_robin/round_robin.cc
+ src/core/ext/filters/client_channel/lb_policy/weighted_target/weighted_target.cc
src/core/ext/filters/client_channel/lb_policy/xds/cds.cc
- src/core/ext/filters/client_channel/lb_policy/xds/xds.cc
+ src/core/ext/filters/client_channel/lb_policy/xds/eds.cc
+ src/core/ext/filters/client_channel/lb_policy/xds/lrs.cc
src/core/ext/filters/client_channel/lb_policy_registry.cc
src/core/ext/filters/client_channel/local_subchannel_pool.cc
src/core/ext/filters/client_channel/parse_address.cc
@@ -2321,6 +2330,7 @@ target_link_libraries(grpc_unsecure
address_sorting
upb
absl::optional
+ absl::strings
absl::inlined_vector
)
if(_gRPC_PLATFORM_IOS OR _gRPC_PLATFORM_MAC)
diff --git a/Makefile b/Makefile
index 465c2e3a284..d6c8cd19efa 100644
--- a/Makefile
+++ b/Makefile
@@ -2176,6 +2176,8 @@ test_cxx: buildtests_cxx
$(Q) $(BINDIR)/$(CONFIG)/bm_error || ( echo test bm_error failed ; exit 1 )
$(E) "[RUN] Testing bm_fullstack_streaming_ping_pong"
$(Q) $(BINDIR)/$(CONFIG)/bm_fullstack_streaming_ping_pong || ( echo test bm_fullstack_streaming_ping_pong failed ; exit 1 )
+ $(E) "[RUN] Testing bm_fullstack_streaming_pump"
+ $(Q) $(BINDIR)/$(CONFIG)/bm_fullstack_streaming_pump || ( echo test bm_fullstack_streaming_pump failed ; exit 1 )
$(E) "[RUN] Testing bm_fullstack_unary_ping_pong"
$(Q) $(BINDIR)/$(CONFIG)/bm_fullstack_unary_ping_pong || ( echo test bm_fullstack_unary_ping_pong failed ; exit 1 )
$(E) "[RUN] Testing bm_metadata"
@@ -2204,8 +2206,6 @@ test_cxx: buildtests_cxx
$(Q) $(BINDIR)/$(CONFIG)/cli_call_test || ( echo test cli_call_test failed ; exit 1 )
$(E) "[RUN] Testing client_callback_end2end_test"
$(Q) $(BINDIR)/$(CONFIG)/client_callback_end2end_test || ( echo test client_callback_end2end_test failed ; exit 1 )
- $(E) "[RUN] Testing client_channel_stress_test"
- $(Q) $(BINDIR)/$(CONFIG)/client_channel_stress_test || ( echo test client_channel_stress_test failed ; exit 1 )
$(E) "[RUN] Testing client_interceptors_end2end_test"
$(Q) $(BINDIR)/$(CONFIG)/client_interceptors_end2end_test || ( echo test client_interceptors_end2end_test failed ; exit 1 )
$(E) "[RUN] Testing codegen_test_full"
@@ -3640,6 +3640,7 @@ LIBGRPC_SRC = \
src/core/ext/filters/client_channel/http_connect_handshaker.cc \
src/core/ext/filters/client_channel/http_proxy.cc \
src/core/ext/filters/client_channel/lb_policy.cc \
+ src/core/ext/filters/client_channel/lb_policy/address_filtering.cc \
src/core/ext/filters/client_channel/lb_policy/child_policy_handler.cc \
src/core/ext/filters/client_channel/lb_policy/grpclb/client_load_reporting_filter.cc \
src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb.cc \
@@ -3648,9 +3649,12 @@ LIBGRPC_SRC = \
src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb_client_stats.cc \
src/core/ext/filters/client_channel/lb_policy/grpclb/load_balancer_api.cc \
src/core/ext/filters/client_channel/lb_policy/pick_first/pick_first.cc \
+ src/core/ext/filters/client_channel/lb_policy/priority/priority.cc \
src/core/ext/filters/client_channel/lb_policy/round_robin/round_robin.cc \
+ src/core/ext/filters/client_channel/lb_policy/weighted_target/weighted_target.cc \
src/core/ext/filters/client_channel/lb_policy/xds/cds.cc \
- src/core/ext/filters/client_channel/lb_policy/xds/xds.cc \
+ src/core/ext/filters/client_channel/lb_policy/xds/eds.cc \
+ src/core/ext/filters/client_channel/lb_policy/xds/lrs.cc \
src/core/ext/filters/client_channel/lb_policy_registry.cc \
src/core/ext/filters/client_channel/local_subchannel_pool.cc \
src/core/ext/filters/client_channel/parse_address.cc \
@@ -4269,6 +4273,7 @@ LIBGRPC_UNSECURE_SRC = \
src/core/ext/filters/client_channel/http_connect_handshaker.cc \
src/core/ext/filters/client_channel/http_proxy.cc \
src/core/ext/filters/client_channel/lb_policy.cc \
+ src/core/ext/filters/client_channel/lb_policy/address_filtering.cc \
src/core/ext/filters/client_channel/lb_policy/child_policy_handler.cc \
src/core/ext/filters/client_channel/lb_policy/grpclb/client_load_reporting_filter.cc \
src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb.cc \
@@ -4277,9 +4282,12 @@ LIBGRPC_UNSECURE_SRC = \
src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb_client_stats.cc \
src/core/ext/filters/client_channel/lb_policy/grpclb/load_balancer_api.cc \
src/core/ext/filters/client_channel/lb_policy/pick_first/pick_first.cc \
+ src/core/ext/filters/client_channel/lb_policy/priority/priority.cc \
src/core/ext/filters/client_channel/lb_policy/round_robin/round_robin.cc \
+ src/core/ext/filters/client_channel/lb_policy/weighted_target/weighted_target.cc \
src/core/ext/filters/client_channel/lb_policy/xds/cds.cc \
- src/core/ext/filters/client_channel/lb_policy/xds/xds.cc \
+ src/core/ext/filters/client_channel/lb_policy/xds/eds.cc \
+ src/core/ext/filters/client_channel/lb_policy/xds/lrs.cc \
src/core/ext/filters/client_channel/lb_policy_registry.cc \
src/core/ext/filters/client_channel/local_subchannel_pool.cc \
src/core/ext/filters/client_channel/parse_address.cc \
diff --git a/build_autogenerated.yaml b/build_autogenerated.yaml
index 9a188b41121..30dba593d4f 100644
--- a/build_autogenerated.yaml
+++ b/build_autogenerated.yaml
@@ -382,6 +382,7 @@ libs:
- src/core/ext/filters/client_channel/http_connect_handshaker.h
- src/core/ext/filters/client_channel/http_proxy.h
- src/core/ext/filters/client_channel/lb_policy.h
+ - src/core/ext/filters/client_channel/lb_policy/address_filtering.h
- src/core/ext/filters/client_channel/lb_policy/child_policy_handler.h
- src/core/ext/filters/client_channel/lb_policy/grpclb/client_load_reporting_filter.h
- src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb.h
@@ -740,6 +741,7 @@ libs:
- src/core/ext/filters/client_channel/http_connect_handshaker.cc
- src/core/ext/filters/client_channel/http_proxy.cc
- src/core/ext/filters/client_channel/lb_policy.cc
+ - src/core/ext/filters/client_channel/lb_policy/address_filtering.cc
- src/core/ext/filters/client_channel/lb_policy/child_policy_handler.cc
- src/core/ext/filters/client_channel/lb_policy/grpclb/client_load_reporting_filter.cc
- src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb.cc
@@ -748,9 +750,12 @@ libs:
- src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb_client_stats.cc
- src/core/ext/filters/client_channel/lb_policy/grpclb/load_balancer_api.cc
- src/core/ext/filters/client_channel/lb_policy/pick_first/pick_first.cc
+ - src/core/ext/filters/client_channel/lb_policy/priority/priority.cc
- src/core/ext/filters/client_channel/lb_policy/round_robin/round_robin.cc
+ - src/core/ext/filters/client_channel/lb_policy/weighted_target/weighted_target.cc
- src/core/ext/filters/client_channel/lb_policy/xds/cds.cc
- - src/core/ext/filters/client_channel/lb_policy/xds/xds.cc
+ - src/core/ext/filters/client_channel/lb_policy/xds/eds.cc
+ - src/core/ext/filters/client_channel/lb_policy/xds/lrs.cc
- src/core/ext/filters/client_channel/lb_policy_registry.cc
- src/core/ext/filters/client_channel/local_subchannel_pool.cc
- src/core/ext/filters/client_channel/parse_address.cc
@@ -1132,6 +1137,7 @@ libs:
- address_sorting
- upb
- absl/types:optional
+ - absl/strings:strings
- absl/container:inlined_vector
baselib: true
dll: true
@@ -1278,6 +1284,7 @@ libs:
- src/core/ext/filters/client_channel/http_connect_handshaker.h
- src/core/ext/filters/client_channel/http_proxy.h
- src/core/ext/filters/client_channel/lb_policy.h
+ - src/core/ext/filters/client_channel/lb_policy/address_filtering.h
- src/core/ext/filters/client_channel/lb_policy/child_policy_handler.h
- src/core/ext/filters/client_channel/lb_policy/grpclb/client_load_reporting_filter.h
- src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb.h
@@ -1571,6 +1578,7 @@ libs:
- src/core/ext/filters/client_channel/http_connect_handshaker.cc
- src/core/ext/filters/client_channel/http_proxy.cc
- src/core/ext/filters/client_channel/lb_policy.cc
+ - src/core/ext/filters/client_channel/lb_policy/address_filtering.cc
- src/core/ext/filters/client_channel/lb_policy/child_policy_handler.cc
- src/core/ext/filters/client_channel/lb_policy/grpclb/client_load_reporting_filter.cc
- src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb.cc
@@ -1579,9 +1587,12 @@ libs:
- src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb_client_stats.cc
- src/core/ext/filters/client_channel/lb_policy/grpclb/load_balancer_api.cc
- src/core/ext/filters/client_channel/lb_policy/pick_first/pick_first.cc
+ - src/core/ext/filters/client_channel/lb_policy/priority/priority.cc
- src/core/ext/filters/client_channel/lb_policy/round_robin/round_robin.cc
+ - src/core/ext/filters/client_channel/lb_policy/weighted_target/weighted_target.cc
- src/core/ext/filters/client_channel/lb_policy/xds/cds.cc
- - src/core/ext/filters/client_channel/lb_policy/xds/xds.cc
+ - src/core/ext/filters/client_channel/lb_policy/xds/eds.cc
+ - src/core/ext/filters/client_channel/lb_policy/xds/lrs.cc
- src/core/ext/filters/client_channel/lb_policy_registry.cc
- src/core/ext/filters/client_channel/local_subchannel_pool.cc
- src/core/ext/filters/client_channel/parse_address.cc
@@ -1888,6 +1899,7 @@ libs:
- address_sorting
- upb
- absl/types:optional
+ - absl/strings:strings
- absl/container:inlined_vector
baselib: true
dll: true
@@ -5115,7 +5127,6 @@ targets:
- posix
- name: bm_fullstack_streaming_pump
build: test
- run: false
language: c++
headers:
- test/cpp/microbenchmarks/fullstack_streaming_pump.h
@@ -5499,6 +5510,7 @@ targets:
- name: client_channel_stress_test
gtest: true
build: test
+ run: false
language: c++
headers:
- test/cpp/end2end/test_service_impl.h
diff --git a/config.m4 b/config.m4
index 66922ad5527..6b450315f4f 100644
--- a/config.m4
+++ b/config.m4
@@ -50,6 +50,7 @@ if test "$PHP_GRPC" != "no"; then
src/core/ext/filters/client_channel/http_connect_handshaker.cc \
src/core/ext/filters/client_channel/http_proxy.cc \
src/core/ext/filters/client_channel/lb_policy.cc \
+ src/core/ext/filters/client_channel/lb_policy/address_filtering.cc \
src/core/ext/filters/client_channel/lb_policy/child_policy_handler.cc \
src/core/ext/filters/client_channel/lb_policy/grpclb/client_load_reporting_filter.cc \
src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb.cc \
@@ -58,9 +59,12 @@ if test "$PHP_GRPC" != "no"; then
src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb_client_stats.cc \
src/core/ext/filters/client_channel/lb_policy/grpclb/load_balancer_api.cc \
src/core/ext/filters/client_channel/lb_policy/pick_first/pick_first.cc \
+ src/core/ext/filters/client_channel/lb_policy/priority/priority.cc \
src/core/ext/filters/client_channel/lb_policy/round_robin/round_robin.cc \
+ src/core/ext/filters/client_channel/lb_policy/weighted_target/weighted_target.cc \
src/core/ext/filters/client_channel/lb_policy/xds/cds.cc \
- src/core/ext/filters/client_channel/lb_policy/xds/xds.cc \
+ src/core/ext/filters/client_channel/lb_policy/xds/eds.cc \
+ src/core/ext/filters/client_channel/lb_policy/xds/lrs.cc \
src/core/ext/filters/client_channel/lb_policy_registry.cc \
src/core/ext/filters/client_channel/local_subchannel_pool.cc \
src/core/ext/filters/client_channel/parse_address.cc \
@@ -821,7 +825,9 @@ if test "$PHP_GRPC" != "no"; then
PHP_ADD_BUILD_DIR($ext_builddir/src/core/ext/filters/client_channel/lb_policy)
PHP_ADD_BUILD_DIR($ext_builddir/src/core/ext/filters/client_channel/lb_policy/grpclb)
PHP_ADD_BUILD_DIR($ext_builddir/src/core/ext/filters/client_channel/lb_policy/pick_first)
+ PHP_ADD_BUILD_DIR($ext_builddir/src/core/ext/filters/client_channel/lb_policy/priority)
PHP_ADD_BUILD_DIR($ext_builddir/src/core/ext/filters/client_channel/lb_policy/round_robin)
+ PHP_ADD_BUILD_DIR($ext_builddir/src/core/ext/filters/client_channel/lb_policy/weighted_target)
PHP_ADD_BUILD_DIR($ext_builddir/src/core/ext/filters/client_channel/lb_policy/xds)
PHP_ADD_BUILD_DIR($ext_builddir/src/core/ext/filters/client_channel/resolver/dns)
PHP_ADD_BUILD_DIR($ext_builddir/src/core/ext/filters/client_channel/resolver/dns/c_ares)
diff --git a/config.w32 b/config.w32
index 541cc74b602..59cdbdb1ce4 100644
--- a/config.w32
+++ b/config.w32
@@ -19,6 +19,7 @@ if (PHP_GRPC != "no") {
"src\\core\\ext\\filters\\client_channel\\http_connect_handshaker.cc " +
"src\\core\\ext\\filters\\client_channel\\http_proxy.cc " +
"src\\core\\ext\\filters\\client_channel\\lb_policy.cc " +
+ "src\\core\\ext\\filters\\client_channel\\lb_policy\\address_filtering.cc " +
"src\\core\\ext\\filters\\client_channel\\lb_policy\\child_policy_handler.cc " +
"src\\core\\ext\\filters\\client_channel\\lb_policy\\grpclb\\client_load_reporting_filter.cc " +
"src\\core\\ext\\filters\\client_channel\\lb_policy\\grpclb\\grpclb.cc " +
@@ -27,9 +28,12 @@ if (PHP_GRPC != "no") {
"src\\core\\ext\\filters\\client_channel\\lb_policy\\grpclb\\grpclb_client_stats.cc " +
"src\\core\\ext\\filters\\client_channel\\lb_policy\\grpclb\\load_balancer_api.cc " +
"src\\core\\ext\\filters\\client_channel\\lb_policy\\pick_first\\pick_first.cc " +
+ "src\\core\\ext\\filters\\client_channel\\lb_policy\\priority\\priority.cc " +
"src\\core\\ext\\filters\\client_channel\\lb_policy\\round_robin\\round_robin.cc " +
+ "src\\core\\ext\\filters\\client_channel\\lb_policy\\weighted_target\\weighted_target.cc " +
"src\\core\\ext\\filters\\client_channel\\lb_policy\\xds\\cds.cc " +
- "src\\core\\ext\\filters\\client_channel\\lb_policy\\xds\\xds.cc " +
+ "src\\core\\ext\\filters\\client_channel\\lb_policy\\xds\\eds.cc " +
+ "src\\core\\ext\\filters\\client_channel\\lb_policy\\xds\\lrs.cc " +
"src\\core\\ext\\filters\\client_channel\\lb_policy_registry.cc " +
"src\\core\\ext\\filters\\client_channel\\local_subchannel_pool.cc " +
"src\\core\\ext\\filters\\client_channel\\parse_address.cc " +
@@ -821,7 +825,9 @@ if (PHP_GRPC != "no") {
FSO.CreateFolder(base_dir+"\\ext\\grpc\\src\\core\\ext\\filters\\client_channel\\lb_policy");
FSO.CreateFolder(base_dir+"\\ext\\grpc\\src\\core\\ext\\filters\\client_channel\\lb_policy\\grpclb");
FSO.CreateFolder(base_dir+"\\ext\\grpc\\src\\core\\ext\\filters\\client_channel\\lb_policy\\pick_first");
+ FSO.CreateFolder(base_dir+"\\ext\\grpc\\src\\core\\ext\\filters\\client_channel\\lb_policy\\priority");
FSO.CreateFolder(base_dir+"\\ext\\grpc\\src\\core\\ext\\filters\\client_channel\\lb_policy\\round_robin");
+ FSO.CreateFolder(base_dir+"\\ext\\grpc\\src\\core\\ext\\filters\\client_channel\\lb_policy\\weighted_target");
FSO.CreateFolder(base_dir+"\\ext\\grpc\\src\\core\\ext\\filters\\client_channel\\lb_policy\\xds");
FSO.CreateFolder(base_dir+"\\ext\\grpc\\src\\core\\ext\\filters\\client_channel\\resolver");
FSO.CreateFolder(base_dir+"\\ext\\grpc\\src\\core\\ext\\filters\\client_channel\\resolver\\dns");
diff --git a/doc/environment_variables.md b/doc/environment_variables.md
index e79c390c9a3..ec1b4f86717 100644
--- a/doc/environment_variables.md
+++ b/doc/environment_variables.md
@@ -57,6 +57,7 @@ some configuration as environment variables that can be set.
- compression - traces compression operations
- connectivity_state - traces connectivity state changes to channels
- cronet - traces state in the cronet transport engine
+ - eds_lb - traces eds LB policy
- executor - traces grpc's internal thread pool ('the executor')
- glb - traces the grpclb load balancer
- handshaker - traces handshaking state
@@ -65,13 +66,16 @@ some configuration as environment variables that can be set.
- http2_stream_state - traces all http2 stream state mutations.
- http1 - traces HTTP/1.x operations performed by gRPC
- inproc - traces the in-process transport
+ - http_keepalive - traces gRPC keepalive pings
- flowctl - traces http2 flow control
+ - lrs_lb - traces lrs LB policy
- op_failure - traces error information when failure is pushed onto a
completion queue
- pick_first - traces the pick first load balancing policy
- plugin_credentials - traces plugin credentials
- pollable_refcount - traces reference counting of 'pollable' objects (only
in DEBUG)
+ - priority_lb - traces priority LB policy
- resource_quota - trace resource quota objects internals
- round_robin - traces the round_robin load balancing policy
- queue_pluck
@@ -84,8 +88,8 @@ some configuration as environment variables that can be set.
- transport_security - traces metadata about secure channel establishment
- tcp - traces bytes in and out of a channel
- tsi - traces tsi transport security
+ - weighted_target_lb - traces weighted_target LB policy
- xds_client - traces xds client
- - xds_lb - traces xds LB policy
- xds_resolver - traces xds resolver
The following tracers will only run in binaries built in DEBUG mode. This is
diff --git a/examples/cpp/README.md b/examples/cpp/README.md
index 0e358bf9a22..a0ff629b1a0 100644
--- a/examples/cpp/README.md
+++ b/examples/cpp/README.md
@@ -1,44 +1,13 @@
-# gRPC in 3 minutes (C++)
+# gRPC C++ Examples
-## Installation
+- **[Hello World][]!** Eager to run your first gRPC example? You'll find
+ instructions for building gRPC and running a simple "Hello World" app in [Quick Start][].
+- **[Route Guide][].** For a basic tutorial on gRPC see [gRPC Basics][].
-To install gRPC on your system, follow the instructions to build from source
-[here](../../BUILDING.md). This also installs the protocol buffer compiler
-`protoc` (if you don't have it already), and the C++ gRPC plugin for `protoc`.
+For information about the other examples in this directory, see their respective
+README files.
-## Hello C++ gRPC!
-
-Here's how to build and run the C++ implementation of the [Hello
-World](../protos/helloworld.proto) example used in [Getting started](..).
-
-### Client and server implementations
-
-The client implementation is at [greeter_client.cc](helloworld/greeter_client.cc).
-
-The server implementation is at [greeter_server.cc](helloworld/greeter_server.cc).
-
-### Try it!
-Build client and server:
-
-```sh
-$ make
-```
-
-Run the server, which will listen on port 50051:
-
-```sh
-$ ./greeter_server
-```
-
-Run the client (in a different terminal):
-
-```sh
-$ ./greeter_client
-```
-
-If things go smoothly, you will see the "Greeter received: Hello world" in the
-client side output.
-
-## Tutorial
-
-You can find a more detailed tutorial in [gRPC Basics: C++](cpptutorial.md)
+[gRPC Basics]: https://grpc.io/docs/tutorials/basic/cpp
+[Hello World]: helloworld
+[Quick Start]: https://grpc.io/docs/quickstart/cpp
+[Route Guide]: route_guide
diff --git a/examples/cpp/cpptutorial.md b/examples/cpp/cpptutorial.md
deleted file mode 100644
index c40676de134..00000000000
--- a/examples/cpp/cpptutorial.md
+++ /dev/null
@@ -1,488 +0,0 @@
-# gRPC Basics: C++
-
-This tutorial provides a basic C++ programmer's introduction to working with
-gRPC. By walking through this example you'll learn how to:
-
-- Define a service in a `.proto` file.
-- Generate server and client code using the protocol buffer compiler.
-- Use the C++ gRPC API to write a simple client and server for your service.
-
-It assumes that you are familiar with
-[protocol buffers](https://developers.google.com/protocol-buffers/docs/overview).
-Note that the example in this tutorial uses the proto3 version of the protocol
-buffers language, which is currently in alpha release: you can find out more in
-the [proto3 language guide](https://developers.google.com/protocol-buffers/docs/proto3)
-and see the [release notes](https://github.com/google/protobuf/releases) for the
-new version in the protocol buffers Github repository.
-
-## Why use gRPC?
-
-Our example is a simple route mapping application that lets clients get
-information about features on their route, create a summary of their route, and
-exchange route information such as traffic updates with the server and other
-clients.
-
-With gRPC we can define our service once in a `.proto` file and implement clients
-and servers in any of gRPC's supported languages, which in turn can be run in
-environments ranging from servers inside Google to your own tablet - all the
-complexity of communication between different languages and environments is
-handled for you by gRPC. We also get all the advantages of working with protocol
-buffers, including efficient serialization, a simple IDL, and easy interface
-updating.
-
-## Example code and setup
-
-The example code for our tutorial is in [examples/cpp/route_guide](route_guide).
-You also should have the relevant tools installed to generate the server and
-client interface code - if you don't already, follow the setup instructions in
-[BUILDING.md](../../BUILDING.md).
-
-## Defining the service
-
-Our first step is to define the gRPC *service* and the method *request* and
-*response* types using
-[protocol buffers](https://developers.google.com/protocol-buffers/docs/overview).
-You can see the complete `.proto` file in
-[`examples/protos/route_guide.proto`](../protos/route_guide.proto).
-
-To define a service, you specify a named `service` in your `.proto` file:
-
-```protobuf
-service RouteGuide {
- ...
-}
-```
-
-Then you define `rpc` methods inside your service definition, specifying their
-request and response types. gRPC lets you define four kinds of service method,
-all of which are used in the `RouteGuide` service:
-
-- A *simple RPC* where the client sends a request to the server using the stub
- and waits for a response to come back, just like a normal function call.
-
-```protobuf
- // Obtains the feature at a given position.
- rpc GetFeature(Point) returns (Feature) {}
-```
-
-- A *server-side streaming RPC* where the client sends a request to the server
- and gets a stream to read a sequence of messages back. The client reads from
- the returned stream until there are no more messages. As you can see in our
- example, you specify a server-side streaming method by placing the `stream`
- keyword before the *response* type.
-
-```protobuf
- // Obtains the Features available within the given Rectangle. Results are
- // streamed rather than returned at once (e.g. in a response message with a
- // repeated field), as the rectangle may cover a large area and contain a
- // huge number of features.
- rpc ListFeatures(Rectangle) returns (stream Feature) {}
-```
-
-- A *client-side streaming RPC* where the client writes a sequence of messages
- and sends them to the server, again using a provided stream. Once the client
- has finished writing the messages, it waits for the server to read them all
- and return its response. You specify a client-side streaming method by placing
- the `stream` keyword before the *request* type.
-
-```protobuf
- // Accepts a stream of Points on a route being traversed, returning a
- // RouteSummary when traversal is completed.
- rpc RecordRoute(stream Point) returns (RouteSummary) {}
-```
-
-- A *bidirectional streaming RPC* where both sides send a sequence of messages
- using a read-write stream. The two streams operate independently, so clients
- and servers can read and write in whatever order they like: for example, the
- server could wait to receive all the client messages before writing its
- responses, or it could alternately read a message then write a message, or
- some other combination of reads and writes. The order of messages in each
- stream is preserved. You specify this type of method by placing the `stream`
- keyword before both the request and the response.
-
-```protobuf
- // Accepts a stream of RouteNotes sent while a route is being traversed,
- // while receiving other RouteNotes (e.g. from other users).
- rpc RouteChat(stream RouteNote) returns (stream RouteNote) {}
-```
-
-Our `.proto` file also contains protocol buffer message type definitions for all
-the request and response types used in our service methods - for example, here's
-the `Point` message type:
-
-```protobuf
-// Points are represented as latitude-longitude pairs in the E7 representation
-// (degrees multiplied by 10**7 and rounded to the nearest integer).
-// Latitudes should be in the range +/- 90 degrees and longitude should be in
-// the range +/- 180 degrees (inclusive).
-message Point {
- int32 latitude = 1;
- int32 longitude = 2;
-}
-```
-
-## Generating client and server code
-
-Next we need to generate the gRPC client and server interfaces from our `.proto`
-service definition. We do this using the protocol buffer compiler `protoc` with
-a special gRPC C++ plugin.
-
-For simplicity, we've provided a [Makefile](route_guide/Makefile) that runs
-`protoc` for you with the appropriate plugin, input, and output (if you want to
-run this yourself, make sure you've installed protoc and followed the gRPC code
-[installation instructions](../../BUILDING.md) first):
-
-```shell
-$ make route_guide.grpc.pb.cc route_guide.pb.cc
-```
-
-which actually runs:
-
-```shell
-$ protoc -I ../../protos --grpc_out=. --plugin=protoc-gen-grpc=`which grpc_cpp_plugin` ../../protos/route_guide.proto
-$ protoc -I ../../protos --cpp_out=. ../../protos/route_guide.proto
-```
-
-Running this command generates the following files in your current directory:
-- `route_guide.pb.h`, the header which declares your generated message classes
-- `route_guide.pb.cc`, which contains the implementation of your message classes
-- `route_guide.grpc.pb.h`, the header which declares your generated service
- classes
-- `route_guide.grpc.pb.cc`, which contains the implementation of your service
- classes
-
-These contain:
-- All the protocol buffer code to populate, serialize, and retrieve our request
- and response message types
-- A class called `RouteGuide` that contains
- - a remote interface type (or *stub*) for clients to call with the methods
- defined in the `RouteGuide` service.
- - two abstract interfaces for servers to implement, also with the methods
- defined in the `RouteGuide` service.
-
-
-
-## Creating the server
-
-First let's look at how we create a `RouteGuide` server. If you're only
-interested in creating gRPC clients, you can skip this section and go straight
-to [Creating the client](#client) (though you might find it interesting
-anyway!).
-
-There are two parts to making our `RouteGuide` service do its job:
-- Implementing the service interface generated from our service definition:
- doing the actual "work" of our service.
-- Running a gRPC server to listen for requests from clients and return the
- service responses.
-
-You can find our example `RouteGuide` server in
-[route_guide/route_guide_server.cc](route_guide/route_guide_server.cc). Let's
-take a closer look at how it works.
-
-### Implementing RouteGuide
-
-As you can see, our server has a `RouteGuideImpl` class that implements the
-generated `RouteGuide::Service` interface:
-
-```cpp
-class RouteGuideImpl final : public RouteGuide::Service {
-...
-}
-```
-In this case we're implementing the *synchronous* version of `RouteGuide`, which
-provides our default gRPC server behaviour. It's also possible to implement an
-asynchronous interface, `RouteGuide::AsyncService`, which allows you to further
-customize your server's threading behaviour, though we won't look at this in
-this tutorial.
-
-`RouteGuideImpl` implements all our service methods. Let's look at the simplest
-type first, `GetFeature`, which just gets a `Point` from the client and returns
-the corresponding feature information from its database in a `Feature`.
-
-```cpp
- Status GetFeature(ServerContext* context, const Point* point,
- Feature* feature) override {
- feature->set_name(GetFeatureName(*point, feature_list_));
- feature->mutable_location()->CopyFrom(*point);
- return Status::OK;
- }
-```
-
-The method is passed a context object for the RPC, the client's `Point` protocol
-buffer request, and a `Feature` protocol buffer to fill in with the response
-information. In the method we populate the `Feature` with the appropriate
-information, and then `return` with an `OK` status to tell gRPC that we've
-finished dealing with the RPC and that the `Feature` can be returned to the
-client.
-
-Now let's look at something a bit more complicated - a streaming RPC.
-`ListFeatures` is a server-side streaming RPC, so we need to send back multiple
-`Feature`s to our client.
-
-```cpp
-Status ListFeatures(ServerContext* context, const Rectangle* rectangle,
- ServerWriter* writer) override {
- auto lo = rectangle->lo();
- auto hi = rectangle->hi();
- long left = std::min(lo.longitude(), hi.longitude());
- long right = std::max(lo.longitude(), hi.longitude());
- long top = std::max(lo.latitude(), hi.latitude());
- long bottom = std::min(lo.latitude(), hi.latitude());
- for (const Feature& f : feature_list_) {
- if (f.location().longitude() >= left &&
- f.location().longitude() <= right &&
- f.location().latitude() >= bottom &&
- f.location().latitude() <= top) {
- writer->Write(f);
- }
- }
- return Status::OK;
-}
-```
-
-As you can see, instead of getting simple request and response objects in our
-method parameters, this time we get a request object (the `Rectangle` in which
-our client wants to find `Feature`s) and a special `ServerWriter` object. In the
-method, we populate as many `Feature` objects as we need to return, writing them
-to the `ServerWriter` using its `Write()` method. Finally, as in our simple RPC,
-we `return Status::OK` to tell gRPC that we've finished writing responses.
-
-If you look at the client-side streaming method `RecordRoute` you'll see it's
-quite similar, except this time we get a `ServerReader` instead of a request
-object and a single response. We use the `ServerReader`s `Read()` method to
-repeatedly read in our client's requests to a request object (in this case a
-`Point`) until there are no more messages: the server needs to check the return
-value of `Read()` after each call. If `true`, the stream is still good and it
-can continue reading; if `false` the message stream has ended.
-
-```cpp
-while (stream->Read(&point)) {
- ...//process client input
-}
-```
-Finally, let's look at our bidirectional streaming RPC `RouteChat()`.
-
-```cpp
- Status RouteChat(ServerContext* context,
- ServerReaderWriter* stream) override {
- std::vector received_notes;
- RouteNote note;
- while (stream->Read(¬e)) {
- for (const RouteNote& n : received_notes) {
- if (n.location().latitude() == note.location().latitude() &&
- n.location().longitude() == note.location().longitude()) {
- stream->Write(n);
- }
- }
- received_notes.push_back(note);
- }
-
- return Status::OK;
- }
-```
-
-This time we get a `ServerReaderWriter` that can be used to read *and* write
-messages. The syntax for reading and writing here is exactly the same as for our
-client-streaming and server-streaming methods. Although each side will always
-get the other's messages in the order they were written, both the client and
-server can read and write in any order — the streams operate completely
-independently.
-
-### Starting the server
-
-Once we've implemented all our methods, we also need to start up a gRPC server
-so that clients can actually use our service. The following snippet shows how we
-do this for our `RouteGuide` service:
-
-```cpp
-void RunServer(const std::string& db_path) {
- std::string server_address("0.0.0.0:50051");
- RouteGuideImpl service(db_path);
-
- ServerBuilder builder;
- builder.AddListeningPort(server_address, grpc::InsecureServerCredentials());
- builder.RegisterService(&service);
- std::unique_ptr server(builder.BuildAndStart());
- std::cout << "Server listening on " << server_address << std::endl;
- server->Wait();
-}
-```
-As you can see, we build and start our server using a `ServerBuilder`. To do this, we:
-
-1. Create an instance of our service implementation class `RouteGuideImpl`.
-1. Create an instance of the factory `ServerBuilder` class.
-1. Specify the address and port we want to use to listen for client requests
- using the builder's `AddListeningPort()` method.
-1. Register our service implementation with the builder.
-1. Call `BuildAndStart()` on the builder to create and start an RPC server for
- our service.
-1. Call `Wait()` on the server to do a blocking wait until process is killed or
- `Shutdown()` is called.
-
-
-## Creating the client
-
-In this section, we'll look at creating a C++ client for our `RouteGuide`
-service. You can see our complete example client code in
-[route_guide/route_guide_client.cc](route_guide/route_guide_client.cc).
-
-### Creating a stub
-
-To call service methods, we first need to create a *stub*.
-
-First we need to create a gRPC *channel* for our stub, specifying the server
-address and port we want to connect to without SSL:
-
-```cpp
-grpc::CreateChannel("localhost:50051", grpc::InsecureChannelCredentials());
-```
-
-Now we can use the channel to create our stub using the `NewStub` method
-provided in the `RouteGuide` class we generated from our `.proto`.
-
-```cpp
-public:
- RouteGuideClient(std::shared_ptr channel, const std::string& db)
- : stub_(RouteGuide::NewStub(channel)) {
- ...
- }
-```
-
-### Calling service methods
-
-Now let's look at how we call our service methods. Note that in this tutorial
-we're calling the *blocking/synchronous* versions of each method: this means
-that the RPC call waits for the server to respond, and will either return a
-response or raise an exception.
-
-#### Simple RPC
-
-Calling the simple RPC `GetFeature` is nearly as straightforward as calling a
-local method.
-
-```cpp
- Point point;
- Feature feature;
- point = MakePoint(409146138, -746188906);
- GetOneFeature(point, &feature);
-
-...
-
- bool GetOneFeature(const Point& point, Feature* feature) {
- ClientContext context;
- Status status = stub_->GetFeature(&context, point, feature);
- ...
- }
-```
-
-As you can see, we create and populate a request protocol buffer object (in our
-case `Point`), and create a response protocol buffer object for the server to
-fill in. We also create a `ClientContext` object for our call - you can
-optionally set RPC configuration values on this object, such as deadlines,
-though for now we'll use the default settings. Note that you cannot reuse this
-object between calls. Finally, we call the method on the stub, passing it the
-context, request, and response. If the method returns `OK`, then we can read the
-response information from the server from our response object.
-
-```cpp
-std::cout << "Found feature called " << feature->name() << " at "
- << feature->location().latitude()/kCoordFactor_ << ", "
- << feature->location().longitude()/kCoordFactor_ << std::endl;
-```
-
-#### Streaming RPCs
-
-Now let's look at our streaming methods. If you've already read [Creating the
-server](#server) some of this may look very familiar - streaming RPCs are
-implemented in a similar way on both sides. Here's where we call the server-side
-streaming method `ListFeatures`, which returns a stream of geographical
-`Feature`s:
-
-```cpp
-std::unique_ptr > reader(
- stub_->ListFeatures(&context, rect));
-while (reader->Read(&feature)) {
- std::cout << "Found feature called "
- << feature.name() << " at "
- << feature.location().latitude()/kCoordFactor_ << ", "
- << feature.location().longitude()/kCoordFactor_ << std::endl;
-}
-Status status = reader->Finish();
-```
-
-Instead of passing the method a context, request, and response, we pass it a
-context and request and get a `ClientReader` object back. The client can use the
-`ClientReader` to read the server's responses. We use the `ClientReader`s
-`Read()` method to repeatedly read in the server's responses to a response
-protocol buffer object (in this case a `Feature`) until there are no more
-messages: the client needs to check the return value of `Read()` after each
-call. If `true`, the stream is still good and it can continue reading; if
-`false` the message stream has ended. Finally, we call `Finish()` on the stream
-to complete the call and get our RPC status.
-
-The client-side streaming method `RecordRoute` is similar, except there we pass
-the method a context and response object and get back a `ClientWriter`.
-
-```cpp
- std::unique_ptr > writer(
- stub_->RecordRoute(&context, &stats));
- for (int i = 0; i < kPoints; i++) {
- const Feature& f = feature_list_[feature_distribution(generator)];
- std::cout << "Visiting point "
- << f.location().latitude()/kCoordFactor_ << ", "
- << f.location().longitude()/kCoordFactor_ << std::endl;
- if (!writer->Write(f.location())) {
- // Broken stream.
- break;
- }
- std::this_thread::sleep_for(std::chrono::milliseconds(
- delay_distribution(generator)));
- }
- writer->WritesDone();
- Status status = writer->Finish();
- if (status.IsOk()) {
- std::cout << "Finished trip with " << stats.point_count() << " points\n"
- << "Passed " << stats.feature_count() << " features\n"
- << "Travelled " << stats.distance() << " meters\n"
- << "It took " << stats.elapsed_time() << " seconds"
- << std::endl;
- } else {
- std::cout << "RecordRoute rpc failed." << std::endl;
- }
-```
-
-Once we've finished writing our client's requests to the stream using `Write()`,
-we need to call `WritesDone()` on the stream to let gRPC know that we've
-finished writing, then `Finish()` to complete the call and get our RPC status.
-If the status is `OK`, our response object that we initially passed to
-`RecordRoute()` will be populated with the server's response.
-
-Finally, let's look at our bidirectional streaming RPC `RouteChat()`. In this
-case, we just pass a context to the method and get back a `ClientReaderWriter`,
-which we can use to both write and read messages.
-
-```cpp
-std::shared_ptr > stream(
- stub_->RouteChat(&context));
-```
-
-The syntax for reading and writing here is exactly the same as for our
-client-streaming and server-streaming methods. Although each side will always
-get the other's messages in the order they were written, both the client and
-server can read and write in any order — the streams operate completely
-independently.
-
-## Try it out!
-
-Build client and server:
-```shell
-$ make
-```
-Run the server, which will listen on port 50051:
-```shell
-$ ./route_guide_server
-```
-Run the client (in a different terminal):
-```shell
-$ ./route_guide_client
-```
diff --git a/examples/cpp/helloworld/README.md b/examples/cpp/helloworld/README.md
index 71718645645..e13c83281a7 100644
--- a/examples/cpp/helloworld/README.md
+++ b/examples/cpp/helloworld/README.md
@@ -1,264 +1,6 @@
-# gRPC C++ Hello World Tutorial
+# gRPC C++ Hello World Example
-### Install gRPC
-Make sure you have installed gRPC on your system. Follow the
-[BUILDING.md](../../../BUILDING.md) instructions.
+You can find a complete set of instructions for building gRPC and running the
+Hello World app in the [C++ Quick Start][].
-### Get the tutorial source code
-
-The example code for this and our other examples lives in the `examples`
-directory. Clone this repository at the [latest stable release tag](https://github.com/grpc/grpc/releases)
-to your local machine by running the following command:
-
-
-```sh
-$ git clone -b RELEASE_TAG_HERE https://github.com/grpc/grpc
-```
-
-Change your current directory to examples/cpp/helloworld
-
-```sh
-$ cd examples/cpp/helloworld/
-```
-
-### Defining a service
-
-The first step in creating our example is to define a *service*: an RPC
-service specifies the methods that can be called remotely with their parameters
-and return types. As you saw in the
-[overview](#protocolbuffers) above, gRPC does this using [protocol
-buffers](https://developers.google.com/protocol-buffers/docs/overview). We
-use the protocol buffers interface definition language (IDL) to define our
-service methods, and define the parameters and return
-types as protocol buffer message types. Both the client and the
-server use interface code generated from the service definition.
-
-Here's our example service definition, defined using protocol buffers IDL in
-[helloworld.proto](../../protos/helloworld.proto). The `Greeting`
-service has one method, `hello`, that lets the server receive a single
-`HelloRequest`
-message from the remote client containing the user's name, then send back
-a greeting in a single `HelloReply`. This is the simplest type of RPC you
-can specify in gRPC - we'll look at some other types later in this document.
-
-```protobuf
-syntax = "proto3";
-
-option java_package = "ex.grpc";
-
-package helloworld;
-
-// The greeting service definition.
-service Greeter {
- // Sends a greeting
- rpc SayHello (HelloRequest) returns (HelloReply) {}
-}
-
-// The request message containing the user's name.
-message HelloRequest {
- string name = 1;
-}
-
-// The response message containing the greetings
-message HelloReply {
- string message = 1;
-}
-
-```
-
-
-### Generating gRPC code
-
-Once we've defined our service, we use the protocol buffer compiler
-`protoc` to generate the special client and server code we need to create
-our application. The generated code contains both stub code for clients to
-use and an abstract interface for servers to implement, both with the method
-defined in our `Greeting` service.
-
-To generate the client and server side interfaces:
-
-```sh
-$ make helloworld.grpc.pb.cc helloworld.pb.cc
-```
-Which internally invokes the proto-compiler as:
-
-```sh
-$ protoc -I ../../protos/ --grpc_out=. --plugin=protoc-gen-grpc=grpc_cpp_plugin ../../protos/helloworld.proto
-$ protoc -I ../../protos/ --cpp_out=. ../../protos/helloworld.proto
-```
-
-### Writing a client
-
-- Create a channel. A channel is a logical connection to an endpoint. A gRPC
- channel can be created with the target address, credentials to use and
- arguments as follows
-
- ```cpp
- auto channel = CreateChannel("localhost:50051", InsecureChannelCredentials());
- ```
-
-- Create a stub. A stub implements the rpc methods of a service and in the
- generated code, a method is provided to create a stub with a channel:
-
- ```cpp
- auto stub = helloworld::Greeter::NewStub(channel);
- ```
-
-- Make a unary rpc, with `ClientContext` and request/response proto messages.
-
- ```cpp
- ClientContext context;
- HelloRequest request;
- request.set_name("hello");
- HelloReply reply;
- Status status = stub->SayHello(&context, request, &reply);
- ```
-
-- Check returned status and response.
-
- ```cpp
- if (status.ok()) {
- // check reply.message()
- } else {
- // rpc failed.
- }
- ```
-
-For a working example, refer to [greeter_client.cc](greeter_client.cc).
-
-### Writing a server
-
-- Implement the service interface
-
- ```cpp
- class GreeterServiceImpl final : public Greeter::Service {
- Status SayHello(ServerContext* context, const HelloRequest* request,
- HelloReply* reply) override {
- std::string prefix("Hello ");
- reply->set_message(prefix + request->name());
- return Status::OK;
- }
- };
-
- ```
-
-- Build a server exporting the service
-
- ```cpp
- GreeterServiceImpl service;
- ServerBuilder builder;
- builder.AddListeningPort("0.0.0.0:50051", grpc::InsecureServerCredentials());
- builder.RegisterService(&service);
- std::unique_ptr server(builder.BuildAndStart());
- ```
-
-For a working example, refer to [greeter_server.cc](greeter_server.cc).
-
-### Writing asynchronous client and server
-
-gRPC uses `CompletionQueue` API for asynchronous operations. The basic work flow
-is
-- bind a `CompletionQueue` to a rpc call
-- do something like a read or write, present with a unique `void*` tag
-- call `CompletionQueue::Next` to wait for operations to complete. If a tag
- appears, it indicates that the corresponding operation is complete.
-
-#### Async client
-
-The channel and stub creation code is the same as the sync client.
-
-- Initiate the rpc and create a handle for the rpc. Bind the rpc to a
- `CompletionQueue`.
-
- ```cpp
- CompletionQueue cq;
- auto rpc = stub->AsyncSayHello(&context, request, &cq);
- ```
-
-- Ask for reply and final status, with a unique tag
-
- ```cpp
- Status status;
- rpc->Finish(&reply, &status, (void*)1);
- ```
-
-- Wait for the completion queue to return the next tag. The reply and status are
- ready once the tag passed into the corresponding `Finish()` call is returned.
-
- ```cpp
- void* got_tag;
- bool ok = false;
- cq.Next(&got_tag, &ok);
- if (ok && got_tag == (void*)1) {
- // check reply and status
- }
- ```
-
-For a working example, refer to [greeter_async_client.cc](greeter_async_client.cc).
-
-#### Async server
-
-The server implementation requests a rpc call with a tag and then wait for the
-completion queue to return the tag. The basic flow is
-
-- Build a server exporting the async service
-
- ```cpp
- helloworld::Greeter::AsyncService service;
- ServerBuilder builder;
- builder.AddListeningPort("0.0.0.0:50051", InsecureServerCredentials());
- builder.RegisterService(&service);
- auto cq = builder.AddCompletionQueue();
- auto server = builder.BuildAndStart();
- ```
-
-- Request one rpc
-
- ```cpp
- ServerContext context;
- HelloRequest request;
- ServerAsyncResponseWriter responder;
- service.RequestSayHello(&context, &request, &responder, &cq, &cq, (void*)1);
- ```
-
-- Wait for the completion queue to return the tag. The context, request and
- responder are ready once the tag is retrieved.
-
- ```cpp
- HelloReply reply;
- Status status;
- void* got_tag;
- bool ok = false;
- cq.Next(&got_tag, &ok);
- if (ok && got_tag == (void*)1) {
- // set reply and status
- responder.Finish(reply, status, (void*)2);
- }
- ```
-
-- Wait for the completion queue to return the tag. The rpc is finished when the
- tag is back.
-
- ```cpp
- void* got_tag;
- bool ok = false;
- cq.Next(&got_tag, &ok);
- if (ok && got_tag == (void*)2) {
- // clean up
- }
- ```
-
-To handle multiple rpcs, the async server creates an object `CallData` to
-maintain the state of each rpc and use the address of it as the unique tag. For
-simplicity the server only uses one completion queue for all events, and runs a
-main loop in `HandleRpcs` to query the queue.
-
-For a working example, refer to [greeter_async_server.cc](greeter_async_server.cc).
-
-#### Flags for the client
-
-```sh
-./greeter_client --target="a target string used to create a GRPC client channel"
-```
-
-The Default value for --target is "localhost:50051".
+[C++ Quick Start]: https://grpc.io/docs/quickstart/cpp
diff --git a/examples/python/multiprocessing/BUILD b/examples/python/multiprocessing/BUILD
index ea9b6a3ec6f..1d831e729b4 100644
--- a/examples/python/multiprocessing/BUILD
+++ b/examples/python/multiprocessing/BUILD
@@ -37,6 +37,7 @@ py_binary(
name = "client",
testonly = 1,
srcs = ["client.py"],
+ imports = ["."],
python_version = "PY3",
srcs_version = "PY3",
deps = [
@@ -50,6 +51,7 @@ py_binary(
name = "server",
testonly = 1,
srcs = ["server.py"],
+ imports = ["."],
python_version = "PY3",
srcs_version = "PY3",
deps = [
diff --git a/examples/python/multiprocessing/README.md b/examples/python/multiprocessing/README.md
index 709a815aca5..5dce50ad3bd 100644
--- a/examples/python/multiprocessing/README.md
+++ b/examples/python/multiprocessing/README.md
@@ -1,28 +1,27 @@
## Multiprocessing with gRPC Python
Multiprocessing allows application developers to sidestep the Python global
-interpreter lock and achieve true concurrency on multicore systems.
+interpreter lock and achieve true parallelism on multicore systems.
Unfortunately, using multiprocessing and gRPC Python is not yet as simple as
instantiating your server with a `futures.ProcessPoolExecutor`.
The library is implemented as a C extension, maintaining much of the state that
drives the system in native code. As such, upon calling
-[`fork`](http://man7.org/linux/man-pages/man2/fork.2.html), much of the
-state copied into the child process is invalid, leading to hangs and crashes.
-
-However, calling `fork` without `exec` in your python process is supported
-*before* any gRPC servers have been instantiated. Application developers can
+[`fork`](http://man7.org/linux/man-pages/man2/fork.2.html), any threads in a
+critical section may leave the state of the gRPC library invalid in the child
+process. See this [excellent research
+paper](https://www.microsoft.com/en-us/research/uploads/prod/2019/04/fork-hotos19.pdf)
+for a thorough discussion of the topic.
+
+Calling `fork` without `exec` in your process *is* supported
+before any gRPC servers have been instantiated. Application developers can
take advantage of this to parallelize their CPU-intensive operations.
## Calculating Prime Numbers with Multiple Processes
This example calculates the first 10,000 prime numbers as an RPC. We instantiate
one server per subprocess, balancing requests between the servers using the
-[`SO_REUSEPORT`](https://lwn.net/Articles/542629/) socket option. Note that this
-option is not available in `manylinux1` distributions, which are, as of the time
-of writing, the only gRPC Python wheels available on PyPI. To take advantage of this
-feature, you'll need to build from source, either using bazel (as we do for
-these examples) or via pip, using `pip install grpcio --no-binary grpcio`.
+[`SO_REUSEPORT`](https://lwn.net/Articles/542629/) socket option.
```python
_PROCESS_COUNT = multiprocessing.cpu_count()
@@ -65,3 +64,11 @@ For example,
```
bazel run //examples/python/multiprocessing:client -- [::]:33915
```
+
+Alternatively, generate code using the following and then run the client and server
+directly:
+
+```python
+cd examples/python/helloworld
+python -m grpc_tools.protoc -I . prime.proto --python_out=. --grpc_python_out=.
+```
diff --git a/examples/python/multiprocessing/client.py b/examples/python/multiprocessing/client.py
index b9acc65fdc5..7676bd4ec88 100644
--- a/examples/python/multiprocessing/client.py
+++ b/examples/python/multiprocessing/client.py
@@ -26,8 +26,8 @@ import sys
import grpc
-from examples.python.multiprocessing import prime_pb2
-from examples.python.multiprocessing import prime_pb2_grpc
+import prime_pb2
+import prime_pb2_grpc
_PROCESS_COUNT = 8
_MAXIMUM_CANDIDATE = 10000
diff --git a/examples/python/multiprocessing/server.py b/examples/python/multiprocessing/server.py
index ad788b8eb51..a5ee00755e6 100644
--- a/examples/python/multiprocessing/server.py
+++ b/examples/python/multiprocessing/server.py
@@ -29,8 +29,8 @@ import sys
import grpc
-from examples.python.multiprocessing import prime_pb2
-from examples.python.multiprocessing import prime_pb2_grpc
+import prime_pb2
+import prime_pb2_grpc
_LOGGER = logging.getLogger(__name__)
@@ -67,12 +67,6 @@ def _run_server(bind_address):
_LOGGER.info('Starting new server.')
options = (('grpc.so_reuseport', 1),)
- # WARNING: This example takes advantage of SO_REUSEPORT. Due to the
- # limitations of manylinux1, none of our precompiled Linux wheels currently
- # support this option. (https://github.com/grpc/grpc/issues/18210). To take
- # advantage of this feature, install from source with
- # `pip install grpcio --no-binary grpcio`.
-
server = grpc.server(futures.ThreadPoolExecutor(
max_workers=_THREAD_CONCURRENCY,),
options=options)
diff --git a/gRPC-C++.podspec b/gRPC-C++.podspec
index c8b176b23ea..77980999b59 100644
--- a/gRPC-C++.podspec
+++ b/gRPC-C++.podspec
@@ -233,6 +233,7 @@ Pod::Spec.new do |s|
'src/core/ext/filters/client_channel/http_connect_handshaker.h',
'src/core/ext/filters/client_channel/http_proxy.h',
'src/core/ext/filters/client_channel/lb_policy.h',
+ 'src/core/ext/filters/client_channel/lb_policy/address_filtering.h',
'src/core/ext/filters/client_channel/lb_policy/child_policy_handler.h',
'src/core/ext/filters/client_channel/lb_policy/grpclb/client_load_reporting_filter.h',
'src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb.h',
@@ -683,6 +684,7 @@ Pod::Spec.new do |s|
'src/core/ext/filters/client_channel/http_connect_handshaker.h',
'src/core/ext/filters/client_channel/http_proxy.h',
'src/core/ext/filters/client_channel/lb_policy.h',
+ 'src/core/ext/filters/client_channel/lb_policy/address_filtering.h',
'src/core/ext/filters/client_channel/lb_policy/child_policy_handler.h',
'src/core/ext/filters/client_channel/lb_policy/grpclb/client_load_reporting_filter.h',
'src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb.h',
diff --git a/gRPC-Core.podspec b/gRPC-Core.podspec
index d140b005d7f..749e77b3fa7 100644
--- a/gRPC-Core.podspec
+++ b/gRPC-Core.podspec
@@ -206,6 +206,8 @@ Pod::Spec.new do |s|
'src/core/ext/filters/client_channel/http_proxy.h',
'src/core/ext/filters/client_channel/lb_policy.cc',
'src/core/ext/filters/client_channel/lb_policy.h',
+ 'src/core/ext/filters/client_channel/lb_policy/address_filtering.cc',
+ 'src/core/ext/filters/client_channel/lb_policy/address_filtering.h',
'src/core/ext/filters/client_channel/lb_policy/child_policy_handler.cc',
'src/core/ext/filters/client_channel/lb_policy/child_policy_handler.h',
'src/core/ext/filters/client_channel/lb_policy/grpclb/client_load_reporting_filter.cc',
@@ -221,10 +223,13 @@ Pod::Spec.new do |s|
'src/core/ext/filters/client_channel/lb_policy/grpclb/load_balancer_api.cc',
'src/core/ext/filters/client_channel/lb_policy/grpclb/load_balancer_api.h',
'src/core/ext/filters/client_channel/lb_policy/pick_first/pick_first.cc',
+ 'src/core/ext/filters/client_channel/lb_policy/priority/priority.cc',
'src/core/ext/filters/client_channel/lb_policy/round_robin/round_robin.cc',
'src/core/ext/filters/client_channel/lb_policy/subchannel_list.h',
+ 'src/core/ext/filters/client_channel/lb_policy/weighted_target/weighted_target.cc',
'src/core/ext/filters/client_channel/lb_policy/xds/cds.cc',
- 'src/core/ext/filters/client_channel/lb_policy/xds/xds.cc',
+ 'src/core/ext/filters/client_channel/lb_policy/xds/eds.cc',
+ 'src/core/ext/filters/client_channel/lb_policy/xds/lrs.cc',
'src/core/ext/filters/client_channel/lb_policy/xds/xds.h',
'src/core/ext/filters/client_channel/lb_policy_factory.h',
'src/core/ext/filters/client_channel/lb_policy_registry.cc',
@@ -1032,6 +1037,7 @@ Pod::Spec.new do |s|
'src/core/ext/filters/client_channel/http_connect_handshaker.h',
'src/core/ext/filters/client_channel/http_proxy.h',
'src/core/ext/filters/client_channel/lb_policy.h',
+ 'src/core/ext/filters/client_channel/lb_policy/address_filtering.h',
'src/core/ext/filters/client_channel/lb_policy/child_policy_handler.h',
'src/core/ext/filters/client_channel/lb_policy/grpclb/client_load_reporting_filter.h',
'src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb.h',
diff --git a/grpc.gemspec b/grpc.gemspec
index c9a1a8835fd..29e5d3d436b 100644
--- a/grpc.gemspec
+++ b/grpc.gemspec
@@ -128,6 +128,8 @@ Gem::Specification.new do |s|
s.files += %w( src/core/ext/filters/client_channel/http_proxy.h )
s.files += %w( src/core/ext/filters/client_channel/lb_policy.cc )
s.files += %w( src/core/ext/filters/client_channel/lb_policy.h )
+ s.files += %w( src/core/ext/filters/client_channel/lb_policy/address_filtering.cc )
+ s.files += %w( src/core/ext/filters/client_channel/lb_policy/address_filtering.h )
s.files += %w( src/core/ext/filters/client_channel/lb_policy/child_policy_handler.cc )
s.files += %w( src/core/ext/filters/client_channel/lb_policy/child_policy_handler.h )
s.files += %w( src/core/ext/filters/client_channel/lb_policy/grpclb/client_load_reporting_filter.cc )
@@ -143,10 +145,13 @@ Gem::Specification.new do |s|
s.files += %w( src/core/ext/filters/client_channel/lb_policy/grpclb/load_balancer_api.cc )
s.files += %w( src/core/ext/filters/client_channel/lb_policy/grpclb/load_balancer_api.h )
s.files += %w( src/core/ext/filters/client_channel/lb_policy/pick_first/pick_first.cc )
+ s.files += %w( src/core/ext/filters/client_channel/lb_policy/priority/priority.cc )
s.files += %w( src/core/ext/filters/client_channel/lb_policy/round_robin/round_robin.cc )
s.files += %w( src/core/ext/filters/client_channel/lb_policy/subchannel_list.h )
+ s.files += %w( src/core/ext/filters/client_channel/lb_policy/weighted_target/weighted_target.cc )
s.files += %w( src/core/ext/filters/client_channel/lb_policy/xds/cds.cc )
- s.files += %w( src/core/ext/filters/client_channel/lb_policy/xds/xds.cc )
+ s.files += %w( src/core/ext/filters/client_channel/lb_policy/xds/eds.cc )
+ s.files += %w( src/core/ext/filters/client_channel/lb_policy/xds/lrs.cc )
s.files += %w( src/core/ext/filters/client_channel/lb_policy/xds/xds.h )
s.files += %w( src/core/ext/filters/client_channel/lb_policy_factory.h )
s.files += %w( src/core/ext/filters/client_channel/lb_policy_registry.cc )
diff --git a/grpc.gyp b/grpc.gyp
index b065ee6f2af..a62c034d65a 100644
--- a/grpc.gyp
+++ b/grpc.gyp
@@ -426,6 +426,7 @@
'address_sorting',
'upb',
'absl/types:optional',
+ 'absl/strings:strings',
'absl/container:inlined_vector',
],
'sources': [
@@ -442,6 +443,7 @@
'src/core/ext/filters/client_channel/http_connect_handshaker.cc',
'src/core/ext/filters/client_channel/http_proxy.cc',
'src/core/ext/filters/client_channel/lb_policy.cc',
+ 'src/core/ext/filters/client_channel/lb_policy/address_filtering.cc',
'src/core/ext/filters/client_channel/lb_policy/child_policy_handler.cc',
'src/core/ext/filters/client_channel/lb_policy/grpclb/client_load_reporting_filter.cc',
'src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb.cc',
@@ -450,9 +452,12 @@
'src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb_client_stats.cc',
'src/core/ext/filters/client_channel/lb_policy/grpclb/load_balancer_api.cc',
'src/core/ext/filters/client_channel/lb_policy/pick_first/pick_first.cc',
+ 'src/core/ext/filters/client_channel/lb_policy/priority/priority.cc',
'src/core/ext/filters/client_channel/lb_policy/round_robin/round_robin.cc',
+ 'src/core/ext/filters/client_channel/lb_policy/weighted_target/weighted_target.cc',
'src/core/ext/filters/client_channel/lb_policy/xds/cds.cc',
- 'src/core/ext/filters/client_channel/lb_policy/xds/xds.cc',
+ 'src/core/ext/filters/client_channel/lb_policy/xds/eds.cc',
+ 'src/core/ext/filters/client_channel/lb_policy/xds/lrs.cc',
'src/core/ext/filters/client_channel/lb_policy_registry.cc',
'src/core/ext/filters/client_channel/local_subchannel_pool.cc',
'src/core/ext/filters/client_channel/parse_address.cc',
@@ -916,6 +921,7 @@
'address_sorting',
'upb',
'absl/types:optional',
+ 'absl/strings:strings',
'absl/container:inlined_vector',
],
'sources': [
@@ -932,6 +938,7 @@
'src/core/ext/filters/client_channel/http_connect_handshaker.cc',
'src/core/ext/filters/client_channel/http_proxy.cc',
'src/core/ext/filters/client_channel/lb_policy.cc',
+ 'src/core/ext/filters/client_channel/lb_policy/address_filtering.cc',
'src/core/ext/filters/client_channel/lb_policy/child_policy_handler.cc',
'src/core/ext/filters/client_channel/lb_policy/grpclb/client_load_reporting_filter.cc',
'src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb.cc',
@@ -940,9 +947,12 @@
'src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb_client_stats.cc',
'src/core/ext/filters/client_channel/lb_policy/grpclb/load_balancer_api.cc',
'src/core/ext/filters/client_channel/lb_policy/pick_first/pick_first.cc',
+ 'src/core/ext/filters/client_channel/lb_policy/priority/priority.cc',
'src/core/ext/filters/client_channel/lb_policy/round_robin/round_robin.cc',
+ 'src/core/ext/filters/client_channel/lb_policy/weighted_target/weighted_target.cc',
'src/core/ext/filters/client_channel/lb_policy/xds/cds.cc',
- 'src/core/ext/filters/client_channel/lb_policy/xds/xds.cc',
+ 'src/core/ext/filters/client_channel/lb_policy/xds/eds.cc',
+ 'src/core/ext/filters/client_channel/lb_policy/xds/lrs.cc',
'src/core/ext/filters/client_channel/lb_policy_registry.cc',
'src/core/ext/filters/client_channel/local_subchannel_pool.cc',
'src/core/ext/filters/client_channel/parse_address.cc',
diff --git a/include/grpc/impl/codegen/grpc_types.h b/include/grpc/impl/codegen/grpc_types.h
index ab4c39f9310..c7dd23caa49 100644
--- a/include/grpc/impl/codegen/grpc_types.h
+++ b/include/grpc/impl/codegen/grpc_types.h
@@ -344,22 +344,11 @@ typedef struct {
balancer before using fallback backend addresses from the resolver.
If 0, enter fallback mode immediately. Default value is 10000. */
#define GRPC_ARG_GRPCLB_FALLBACK_TIMEOUT_MS "grpc.grpclb_fallback_timeout_ms"
-/* Timeout in milliseconds to wait for the serverlist from the xDS load
- balancer before using fallback backend addresses from the resolver.
- If 0, enter fallback mode immediately. Default value is 10000. */
-#define GRPC_ARG_XDS_FALLBACK_TIMEOUT_MS "grpc.xds_fallback_timeout_ms"
-/* Time in milliseconds to wait before a locality is deleted after it's removed
- from the received EDS update. If 0, delete the locality immediately. Default
- value is 15 minutes. */
-#define GRPC_ARG_LOCALITY_RETENTION_INTERVAL_MS \
- "grpc.xds_locality_retention_interval_ms"
-/* Timeout in milliseconds to wait for the localities of a specific priority to
- complete their initial connection attempt before xDS fails over to the next
- priority. Specifically, the connection attempt of a priority is considered
- completed when any locality of that priority is ready or all the localities
- of that priority fail to connect. If 0, failover happens immediately. Default
- value is 10 seconds. */
-#define GRPC_ARG_XDS_FAILOVER_TIMEOUT_MS "grpc.xds_failover_timeout_ms"
+/* Timeout in milliseconds to wait for the child of a specific priority to
+ complete its initial connection attempt before the priority LB policy fails
+ over to the next priority. Default value is 10 seconds. */
+#define GRPC_ARG_PRIORITY_FAILOVER_TIMEOUT_MS \
+ "grpc.priority_failover_timeout_ms"
/* Timeout in milliseconds to wait for a resource to be returned from
* the xds server before assuming that it does not exist.
* The default is 15 seconds. */
diff --git a/package.xml b/package.xml
index 32930b6f65c..06d1669ec48 100644
--- a/package.xml
+++ b/package.xml
@@ -108,6 +108,8 @@
+
+
@@ -123,10 +125,13 @@
+
+
-
+
+
diff --git a/src/core/ext/filters/client_channel/lb_policy/address_filtering.cc b/src/core/ext/filters/client_channel/lb_policy/address_filtering.cc
new file mode 100644
index 00000000000..67843df78e5
--- /dev/null
+++ b/src/core/ext/filters/client_channel/lb_policy/address_filtering.cc
@@ -0,0 +1,83 @@
+//
+// Copyright 2020 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
+
+#include "src/core/ext/filters/client_channel/lb_policy/address_filtering.h"
+
+#include "src/core/lib/channel/channel_args.h"
+
+#define GRPC_ARG_HIERARCHICAL_PATH "grpc.internal.address.hierarchical_path"
+
+namespace grpc_core {
+
+namespace {
+
+void* HierarchicalPathCopy(void* p) {
+ std::vector* path = static_cast*>(p);
+ return static_cast(new std::vector(*path));
+}
+
+void HierarchicalPathDestroy(void* p) {
+ std::vector* path = static_cast*>(p);
+ delete path;
+}
+
+int HierarchicalPathCompare(void* p1, void* p2) {
+ std::vector* path1 = static_cast*>(p1);
+ std::vector* path2 = static_cast*>(p2);
+ for (size_t i = 0; i < path1->size(); ++i) {
+ if (path2->size() == i) return 1;
+ int r = (*path1)[i].compare((*path2)[i]);
+ if (r != 0) return r;
+ }
+ if (path2->size() > path1->size()) return -1;
+ return 0;
+}
+
+const grpc_arg_pointer_vtable hierarchical_path_arg_vtable = {
+ HierarchicalPathCopy, HierarchicalPathDestroy, HierarchicalPathCompare};
+
+} // namespace
+
+grpc_arg MakeHierarchicalPathArg(const std::vector& path) {
+ return grpc_channel_arg_pointer_create(
+ const_cast(GRPC_ARG_HIERARCHICAL_PATH),
+ const_cast*>(&path),
+ &hierarchical_path_arg_vtable);
+}
+
+HierarchicalAddressMap MakeHierarchicalAddressMap(
+ const ServerAddressList& addresses) {
+ HierarchicalAddressMap result;
+ for (const ServerAddress& address : addresses) {
+ auto* path = grpc_channel_args_find_pointer>(
+ address.args(), GRPC_ARG_HIERARCHICAL_PATH);
+ if (path == nullptr || path->empty()) continue;
+ auto it = path->begin();
+ ServerAddressList& target_list = result[*it];
+ ++it;
+ std::vector remaining_path(it, path->end());
+ const char* name_to_remove = GRPC_ARG_HIERARCHICAL_PATH;
+ grpc_arg new_arg = MakeHierarchicalPathArg(remaining_path);
+ grpc_channel_args* new_args = grpc_channel_args_copy_and_add_and_remove(
+ address.args(), &name_to_remove, 1, &new_arg, 1);
+ target_list.emplace_back(address.address(), new_args);
+ }
+ return result;
+}
+
+} // namespace grpc_core
diff --git a/src/core/ext/filters/client_channel/lb_policy/address_filtering.h b/src/core/ext/filters/client_channel/lb_policy/address_filtering.h
new file mode 100644
index 00000000000..03a1c228e7a
--- /dev/null
+++ b/src/core/ext/filters/client_channel/lb_policy/address_filtering.h
@@ -0,0 +1,99 @@
+//
+// Copyright 2020 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_CORE_EXT_FILTERS_CLIENT_CHANNEL_LB_POLICY_ADDRESS_FILTERING_H
+#define GRPC_CORE_EXT_FILTERS_CLIENT_CHANNEL_LB_POLICY_ADDRESS_FILTERING_H
+
+#include
+
+#include