grpc 1.6.7 → 1.7.0.pre1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of grpc might be problematic. Click here for more details.
- checksums.yaml +4 -4
 - data/Makefile +579 -77
 - data/include/grpc/byte_buffer.h +1 -63
 - data/include/grpc/compression.h +27 -5
 - data/include/grpc/fork.h +24 -0
 - data/include/grpc/grpc.h +12 -6
 - data/include/grpc/grpc_security.h +28 -7
 - data/include/grpc/impl/codegen/atm.h +1 -0
 - data/include/grpc/impl/codegen/byte_buffer.h +86 -0
 - data/include/grpc/impl/codegen/compression_types.h +63 -5
 - data/include/grpc/impl/codegen/fork.h +48 -0
 - data/include/grpc/impl/codegen/grpc_types.h +26 -9
 - data/include/grpc/impl/codegen/port_platform.h +11 -4
 - data/include/grpc/impl/codegen/slice.h +6 -1
 - data/include/grpc/impl/codegen/sync.h +3 -1
 - data/include/grpc/impl/codegen/sync_custom.h +36 -0
 - data/include/grpc/module.modulemap +75 -3
 - data/include/grpc/slice.h +1 -5
 - data/include/grpc/support/sync_custom.h +24 -0
 - data/src/core/ext/census/base_resources.c +14 -14
 - data/src/core/ext/census/context.c +7 -5
 - data/src/core/ext/census/grpc_filter.c +12 -14
 - data/src/core/ext/census/mlog.c +2 -1
 - data/src/core/ext/census/resource.c +13 -9
 - data/src/core/ext/filters/client_channel/channel_connectivity.c +15 -8
 - data/src/core/ext/filters/client_channel/client_channel.c +418 -439
 - data/src/core/ext/filters/client_channel/client_channel_factory.c +4 -5
 - data/src/core/ext/filters/client_channel/client_channel_plugin.c +2 -2
 - data/src/core/ext/filters/client_channel/http_connect_handshaker.c +7 -5
 - data/src/core/ext/filters/client_channel/http_proxy.c +17 -21
 - data/src/core/ext/filters/client_channel/lb_policy.c +1 -1
 - data/src/core/ext/filters/client_channel/lb_policy/grpclb/client_load_reporting_filter.c +7 -7
 - data/src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb.c +371 -257
 - data/src/core/ext/filters/client_channel/lb_policy/grpclb/grpclb_client_stats.c +7 -5
 - data/src/core/ext/filters/client_channel/lb_policy/grpclb/load_balancer_api.c +25 -14
 - data/src/core/ext/filters/client_channel/lb_policy/pick_first/pick_first.c +16 -16
 - data/src/core/ext/filters/client_channel/lb_policy/round_robin/round_robin.c +33 -28
 - data/src/core/ext/filters/client_channel/lb_policy_factory.c +10 -8
 - data/src/core/ext/filters/client_channel/lb_policy_factory.h +1 -1
 - data/src/core/ext/filters/client_channel/proxy_mapper_registry.c +1 -1
 - data/src/core/ext/filters/client_channel/resolver/dns/c_ares/dns_resolver_ares.c +7 -6
 - data/src/core/ext/filters/client_channel/resolver/dns/c_ares/grpc_ares_ev_driver_posix.c +62 -28
 - data/src/core/ext/filters/client_channel/resolver/dns/c_ares/grpc_ares_wrapper.c +29 -23
 - data/src/core/ext/filters/client_channel/resolver/fake/fake_resolver.c +25 -14
 - data/src/core/ext/filters/client_channel/retry_throttle.c +9 -6
 - data/src/core/ext/filters/client_channel/subchannel.c +30 -30
 - data/src/core/ext/filters/client_channel/subchannel.h +1 -4
 - data/src/core/ext/filters/client_channel/subchannel_index.c +31 -15
 - data/src/core/ext/filters/client_channel/subchannel_index.h +7 -0
 - data/src/core/ext/filters/client_channel/uri_parser.c +4 -3
 - data/src/core/ext/filters/deadline/deadline_filter.c +78 -39
 - data/src/core/ext/filters/deadline/deadline_filter.h +7 -1
 - data/src/core/ext/filters/http/client/http_client_filter.c +14 -14
 - data/src/core/ext/filters/http/http_filters_plugin.c +1 -1
 - data/src/core/ext/filters/http/message_compress/message_compress_filter.c +240 -175
 - data/src/core/ext/filters/http/server/http_server_filter.c +48 -36
 - data/src/core/ext/filters/load_reporting/{load_reporting_filter.c → server_load_reporting_filter.c} +11 -12
 - data/src/core/ext/filters/load_reporting/{load_reporting_filter.h → server_load_reporting_filter.h} +6 -5
 - data/src/core/ext/filters/load_reporting/{load_reporting.c → server_load_reporting_plugin.c} +19 -13
 - data/src/core/ext/filters/load_reporting/{load_reporting.h → server_load_reporting_plugin.h} +4 -3
 - data/src/core/ext/filters/max_age/max_age_filter.c +2 -3
 - data/src/core/ext/filters/message_size/message_size_filter.c +4 -2
 - data/src/core/ext/filters/workarounds/workaround_cronet_compression_filter.c +0 -1
 - data/src/core/ext/transport/chttp2/client/chttp2_connector.c +5 -5
 - data/src/core/ext/transport/chttp2/client/insecure/channel_create.c +1 -1
 - data/src/core/ext/transport/chttp2/client/insecure/channel_create_posix.c +1 -1
 - data/src/core/ext/transport/chttp2/server/chttp2_server.c +20 -18
 - data/src/core/ext/transport/chttp2/transport/chttp2_plugin.c +1 -0
 - data/src/core/ext/transport/chttp2/transport/chttp2_transport.c +493 -210
 - data/src/core/ext/transport/chttp2/transport/chttp2_transport.h +1 -0
 - data/src/core/ext/transport/chttp2/transport/flow_control.c +9 -8
 - data/src/core/ext/transport/chttp2/transport/frame_data.c +2 -2
 - data/src/core/ext/transport/chttp2/transport/frame_goaway.c +2 -2
 - data/src/core/ext/transport/chttp2/transport/frame_ping.c +5 -4
 - data/src/core/ext/transport/chttp2/transport/frame_rst_stream.c +1 -1
 - data/src/core/ext/transport/chttp2/transport/frame_settings.c +10 -9
 - data/src/core/ext/transport/chttp2/transport/frame_window_update.c +9 -5
 - data/src/core/ext/transport/chttp2/transport/hpack_encoder.c +62 -41
 - data/src/core/ext/transport/chttp2/transport/hpack_parser.c +52 -8
 - data/src/core/ext/transport/chttp2/transport/hpack_table.c +2 -2
 - data/src/core/ext/transport/chttp2/transport/incoming_metadata.c +3 -2
 - data/src/core/ext/transport/chttp2/transport/internal.h +60 -30
 - data/src/core/ext/transport/chttp2/transport/parsing.c +16 -5
 - data/src/core/ext/transport/chttp2/transport/stream_lists.c +36 -16
 - data/src/core/ext/transport/chttp2/transport/stream_map.c +6 -4
 - data/src/core/ext/transport/chttp2/transport/writing.c +133 -105
 - data/src/core/ext/transport/inproc/inproc_transport.c +61 -65
 - data/src/core/lib/channel/channel_args.c +112 -12
 - data/src/core/lib/channel/channel_args.h +31 -0
 - data/src/core/lib/channel/channel_stack.c +1 -15
 - data/src/core/lib/channel/channel_stack.h +3 -10
 - data/src/core/lib/channel/channel_stack_builder.c +41 -10
 - data/src/core/lib/channel/channel_stack_builder.h +10 -0
 - data/src/core/lib/channel/connected_channel.c +94 -23
 - data/src/core/lib/channel/handshaker.c +8 -6
 - data/src/core/lib/channel/handshaker_registry.c +1 -1
 - data/src/core/lib/compression/algorithm_metadata.h +14 -0
 - data/src/core/lib/compression/compression.c +101 -1
 - data/src/core/lib/compression/stream_compression.c +32 -146
 - data/src/core/lib/compression/stream_compression.h +28 -4
 - data/src/core/lib/compression/stream_compression_gzip.c +228 -0
 - data/src/core/lib/{iomgr/ev_epoll_thread_pool_linux.h → compression/stream_compression_gzip.h} +5 -7
 - data/src/core/lib/compression/stream_compression_identity.c +94 -0
 - data/src/core/lib/{iomgr/ev_epoll_limited_pollers_linux.h → compression/stream_compression_identity.h} +7 -8
 - data/src/core/lib/debug/stats.c +174 -0
 - data/src/core/lib/debug/stats.h +61 -0
 - data/src/core/lib/debug/stats_data.c +687 -0
 - data/src/core/lib/debug/stats_data.h +470 -0
 - data/src/core/lib/debug/trace.c +3 -3
 - data/src/core/lib/debug/trace.h +1 -1
 - data/src/core/lib/http/format_request.c +1 -1
 - data/src/core/lib/http/httpcli.c +8 -7
 - data/src/core/lib/http/httpcli_security_connector.c +2 -1
 - data/src/core/lib/http/parser.c +4 -3
 - data/src/core/lib/iomgr/call_combiner.c +202 -0
 - data/src/core/lib/iomgr/call_combiner.h +121 -0
 - data/src/core/lib/iomgr/closure.c +18 -4
 - data/src/core/lib/iomgr/combiner.c +11 -4
 - data/src/core/lib/iomgr/error.c +26 -24
 - data/src/core/lib/iomgr/ev_epoll1_linux.c +395 -212
 - data/src/core/lib/iomgr/ev_epollex_linux.c +141 -128
 - data/src/core/lib/iomgr/ev_epollsig_linux.c +44 -41
 - data/src/core/lib/iomgr/ev_poll_posix.c +99 -75
 - data/src/core/lib/iomgr/ev_posix.c +5 -9
 - data/src/core/lib/iomgr/ev_posix.h +1 -1
 - data/src/core/lib/iomgr/exec_ctx.h +6 -1
 - data/src/core/lib/iomgr/executor.c +142 -36
 - data/src/core/lib/iomgr/executor.h +6 -1
 - data/src/core/lib/iomgr/fork_posix.c +88 -0
 - data/src/core/lib/iomgr/fork_windows.c +39 -0
 - data/src/core/lib/iomgr/iocp_windows.c +2 -0
 - data/src/core/lib/iomgr/iomgr.c +2 -8
 - data/src/core/lib/iomgr/is_epollexclusive_available.c +6 -6
 - data/src/core/lib/iomgr/load_file.c +2 -1
 - data/src/core/lib/iomgr/polling_entity.c +9 -9
 - data/src/core/lib/iomgr/polling_entity.h +7 -1
 - data/src/core/lib/iomgr/pollset.h +1 -1
 - data/src/core/lib/iomgr/pollset_uv.c +1 -1
 - data/src/core/lib/iomgr/pollset_windows.c +3 -3
 - data/src/core/lib/iomgr/port.h +4 -0
 - data/src/core/lib/iomgr/resolve_address_posix.c +8 -7
 - data/src/core/lib/iomgr/resolve_address_windows.c +1 -1
 - data/src/core/lib/iomgr/resource_quota.c +24 -19
 - data/src/core/lib/iomgr/socket_factory_posix.c +4 -4
 - data/src/core/lib/iomgr/socket_mutator.c +4 -4
 - data/src/core/lib/iomgr/socket_utils_windows.c +0 -4
 - data/src/core/lib/iomgr/tcp_client_posix.c +5 -4
 - data/src/core/lib/iomgr/tcp_posix.c +181 -20
 - data/src/core/lib/iomgr/tcp_server_posix.c +8 -7
 - data/src/core/lib/iomgr/tcp_server_utils_posix_common.c +1 -1
 - data/src/core/lib/iomgr/timer.h +4 -0
 - data/src/core/lib/iomgr/timer_generic.c +138 -3
 - data/src/core/lib/iomgr/timer_generic.h +3 -0
 - data/src/core/lib/iomgr/timer_heap.c +4 -4
 - data/src/core/lib/iomgr/timer_manager.c +2 -2
 - data/src/core/lib/iomgr/timer_uv.c +2 -0
 - data/src/core/lib/iomgr/udp_server.c +10 -8
 - data/src/core/lib/iomgr/unix_sockets_posix.c +4 -2
 - data/src/core/lib/iomgr/wakeup_fd_cv.c +9 -8
 - data/src/core/lib/iomgr/wakeup_fd_cv.h +2 -2
 - data/src/core/lib/json/json.c +1 -1
 - data/src/core/lib/json/json_string.c +13 -13
 - data/src/core/lib/profiling/timers.h +18 -8
 - data/src/core/lib/security/credentials/composite/composite_credentials.c +4 -10
 - data/src/core/lib/security/credentials/google_default/google_default_credentials.c +2 -1
 - data/src/core/lib/security/credentials/jwt/jwt_verifier.c +11 -6
 - data/src/core/lib/security/credentials/oauth2/oauth2_credentials.c +4 -4
 - data/src/core/lib/security/credentials/plugin/plugin_credentials.c +132 -50
 - data/src/core/lib/security/credentials/plugin/plugin_credentials.h +2 -0
 - data/src/core/lib/security/transport/client_auth_filter.c +68 -135
 - data/src/core/lib/security/transport/secure_endpoint.c +110 -90
 - data/src/core/lib/security/transport/secure_endpoint.h +8 -3
 - data/src/core/lib/security/transport/security_connector.c +10 -12
 - data/src/core/lib/security/transport/security_handshaker.c +45 -24
 - data/src/core/lib/security/transport/server_auth_filter.c +71 -20
 - data/src/core/lib/slice/b64.c +2 -2
 - data/src/core/lib/slice/slice.c +16 -14
 - data/src/core/lib/slice/slice_buffer.c +5 -4
 - data/src/core/lib/slice/slice_hash_table.c +3 -2
 - data/src/core/lib/slice/slice_intern.c +8 -5
 - data/src/core/lib/support/block_annotate.h +22 -0
 - data/src/core/lib/support/fork.c +62 -0
 - data/src/core/lib/support/fork.h +35 -0
 - data/src/core/lib/support/log_linux.c +1 -1
 - data/src/core/lib/support/string.c +15 -1
 - data/src/core/lib/support/string.h +3 -0
 - data/src/core/lib/support/thd_internal.h +6 -0
 - data/src/core/lib/support/thd_posix.c +56 -0
 - data/src/core/lib/support/thd_windows.c +2 -0
 - data/src/core/lib/surface/alarm.c +22 -15
 - data/src/core/lib/surface/byte_buffer.c +4 -2
 - data/src/core/lib/surface/call.c +442 -141
 - data/src/core/lib/surface/call.h +6 -6
 - data/src/core/lib/surface/call_log_batch.c +1 -1
 - data/src/core/lib/surface/call_test_only.h +12 -0
 - data/src/core/lib/surface/channel.c +39 -4
 - data/src/core/lib/surface/channel_init.c +6 -6
 - data/src/core/lib/surface/channel_ping.c +2 -2
 - data/src/core/lib/surface/completion_queue.c +56 -57
 - data/src/core/lib/surface/init.c +17 -3
 - data/src/core/lib/surface/init_secure.c +5 -1
 - data/src/core/lib/surface/lame_client.cc +9 -10
 - data/src/core/lib/surface/server.c +81 -72
 - data/src/core/lib/surface/version.c +2 -2
 - data/src/core/lib/transport/byte_stream.c +1 -0
 - data/src/core/lib/transport/byte_stream.h +3 -1
 - data/src/core/lib/transport/connectivity_state.c +2 -1
 - data/src/core/lib/transport/metadata.c +7 -4
 - data/src/core/lib/transport/metadata_batch.c +18 -16
 - data/src/core/lib/transport/metadata_batch.h +1 -0
 - data/src/core/lib/transport/service_config.c +5 -3
 - data/src/core/lib/transport/static_metadata.c +395 -614
 - data/src/core/lib/transport/static_metadata.h +165 -133
 - data/src/core/lib/transport/status_conversion.c +1 -1
 - data/src/core/lib/transport/transport.c +20 -20
 - data/src/core/lib/transport/transport.h +8 -5
 - data/src/core/lib/transport/transport_impl.h +0 -3
 - data/src/core/lib/transport/transport_op_string.c +8 -1
 - data/src/core/plugin_registry/grpc_plugin_registry.c +4 -4
 - data/src/core/tsi/fake_transport_security.c +133 -2
 - data/src/core/tsi/fake_transport_security.h +5 -0
 - data/src/core/tsi/ssl_transport_security.c +105 -8
 - data/src/core/tsi/ssl_transport_security.h +30 -7
 - data/src/core/tsi/transport_security.h +8 -2
 - data/src/core/tsi/transport_security_grpc.c +20 -13
 - data/src/core/tsi/transport_security_grpc.h +13 -9
 - data/src/ruby/ext/grpc/rb_call_credentials.c +6 -2
 - data/src/ruby/ext/grpc/rb_grpc.c +1 -1
 - data/src/ruby/ext/grpc/rb_grpc_imports.generated.c +30 -20
 - data/src/ruby/ext/grpc/rb_grpc_imports.generated.h +50 -35
 - data/src/ruby/lib/grpc.rb +1 -0
 - data/src/ruby/lib/grpc/generic/active_call.rb +34 -9
 - data/src/ruby/lib/grpc/generic/bidi_call.rb +19 -10
 - data/src/ruby/lib/grpc/generic/client_stub.rb +95 -38
 - data/src/ruby/lib/grpc/generic/interceptor_registry.rb +53 -0
 - data/src/ruby/lib/grpc/generic/interceptors.rb +186 -0
 - data/src/ruby/lib/grpc/generic/rpc_desc.rb +66 -20
 - data/src/ruby/lib/grpc/generic/rpc_server.rb +15 -3
 - data/src/ruby/lib/grpc/google_rpc_status_utils.rb +1 -2
 - data/src/ruby/lib/grpc/version.rb +1 -1
 - data/src/ruby/pb/grpc/testing/duplicate/echo_duplicate_services_pb.rb +1 -0
 - data/src/ruby/spec/channel_connection_spec.rb +1 -34
 - data/src/ruby/spec/client_server_spec.rb +188 -82
 - data/src/ruby/spec/generic/active_call_spec.rb +65 -11
 - data/src/ruby/spec/generic/client_interceptors_spec.rb +153 -0
 - data/src/ruby/spec/generic/interceptor_registry_spec.rb +65 -0
 - data/src/ruby/spec/generic/rpc_desc_spec.rb +38 -0
 - data/src/ruby/spec/generic/rpc_server_spec.rb +1 -34
 - data/src/ruby/spec/generic/server_interceptors_spec.rb +218 -0
 - data/src/ruby/spec/spec_helper.rb +4 -0
 - data/src/ruby/spec/support/helpers.rb +73 -0
 - data/src/ruby/spec/support/services.rb +147 -0
 - data/third_party/cares/ares_build.h +21 -62
 - data/third_party/cares/cares/ares.h +23 -1
 - data/third_party/cares/cares/ares__close_sockets.c +2 -2
 - data/third_party/cares/cares/ares_create_query.c +3 -3
 - data/third_party/cares/cares/ares_expand_name.c +6 -2
 - data/third_party/cares/cares/ares_expand_string.c +1 -1
 - data/third_party/cares/cares/ares_getnameinfo.c +27 -7
 - data/third_party/cares/cares/ares_init.c +407 -39
 - data/third_party/cares/cares/ares_library_init.c +10 -0
 - data/third_party/cares/cares/ares_library_init.h +2 -1
 - data/third_party/cares/cares/ares_nowarn.c +6 -6
 - data/third_party/cares/cares/ares_nowarn.h +2 -2
 - data/third_party/cares/cares/ares_parse_naptr_reply.c +6 -1
 - data/third_party/cares/cares/ares_private.h +11 -0
 - data/third_party/cares/cares/ares_process.c +126 -37
 - data/third_party/cares/cares/ares_version.h +2 -2
 - data/third_party/cares/cares/ares_writev.c +2 -2
 - data/third_party/cares/cares/config-win32.h +8 -34
 - data/third_party/cares/cares/inet_net_pton.c +2 -2
 - data/third_party/cares/cares/setup_once.h +5 -5
 - data/third_party/cares/config_darwin/ares_config.h +98 -196
 - data/third_party/cares/config_linux/ares_config.h +103 -203
 - metadata +47 -20
 - data/src/core/lib/iomgr/ev_epoll_limited_pollers_linux.c +0 -1957
 - data/src/core/lib/iomgr/ev_epoll_thread_pool_linux.c +0 -1182
 
| 
         @@ -73,7 +73,7 @@ grpc_lb_addresses *grpc_lb_addresses_copy(const grpc_lb_addresses *addresses); 
     | 
|
| 
       73 
73 
     | 
    
         
             
             * \a address is a socket address of length \a address_len.
         
     | 
| 
       74 
74 
     | 
    
         
             
             * Takes ownership of \a balancer_name. */
         
     | 
| 
       75 
75 
     | 
    
         
             
            void grpc_lb_addresses_set_address(grpc_lb_addresses *addresses, size_t index,
         
     | 
| 
       76 
     | 
    
         
            -
                                               void *address, size_t address_len,
         
     | 
| 
      
 76 
     | 
    
         
            +
                                               const void *address, size_t address_len,
         
     | 
| 
       77 
77 
     | 
    
         
             
                                               bool is_balancer, const char *balancer_name,
         
     | 
| 
       78 
78 
     | 
    
         
             
                                               void *user_data);
         
     | 
| 
       79 
79 
     | 
    
         | 
| 
         @@ -34,7 +34,7 @@ typedef struct { 
     | 
|
| 
       34 
34 
     | 
    
         
             
            static void grpc_proxy_mapper_list_register(grpc_proxy_mapper_list* list,
         
     | 
| 
       35 
35 
     | 
    
         
             
                                                        bool at_start,
         
     | 
| 
       36 
36 
     | 
    
         
             
                                                        grpc_proxy_mapper* mapper) {
         
     | 
| 
       37 
     | 
    
         
            -
              list->list = gpr_realloc(
         
     | 
| 
      
 37 
     | 
    
         
            +
              list->list = (grpc_proxy_mapper**)gpr_realloc(
         
     | 
| 
       38 
38 
     | 
    
         
             
                  list->list, (list->num_mappers + 1) * sizeof(grpc_proxy_mapper*));
         
     | 
| 
       39 
39 
     | 
    
         
             
              if (at_start) {
         
     | 
| 
       40 
40 
     | 
    
         
             
                memmove(list->list + 1, list->list,
         
     | 
| 
         @@ -144,7 +144,7 @@ static void dns_ares_channel_saw_error_locked(grpc_exec_ctx *exec_ctx, 
     | 
|
| 
       144 
144 
     | 
    
         | 
| 
       145 
145 
     | 
    
         
             
            static void dns_ares_on_retry_timer_locked(grpc_exec_ctx *exec_ctx, void *arg,
         
     | 
| 
       146 
146 
     | 
    
         
             
                                                       grpc_error *error) {
         
     | 
| 
       147 
     | 
    
         
            -
              ares_dns_resolver *r = arg;
         
     | 
| 
      
 147 
     | 
    
         
            +
              ares_dns_resolver *r = (ares_dns_resolver *)arg;
         
     | 
| 
       148 
148 
     | 
    
         
             
              r->have_retry_timer = false;
         
     | 
| 
       149 
149 
     | 
    
         
             
              if (error == GRPC_ERROR_NONE) {
         
     | 
| 
       150 
150 
     | 
    
         
             
                if (!r->resolving) {
         
     | 
| 
         @@ -204,7 +204,7 @@ static char *choose_service_config(char *service_config_choice_json) { 
     | 
|
| 
       204 
204 
     | 
    
         
             
                    int random_pct = rand() % 100;
         
     | 
| 
       205 
205 
     | 
    
         
             
                    int percentage;
         
     | 
| 
       206 
206 
     | 
    
         
             
                    if (sscanf(field->value, "%d", &percentage) != 1 ||
         
     | 
| 
       207 
     | 
    
         
            -
                        random_pct > percentage) {
         
     | 
| 
      
 207 
     | 
    
         
            +
                        random_pct > percentage || percentage == 0) {
         
     | 
| 
       208 
208 
     | 
    
         
             
                      service_config_json = NULL;
         
     | 
| 
       209 
209 
     | 
    
         
             
                      break;
         
     | 
| 
       210 
210 
     | 
    
         
             
                    }
         
     | 
| 
         @@ -227,7 +227,7 @@ static char *choose_service_config(char *service_config_choice_json) { 
     | 
|
| 
       227 
227 
     | 
    
         | 
| 
       228 
228 
     | 
    
         
             
            static void dns_ares_on_resolved_locked(grpc_exec_ctx *exec_ctx, void *arg,
         
     | 
| 
       229 
229 
     | 
    
         
             
                                                    grpc_error *error) {
         
     | 
| 
       230 
     | 
    
         
            -
              ares_dns_resolver *r = arg;
         
     | 
| 
      
 230 
     | 
    
         
            +
              ares_dns_resolver *r = (ares_dns_resolver *)arg;
         
     | 
| 
       231 
231 
     | 
    
         
             
              grpc_channel_args *result = NULL;
         
     | 
| 
       232 
232 
     | 
    
         
             
              GPR_ASSERT(r->resolving);
         
     | 
| 
       233 
233 
     | 
    
         
             
              r->resolving = false;
         
     | 
| 
         @@ -249,7 +249,7 @@ static void dns_ares_on_resolved_locked(grpc_exec_ctx *exec_ctx, void *arg, 
     | 
|
| 
       249 
249 
     | 
    
         
             
                            service_config_string);
         
     | 
| 
       250 
250 
     | 
    
         
             
                    args_to_remove[num_args_to_remove++] = GRPC_ARG_SERVICE_CONFIG;
         
     | 
| 
       251 
251 
     | 
    
         
             
                    new_args[num_args_to_add++] = grpc_channel_arg_string_create(
         
     | 
| 
       252 
     | 
    
         
            -
                        GRPC_ARG_SERVICE_CONFIG, service_config_string);
         
     | 
| 
      
 252 
     | 
    
         
            +
                        (char *)GRPC_ARG_SERVICE_CONFIG, service_config_string);
         
     | 
| 
       253 
253 
     | 
    
         
             
                    service_config = grpc_service_config_create(service_config_string);
         
     | 
| 
       254 
254 
     | 
    
         
             
                    if (service_config != NULL) {
         
     | 
| 
       255 
255 
     | 
    
         
             
                      const char *lb_policy_name =
         
     | 
| 
         @@ -257,7 +257,7 @@ static void dns_ares_on_resolved_locked(grpc_exec_ctx *exec_ctx, void *arg, 
     | 
|
| 
       257 
257 
     | 
    
         
             
                      if (lb_policy_name != NULL) {
         
     | 
| 
       258 
258 
     | 
    
         
             
                        args_to_remove[num_args_to_remove++] = GRPC_ARG_LB_POLICY_NAME;
         
     | 
| 
       259 
259 
     | 
    
         
             
                        new_args[num_args_to_add++] = grpc_channel_arg_string_create(
         
     | 
| 
       260 
     | 
    
         
            -
                            GRPC_ARG_LB_POLICY_NAME, (char *)lb_policy_name);
         
     | 
| 
      
 260 
     | 
    
         
            +
                            (char *)GRPC_ARG_LB_POLICY_NAME, (char *)lb_policy_name);
         
     | 
| 
       261 
261 
     | 
    
         
             
                      }
         
     | 
| 
       262 
262 
     | 
    
         
             
                    }
         
     | 
| 
       263 
263 
     | 
    
         
             
                  }
         
     | 
| 
         @@ -363,7 +363,8 @@ static grpc_resolver *dns_ares_create(grpc_exec_ctx *exec_ctx, 
     | 
|
| 
       363 
363 
     | 
    
         
             
              const char *path = args->uri->path;
         
     | 
| 
       364 
364 
     | 
    
         
             
              if (path[0] == '/') ++path;
         
     | 
| 
       365 
365 
     | 
    
         
             
              /* Create resolver. */
         
     | 
| 
       366 
     | 
    
         
            -
              ares_dns_resolver *r = 
     | 
| 
      
 366 
     | 
    
         
            +
              ares_dns_resolver *r =
         
     | 
| 
      
 367 
     | 
    
         
            +
                  (ares_dns_resolver *)gpr_zalloc(sizeof(ares_dns_resolver));
         
     | 
| 
       367 
368 
     | 
    
         
             
              grpc_resolver_init(&r->base, &dns_ares_resolver_vtable, args->combiner);
         
     | 
| 
       368 
369 
     | 
    
         
             
              if (0 != strcmp(args->uri->authority, "")) {
         
     | 
| 
       369 
370 
     | 
    
         
             
                r->dns_server = gpr_strdup(args->uri->authority);
         
     | 
| 
         @@ -20,6 +20,7 @@ 
     | 
|
| 
       20 
20 
     | 
    
         
             
            #if GRPC_ARES == 1 && defined(GRPC_POSIX_SOCKET)
         
     | 
| 
       21 
21 
     | 
    
         | 
| 
       22 
22 
     | 
    
         
             
            #include <ares.h>
         
     | 
| 
      
 23 
     | 
    
         
            +
            #include <sys/ioctl.h>
         
     | 
| 
       23 
24 
     | 
    
         | 
| 
       24 
25 
     | 
    
         
             
            #include "src/core/ext/filters/client_channel/resolver/dns/c_ares/grpc_ares_ev_driver.h"
         
     | 
| 
       25 
26 
     | 
    
         | 
| 
         @@ -37,8 +38,6 @@ 
     | 
|
| 
       37 
38 
     | 
    
         
             
            typedef struct fd_node {
         
     | 
| 
       38 
39 
     | 
    
         
             
              /** the owner of this fd node */
         
     | 
| 
       39 
40 
     | 
    
         
             
              grpc_ares_ev_driver *ev_driver;
         
     | 
| 
       40 
     | 
    
         
            -
              /** the grpc_fd owned by this fd node */
         
     | 
| 
       41 
     | 
    
         
            -
              grpc_fd *grpc_fd;
         
     | 
| 
       42 
41 
     | 
    
         
             
              /** a closure wrapping on_readable_cb, which should be invoked when the
         
     | 
| 
       43 
42 
     | 
    
         
             
                  grpc_fd in this node becomes readable. */
         
     | 
| 
       44 
43 
     | 
    
         
             
              grpc_closure read_closure;
         
     | 
| 
         @@ -50,10 +49,14 @@ typedef struct fd_node { 
     | 
|
| 
       50 
49 
     | 
    
         | 
| 
       51 
50 
     | 
    
         
             
              /** mutex guarding the rest of the state */
         
     | 
| 
       52 
51 
     | 
    
         
             
              gpr_mu mu;
         
     | 
| 
      
 52 
     | 
    
         
            +
              /** the grpc_fd owned by this fd node */
         
     | 
| 
      
 53 
     | 
    
         
            +
              grpc_fd *fd;
         
     | 
| 
       53 
54 
     | 
    
         
             
              /** if the readable closure has been registered */
         
     | 
| 
       54 
55 
     | 
    
         
             
              bool readable_registered;
         
     | 
| 
       55 
56 
     | 
    
         
             
              /** if the writable closure has been registered */
         
     | 
| 
       56 
57 
     | 
    
         
             
              bool writable_registered;
         
     | 
| 
      
 58 
     | 
    
         
            +
              /** if the fd is being shut down */
         
     | 
| 
      
 59 
     | 
    
         
            +
              bool shutting_down;
         
     | 
| 
       57 
60 
     | 
    
         
             
            } fd_node;
         
     | 
| 
       58 
61 
     | 
    
         | 
| 
       59 
62 
     | 
    
         
             
            struct grpc_ares_ev_driver {
         
     | 
| 
         @@ -96,22 +99,34 @@ static void grpc_ares_ev_driver_unref(grpc_ares_ev_driver *ev_driver) { 
     | 
|
| 
       96 
99 
     | 
    
         
             
            }
         
     | 
| 
       97 
100 
     | 
    
         | 
| 
       98 
101 
     | 
    
         
             
            static void fd_node_destroy(grpc_exec_ctx *exec_ctx, fd_node *fdn) {
         
     | 
| 
       99 
     | 
    
         
            -
              gpr_log(GPR_DEBUG, "delete fd: %d", grpc_fd_wrapped_fd(fdn-> 
     | 
| 
      
 102 
     | 
    
         
            +
              gpr_log(GPR_DEBUG, "delete fd: %d", grpc_fd_wrapped_fd(fdn->fd));
         
     | 
| 
       100 
103 
     | 
    
         
             
              GPR_ASSERT(!fdn->readable_registered);
         
     | 
| 
       101 
104 
     | 
    
         
             
              GPR_ASSERT(!fdn->writable_registered);
         
     | 
| 
       102 
105 
     | 
    
         
             
              gpr_mu_destroy(&fdn->mu);
         
     | 
| 
       103 
     | 
    
         
            -
              grpc_pollset_set_del_fd(exec_ctx, fdn->ev_driver->pollset_set, fdn->grpc_fd);
         
     | 
| 
       104 
106 
     | 
    
         
             
              /* c-ares library has closed the fd inside grpc_fd. This fd may be picked up
         
     | 
| 
       105 
107 
     | 
    
         
             
                 immediately by another thread, and should not be closed by the following
         
     | 
| 
       106 
108 
     | 
    
         
             
                 grpc_fd_orphan. */
         
     | 
| 
       107 
     | 
    
         
            -
              grpc_fd_orphan(exec_ctx, fdn-> 
     | 
| 
      
 109 
     | 
    
         
            +
              grpc_fd_orphan(exec_ctx, fdn->fd, NULL, NULL, true /* already_closed */,
         
     | 
| 
       108 
110 
     | 
    
         
             
                             "c-ares query finished");
         
     | 
| 
       109 
111 
     | 
    
         
             
              gpr_free(fdn);
         
     | 
| 
       110 
112 
     | 
    
         
             
            }
         
     | 
| 
       111 
113 
     | 
    
         | 
| 
      
 114 
     | 
    
         
            +
            static void fd_node_shutdown(grpc_exec_ctx *exec_ctx, fd_node *fdn) {
         
     | 
| 
      
 115 
     | 
    
         
            +
              gpr_mu_lock(&fdn->mu);
         
     | 
| 
      
 116 
     | 
    
         
            +
              fdn->shutting_down = true;
         
     | 
| 
      
 117 
     | 
    
         
            +
              if (!fdn->readable_registered && !fdn->writable_registered) {
         
     | 
| 
      
 118 
     | 
    
         
            +
                gpr_mu_unlock(&fdn->mu);
         
     | 
| 
      
 119 
     | 
    
         
            +
                fd_node_destroy(exec_ctx, fdn);
         
     | 
| 
      
 120 
     | 
    
         
            +
              } else {
         
     | 
| 
      
 121 
     | 
    
         
            +
                grpc_fd_shutdown(exec_ctx, fdn->fd, GRPC_ERROR_CREATE_FROM_STATIC_STRING(
         
     | 
| 
      
 122 
     | 
    
         
            +
                                                        "c-ares fd shutdown"));
         
     | 
| 
      
 123 
     | 
    
         
            +
                gpr_mu_unlock(&fdn->mu);
         
     | 
| 
      
 124 
     | 
    
         
            +
              }
         
     | 
| 
      
 125 
     | 
    
         
            +
            }
         
     | 
| 
      
 126 
     | 
    
         
            +
             
     | 
| 
       112 
127 
     | 
    
         
             
            grpc_error *grpc_ares_ev_driver_create(grpc_ares_ev_driver **ev_driver,
         
     | 
| 
       113 
128 
     | 
    
         
             
                                                   grpc_pollset_set *pollset_set) {
         
     | 
| 
       114 
     | 
    
         
            -
              *ev_driver = gpr_malloc(sizeof(grpc_ares_ev_driver));
         
     | 
| 
      
 129 
     | 
    
         
            +
              *ev_driver = (grpc_ares_ev_driver *)gpr_malloc(sizeof(grpc_ares_ev_driver));
         
     | 
| 
       115 
130 
     | 
    
         
             
              int status = ares_init(&(*ev_driver)->channel);
         
     | 
| 
       116 
131 
     | 
    
         
             
              gpr_log(GPR_DEBUG, "grpc_ares_ev_driver_create");
         
     | 
| 
       117 
132 
     | 
    
         
             
              if (status != ARES_SUCCESS) {
         
     | 
| 
         @@ -150,9 +165,8 @@ void grpc_ares_ev_driver_shutdown(grpc_exec_ctx *exec_ctx, 
     | 
|
| 
       150 
165 
     | 
    
         
             
              ev_driver->shutting_down = true;
         
     | 
| 
       151 
166 
     | 
    
         
             
              fd_node *fn = ev_driver->fds;
         
     | 
| 
       152 
167 
     | 
    
         
             
              while (fn != NULL) {
         
     | 
| 
       153 
     | 
    
         
            -
                grpc_fd_shutdown(
         
     | 
| 
       154 
     | 
    
         
            -
             
     | 
| 
       155 
     | 
    
         
            -
                    GRPC_ERROR_CREATE_FROM_STATIC_STRING("grpc_ares_ev_driver_shutdown"));
         
     | 
| 
      
 168 
     | 
    
         
            +
                grpc_fd_shutdown(exec_ctx, fn->fd, GRPC_ERROR_CREATE_FROM_STATIC_STRING(
         
     | 
| 
      
 169 
     | 
    
         
            +
                                                       "grpc_ares_ev_driver_shutdown"));
         
     | 
| 
       156 
170 
     | 
    
         
             
                fn = fn->next;
         
     | 
| 
       157 
171 
     | 
    
         
             
              }
         
     | 
| 
       158 
172 
     | 
    
         
             
              gpr_mu_unlock(&ev_driver->mu);
         
     | 
| 
         @@ -165,7 +179,7 @@ static fd_node *pop_fd_node(fd_node **head, int fd) { 
     | 
|
| 
       165 
179 
     | 
    
         
             
              dummy_head.next = *head;
         
     | 
| 
       166 
180 
     | 
    
         
             
              fd_node *node = &dummy_head;
         
     | 
| 
       167 
181 
     | 
    
         
             
              while (node->next != NULL) {
         
     | 
| 
       168 
     | 
    
         
            -
                if (grpc_fd_wrapped_fd(node->next-> 
     | 
| 
      
 182 
     | 
    
         
            +
                if (grpc_fd_wrapped_fd(node->next->fd) == fd) {
         
     | 
| 
       169 
183 
     | 
    
         
             
                  fd_node *ret = node->next;
         
     | 
| 
       170 
184 
     | 
    
         
             
                  node->next = node->next->next;
         
     | 
| 
       171 
185 
     | 
    
         
             
                  *head = dummy_head.next;
         
     | 
| 
         @@ -176,18 +190,33 @@ static fd_node *pop_fd_node(fd_node **head, int fd) { 
     | 
|
| 
       176 
190 
     | 
    
         
             
              return NULL;
         
     | 
| 
       177 
191 
     | 
    
         
             
            }
         
     | 
| 
       178 
192 
     | 
    
         | 
| 
      
 193 
     | 
    
         
            +
            /* Check if \a fd is still readable */
         
     | 
| 
      
 194 
     | 
    
         
            +
            static bool grpc_ares_is_fd_still_readable(grpc_ares_ev_driver *ev_driver,
         
     | 
| 
      
 195 
     | 
    
         
            +
                                                       int fd) {
         
     | 
| 
      
 196 
     | 
    
         
            +
              size_t bytes_available = 0;
         
     | 
| 
      
 197 
     | 
    
         
            +
              return ioctl(fd, FIONREAD, &bytes_available) == 0 && bytes_available > 0;
         
     | 
| 
      
 198 
     | 
    
         
            +
            }
         
     | 
| 
      
 199 
     | 
    
         
            +
             
     | 
| 
       179 
200 
     | 
    
         
             
            static void on_readable_cb(grpc_exec_ctx *exec_ctx, void *arg,
         
     | 
| 
       180 
201 
     | 
    
         
             
                                       grpc_error *error) {
         
     | 
| 
       181 
     | 
    
         
            -
              fd_node *fdn = arg;
         
     | 
| 
      
 202 
     | 
    
         
            +
              fd_node *fdn = (fd_node *)arg;
         
     | 
| 
       182 
203 
     | 
    
         
             
              grpc_ares_ev_driver *ev_driver = fdn->ev_driver;
         
     | 
| 
       183 
204 
     | 
    
         
             
              gpr_mu_lock(&fdn->mu);
         
     | 
| 
      
 205 
     | 
    
         
            +
              const int fd = grpc_fd_wrapped_fd(fdn->fd);
         
     | 
| 
       184 
206 
     | 
    
         
             
              fdn->readable_registered = false;
         
     | 
| 
      
 207 
     | 
    
         
            +
              if (fdn->shutting_down && !fdn->writable_registered) {
         
     | 
| 
      
 208 
     | 
    
         
            +
                gpr_mu_unlock(&fdn->mu);
         
     | 
| 
      
 209 
     | 
    
         
            +
                fd_node_destroy(exec_ctx, fdn);
         
     | 
| 
      
 210 
     | 
    
         
            +
                grpc_ares_ev_driver_unref(ev_driver);
         
     | 
| 
      
 211 
     | 
    
         
            +
                return;
         
     | 
| 
      
 212 
     | 
    
         
            +
              }
         
     | 
| 
       185 
213 
     | 
    
         
             
              gpr_mu_unlock(&fdn->mu);
         
     | 
| 
       186 
214 
     | 
    
         | 
| 
       187 
     | 
    
         
            -
              gpr_log(GPR_DEBUG, "readable on %d",  
     | 
| 
      
 215 
     | 
    
         
            +
              gpr_log(GPR_DEBUG, "readable on %d", fd);
         
     | 
| 
       188 
216 
     | 
    
         
             
              if (error == GRPC_ERROR_NONE) {
         
     | 
| 
       189 
     | 
    
         
            -
                 
     | 
| 
       190 
     | 
    
         
            -
             
     | 
| 
      
 217 
     | 
    
         
            +
                do {
         
     | 
| 
      
 218 
     | 
    
         
            +
                  ares_process_fd(ev_driver->channel, fd, ARES_SOCKET_BAD);
         
     | 
| 
      
 219 
     | 
    
         
            +
                } while (grpc_ares_is_fd_still_readable(ev_driver, fd));
         
     | 
| 
       191 
220 
     | 
    
         
             
              } else {
         
     | 
| 
       192 
221 
     | 
    
         
             
                // If error is not GRPC_ERROR_NONE, it means the fd has been shutdown or
         
     | 
| 
       193 
222 
     | 
    
         
             
                // timed out. The pending lookups made on this ev_driver will be cancelled
         
     | 
| 
         @@ -205,16 +234,22 @@ static void on_readable_cb(grpc_exec_ctx *exec_ctx, void *arg, 
     | 
|
| 
       205 
234 
     | 
    
         | 
| 
       206 
235 
     | 
    
         
             
            static void on_writable_cb(grpc_exec_ctx *exec_ctx, void *arg,
         
     | 
| 
       207 
236 
     | 
    
         
             
                                       grpc_error *error) {
         
     | 
| 
       208 
     | 
    
         
            -
              fd_node *fdn = arg;
         
     | 
| 
      
 237 
     | 
    
         
            +
              fd_node *fdn = (fd_node *)arg;
         
     | 
| 
       209 
238 
     | 
    
         
             
              grpc_ares_ev_driver *ev_driver = fdn->ev_driver;
         
     | 
| 
       210 
239 
     | 
    
         
             
              gpr_mu_lock(&fdn->mu);
         
     | 
| 
      
 240 
     | 
    
         
            +
              const int fd = grpc_fd_wrapped_fd(fdn->fd);
         
     | 
| 
       211 
241 
     | 
    
         
             
              fdn->writable_registered = false;
         
     | 
| 
      
 242 
     | 
    
         
            +
              if (fdn->shutting_down && !fdn->readable_registered) {
         
     | 
| 
      
 243 
     | 
    
         
            +
                gpr_mu_unlock(&fdn->mu);
         
     | 
| 
      
 244 
     | 
    
         
            +
                fd_node_destroy(exec_ctx, fdn);
         
     | 
| 
      
 245 
     | 
    
         
            +
                grpc_ares_ev_driver_unref(ev_driver);
         
     | 
| 
      
 246 
     | 
    
         
            +
                return;
         
     | 
| 
      
 247 
     | 
    
         
            +
              }
         
     | 
| 
       212 
248 
     | 
    
         
             
              gpr_mu_unlock(&fdn->mu);
         
     | 
| 
       213 
249 
     | 
    
         | 
| 
       214 
     | 
    
         
            -
              gpr_log(GPR_DEBUG, "writable on %d",  
     | 
| 
      
 250 
     | 
    
         
            +
              gpr_log(GPR_DEBUG, "writable on %d", fd);
         
     | 
| 
       215 
251 
     | 
    
         
             
              if (error == GRPC_ERROR_NONE) {
         
     | 
| 
       216 
     | 
    
         
            -
                ares_process_fd(ev_driver->channel, ARES_SOCKET_BAD,
         
     | 
| 
       217 
     | 
    
         
            -
                                grpc_fd_wrapped_fd(fdn->grpc_fd));
         
     | 
| 
      
 252 
     | 
    
         
            +
                ares_process_fd(ev_driver->channel, ARES_SOCKET_BAD, fd);
         
     | 
| 
       218 
253 
     | 
    
         
             
              } else {
         
     | 
| 
       219 
254 
     | 
    
         
             
                // If error is not GRPC_ERROR_NONE, it means the fd has been shutdown or
         
     | 
| 
       220 
255 
     | 
    
         
             
                // timed out. The pending lookups made on this ev_driver will be cancelled
         
     | 
| 
         @@ -251,19 +286,19 @@ static void grpc_ares_notify_on_event_locked(grpc_exec_ctx *exec_ctx, 
     | 
|
| 
       251 
286 
     | 
    
         
             
                    if (fdn == NULL) {
         
     | 
| 
       252 
287 
     | 
    
         
             
                      char *fd_name;
         
     | 
| 
       253 
288 
     | 
    
         
             
                      gpr_asprintf(&fd_name, "ares_ev_driver-%" PRIuPTR, i);
         
     | 
| 
       254 
     | 
    
         
            -
                      fdn = gpr_malloc(sizeof(fd_node));
         
     | 
| 
      
 289 
     | 
    
         
            +
                      fdn = (fd_node *)gpr_malloc(sizeof(fd_node));
         
     | 
| 
       255 
290 
     | 
    
         
             
                      gpr_log(GPR_DEBUG, "new fd: %d", socks[i]);
         
     | 
| 
       256 
     | 
    
         
            -
                      fdn-> 
     | 
| 
      
 291 
     | 
    
         
            +
                      fdn->fd = grpc_fd_create(socks[i], fd_name);
         
     | 
| 
       257 
292 
     | 
    
         
             
                      fdn->ev_driver = ev_driver;
         
     | 
| 
       258 
293 
     | 
    
         
             
                      fdn->readable_registered = false;
         
     | 
| 
       259 
294 
     | 
    
         
             
                      fdn->writable_registered = false;
         
     | 
| 
      
 295 
     | 
    
         
            +
                      fdn->shutting_down = false;
         
     | 
| 
       260 
296 
     | 
    
         
             
                      gpr_mu_init(&fdn->mu);
         
     | 
| 
       261 
297 
     | 
    
         
             
                      GRPC_CLOSURE_INIT(&fdn->read_closure, on_readable_cb, fdn,
         
     | 
| 
       262 
298 
     | 
    
         
             
                                        grpc_schedule_on_exec_ctx);
         
     | 
| 
       263 
299 
     | 
    
         
             
                      GRPC_CLOSURE_INIT(&fdn->write_closure, on_writable_cb, fdn,
         
     | 
| 
       264 
300 
     | 
    
         
             
                                        grpc_schedule_on_exec_ctx);
         
     | 
| 
       265 
     | 
    
         
            -
                      grpc_pollset_set_add_fd(exec_ctx, ev_driver->pollset_set,
         
     | 
| 
       266 
     | 
    
         
            -
                                              fdn->grpc_fd);
         
     | 
| 
      
 301 
     | 
    
         
            +
                      grpc_pollset_set_add_fd(exec_ctx, ev_driver->pollset_set, fdn->fd);
         
     | 
| 
       267 
302 
     | 
    
         
             
                      gpr_free(fd_name);
         
     | 
| 
       268 
303 
     | 
    
         
             
                    }
         
     | 
| 
       269 
304 
     | 
    
         
             
                    fdn->next = new_list;
         
     | 
| 
         @@ -274,9 +309,8 @@ static void grpc_ares_notify_on_event_locked(grpc_exec_ctx *exec_ctx, 
     | 
|
| 
       274 
309 
     | 
    
         
             
                    if (ARES_GETSOCK_READABLE(socks_bitmask, i) &&
         
     | 
| 
       275 
310 
     | 
    
         
             
                        !fdn->readable_registered) {
         
     | 
| 
       276 
311 
     | 
    
         
             
                      grpc_ares_ev_driver_ref(ev_driver);
         
     | 
| 
       277 
     | 
    
         
            -
                      gpr_log(GPR_DEBUG, "notify read on: %d",
         
     | 
| 
       278 
     | 
    
         
            -
             
     | 
| 
       279 
     | 
    
         
            -
                      grpc_fd_notify_on_read(exec_ctx, fdn->grpc_fd, &fdn->read_closure);
         
     | 
| 
      
 312 
     | 
    
         
            +
                      gpr_log(GPR_DEBUG, "notify read on: %d", grpc_fd_wrapped_fd(fdn->fd));
         
     | 
| 
      
 313 
     | 
    
         
            +
                      grpc_fd_notify_on_read(exec_ctx, fdn->fd, &fdn->read_closure);
         
     | 
| 
       280 
314 
     | 
    
         
             
                      fdn->readable_registered = true;
         
     | 
| 
       281 
315 
     | 
    
         
             
                    }
         
     | 
| 
       282 
316 
     | 
    
         
             
                    // Register write_closure if the socket is writable and write_closure
         
     | 
| 
         @@ -284,9 +318,9 @@ static void grpc_ares_notify_on_event_locked(grpc_exec_ctx *exec_ctx, 
     | 
|
| 
       284 
318 
     | 
    
         
             
                    if (ARES_GETSOCK_WRITABLE(socks_bitmask, i) &&
         
     | 
| 
       285 
319 
     | 
    
         
             
                        !fdn->writable_registered) {
         
     | 
| 
       286 
320 
     | 
    
         
             
                      gpr_log(GPR_DEBUG, "notify write on: %d",
         
     | 
| 
       287 
     | 
    
         
            -
                              grpc_fd_wrapped_fd(fdn-> 
     | 
| 
      
 321 
     | 
    
         
            +
                              grpc_fd_wrapped_fd(fdn->fd));
         
     | 
| 
       288 
322 
     | 
    
         
             
                      grpc_ares_ev_driver_ref(ev_driver);
         
     | 
| 
       289 
     | 
    
         
            -
                      grpc_fd_notify_on_write(exec_ctx, fdn-> 
     | 
| 
      
 323 
     | 
    
         
            +
                      grpc_fd_notify_on_write(exec_ctx, fdn->fd, &fdn->write_closure);
         
     | 
| 
       290 
324 
     | 
    
         
             
                      fdn->writable_registered = true;
         
     | 
| 
       291 
325 
     | 
    
         
             
                    }
         
     | 
| 
       292 
326 
     | 
    
         
             
                    gpr_mu_unlock(&fdn->mu);
         
     | 
| 
         @@ -299,7 +333,7 @@ static void grpc_ares_notify_on_event_locked(grpc_exec_ctx *exec_ctx, 
     | 
|
| 
       299 
333 
     | 
    
         
             
              while (ev_driver->fds != NULL) {
         
     | 
| 
       300 
334 
     | 
    
         
             
                fd_node *cur = ev_driver->fds;
         
     | 
| 
       301 
335 
     | 
    
         
             
                ev_driver->fds = ev_driver->fds->next;
         
     | 
| 
       302 
     | 
    
         
            -
                 
     | 
| 
      
 336 
     | 
    
         
            +
                fd_node_shutdown(exec_ctx, cur);
         
     | 
| 
       303 
337 
     | 
    
         
             
              }
         
     | 
| 
       304 
338 
     | 
    
         
             
              ev_driver->fds = new_list;
         
     | 
| 
       305 
339 
     | 
    
         
             
              // If the ev driver has no working fd, all the tasks are done.
         
     | 
| 
         @@ -123,8 +123,8 @@ static void grpc_ares_request_unref(grpc_exec_ctx *exec_ctx, 
     | 
|
| 
       123 
123 
     | 
    
         
             
            static grpc_ares_hostbyname_request *create_hostbyname_request(
         
     | 
| 
       124 
124 
     | 
    
         
             
                grpc_ares_request *parent_request, char *host, uint16_t port,
         
     | 
| 
       125 
125 
     | 
    
         
             
                bool is_balancer) {
         
     | 
| 
       126 
     | 
    
         
            -
              grpc_ares_hostbyname_request *hr =
         
     | 
| 
       127 
     | 
    
         
            -
                   
     | 
| 
      
 126 
     | 
    
         
            +
              grpc_ares_hostbyname_request *hr = (grpc_ares_hostbyname_request *)gpr_zalloc(
         
     | 
| 
      
 127 
     | 
    
         
            +
                  sizeof(grpc_ares_hostbyname_request));
         
     | 
| 
       128 
128 
     | 
    
         
             
              hr->parent_request = parent_request;
         
     | 
| 
       129 
129 
     | 
    
         
             
              hr->host = gpr_strdup(host);
         
     | 
| 
       130 
130 
     | 
    
         
             
              hr->port = port;
         
     | 
| 
         @@ -158,9 +158,9 @@ static void on_hostbyname_done_cb(void *arg, int status, int timeouts, 
     | 
|
| 
       158 
158 
     | 
    
         
             
                for (i = 0; hostent->h_addr_list[i] != NULL; i++) {
         
     | 
| 
       159 
159 
     | 
    
         
             
                }
         
     | 
| 
       160 
160 
     | 
    
         
             
                (*lb_addresses)->num_addresses += i;
         
     | 
| 
       161 
     | 
    
         
            -
                (*lb_addresses)->addresses =
         
     | 
| 
       162 
     | 
    
         
            -
                     
     | 
| 
       163 
     | 
    
         
            -
             
     | 
| 
      
 161 
     | 
    
         
            +
                (*lb_addresses)->addresses = (grpc_lb_address *)gpr_realloc(
         
     | 
| 
      
 162 
     | 
    
         
            +
                    (*lb_addresses)->addresses,
         
     | 
| 
      
 163 
     | 
    
         
            +
                    sizeof(grpc_lb_address) * (*lb_addresses)->num_addresses);
         
     | 
| 
       164 
164 
     | 
    
         
             
                for (i = prev_naddr; i < (*lb_addresses)->num_addresses; i++) {
         
     | 
| 
       165 
165 
     | 
    
         
             
                  switch (hostent->h_addrtype) {
         
     | 
| 
       166 
166 
     | 
    
         
             
                    case AF_INET6: {
         
     | 
| 
         @@ -174,7 +174,7 @@ static void on_hostbyname_done_cb(void *arg, int status, int timeouts, 
     | 
|
| 
       174 
174 
     | 
    
         
             
                      grpc_lb_addresses_set_address(
         
     | 
| 
       175 
175 
     | 
    
         
             
                          *lb_addresses, i, &addr, addr_len,
         
     | 
| 
       176 
176 
     | 
    
         
             
                          hr->is_balancer /* is_balancer */,
         
     | 
| 
       177 
     | 
    
         
            -
                          hr->is_balancer ?  
     | 
| 
      
 177 
     | 
    
         
            +
                          hr->is_balancer ? hr->host : NULL /* balancer_name */,
         
     | 
| 
       178 
178 
     | 
    
         
             
                          NULL /* user_data */);
         
     | 
| 
       179 
179 
     | 
    
         
             
                      char output[INET6_ADDRSTRLEN];
         
     | 
| 
       180 
180 
     | 
    
         
             
                      ares_inet_ntop(AF_INET6, &addr.sin6_addr, output, INET6_ADDRSTRLEN);
         
     | 
| 
         @@ -195,7 +195,7 @@ static void on_hostbyname_done_cb(void *arg, int status, int timeouts, 
     | 
|
| 
       195 
195 
     | 
    
         
             
                      grpc_lb_addresses_set_address(
         
     | 
| 
       196 
196 
     | 
    
         
             
                          *lb_addresses, i, &addr, addr_len,
         
     | 
| 
       197 
197 
     | 
    
         
             
                          hr->is_balancer /* is_balancer */,
         
     | 
| 
       198 
     | 
    
         
            -
                          hr->is_balancer ?  
     | 
| 
      
 198 
     | 
    
         
            +
                          hr->is_balancer ? hr->host : NULL /* balancer_name */,
         
     | 
| 
       199 
199 
     | 
    
         
             
                          NULL /* user_data */);
         
     | 
| 
       200 
200 
     | 
    
         
             
                      char output[INET_ADDRSTRLEN];
         
     | 
| 
       201 
201 
     | 
    
         
             
                      ares_inet_ntop(AF_INET, &addr.sin_addr, output, INET_ADDRSTRLEN);
         
     | 
| 
         @@ -275,14 +275,15 @@ static void on_txt_done_cb(void *arg, int status, int timeouts, 
     | 
|
| 
       275 
275 
     | 
    
         
             
              gpr_log(GPR_DEBUG, "on_txt_done_cb");
         
     | 
| 
       276 
276 
     | 
    
         
             
              char *error_msg;
         
     | 
| 
       277 
277 
     | 
    
         
             
              grpc_ares_request *r = (grpc_ares_request *)arg;
         
     | 
| 
      
 278 
     | 
    
         
            +
              const size_t prefix_len = sizeof(g_service_config_attribute_prefix) - 1;
         
     | 
| 
      
 279 
     | 
    
         
            +
              struct ares_txt_ext *result = NULL;
         
     | 
| 
      
 280 
     | 
    
         
            +
              struct ares_txt_ext *reply = NULL;
         
     | 
| 
      
 281 
     | 
    
         
            +
              grpc_error *error = GRPC_ERROR_NONE;
         
     | 
| 
       278 
282 
     | 
    
         
             
              gpr_mu_lock(&r->mu);
         
     | 
| 
       279 
283 
     | 
    
         
             
              if (status != ARES_SUCCESS) goto fail;
         
     | 
| 
       280 
     | 
    
         
            -
              struct ares_txt_ext *reply = NULL;
         
     | 
| 
       281 
284 
     | 
    
         
             
              status = ares_parse_txt_reply_ext(buf, len, &reply);
         
     | 
| 
       282 
285 
     | 
    
         
             
              if (status != ARES_SUCCESS) goto fail;
         
     | 
| 
       283 
286 
     | 
    
         
             
              // Find service config in TXT record.
         
     | 
| 
       284 
     | 
    
         
            -
              const size_t prefix_len = sizeof(g_service_config_attribute_prefix) - 1;
         
     | 
| 
       285 
     | 
    
         
            -
              struct ares_txt_ext *result;
         
     | 
| 
       286 
287 
     | 
    
         
             
              for (result = reply; result != NULL; result = result->next) {
         
     | 
| 
       287 
288 
     | 
    
         
             
                if (result->record_start &&
         
     | 
| 
       288 
289 
     | 
    
         
             
                    memcmp(result->txt, g_service_config_attribute_prefix, prefix_len) ==
         
     | 
| 
         @@ -293,12 +294,12 @@ static void on_txt_done_cb(void *arg, int status, int timeouts, 
     | 
|
| 
       293 
294 
     | 
    
         
             
              // Found a service config record.
         
     | 
| 
       294 
295 
     | 
    
         
             
              if (result != NULL) {
         
     | 
| 
       295 
296 
     | 
    
         
             
                size_t service_config_len = result->length - prefix_len;
         
     | 
| 
       296 
     | 
    
         
            -
                *r->service_config_json_out = gpr_malloc(service_config_len + 1);
         
     | 
| 
      
 297 
     | 
    
         
            +
                *r->service_config_json_out = (char *)gpr_malloc(service_config_len + 1);
         
     | 
| 
       297 
298 
     | 
    
         
             
                memcpy(*r->service_config_json_out, result->txt + prefix_len,
         
     | 
| 
       298 
299 
     | 
    
         
             
                       service_config_len);
         
     | 
| 
       299 
300 
     | 
    
         
             
                for (result = result->next; result != NULL && !result->record_start;
         
     | 
| 
       300 
301 
     | 
    
         
             
                     result = result->next) {
         
     | 
| 
       301 
     | 
    
         
            -
                  *r->service_config_json_out = gpr_realloc(
         
     | 
| 
      
 302 
     | 
    
         
            +
                  *r->service_config_json_out = (char *)gpr_realloc(
         
     | 
| 
       302 
303 
     | 
    
         
             
                      *r->service_config_json_out, service_config_len + result->length + 1);
         
     | 
| 
       303 
304 
     | 
    
         
             
                  memcpy(*r->service_config_json_out + service_config_len, result->txt,
         
     | 
| 
       304 
305 
     | 
    
         
             
                         result->length);
         
     | 
| 
         @@ -313,7 +314,7 @@ static void on_txt_done_cb(void *arg, int status, int timeouts, 
     | 
|
| 
       313 
314 
     | 
    
         
             
            fail:
         
     | 
| 
       314 
315 
     | 
    
         
             
              gpr_asprintf(&error_msg, "C-ares TXT lookup status is not ARES_SUCCESS: %s",
         
     | 
| 
       315 
316 
     | 
    
         
             
                           ares_strerror(status));
         
     | 
| 
       316 
     | 
    
         
            -
               
     | 
| 
      
 317 
     | 
    
         
            +
              error = GRPC_ERROR_CREATE_FROM_COPIED_STRING(error_msg);
         
     | 
| 
       317 
318 
     | 
    
         
             
              gpr_free(error_msg);
         
     | 
| 
       318 
319 
     | 
    
         
             
              if (r->error == GRPC_ERROR_NONE) {
         
     | 
| 
       319 
320 
     | 
    
         
             
                r->error = error;
         
     | 
| 
         @@ -331,6 +332,9 @@ static grpc_ares_request *grpc_dns_lookup_ares_impl( 
     | 
|
| 
       331 
332 
     | 
    
         
             
                grpc_closure *on_done, grpc_lb_addresses **addrs, bool check_grpclb,
         
     | 
| 
       332 
333 
     | 
    
         
             
                char **service_config_json) {
         
     | 
| 
       333 
334 
     | 
    
         
             
              grpc_error *error = GRPC_ERROR_NONE;
         
     | 
| 
      
 335 
     | 
    
         
            +
              grpc_ares_hostbyname_request *hr = NULL;
         
     | 
| 
      
 336 
     | 
    
         
            +
              grpc_ares_request *r = NULL;
         
     | 
| 
      
 337 
     | 
    
         
            +
              ares_channel *channel = NULL;
         
     | 
| 
       334 
338 
     | 
    
         
             
              /* TODO(zyc): Enable tracing after #9603 is checked in */
         
     | 
| 
       335 
339 
     | 
    
         
             
              /* if (grpc_dns_trace) {
         
     | 
| 
       336 
340 
     | 
    
         
             
                  gpr_log(GPR_DEBUG, "resolve_address (blocking): name=%s, default_port=%s",
         
     | 
| 
         @@ -360,7 +364,7 @@ static grpc_ares_request *grpc_dns_lookup_ares_impl( 
     | 
|
| 
       360 
364 
     | 
    
         
             
              error = grpc_ares_ev_driver_create(&ev_driver, interested_parties);
         
     | 
| 
       361 
365 
     | 
    
         
             
              if (error != GRPC_ERROR_NONE) goto error_cleanup;
         
     | 
| 
       362 
366 
     | 
    
         | 
| 
       363 
     | 
    
         
            -
               
     | 
| 
      
 367 
     | 
    
         
            +
              r = (grpc_ares_request *)gpr_zalloc(sizeof(grpc_ares_request));
         
     | 
| 
       364 
368 
     | 
    
         
             
              gpr_mu_init(&r->mu);
         
     | 
| 
       365 
369 
     | 
    
         
             
              r->ev_driver = ev_driver;
         
     | 
| 
       366 
370 
     | 
    
         
             
              r->on_done = on_done;
         
     | 
| 
         @@ -368,7 +372,7 @@ static grpc_ares_request *grpc_dns_lookup_ares_impl( 
     | 
|
| 
       368 
372 
     | 
    
         
             
              r->service_config_json_out = service_config_json;
         
     | 
| 
       369 
373 
     | 
    
         
             
              r->success = false;
         
     | 
| 
       370 
374 
     | 
    
         
             
              r->error = GRPC_ERROR_NONE;
         
     | 
| 
       371 
     | 
    
         
            -
               
     | 
| 
      
 375 
     | 
    
         
            +
              channel = grpc_ares_ev_driver_get_channel(r->ev_driver);
         
     | 
| 
       372 
376 
     | 
    
         | 
| 
       373 
377 
     | 
    
         
             
              // If dns_server is specified, use it.
         
     | 
| 
       374 
378 
     | 
    
         
             
              if (dns_server != NULL) {
         
     | 
| 
         @@ -409,12 +413,12 @@ static grpc_ares_request *grpc_dns_lookup_ares_impl( 
     | 
|
| 
       409 
413 
     | 
    
         
             
              }
         
     | 
| 
       410 
414 
     | 
    
         
             
              gpr_ref_init(&r->pending_queries, 1);
         
     | 
| 
       411 
415 
     | 
    
         
             
              if (grpc_ipv6_loopback_available()) {
         
     | 
| 
       412 
     | 
    
         
            -
                 
     | 
| 
       413 
     | 
    
         
            -
             
     | 
| 
      
 416 
     | 
    
         
            +
                hr = create_hostbyname_request(r, host, strhtons(port),
         
     | 
| 
      
 417 
     | 
    
         
            +
                                               false /* is_balancer */);
         
     | 
| 
       414 
418 
     | 
    
         
             
                ares_gethostbyname(*channel, hr->host, AF_INET6, on_hostbyname_done_cb, hr);
         
     | 
| 
       415 
419 
     | 
    
         
             
              }
         
     | 
| 
       416 
     | 
    
         
            -
               
     | 
| 
       417 
     | 
    
         
            -
             
     | 
| 
      
 420 
     | 
    
         
            +
              hr = create_hostbyname_request(r, host, strhtons(port),
         
     | 
| 
      
 421 
     | 
    
         
            +
                                             false /* is_balancer */);
         
     | 
| 
       418 
422 
     | 
    
         
             
              ares_gethostbyname(*channel, hr->host, AF_INET, on_hostbyname_done_cb, hr);
         
     | 
| 
       419 
423 
     | 
    
         
             
              if (check_grpclb) {
         
     | 
| 
       420 
424 
     | 
    
         
             
                /* Query the SRV record */
         
     | 
| 
         @@ -502,10 +506,11 @@ static void on_dns_lookup_done_cb(grpc_exec_ctx *exec_ctx, void *arg, 
     | 
|
| 
       502 
506 
     | 
    
         
             
              if (r->lb_addrs == NULL || r->lb_addrs->num_addresses == 0) {
         
     | 
| 
       503 
507 
     | 
    
         
             
                *resolved_addresses = NULL;
         
     | 
| 
       504 
508 
     | 
    
         
             
              } else {
         
     | 
| 
       505 
     | 
    
         
            -
                *resolved_addresses = 
     | 
| 
      
 509 
     | 
    
         
            +
                *resolved_addresses =
         
     | 
| 
      
 510 
     | 
    
         
            +
                    (grpc_resolved_addresses *)gpr_zalloc(sizeof(grpc_resolved_addresses));
         
     | 
| 
       506 
511 
     | 
    
         
             
                (*resolved_addresses)->naddrs = r->lb_addrs->num_addresses;
         
     | 
| 
       507 
     | 
    
         
            -
                (*resolved_addresses)->addrs =  
     | 
| 
       508 
     | 
    
         
            -
             
     | 
| 
      
 512 
     | 
    
         
            +
                (*resolved_addresses)->addrs = (grpc_resolved_address *)gpr_zalloc(
         
     | 
| 
      
 513 
     | 
    
         
            +
                    sizeof(grpc_resolved_address) * (*resolved_addresses)->naddrs);
         
     | 
| 
       509 
514 
     | 
    
         
             
                for (size_t i = 0; i < (*resolved_addresses)->naddrs; i++) {
         
     | 
| 
       510 
515 
     | 
    
         
             
                  GPR_ASSERT(!r->lb_addrs->addresses[i].is_balancer);
         
     | 
| 
       511 
516 
     | 
    
         
             
                  memcpy(&(*resolved_addresses)->addrs[i],
         
     | 
| 
         @@ -525,7 +530,8 @@ static void grpc_resolve_address_ares_impl(grpc_exec_ctx *exec_ctx, 
     | 
|
| 
       525 
530 
     | 
    
         
             
                                                       grpc_closure *on_done,
         
     | 
| 
       526 
531 
     | 
    
         
             
                                                       grpc_resolved_addresses **addrs) {
         
     | 
| 
       527 
532 
     | 
    
         
             
              grpc_resolve_address_ares_request *r =
         
     | 
| 
       528 
     | 
    
         
            -
                   
     | 
| 
      
 533 
     | 
    
         
            +
                  (grpc_resolve_address_ares_request *)gpr_zalloc(
         
     | 
| 
      
 534 
     | 
    
         
            +
                      sizeof(grpc_resolve_address_ares_request));
         
     | 
| 
       529 
535 
     | 
    
         
             
              r->addrs_out = addrs;
         
     | 
| 
       530 
536 
     | 
    
         
             
              r->on_resolve_address_done = on_done;
         
     | 
| 
       531 
537 
     | 
    
         
             
              GRPC_CLOSURE_INIT(&r->on_dns_lookup_done, on_dns_lookup_done_cb, r,
         
     | 
| 
         @@ -32,6 +32,7 @@ 
     | 
|
| 
       32 
32 
     | 
    
         
             
            #include "src/core/ext/filters/client_channel/parse_address.h"
         
     | 
| 
       33 
33 
     | 
    
         
             
            #include "src/core/ext/filters/client_channel/resolver_registry.h"
         
     | 
| 
       34 
34 
     | 
    
         
             
            #include "src/core/lib/channel/channel_args.h"
         
     | 
| 
      
 35 
     | 
    
         
            +
            #include "src/core/lib/iomgr/closure.h"
         
     | 
| 
       35 
36 
     | 
    
         
             
            #include "src/core/lib/iomgr/combiner.h"
         
     | 
| 
       36 
37 
     | 
    
         
             
            #include "src/core/lib/iomgr/resolve_address.h"
         
     | 
| 
       37 
38 
     | 
    
         
             
            #include "src/core/lib/iomgr/unix_sockets_posix.h"
         
     | 
| 
         @@ -125,7 +126,6 @@ static const grpc_resolver_vtable fake_resolver_vtable = { 
     | 
|
| 
       125 
126 
     | 
    
         | 
| 
       126 
127 
     | 
    
         
             
            struct grpc_fake_resolver_response_generator {
         
     | 
| 
       127 
128 
     | 
    
         
             
              fake_resolver* resolver;  // Set by the fake_resolver constructor to itself.
         
     | 
| 
       128 
     | 
    
         
            -
              grpc_channel_args* next_response;
         
     | 
| 
       129 
129 
     | 
    
         
             
              gpr_refcount refcount;
         
     | 
| 
       130 
130 
     | 
    
         
             
            };
         
     | 
| 
       131 
131 
     | 
    
         | 
| 
         @@ -151,19 +151,26 @@ void grpc_fake_resolver_response_generator_unref( 
     | 
|
| 
       151 
151 
     | 
    
         
             
              }
         
     | 
| 
       152 
152 
     | 
    
         
             
            }
         
     | 
| 
       153 
153 
     | 
    
         | 
| 
       154 
     | 
    
         
            -
             
     | 
| 
       155 
     | 
    
         
            -
             
     | 
| 
       156 
     | 
    
         
            -
              grpc_fake_resolver_response_generator* generator 
     | 
| 
       157 
     | 
    
         
            -
             
     | 
| 
      
 154 
     | 
    
         
            +
            typedef struct set_response_closure_arg {
         
     | 
| 
      
 155 
     | 
    
         
            +
              grpc_closure set_response_closure;
         
     | 
| 
      
 156 
     | 
    
         
            +
              grpc_fake_resolver_response_generator* generator;
         
     | 
| 
      
 157 
     | 
    
         
            +
              grpc_channel_args* next_response;
         
     | 
| 
      
 158 
     | 
    
         
            +
            } set_response_closure_arg;
         
     | 
| 
      
 159 
     | 
    
         
            +
             
     | 
| 
      
 160 
     | 
    
         
            +
            static void set_response_closure_fn(grpc_exec_ctx* exec_ctx, void* arg,
         
     | 
| 
      
 161 
     | 
    
         
            +
                                                grpc_error* error) {
         
     | 
| 
      
 162 
     | 
    
         
            +
              set_response_closure_arg* closure_arg = (set_response_closure_arg*)arg;
         
     | 
| 
      
 163 
     | 
    
         
            +
              grpc_fake_resolver_response_generator* generator = closure_arg->generator;
         
     | 
| 
       158 
164 
     | 
    
         
             
              fake_resolver* r = generator->resolver;
         
     | 
| 
       159 
165 
     | 
    
         
             
              if (r->next_results != NULL) {
         
     | 
| 
       160 
166 
     | 
    
         
             
                grpc_channel_args_destroy(exec_ctx, r->next_results);
         
     | 
| 
       161 
167 
     | 
    
         
             
              }
         
     | 
| 
       162 
     | 
    
         
            -
              r->next_results =  
     | 
| 
      
 168 
     | 
    
         
            +
              r->next_results = closure_arg->next_response;
         
     | 
| 
       163 
169 
     | 
    
         
             
              if (r->results_upon_error != NULL) {
         
     | 
| 
       164 
170 
     | 
    
         
             
                grpc_channel_args_destroy(exec_ctx, r->results_upon_error);
         
     | 
| 
       165 
171 
     | 
    
         
             
              }
         
     | 
| 
       166 
     | 
    
         
            -
              r->results_upon_error = grpc_channel_args_copy( 
     | 
| 
      
 172 
     | 
    
         
            +
              r->results_upon_error = grpc_channel_args_copy(closure_arg->next_response);
         
     | 
| 
      
 173 
     | 
    
         
            +
              gpr_free(closure_arg);
         
     | 
| 
       167 
174 
     | 
    
         
             
              fake_resolver_maybe_finish_next_locked(exec_ctx, r);
         
     | 
| 
       168 
175 
     | 
    
         
             
            }
         
     | 
| 
       169 
176 
     | 
    
         | 
| 
         @@ -171,12 +178,16 @@ void grpc_fake_resolver_response_generator_set_response( 
     | 
|
| 
       171 
178 
     | 
    
         
             
                grpc_exec_ctx* exec_ctx, grpc_fake_resolver_response_generator* generator,
         
     | 
| 
       172 
179 
     | 
    
         
             
                grpc_channel_args* next_response) {
         
     | 
| 
       173 
180 
     | 
    
         
             
              GPR_ASSERT(generator->resolver != NULL);
         
     | 
| 
       174 
     | 
    
         
            -
               
     | 
| 
       175 
     | 
    
         
            -
             
     | 
| 
       176 
     | 
    
         
            -
             
     | 
| 
       177 
     | 
    
         
            -
             
     | 
| 
       178 
     | 
    
         
            -
             
     | 
| 
       179 
     | 
    
         
            -
             
     | 
| 
      
 181 
     | 
    
         
            +
              set_response_closure_arg* closure_arg =
         
     | 
| 
      
 182 
     | 
    
         
            +
                  (set_response_closure_arg*)gpr_zalloc(sizeof(*closure_arg));
         
     | 
| 
      
 183 
     | 
    
         
            +
              closure_arg->generator = generator;
         
     | 
| 
      
 184 
     | 
    
         
            +
              closure_arg->next_response = grpc_channel_args_copy(next_response);
         
     | 
| 
      
 185 
     | 
    
         
            +
              GRPC_CLOSURE_SCHED(exec_ctx,
         
     | 
| 
      
 186 
     | 
    
         
            +
                                 GRPC_CLOSURE_INIT(&closure_arg->set_response_closure,
         
     | 
| 
      
 187 
     | 
    
         
            +
                                                   set_response_closure_fn, closure_arg,
         
     | 
| 
      
 188 
     | 
    
         
            +
                                                   grpc_combiner_scheduler(
         
     | 
| 
      
 189 
     | 
    
         
            +
                                                       generator->resolver->base.combiner)),
         
     | 
| 
      
 190 
     | 
    
         
            +
                                 GRPC_ERROR_NONE);
         
     | 
| 
       180 
191 
     | 
    
         
             
            }
         
     | 
| 
       181 
192 
     | 
    
         | 
| 
       182 
193 
     | 
    
         
             
            static void* response_generator_arg_copy(void* p) {
         
     | 
| 
         @@ -199,7 +210,7 @@ grpc_arg grpc_fake_resolver_response_generator_arg( 
     | 
|
| 
       199 
210 
     | 
    
         
             
                grpc_fake_resolver_response_generator* generator) {
         
     | 
| 
       200 
211 
     | 
    
         
             
              grpc_arg arg;
         
     | 
| 
       201 
212 
     | 
    
         
             
              arg.type = GRPC_ARG_POINTER;
         
     | 
| 
       202 
     | 
    
         
            -
              arg.key = GRPC_ARG_FAKE_RESOLVER_RESPONSE_GENERATOR;
         
     | 
| 
      
 213 
     | 
    
         
            +
              arg.key = (char*)GRPC_ARG_FAKE_RESOLVER_RESPONSE_GENERATOR;
         
     | 
| 
       203 
214 
     | 
    
         
             
              arg.value.pointer.p = generator;
         
     | 
| 
       204 
215 
     | 
    
         
             
              arg.value.pointer.vtable = &response_generator_arg_vtable;
         
     | 
| 
       205 
216 
     | 
    
         
             
              return arg;
         
     |