Resolved merge conflicts with master

pull/2942/head
murgatroid99 9 years ago
commit c04c03cb52
  1. 30
      BUILD
  2. 269
      Makefile
  3. 76
      build.json
  4. 5
      gRPC.podspec
  5. 2
      include/grpc++/completion_queue.h
  6. 8
      include/grpc++/impl/call.h
  7. 15
      include/grpc++/impl/rpc_service_method.h
  8. 2
      include/grpc++/server.h
  9. 2
      include/grpc++/server_context.h
  10. 4
      include/grpc/byte_buffer.h
  11. 55
      include/grpc/grpc.h
  12. 41
      include/grpc/grpc_zookeeper.h
  13. 2
      include/grpc/support/port_platform.h
  14. 33
      include/grpc/support/sync.h
  15. 2
      src/compiler/csharp_generator_helpers.h
  16. 9
      src/compiler/generator_helpers.h
  17. 33
      src/compiler/objective_c_generator.cc
  18. 28
      src/compiler/objective_c_plugin.cc
  19. 501
      src/core/client_config/resolvers/zookeeper_resolver.c
  20. 42
      src/core/client_config/resolvers/zookeeper_resolver.h
  21. 4
      src/core/compression/algorithm.c
  22. 438
      src/core/iomgr/udp_server.c
  23. 85
      src/core/iomgr/udp_server.h
  24. 157
      src/core/support/cancellable.c
  25. 15
      src/core/support/sync.c
  26. 17
      src/core/surface/call.c
  27. 9
      src/core/surface/channel.c
  28. 4
      src/core/surface/channel_create.c
  29. 10
      src/core/surface/completion_queue.c
  30. 32
      src/core/surface/init.c
  31. 4
      src/core/surface/server.c
  32. 3
      src/core/surface/server_create.c
  33. 1
      src/core/transport/stream_op.c
  34. 1
      src/core/transport/stream_op.h
  35. 9
      src/cpp/client/channel.cc
  36. 8
      src/cpp/client/client_context.cc
  37. 2
      src/cpp/client/insecure_credentials.cc
  38. 14
      src/cpp/common/completion_queue.cc
  39. 46
      src/cpp/server/server.cc
  40. 10
      src/cpp/server/server_builder.cc
  41. 1
      src/cpp/server/server_context.cc
  42. 47
      src/csharp/ext/grpc_csharp_ext.c
  43. 8
      src/node/ext/call.cc
  44. 64
      src/node/ext/channel.cc
  45. 2
      src/node/ext/channel.h
  46. 6
      src/node/ext/completion_queue_async_worker.cc
  47. 19
      src/node/ext/node_grpc.cc
  48. 12
      src/node/ext/server.cc
  49. 29
      src/node/src/client.js
  50. 87
      src/node/test/channel_test.js
  51. 18
      src/node/test/constant_test.js
  52. 52
      src/node/test/surface_test.js
  53. 5
      src/objective-c/GRPCClient/private/GRPCCompletionQueue.m
  54. 2
      src/objective-c/GRPCClient/private/GRPCHost.m
  55. 2
      src/objective-c/GRPCClient/private/GRPCUnsecuredChannel.m
  56. 4
      src/objective-c/GRPCClient/private/GRPCWrappedCall.m
  57. 9
      src/php/ext/grpc/call.c
  58. 6
      src/php/ext/grpc/channel.c
  59. 7
      src/php/ext/grpc/completion_queue.c
  60. 11
      src/php/ext/grpc/server.c
  61. 6
      src/python/grpcio/grpc/_adapter/_c/types/call.c
  62. 4
      src/python/grpcio/grpc/_adapter/_c/types/channel.c
  63. 4
      src/python/grpcio/grpc/_adapter/_c/types/completion_queue.c
  64. 4
      src/python/grpcio/grpc/_adapter/_c/types/server.c
  65. 4
      src/ruby/ext/grpc/rb_call.c
  66. 4
      src/ruby/ext/grpc/rb_channel.c
  67. 6
      src/ruby/ext/grpc/rb_completion_queue.c
  68. 4
      src/ruby/ext/grpc/rb_server.c
  69. 214
      templates/Makefile.template
  70. 2
      templates/vsprojects/grpc_test_util_unsecure/grpc_test_util_unsecure.vcxproj.template
  71. 43
      test/build/zookeeper.c
  72. 7
      test/core/bad_client/bad_client.c
  73. 4
      test/core/bad_client/tests/connection_prefix.c
  74. 4
      test/core/bad_client/tests/initial_settings_frame.c
  75. 4
      test/core/end2end/cq_verifier.c
  76. 33
      test/core/end2end/dualstack_socket_test.c
  77. 6
      test/core/end2end/fixtures/chttp2_fake_security.c
  78. 8
      test/core/end2end/fixtures/chttp2_fullstack.c
  79. 8
      test/core/end2end/fixtures/chttp2_fullstack_compression.c
  80. 8
      test/core/end2end/fixtures/chttp2_fullstack_uds_posix.c
  81. 8
      test/core/end2end/fixtures/chttp2_fullstack_uds_posix_with_poll.c
  82. 8
      test/core/end2end/fixtures/chttp2_fullstack_with_poll.c
  83. 12
      test/core/end2end/fixtures/chttp2_fullstack_with_proxy.c
  84. 6
      test/core/end2end/fixtures/chttp2_simple_ssl_fullstack.c
  85. 6
      test/core/end2end/fixtures/chttp2_simple_ssl_fullstack_with_poll.c
  86. 8
      test/core/end2end/fixtures/chttp2_simple_ssl_fullstack_with_proxy.c
  87. 6
      test/core/end2end/fixtures/chttp2_simple_ssl_with_oauth2_fullstack.c
  88. 4
      test/core/end2end/fixtures/chttp2_socket_pair.c
  89. 4
      test/core/end2end/fixtures/chttp2_socket_pair_one_byte_at_a_time.c
  90. 4
      test/core/end2end/fixtures/chttp2_socket_pair_with_grpc_trace.c
  91. 41
      test/core/end2end/fixtures/proxy.c
  92. 16
      test/core/end2end/multiple_server_queues_test.c
  93. 14
      test/core/end2end/no_server_test.c
  94. 15
      test/core/end2end/tests/bad_hostname.c
  95. 31
      test/core/end2end/tests/cancel_after_accept.c
  96. 32
      test/core/end2end/tests/cancel_after_accept_and_writes_closed.c
  97. 19
      test/core/end2end/tests/cancel_after_invoke.c
  98. 19
      test/core/end2end/tests/cancel_before_invoke.c
  99. 9
      test/core/end2end/tests/cancel_in_a_vacuum.c
  100. 5
      test/core/end2end/tests/cancel_test_helpers.h
  101. Some files were not shown because too many files have changed in this diff Show More

30
BUILD

@ -52,7 +52,6 @@ cc_library(
"src/core/support/string_win32.h",
"src/core/support/thd_internal.h",
"src/core/support/alloc.c",
"src/core/support/cancellable.c",
"src/core/support/cmdline.c",
"src/core/support/cpu_iphone.c",
"src/core/support/cpu_linux.c",
@ -96,7 +95,6 @@ cc_library(
"include/grpc/support/atm_gcc_atomic.h",
"include/grpc/support/atm_gcc_sync.h",
"include/grpc/support/atm_win32.h",
"include/grpc/support/cancellable_platform.h",
"include/grpc/support/cmdline.h",
"include/grpc/support/cpu.h",
"include/grpc/support/histogram.h",
@ -202,6 +200,7 @@ cc_library(
"src/core/iomgr/tcp_server.h",
"src/core/iomgr/tcp_windows.h",
"src/core/iomgr/time_averaged_stats.h",
"src/core/iomgr/udp_server.h",
"src/core/iomgr/wakeup_fd_pipe.h",
"src/core/iomgr/wakeup_fd_posix.h",
"src/core/json/json.h",
@ -326,6 +325,7 @@ cc_library(
"src/core/iomgr/tcp_server_windows.c",
"src/core/iomgr/tcp_windows.c",
"src/core/iomgr/time_averaged_stats.c",
"src/core/iomgr/udp_server.c",
"src/core/iomgr/wakeup_fd_eventfd.c",
"src/core/iomgr/wakeup_fd_nospecial.c",
"src/core/iomgr/wakeup_fd_pipe.c",
@ -466,6 +466,7 @@ cc_library(
"src/core/iomgr/tcp_server.h",
"src/core/iomgr/tcp_windows.h",
"src/core/iomgr/time_averaged_stats.h",
"src/core/iomgr/udp_server.h",
"src/core/iomgr/wakeup_fd_pipe.h",
"src/core/iomgr/wakeup_fd_posix.h",
"src/core/json/json.h",
@ -570,6 +571,7 @@ cc_library(
"src/core/iomgr/tcp_server_windows.c",
"src/core/iomgr/tcp_windows.c",
"src/core/iomgr/time_averaged_stats.c",
"src/core/iomgr/udp_server.c",
"src/core/iomgr/wakeup_fd_eventfd.c",
"src/core/iomgr/wakeup_fd_nospecial.c",
"src/core/iomgr/wakeup_fd_pipe.c",
@ -647,6 +649,26 @@ cc_library(
)
cc_library(
name = "grpc_zookeeper",
srcs = [
"src/core/client_config/resolvers/zookeeper_resolver.h",
"src/core/client_config/resolvers/zookeeper_resolver.c",
],
hdrs = [
"include/grpc/grpc_zookeeper.h",
],
includes = [
"include",
".",
],
deps = [
":gpr",
":grpc",
],
)
cc_library(
name = "grpc++",
srcs = [
@ -888,7 +910,6 @@ objc_library(
name = "gpr_objc",
srcs = [
"src/core/support/alloc.c",
"src/core/support/cancellable.c",
"src/core/support/cmdline.c",
"src/core/support/cpu_iphone.c",
"src/core/support/cpu_linux.c",
@ -932,7 +953,6 @@ objc_library(
"include/grpc/support/atm_gcc_atomic.h",
"include/grpc/support/atm_gcc_sync.h",
"include/grpc/support/atm_win32.h",
"include/grpc/support/cancellable_platform.h",
"include/grpc/support/cmdline.h",
"include/grpc/support/cpu.h",
"include/grpc/support/histogram.h",
@ -1055,6 +1075,7 @@ objc_library(
"src/core/iomgr/tcp_server_windows.c",
"src/core/iomgr/tcp_windows.c",
"src/core/iomgr/time_averaged_stats.c",
"src/core/iomgr/udp_server.c",
"src/core/iomgr/wakeup_fd_eventfd.c",
"src/core/iomgr/wakeup_fd_nospecial.c",
"src/core/iomgr/wakeup_fd_pipe.c",
@ -1192,6 +1213,7 @@ objc_library(
"src/core/iomgr/tcp_server.h",
"src/core/iomgr/tcp_windows.h",
"src/core/iomgr/time_averaged_stats.h",
"src/core/iomgr/udp_server.h",
"src/core/iomgr/wakeup_fd_pipe.h",
"src/core/iomgr/wakeup_fd_posix.h",
"src/core/json/json.h",

File diff suppressed because one or more lines are too long

@ -171,6 +171,7 @@
"src/core/iomgr/tcp_server.h",
"src/core/iomgr/tcp_windows.h",
"src/core/iomgr/time_averaged_stats.h",
"src/core/iomgr/udp_server.h",
"src/core/iomgr/wakeup_fd_pipe.h",
"src/core/iomgr/wakeup_fd_posix.h",
"src/core/json/json.h",
@ -274,6 +275,7 @@
"src/core/iomgr/tcp_server_windows.c",
"src/core/iomgr/tcp_windows.c",
"src/core/iomgr/time_averaged_stats.c",
"src/core/iomgr/udp_server.c",
"src/core/iomgr/wakeup_fd_eventfd.c",
"src/core/iomgr/wakeup_fd_nospecial.c",
"src/core/iomgr/wakeup_fd_pipe.c",
@ -367,7 +369,6 @@
"include/grpc/support/atm_gcc_atomic.h",
"include/grpc/support/atm_gcc_sync.h",
"include/grpc/support/atm_win32.h",
"include/grpc/support/cancellable_platform.h",
"include/grpc/support/cmdline.h",
"include/grpc/support/cpu.h",
"include/grpc/support/histogram.h",
@ -402,7 +403,6 @@
],
"src": [
"src/core/support/alloc.c",
"src/core/support/cancellable.c",
"src/core/support/cmdline.c",
"src/core/support/cpu_iphone.c",
"src/core/support/cpu_linux.c",
@ -572,6 +572,29 @@
"secure": "no",
"vs_project_guid": "{46CEDFFF-9692-456A-AA24-38B5D6BCF4C5}"
},
{
"name": "grpc_zookeeper",
"build": "all",
"language": "c",
"public_headers": [
"include/grpc/grpc_zookeeper.h"
],
"headers": [
"src/core/client_config/resolvers/zookeeper_resolver.h"
],
"src": [
"src/core/client_config/resolvers/zookeeper_resolver.c"
],
"deps": [
"gpr",
"grpc"
],
"external_deps": [
"zookeeper"
],
"secure": "no",
"vs_project_guid": "{F14EBEC1-DC43-45D3-8A7D-1A47072EFE50}"
},
{
"name": "reconnect_server",
"build": "private",
@ -1106,18 +1129,6 @@
"grpc"
]
},
{
"name": "gpr_cancellable_test",
"build": "test",
"language": "c",
"src": [
"test/core/support/cancellable_test.c"
],
"deps": [
"gpr_test_util",
"gpr"
]
},
{
"name": "gpr_cmdline_test",
"build": "test",
@ -1875,6 +1886,23 @@
"gpr"
]
},
{
"name": "udp_server_test",
"build": "test",
"language": "c",
"src": [
"test/core/iomgr/udp_server_test.c"
],
"deps": [
"grpc_test_util",
"grpc",
"gpr_test_util",
"gpr"
],
"platforms": [
"posix"
]
},
{
"name": "uri_parser_test",
"build": "test",
@ -2642,6 +2670,26 @@
"gpr_test_util",
"gpr"
]
},
{
"name": "zookeeper_test",
"build": "test",
"language": "c++",
"src": [
"test/cpp/end2end/zookeeper_test.cc"
],
"deps": [
"grpc++_test_util",
"grpc_test_util",
"grpc++",
"grpc_zookeeper",
"grpc",
"gpr_test_util",
"gpr"
],
"external_deps": [
"zookeeper"
]
}
]
}

@ -73,7 +73,6 @@ Pod::Spec.new do |s|
'grpc/support/atm_gcc_atomic.h',
'grpc/support/atm_gcc_sync.h',
'grpc/support/atm_win32.h',
'grpc/support/cancellable_platform.h',
'grpc/support/cmdline.h',
'grpc/support/cpu.h',
'grpc/support/histogram.h',
@ -97,7 +96,6 @@ Pod::Spec.new do |s|
'grpc/support/tls_pthread.h',
'grpc/support/useful.h',
'src/core/support/alloc.c',
'src/core/support/cancellable.c',
'src/core/support/cmdline.c',
'src/core/support/cpu_iphone.c',
'src/core/support/cpu_linux.c',
@ -204,6 +202,7 @@ Pod::Spec.new do |s|
'src/core/iomgr/tcp_server.h',
'src/core/iomgr/tcp_windows.h',
'src/core/iomgr/time_averaged_stats.h',
'src/core/iomgr/udp_server.h',
'src/core/iomgr/wakeup_fd_pipe.h',
'src/core/iomgr/wakeup_fd_posix.h',
'src/core/json/json.h',
@ -335,6 +334,7 @@ Pod::Spec.new do |s|
'src/core/iomgr/tcp_server_windows.c',
'src/core/iomgr/tcp_windows.c',
'src/core/iomgr/time_averaged_stats.c',
'src/core/iomgr/udp_server.c',
'src/core/iomgr/wakeup_fd_eventfd.c',
'src/core/iomgr/wakeup_fd_nospecial.c',
'src/core/iomgr/wakeup_fd_pipe.c',
@ -471,6 +471,7 @@ Pod::Spec.new do |s|
'src/core/iomgr/tcp_server.h',
'src/core/iomgr/tcp_windows.h',
'src/core/iomgr/time_averaged_stats.h',
'src/core/iomgr/udp_server.h',
'src/core/iomgr/wakeup_fd_pipe.h',
'src/core/iomgr/wakeup_fd_posix.h',
'src/core/json/json.h',

@ -63,6 +63,7 @@ template <class ServiceType, class RequestType, class ResponseType>
class ServerStreamingHandler;
template <class ServiceType, class RequestType, class ResponseType>
class BidiStreamingHandler;
class UnknownMethodHandler;
class ChannelInterface;
class ClientContext;
@ -138,6 +139,7 @@ class CompletionQueue : public GrpcLibrary {
friend class ServerStreamingHandler;
template <class ServiceType, class RequestType, class ResponseType>
friend class BidiStreamingHandler;
friend class UnknownMethodHandler;
friend class ::grpc::Server;
friend class ::grpc::ServerContext;
template <class InputMessage, class OutputMessage>

@ -173,6 +173,7 @@ class CallOpSendInitialMetadata {
grpc_op* op = &ops[(*nops)++];
op->op = GRPC_OP_SEND_INITIAL_METADATA;
op->flags = 0;
op->reserved = NULL;
op->data.send_initial_metadata.count = initial_metadata_count_;
op->data.send_initial_metadata.metadata = initial_metadata_;
}
@ -206,6 +207,7 @@ class CallOpSendMessage {
grpc_op* op = &ops[(*nops)++];
op->op = GRPC_OP_SEND_MESSAGE;
op->flags = write_options_.flags();
op->reserved = NULL;
op->data.send_message = send_buf_;
// Flags are per-message: clear them after use.
write_options_.Clear();
@ -248,6 +250,7 @@ class CallOpRecvMessage {
grpc_op* op = &ops[(*nops)++];
op->op = GRPC_OP_RECV_MESSAGE;
op->flags = 0;
op->reserved = NULL;
op->data.recv_message = &recv_buf_;
}
@ -313,6 +316,7 @@ class CallOpGenericRecvMessage {
grpc_op* op = &ops[(*nops)++];
op->op = GRPC_OP_RECV_MESSAGE;
op->flags = 0;
op->reserved = NULL;
op->data.recv_message = &recv_buf_;
}
@ -350,6 +354,7 @@ class CallOpClientSendClose {
grpc_op* op = &ops[(*nops)++];
op->op = GRPC_OP_SEND_CLOSE_FROM_CLIENT;
op->flags = 0;
op->reserved = NULL;
}
void FinishOp(bool* status, int max_message_size) { send_ = false; }
@ -383,6 +388,7 @@ class CallOpServerSendStatus {
op->data.send_status_from_server.status_details =
send_status_details_.empty() ? nullptr : send_status_details_.c_str();
op->flags = 0;
op->reserved = NULL;
}
void FinishOp(bool* status, int max_message_size) {
@ -416,6 +422,7 @@ class CallOpRecvInitialMetadata {
op->op = GRPC_OP_RECV_INITIAL_METADATA;
op->data.recv_initial_metadata = &recv_initial_metadata_arr_;
op->flags = 0;
op->reserved = NULL;
}
void FinishOp(bool* status, int max_message_size) {
if (recv_initial_metadata_ == nullptr) return;
@ -453,6 +460,7 @@ class CallOpClientRecvStatus {
op->data.recv_status_on_client.status_details_capacity =
&status_details_capacity_;
op->flags = 0;
op->reserved = NULL;
}
void FinishOp(bool* status, int max_message_size) {

@ -208,6 +208,21 @@ class BidiStreamingHandler : public MethodHandler {
ServiceType* service_;
};
// Handle unknown method by returning UNIMPLEMENTED error.
class UnknownMethodHandler : public MethodHandler {
public:
void RunHandler(const HandlerParameter& param) GRPC_FINAL {
Status status(StatusCode::UNIMPLEMENTED, "");
CallOpSet<CallOpSendInitialMetadata, CallOpServerSendStatus> ops;
if (!param.server_context->sent_initial_metadata_) {
ops.SendInitialMetadata(param.server_context->initial_metadata_);
}
ops.ServerSendStatus(param.server_context->trailing_metadata_, status);
param.call->PerformOps(&ops);
param.call->cq()->Pluck(&ops);
}
};
// Server side rpc method class
class RpcServiceMethod : public RpcMethod {
public:

@ -228,6 +228,8 @@ class Server GRPC_FINAL : public GrpcLibrary, private CallHook {
grpc::condition_variable callback_cv_;
std::list<SyncRequest>* sync_methods_;
std::unique_ptr<RpcServiceMethod> unknown_method_;
bool has_generic_service_;
// Pointer to the c grpc server.
grpc_server* const server_;

@ -73,6 +73,7 @@ template <class ServiceType, class RequestType, class ResponseType>
class ServerStreamingHandler;
template <class ServiceType, class RequestType, class ResponseType>
class BidiStreamingHandler;
class UnknownMethodHandler;
class Call;
class CallOpBuffer;
@ -159,6 +160,7 @@ class ServerContext {
friend class ServerStreamingHandler;
template <class ServiceType, class RequestType, class ResponseType>
friend class BidiStreamingHandler;
friend class UnknownMethodHandler;
friend class ::grpc::ClientContext;
// Prevent copying.

@ -47,8 +47,12 @@ typedef enum {
} grpc_byte_buffer_type;
struct grpc_byte_buffer {
void *reserved;
grpc_byte_buffer_type type;
union {
struct {
void *reserved[8];
} reserved;
struct {
grpc_compression_algorithm compression;
gpr_slice_buffer slice_buffer;

@ -202,13 +202,14 @@ typedef struct grpc_metadata {
const char *key;
const char *value;
size_t value_length;
gpr_uint32 flags;
/** The following fields are reserved for grpc internal use.
There is no need to initialize them, and they will be set to garbage
during
calls to grpc. */
struct {
void *obfuscated[3];
void *obfuscated[4];
} internal_data;
} grpc_metadata;
@ -251,6 +252,7 @@ typedef struct {
char *host;
size_t host_capacity;
gpr_timespec deadline;
void *reserved;
} grpc_call_details;
void grpc_call_details_init(grpc_call_details *details);
@ -306,7 +308,13 @@ typedef struct grpc_op {
grpc_op_type op;
/** Write flags bitset for grpc_begin_messages */
gpr_uint32 flags;
/** Reserved for future usage */
void *reserved;
union {
/** Reserved for future usage */
struct {
void *reserved[8];
} reserved;
struct {
size_t count;
grpc_metadata *metadata;
@ -368,6 +376,23 @@ typedef struct grpc_op {
} data;
} grpc_op;
/** Registers a plugin to be initialized and destroyed with the library.
The \a init and \a destroy functions will be invoked as part of
\a grpc_init() and \a grpc_shutdown(), respectively.
Note that these functions can be invoked an arbitrary number of times
(and hence so will \a init and \a destroy).
It is safe to pass NULL to either argument. Plugins are destroyed in
the reverse order they were initialized. */
void grpc_register_plugin(void (*init)(void), void (*destroy)(void));
/** Frees the memory used by all the plugin information.
While grpc_init and grpc_shutdown can be called multiple times, the plugins
won't be unregistered and their memory cleaned up unless you call that
function. Using atexit(grpc_unregister_all_plugins) is a valid method. */
void grpc_unregister_all_plugins();
/* Propagation bits: this can be bitwise or-ed to form propagation_mask for
* grpc_call */
/** Propagate deadline */
@ -408,7 +433,7 @@ void grpc_shutdown(void);
const char *grpc_version_string(void);
/** Create a completion queue */
grpc_completion_queue *grpc_completion_queue_create(void);
grpc_completion_queue *grpc_completion_queue_create(void *reserved);
/** Blocks until an event is available, the completion queue is being shut down,
or deadline is reached.
@ -419,7 +444,7 @@ grpc_completion_queue *grpc_completion_queue_create(void);
Callers must not call grpc_completion_queue_next and
grpc_completion_queue_pluck simultaneously on the same completion queue. */
grpc_event grpc_completion_queue_next(grpc_completion_queue *cq,
gpr_timespec deadline);
gpr_timespec deadline, void *reserved);
/** Blocks until an event with tag 'tag' is available, the completion queue is
being shutdown or deadline is reached.
@ -433,7 +458,7 @@ grpc_event grpc_completion_queue_next(grpc_completion_queue *cq,
Completion queues support a maximum of GRPC_MAX_COMPLETION_QUEUE_PLUCKERS
concurrently executing plucks at any time. */
grpc_event grpc_completion_queue_pluck(grpc_completion_queue *cq, void *tag,
gpr_timespec deadline);
gpr_timespec deadline, void *reserved);
/** Maximum number of outstanding grpc_completion_queue_pluck executions per
completion queue */
@ -476,17 +501,17 @@ grpc_call *grpc_channel_create_call(grpc_channel *channel,
gpr_uint32 propagation_mask,
grpc_completion_queue *completion_queue,
const char *method, const char *host,
gpr_timespec deadline);
gpr_timespec deadline, void *reserved);
/** Pre-register a method/host pair on a channel. */
void *grpc_channel_register_call(grpc_channel *channel, const char *method,
const char *host);
const char *host, void *reserved);
/** Create a call given a handle returned from grpc_channel_register_call */
grpc_call *grpc_channel_create_registered_call(
grpc_channel *channel, grpc_call *parent_call, gpr_uint32 propagation_mask,
grpc_completion_queue *completion_queue, void *registered_call_handle,
gpr_timespec deadline);
gpr_timespec deadline, void *reserved);
/** Start a batch of operations defined in the array ops; when complete, post a
completion of type 'tag' to the completion queue bound to the call.
@ -500,7 +525,7 @@ grpc_call *grpc_channel_create_registered_call(
containing just send operations independently from batches containing just
receive operations. */
grpc_call_error grpc_call_start_batch(grpc_call *call, const grpc_op *ops,
size_t nops, void *tag);
size_t nops, void *tag, void *reserved);
/** Returns a newly allocated string representing the endpoint to which this
call is communicating with. The string is in the uri format accepted by
@ -532,7 +557,8 @@ char *grpc_channel_get_target(grpc_channel *channel);
more on this. The data in 'args' need only live through the invocation of
this function. */
grpc_channel *grpc_insecure_channel_create(const char *target,
const grpc_channel_args *args);
const grpc_channel_args *args,
void *reserved);
/** Create a lame client: this client fails every operation attempted on it. */
grpc_channel *grpc_lame_client_channel_create(const char *target);
@ -551,7 +577,7 @@ void grpc_channel_destroy(grpc_channel *channel);
THREAD-SAFETY grpc_call_cancel and grpc_call_cancel_with_status
are thread-safe, and can be called at any point before grpc_call_destroy
is called.*/
grpc_call_error grpc_call_cancel(grpc_call *call);
grpc_call_error grpc_call_cancel(grpc_call *call, void *reserved);
/** Called by clients to cancel an RPC on the server.
Can be called multiple times, from any thread.
@ -561,7 +587,8 @@ grpc_call_error grpc_call_cancel(grpc_call *call);
remote endpoint. */
grpc_call_error grpc_call_cancel_with_status(grpc_call *call,
grpc_status_code status,
const char *description);
const char *description,
void *reserved);
/** Destroy a call.
THREAD SAFETY: grpc_call_destroy is thread-compatible */
@ -600,14 +627,16 @@ grpc_call_error grpc_server_request_registered_call(
be specified with args. If no additional configuration is needed, args can
be NULL. See grpc_channel_args for more. The data in 'args' need only live
through the invocation of this function. */
grpc_server *grpc_server_create(const grpc_channel_args *args);
grpc_server *grpc_server_create(const grpc_channel_args *args,
void *reserved);
/** Register a completion queue with the server. Must be done for any
notification completion queue that is passed to grpc_server_request_*_call
and to grpc_server_shutdown_and_notify. Must be performed prior to
grpc_server_start. */
void grpc_server_register_completion_queue(grpc_server *server,
grpc_completion_queue *cq);
grpc_completion_queue *cq,
void *reserved);
/** Add a HTTP2 over plaintext over tcp listener.
Returns bound port number on success, 0 on failure.

@ -31,26 +31,29 @@
*
*/
#ifndef GRPC_SUPPORT_CANCELLABLE_PLATFORM_H
#define GRPC_SUPPORT_CANCELLABLE_PLATFORM_H
/** Support zookeeper as alternative name system in addition to DNS
* Zookeeper name in gRPC is represented as a URI:
* zookeeper://host:port/path/service/instance
*
* Where zookeeper is the name system scheme
* host:port is the address of a zookeeper server
* /path/service/instance is the zookeeper name to be resolved
*
* Refer doc/naming.md for more details
*/
#ifndef GRPC_GRPC_ZOOKEEPER_H
#define GRPC_GRPC_ZOOKEEPER_H
#include <grpc/support/atm.h>
#include <grpc/support/sync.h>
#ifdef __cplusplus
extern "C" {
#endif
struct gpr_cancellable_list_ {
/* a doubly-linked list on cancellable's waiters queue */
struct gpr_cancellable_list_ *next;
struct gpr_cancellable_list_ *prev;
/* The following two fields are arguments to gpr_cv_cancellable_wait() */
gpr_mu *mu;
gpr_cv *cv;
};
/** Register zookeeper name resolver in grpc */
void grpc_zookeeper_register();
/* Internal definition of gpr_cancellable. */
typedef struct {
gpr_mu mu; /* protects waiters and modifications to cancelled */
gpr_atm cancelled;
struct gpr_cancellable_list_ waiters;
} gpr_cancellable;
#ifdef __cplusplus
}
#endif
#endif /* GRPC_SUPPORT_CANCELLABLE_PLATFORM_H */
#endif /* GRPC_GRPC_ZOOKEEPER_H */

@ -173,6 +173,8 @@
#endif /* _LP64 */
#elif defined(__APPLE__)
#include <TargetConditionals.h>
/* Provides IPV6_RECVPKTINFO */
#define __APPLE_USE_RFC_3542
#ifndef _BSD_SOURCE
#define _BSD_SOURCE
#endif

@ -65,7 +65,6 @@
#endif
#include <grpc/support/time.h> /* for gpr_timespec */
#include <grpc/support/cancellable_platform.h>
#ifdef __cplusplus
extern "C" {
@ -121,11 +120,6 @@ void gpr_cv_destroy(gpr_cv *cv);
holds an exclusive lock on *mu. */
int gpr_cv_wait(gpr_cv *cv, gpr_mu *mu, gpr_timespec abs_deadline);
/* Behave like gpr_cv_wait(cv, mu, abs_deadline), except behave as though
the deadline has expired if *c is cancelled. */
int gpr_cv_cancellable_wait(gpr_cv *cv, gpr_mu *mu, gpr_timespec abs_deadline,
gpr_cancellable *c);
/* If any threads are waiting on *cv, wake at least one.
Clients may treat this as an optimization of gpr_cv_broadcast()
for use in the case where waking more than one waiter is not useful.
@ -135,28 +129,6 @@ void gpr_cv_signal(gpr_cv *cv);
/* Wake all threads waiting on *cv. Requires: *cv initialized. */
void gpr_cv_broadcast(gpr_cv *cv);
/* --- Cancellation ---
A gpr_cancellable can be used with gpr_cv_cancellable_wait()
or gpr_event_cancellable_wait() cancel pending waits. */
/* Initialize *c. */
void gpr_cancellable_init(gpr_cancellable *c);
/* Cause *c no longer to be initialized, freeing any memory in use. Requires:
*c initialized; no other concurrent operation on *c. */
void gpr_cancellable_destroy(gpr_cancellable *c);
/* Return non-zero iff *c has been cancelled. Requires *c initialized.
This call is faster than acquiring a mutex on most platforms. */
int gpr_cancellable_is_cancelled(gpr_cancellable *c);
/* Cancel *c. If *c was not previously cancelled, cause
gpr_cancellable_init() to return non-zero, and outstanding and future
calls to gpr_cv_cancellable_wait() and gpr_event_cancellable_wait() to
return immediately indicating a timeout has occurred; otherwise do nothing.
Requires *c initialized.*/
void gpr_cancellable_cancel(gpr_cancellable *c);
/* --- One-time initialization ---
gpr_once must be declared with static storage class, and initialized with
@ -199,11 +171,6 @@ void *gpr_event_get(gpr_event *ev);
on most platforms. */
void *gpr_event_wait(gpr_event *ev, gpr_timespec abs_deadline);
/* Behave like gpr_event_wait(ev, abs_deadline), except behave as though
the deadline has expired if *c is cancelled. */
void *gpr_event_cancellable_wait(gpr_event *ev, gpr_timespec abs_deadline,
gpr_cancellable *c);
/* --- Reference counting ---
These calls act on the type gpr_refcount. It requires no destruction. */

@ -41,7 +41,7 @@ namespace grpc_csharp_generator {
inline bool ServicesFilename(const grpc::protobuf::FileDescriptor *file,
grpc::string *file_name_or_error) {
*file_name_or_error = grpc_generator::FileNameInUpperCamel(file) + "Grpc.cs";
*file_name_or_error = grpc_generator::FileNameInUpperCamel(file, false) + "Grpc.cs";
return true;
}

@ -125,16 +125,23 @@ inline grpc::string LowerUnderscoreToUpperCamel(grpc::string str) {
return result;
}
inline grpc::string FileNameInUpperCamel(const grpc::protobuf::FileDescriptor *file) {
inline grpc::string FileNameInUpperCamel(const grpc::protobuf::FileDescriptor *file,
bool include_package_path) {
std::vector<grpc::string> tokens = tokenize(StripProto(file->name()), "/");
grpc::string result = "";
if (include_package_path) {
for (unsigned int i = 0; i < tokens.size() - 1; i++) {
result += tokens[i] + "/";
}
}
result += LowerUnderscoreToUpperCamel(tokens.back());
return result;
}
inline grpc::string FileNameInUpperCamel(const grpc::protobuf::FileDescriptor *file) {
return FileNameInUpperCamel(file, true);
}
enum MethodType {
METHODTYPE_NO_STREAMING,
METHODTYPE_CLIENT_STREAMING,

@ -44,7 +44,6 @@ using ::google::protobuf::compiler::objectivec::ClassName;
using ::grpc::protobuf::io::Printer;
using ::grpc::protobuf::MethodDescriptor;
using ::grpc::protobuf::ServiceDescriptor;
using ::grpc::string;
using ::std::map;
namespace grpc_objective_c_generator {
@ -52,7 +51,7 @@ namespace {
void PrintProtoRpcDeclarationAsPragma(Printer *printer,
const MethodDescriptor *method,
map<string, string> vars) {
map< ::grpc::string, ::grpc::string> vars) {
vars["client_stream"] = method->client_streaming() ? "stream " : "";
vars["server_stream"] = method->server_streaming() ? "stream " : "";
@ -62,7 +61,7 @@ void PrintProtoRpcDeclarationAsPragma(Printer *printer,
}
void PrintMethodSignature(Printer *printer, const MethodDescriptor *method,
const map<string, string> &vars) {
const map< ::grpc::string, ::grpc::string> &vars) {
// TODO(jcanizales): Print method comments.
printer->Print(vars, "- ($return_type$)$method_name$With");
@ -85,7 +84,7 @@ void PrintMethodSignature(Printer *printer, const MethodDescriptor *method,
}
void PrintSimpleSignature(Printer *printer, const MethodDescriptor *method,
map<string, string> vars) {
map< ::grpc::string, ::grpc::string> vars) {
vars["method_name"] =
grpc_generator::LowercaseFirstLetter(vars["method_name"]);
vars["return_type"] = "void";
@ -93,14 +92,14 @@ void PrintSimpleSignature(Printer *printer, const MethodDescriptor *method,
}
void PrintAdvancedSignature(Printer *printer, const MethodDescriptor *method,
map<string, string> vars) {
map< ::grpc::string, ::grpc::string> vars) {
vars["method_name"] = "RPCTo" + vars["method_name"];
vars["return_type"] = "ProtoRPC *";
PrintMethodSignature(printer, method, vars);
}
inline map<string, string> GetMethodVars(const MethodDescriptor *method) {
map<string, string> res;
inline map< ::grpc::string, ::grpc::string> GetMethodVars(const MethodDescriptor *method) {
map< ::grpc::string, ::grpc::string> res;
res["method_name"] = method->name();
res["request_type"] = method->input_type()->name();
res["response_type"] = method->output_type()->name();
@ -110,7 +109,7 @@ inline map<string, string> GetMethodVars(const MethodDescriptor *method) {
}
void PrintMethodDeclarations(Printer *printer, const MethodDescriptor *method) {
map<string, string> vars = GetMethodVars(method);
map< ::grpc::string, ::grpc::string> vars = GetMethodVars(method);
PrintProtoRpcDeclarationAsPragma(printer, method, vars);
@ -121,7 +120,7 @@ void PrintMethodDeclarations(Printer *printer, const MethodDescriptor *method) {
}
void PrintSimpleImplementation(Printer *printer, const MethodDescriptor *method,
map<string, string> vars) {
map< ::grpc::string, ::grpc::string> vars) {
printer->Print("{\n");
printer->Print(vars, " [[self RPCTo$method_name$With");
if (method->client_streaming()) {
@ -139,7 +138,7 @@ void PrintSimpleImplementation(Printer *printer, const MethodDescriptor *method,
void PrintAdvancedImplementation(Printer *printer,
const MethodDescriptor *method,
map<string, string> vars) {
map< ::grpc::string, ::grpc::string> vars) {
printer->Print("{\n");
printer->Print(vars, " return [self RPCToMethod:@\"$method_name$\"\n");
@ -164,7 +163,7 @@ void PrintAdvancedImplementation(Printer *printer,
void PrintMethodImplementations(Printer *printer,
const MethodDescriptor *method) {
map<string, string> vars = GetMethodVars(method);
map< ::grpc::string, ::grpc::string> vars = GetMethodVars(method);
PrintProtoRpcDeclarationAsPragma(printer, method, vars);
@ -179,14 +178,14 @@ void PrintMethodImplementations(Printer *printer,
} // namespace
string GetHeader(const ServiceDescriptor *service) {
string output;
::grpc::string GetHeader(const ServiceDescriptor *service) {
::grpc::string output;
{
// Scope the output stream so it closes and finalizes output to the string.
grpc::protobuf::io::StringOutputStream output_stream(&output);
Printer printer(&output_stream, '$');
map<string, string> vars = {{"service_class", ServiceClassName(service)}};
map< ::grpc::string, ::grpc::string> vars = {{"service_class", ServiceClassName(service)}};
printer.Print(vars, "@protocol $service_class$ <NSObject>\n\n");
@ -209,14 +208,14 @@ string GetHeader(const ServiceDescriptor *service) {
return output;
}
string GetSource(const ServiceDescriptor *service) {
string output;
::grpc::string GetSource(const ServiceDescriptor *service) {
::grpc::string output;
{
// Scope the output stream so it closes and finalizes output to the string.
grpc::protobuf::io::StringOutputStream output_stream(&output);
Printer printer(&output_stream, '$');
map<string, string> vars = {{"service_name", service->name()},
map< ::grpc::string,::grpc::string> vars = {{"service_name", service->name()},
{"service_class", ServiceClassName(service)},
{"package", service->file()->package()}};

@ -39,44 +39,43 @@
#include "src/compiler/objective_c_generator.h"
#include "src/compiler/objective_c_generator_helpers.h"
using ::grpc::string;
class ObjectiveCGrpcGenerator : public grpc::protobuf::compiler::CodeGenerator {
public:
ObjectiveCGrpcGenerator() {}
virtual ~ObjectiveCGrpcGenerator() {}
virtual bool Generate(const grpc::protobuf::FileDescriptor *file,
const string &parameter,
const ::grpc::string &parameter,
grpc::protobuf::compiler::GeneratorContext *context,
string *error) const {
::grpc::string *error) const {
if (file->service_count() == 0) {
// No services. Do nothing.
return true;
}
string file_name = grpc_generator::FileNameInUpperCamel(file);
string prefix = file->options().objc_class_prefix();
::grpc::string file_name = grpc_generator::FileNameInUpperCamel(file);
::grpc::string prefix = file->options().objc_class_prefix();
{
// Generate .pbrpc.h
string imports = string("#import \"") + file_name + ".pbobjc.h\"\n\n"
::grpc::string imports = ::grpc::string("#import \"") + file_name +
".pbobjc.h\"\n\n"
"#import <ProtoRPC/ProtoService.h>\n"
"#import <RxLibrary/GRXWriteable.h>\n"
"#import <RxLibrary/GRXWriter.h>\n";
// TODO(jcanizales): Instead forward-declare the input and output types
// and import the files in the .pbrpc.m
string proto_imports;
::grpc::string proto_imports;
for (int i = 0; i < file->dependency_count(); i++) {
string header = grpc_objective_c_generator::MessageHeaderName(
::grpc::string header = grpc_objective_c_generator::MessageHeaderName(
file->dependency(i));
proto_imports += string("#import \"") + header + "\"\n";
proto_imports += ::grpc::string("#import \"") + header + "\"\n";
}
string declarations;
::grpc::string declarations;
for (int i = 0; i < file->service_count(); i++) {
const grpc::protobuf::ServiceDescriptor *service = file->service(i);
declarations += grpc_objective_c_generator::GetHeader(service);
@ -89,11 +88,12 @@ class ObjectiveCGrpcGenerator : public grpc::protobuf::compiler::CodeGenerator {
{
// Generate .pbrpc.m
string imports = string("#import \"") + file_name + ".pbrpc.h\"\n\n"
::grpc::string imports = ::grpc::string("#import \"") + file_name +
".pbrpc.h\"\n\n"
"#import <ProtoRPC/ProtoRPC.h>\n"
"#import <RxLibrary/GRXWriter+Immediate.h>\n";
string definitions;
::grpc::string definitions;
for (int i = 0; i < file->service_count(); i++) {
const grpc::protobuf::ServiceDescriptor *service = file->service(i);
definitions += grpc_objective_c_generator::GetSource(service);
@ -108,7 +108,7 @@ class ObjectiveCGrpcGenerator : public grpc::protobuf::compiler::CodeGenerator {
private:
// Write the given code into the given file.
void Write(grpc::protobuf::compiler::GeneratorContext *context,
const string &filename, const string &code) const {
const ::grpc::string &filename, const ::grpc::string &code) const {
std::unique_ptr<grpc::protobuf::io::ZeroCopyOutputStream> output(
context->Open(filename));
grpc::protobuf::io::CodedOutputStream coded_out(output.get());

@ -0,0 +1,501 @@
/*
*
* Copyright 2015, Google Inc.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
* met:
*
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* * Redistributions in binary form must reproduce the above
* copyright notice, this list of conditions and the following disclaimer
* in the documentation and/or other materials provided with the
* distribution.
* * Neither the name of Google Inc. nor the names of its
* contributors may be used to endorse or promote products derived from
* this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
* OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
*/
#include "src/core/client_config/resolvers/zookeeper_resolver.h"
#include <string.h>
#include <grpc/support/alloc.h>
#include <grpc/support/string_util.h>
#include <grpc/grpc_zookeeper.h>
#include <zookeeper/zookeeper.h>
#include "src/core/client_config/lb_policies/pick_first.h"
#include "src/core/client_config/resolver_registry.h"
#include "src/core/iomgr/resolve_address.h"
#include "src/core/support/string.h"
#include "src/core/json/json.h"
/** Zookeeper session expiration time in milliseconds */
#define GRPC_ZOOKEEPER_SESSION_TIMEOUT 15000
typedef struct {
/** base class: must be first */
grpc_resolver base;
/** refcount */
gpr_refcount refs;
/** name to resolve */
char *name;
/** subchannel factory */
grpc_subchannel_factory *subchannel_factory;
/** load balancing policy factory */
grpc_lb_policy *(*lb_policy_factory)(grpc_subchannel **subchannels,
size_t num_subchannels);
/** mutex guarding the rest of the state */
gpr_mu mu;
/** are we currently resolving? */
int resolving;
/** which version of resolved_config have we published? */
int published_version;
/** which version of resolved_config is current? */
int resolved_version;
/** pending next completion, or NULL */
grpc_iomgr_closure *next_completion;
/** target config address for next completion */
grpc_client_config **target_config;
/** current (fully resolved) config */
grpc_client_config *resolved_config;
/** zookeeper handle */
zhandle_t *zookeeper_handle;
/** zookeeper resolved addresses */
grpc_resolved_addresses *resolved_addrs;
/** total number of addresses to be resolved */
int resolved_total;
/** number of addresses resolved */
int resolved_num;
} zookeeper_resolver;
static void zookeeper_destroy(grpc_resolver *r);
static void zookeeper_start_resolving_locked(zookeeper_resolver *r);
static void zookeeper_maybe_finish_next_locked(zookeeper_resolver *r);
static void zookeeper_shutdown(grpc_resolver *r);
static void zookeeper_channel_saw_error(grpc_resolver *r,
struct sockaddr *failing_address,
int failing_address_len);
static void zookeeper_next(grpc_resolver *r, grpc_client_config **target_config,
grpc_iomgr_closure *on_complete);
static const grpc_resolver_vtable zookeeper_resolver_vtable = {
zookeeper_destroy, zookeeper_shutdown, zookeeper_channel_saw_error,
zookeeper_next};
static void zookeeper_shutdown(grpc_resolver *resolver) {
zookeeper_resolver *r = (zookeeper_resolver *)resolver;
gpr_mu_lock(&r->mu);
if (r->next_completion != NULL) {
*r->target_config = NULL;
grpc_iomgr_add_callback(r->next_completion);
r->next_completion = NULL;
}
zookeeper_close(r->zookeeper_handle);
gpr_mu_unlock(&r->mu);
}
static void zookeeper_channel_saw_error(grpc_resolver *resolver,
struct sockaddr *sa, int len) {
zookeeper_resolver *r = (zookeeper_resolver *)resolver;
gpr_mu_lock(&r->mu);
if (r->resolving == 0) {
zookeeper_start_resolving_locked(r);
}
gpr_mu_unlock(&r->mu);
}
static void zookeeper_next(grpc_resolver *resolver,
grpc_client_config **target_config,
grpc_iomgr_closure *on_complete) {
zookeeper_resolver *r = (zookeeper_resolver *)resolver;
gpr_mu_lock(&r->mu);
GPR_ASSERT(r->next_completion == NULL);
r->next_completion = on_complete;
r->target_config = target_config;
if (r->resolved_version == 0 && r->resolving == 0) {
zookeeper_start_resolving_locked(r);
} else {
zookeeper_maybe_finish_next_locked(r);
}
gpr_mu_unlock(&r->mu);
}
/** Zookeeper global watcher for connection management
TODO: better connection management besides logs */
static void zookeeper_global_watcher(zhandle_t *zookeeper_handle, int type,
int state, const char *path,
void *watcher_ctx) {
if (type == ZOO_SESSION_EVENT) {
if (state == ZOO_EXPIRED_SESSION_STATE) {
gpr_log(GPR_ERROR, "Zookeeper session expired");
} else if (state == ZOO_AUTH_FAILED_STATE) {
gpr_log(GPR_ERROR, "Zookeeper authentication failed");
}
}
}
/** Zookeeper watcher triggered by changes to watched nodes
Once triggered, it tries to resolve again to get updated addresses */
static void zookeeper_watcher(zhandle_t *zookeeper_handle, int type, int state,
const char *path, void *watcher_ctx) {
if (watcher_ctx != NULL) {
zookeeper_resolver *r = (zookeeper_resolver *)watcher_ctx;
if (state == ZOO_CONNECTED_STATE) {
gpr_mu_lock(&r->mu);
if (r->resolving == 0) {
zookeeper_start_resolving_locked(r);
}
gpr_mu_unlock(&r->mu);
}
}
}
/** Callback function after getting all resolved addresses
Creates a subchannel for each address */
static void zookeeper_on_resolved(void *arg,
grpc_resolved_addresses *addresses) {
zookeeper_resolver *r = arg;
grpc_client_config *config = NULL;
grpc_subchannel **subchannels;
grpc_subchannel_args args;
grpc_lb_policy *lb_policy;
size_t i;
if (addresses != NULL) {
config = grpc_client_config_create();
subchannels = gpr_malloc(sizeof(grpc_subchannel *) * addresses->naddrs);
for (i = 0; i < addresses->naddrs; i++) {
memset(&args, 0, sizeof(args));
args.addr = (struct sockaddr *)(addresses->addrs[i].addr);
args.addr_len = addresses->addrs[i].len;
subchannels[i] = grpc_subchannel_factory_create_subchannel(
r->subchannel_factory, &args);
}
lb_policy = r->lb_policy_factory(subchannels, addresses->naddrs);
grpc_client_config_set_lb_policy(config, lb_policy);
GRPC_LB_POLICY_UNREF(lb_policy, "construction");
grpc_resolved_addresses_destroy(addresses);
gpr_free(subchannels);
}
gpr_mu_lock(&r->mu);
GPR_ASSERT(r->resolving == 1);
r->resolving = 0;
if (r->resolved_config != NULL) {
grpc_client_config_unref(r->resolved_config);
}
r->resolved_config = config;
r->resolved_version++;
zookeeper_maybe_finish_next_locked(r);
gpr_mu_unlock(&r->mu);
GRPC_RESOLVER_UNREF(&r->base, "zookeeper-resolving");
}
/** Callback function for each DNS resolved address */
static void zookeeper_dns_resolved(void *arg,
grpc_resolved_addresses *addresses) {
size_t i;
zookeeper_resolver *r = arg;
int resolve_done = 0;
gpr_mu_lock(&r->mu);
r->resolved_num++;
r->resolved_addrs->addrs =
gpr_realloc(r->resolved_addrs->addrs,
sizeof(grpc_resolved_address) *
(r->resolved_addrs->naddrs + addresses->naddrs));
for (i = 0; i < addresses->naddrs; i++) {
memcpy(r->resolved_addrs->addrs[i + r->resolved_addrs->naddrs].addr,
addresses->addrs[i].addr, addresses->addrs[i].len);
r->resolved_addrs->addrs[i + r->resolved_addrs->naddrs].len =
addresses->addrs[i].len;
}
r->resolved_addrs->naddrs += addresses->naddrs;
grpc_resolved_addresses_destroy(addresses);
/** Wait for all addresses to be resolved */
resolve_done = (r->resolved_num == r->resolved_total);
gpr_mu_unlock(&r->mu);
if (resolve_done) {
zookeeper_on_resolved(r, r->resolved_addrs);
}
}
/** Parses JSON format address of a zookeeper node */
static char *zookeeper_parse_address(const char *value, int value_len) {
grpc_json *json;
grpc_json *cur;
const char *host;
const char *port;
char* buffer;
char *address = NULL;
buffer = gpr_malloc(value_len);
memcpy(buffer, value, value_len);
json = grpc_json_parse_string_with_len(buffer, value_len);
if (json != NULL) {
host = NULL;
port = NULL;
for (cur = json->child; cur != NULL; cur = cur->next) {
if (!strcmp(cur->key, "host")) {
host = cur->value;
if (port != NULL) {
break;
}
} else if (!strcmp(cur->key, "port")) {
port = cur->value;
if (host != NULL) {
break;
}
}
}
if (host != NULL && port != NULL) {
gpr_asprintf(&address, "%s:%s", host, port);
}
grpc_json_destroy(json);
}
gpr_free(buffer);
return address;
}
static void zookeeper_get_children_node_completion(int rc, const char *value,
int value_len,
const struct Stat *stat,
const void *arg) {
char *address = NULL;
zookeeper_resolver *r = (zookeeper_resolver *)arg;
int resolve_done = 0;
if (rc != 0) {
gpr_log(GPR_ERROR, "Error in getting a child node of %s", r->name);
return;
}
address = zookeeper_parse_address(value, value_len);
if (address != NULL) {
/** Further resolves address by DNS */
grpc_resolve_address(address, NULL, zookeeper_dns_resolved, r);
gpr_free(address);
} else {
gpr_log(GPR_ERROR, "Error in resolving a child node of %s", r->name);
gpr_mu_lock(&r->mu);
r->resolved_total--;
resolve_done = (r->resolved_num == r->resolved_total);
gpr_mu_unlock(&r->mu);
if (resolve_done) {
zookeeper_on_resolved(r, r->resolved_addrs);
}
}
}
static void zookeeper_get_children_completion(
int rc, const struct String_vector *children, const void *arg) {
char *path;
int status;
int i;
zookeeper_resolver *r = (zookeeper_resolver *)arg;
if (rc != 0) {
gpr_log(GPR_ERROR, "Error in getting zookeeper children of %s", r->name);
return;
}
if (children->count == 0) {
gpr_log(GPR_ERROR, "Error in resolving zookeeper address %s", r->name);
return;
}
r->resolved_addrs = gpr_malloc(sizeof(grpc_resolved_addresses));
r->resolved_addrs->addrs = NULL;
r->resolved_addrs->naddrs = 0;
r->resolved_total = children->count;
/** TODO: Replace expensive heap allocation with stack
if we can get maximum length of zookeeper path */
for (i = 0; i < children->count; i++) {
gpr_asprintf(&path, "%s/%s", r->name, children->data[i]);
status = zoo_awget(r->zookeeper_handle, path, zookeeper_watcher, r,
zookeeper_get_children_node_completion, r);
gpr_free(path);
if (status != 0) {
gpr_log(GPR_ERROR, "Error in getting zookeeper node %s", path);
}
}
}
static void zookeeper_get_node_completion(int rc, const char *value,
int value_len,
const struct Stat *stat,
const void *arg) {
int status;
char *address = NULL;
zookeeper_resolver *r = (zookeeper_resolver *)arg;
r->resolved_addrs = NULL;
r->resolved_total = 0;
r->resolved_num = 0;
if (rc != 0) {
gpr_log(GPR_ERROR, "Error in getting zookeeper node %s", r->name);
return;
}
/** If zookeeper node of path r->name does not have address
(i.e. service node), get its children */
address = zookeeper_parse_address(value, value_len);
if (address != NULL) {
r->resolved_addrs = gpr_malloc(sizeof(grpc_resolved_addresses));
r->resolved_addrs->addrs = NULL;
r->resolved_addrs->naddrs = 0;
r->resolved_total = 1;
/** Further resolves address by DNS */
grpc_resolve_address(address, NULL, zookeeper_dns_resolved, r);
gpr_free(address);
return;
}
status = zoo_awget_children(r->zookeeper_handle, r->name, zookeeper_watcher,
r, zookeeper_get_children_completion, r);
if (status != 0) {
gpr_log(GPR_ERROR, "Error in getting zookeeper children of %s", r->name);
}
}
static void zookeeper_resolve_address(zookeeper_resolver *r) {
int status;
status = zoo_awget(r->zookeeper_handle, r->name, zookeeper_watcher, r,
zookeeper_get_node_completion, r);
if (status != 0) {
gpr_log(GPR_ERROR, "Error in getting zookeeper node %s", r->name);
}
}
static void zookeeper_start_resolving_locked(zookeeper_resolver *r) {
GRPC_RESOLVER_REF(&r->base, "zookeeper-resolving");
GPR_ASSERT(r->resolving == 0);
r->resolving = 1;
zookeeper_resolve_address(r);
}
static void zookeeper_maybe_finish_next_locked(zookeeper_resolver *r) {
if (r->next_completion != NULL &&
r->resolved_version != r->published_version) {
*r->target_config = r->resolved_config;
if (r->resolved_config != NULL) {
grpc_client_config_ref(r->resolved_config);
}
grpc_iomgr_add_callback(r->next_completion);
r->next_completion = NULL;
r->published_version = r->resolved_version;
}
}
static void zookeeper_destroy(grpc_resolver *gr) {
zookeeper_resolver *r = (zookeeper_resolver *)gr;
gpr_mu_destroy(&r->mu);
if (r->resolved_config != NULL) {
grpc_client_config_unref(r->resolved_config);
}
grpc_subchannel_factory_unref(r->subchannel_factory);
gpr_free(r->name);
gpr_free(r);
}
static grpc_resolver *zookeeper_create(
grpc_uri *uri,
grpc_lb_policy *(*lb_policy_factory)(grpc_subchannel **subchannels,
size_t num_subchannels),
grpc_subchannel_factory *subchannel_factory) {
zookeeper_resolver *r;
size_t length;
char *path = uri->path;
if (0 == strcmp(uri->authority, "")) {
gpr_log(GPR_ERROR, "No authority specified in zookeeper uri");
return NULL;
}
/** Removes the trailing slash if exists */
length = strlen(path);
if (length > 1 && path[length - 1] == '/') {
path[length - 1] = 0;
}
r = gpr_malloc(sizeof(zookeeper_resolver));
memset(r, 0, sizeof(*r));
gpr_ref_init(&r->refs, 1);
gpr_mu_init(&r->mu);
grpc_resolver_init(&r->base, &zookeeper_resolver_vtable);
r->name = gpr_strdup(path);
r->subchannel_factory = subchannel_factory;
r->lb_policy_factory = lb_policy_factory;
grpc_subchannel_factory_ref(subchannel_factory);
/** Initializes zookeeper client */
zoo_set_debug_level(ZOO_LOG_LEVEL_WARN);
r->zookeeper_handle = zookeeper_init(uri->authority, zookeeper_global_watcher,
GRPC_ZOOKEEPER_SESSION_TIMEOUT, 0, 0, 0);
if (r->zookeeper_handle == NULL) {
gpr_log(GPR_ERROR, "Unable to connect to zookeeper server");
return NULL;
}
return &r->base;
}
static void zookeeper_plugin_init() {
grpc_register_resolver_type("zookeeper",
grpc_zookeeper_resolver_factory_create());
}
void grpc_zookeeper_register() {
grpc_register_plugin(zookeeper_plugin_init, NULL);
}
/*
* FACTORY
*/
static void zookeeper_factory_ref(grpc_resolver_factory *factory) {}
static void zookeeper_factory_unref(grpc_resolver_factory *factory) {}
static grpc_resolver *zookeeper_factory_create_resolver(
grpc_resolver_factory *factory, grpc_uri *uri,
grpc_subchannel_factory *subchannel_factory) {
return zookeeper_create(uri, grpc_create_pick_first_lb_policy,
subchannel_factory);
}
static const grpc_resolver_factory_vtable zookeeper_factory_vtable = {
zookeeper_factory_ref, zookeeper_factory_unref,
zookeeper_factory_create_resolver};
static grpc_resolver_factory zookeeper_resolver_factory = {
&zookeeper_factory_vtable};
grpc_resolver_factory *grpc_zookeeper_resolver_factory_create() {
return &zookeeper_resolver_factory;
}

@ -0,0 +1,42 @@
/*
*
* Copyright 2015, Google Inc.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
* met:
*
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* * Redistributions in binary form must reproduce the above
* copyright notice, this list of conditions and the following disclaimer
* in the documentation and/or other materials provided with the
* distribution.
* * Neither the name of Google Inc. nor the names of its
* contributors may be used to endorse or promote products derived from
* this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
* OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
*/
#ifndef GRPC_INTERNAL_CORE_CLIENT_CONFIG_RESOLVERS_ZOOKEEPER_RESOLVER_H
#define GRPC_INTERNAL_CORE_CLIENT_CONFIG_RESOLVERS_ZOOKEEPER_RESOLVER_H
#include "src/core/client_config/resolver_factory.h"
/** Create a zookeeper resolver factory */
grpc_resolver_factory *grpc_zookeeper_resolver_factory_create(void);
#endif /* GRPC_INTERNAL_CORE_CLIENT_CONFIG_RESOLVERS_ZOOKEEPER_RESOLVER_H */

@ -37,7 +37,7 @@
int grpc_compression_algorithm_parse(const char* name,
grpc_compression_algorithm *algorithm) {
if (strcmp(name, "none") == 0) {
if (strcmp(name, "identity") == 0) {
*algorithm = GRPC_COMPRESS_NONE;
} else if (strcmp(name, "gzip") == 0) {
*algorithm = GRPC_COMPRESS_GZIP;
@ -53,7 +53,7 @@ int grpc_compression_algorithm_name(grpc_compression_algorithm algorithm,
char **name) {
switch (algorithm) {
case GRPC_COMPRESS_NONE:
*name = "none";
*name = "identity";
break;
case GRPC_COMPRESS_DEFLATE:
*name = "deflate";

@ -0,0 +1,438 @@
/*
*
* Copyright 2015, Google Inc.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
* met:
*
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* * Redistributions in binary form must reproduce the above
* copyright notice, this list of conditions and the following disclaimer
* in the documentation and/or other materials provided with the
* distribution.
* * Neither the name of Google Inc. nor the names of its
* contributors may be used to endorse or promote products derived from
* this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
* OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
*/
/* FIXME: "posix" files shouldn't be depending on _GNU_SOURCE */
#ifndef _GNU_SOURCE
#define _GNU_SOURCE
#endif
#include <grpc/support/port_platform.h>
#ifdef GPR_POSIX_SOCKET
#include "src/core/iomgr/udp_server.h"
#include <errno.h>
#include <fcntl.h>
#include <limits.h>
#include <netinet/in.h>
#include <netinet/tcp.h>
#include <string.h>
#include <sys/socket.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <sys/un.h>
#include <unistd.h>
#include "src/core/iomgr/fd_posix.h"
#include "src/core/iomgr/pollset_posix.h"
#include "src/core/iomgr/resolve_address.h"
#include "src/core/iomgr/sockaddr_utils.h"
#include "src/core/iomgr/socket_utils_posix.h"
#include "src/core/support/string.h"
#include <grpc/support/alloc.h>
#include <grpc/support/log.h>
#include <grpc/support/sync.h>
#include <grpc/support/string_util.h>
#include <grpc/support/time.h>
#define INIT_PORT_CAP 2
/* one listening port */
typedef struct {
int fd;
grpc_fd *emfd;
grpc_udp_server *server;
union {
gpr_uint8 untyped[GRPC_MAX_SOCKADDR_SIZE];
struct sockaddr sockaddr;
struct sockaddr_un un;
} addr;
int addr_len;
grpc_iomgr_closure read_closure;
grpc_iomgr_closure destroyed_closure;
grpc_udp_server_read_cb read_cb;
} server_port;
static void unlink_if_unix_domain_socket(const struct sockaddr_un *un) {
struct stat st;
if (stat(un->sun_path, &st) == 0 && (st.st_mode & S_IFMT) == S_IFSOCK) {
unlink(un->sun_path);
}
}
/* the overall server */
struct grpc_udp_server {
grpc_udp_server_cb cb;
void *cb_arg;
gpr_mu mu;
gpr_cv cv;
/* active port count: how many ports are actually still listening */
size_t active_ports;
/* destroyed port count: how many ports are completely destroyed */
size_t destroyed_ports;
/* is this server shutting down? (boolean) */
int shutdown;
/* all listening ports */
server_port *ports;
size_t nports;
size_t port_capacity;
/* shutdown callback */
void (*shutdown_complete)(void *);
void *shutdown_complete_arg;
/* all pollsets interested in new connections */
grpc_pollset **pollsets;
/* number of pollsets in the pollsets array */
size_t pollset_count;
};
grpc_udp_server *grpc_udp_server_create(void) {
grpc_udp_server *s = gpr_malloc(sizeof(grpc_udp_server));
gpr_mu_init(&s->mu);
gpr_cv_init(&s->cv);
s->active_ports = 0;
s->destroyed_ports = 0;
s->shutdown = 0;
s->cb = NULL;
s->cb_arg = NULL;
s->ports = gpr_malloc(sizeof(server_port) * INIT_PORT_CAP);
s->nports = 0;
s->port_capacity = INIT_PORT_CAP;
return s;
}
static void finish_shutdown(grpc_udp_server *s) {
s->shutdown_complete(s->shutdown_complete_arg);
gpr_mu_destroy(&s->mu);
gpr_cv_destroy(&s->cv);
gpr_free(s->ports);
gpr_free(s);
}
static void destroyed_port(void *server, int success) {
grpc_udp_server *s = server;
gpr_mu_lock(&s->mu);
s->destroyed_ports++;
if (s->destroyed_ports == s->nports) {
gpr_mu_unlock(&s->mu);
finish_shutdown(s);
} else {
gpr_mu_unlock(&s->mu);
}
}
static void dont_care_about_shutdown_completion(void *ignored) {}
/* called when all listening endpoints have been shutdown, so no further
events will be received on them - at this point it's safe to destroy
things */
static void deactivated_all_ports(grpc_udp_server *s) {
size_t i;
/* delete ALL the things */
gpr_mu_lock(&s->mu);
if (!s->shutdown) {
gpr_mu_unlock(&s->mu);
return;
}
if (s->nports) {
for (i = 0; i < s->nports; i++) {
server_port *sp = &s->ports[i];
if (sp->addr.sockaddr.sa_family == AF_UNIX) {
unlink_if_unix_domain_socket(&sp->addr.un);
}
sp->destroyed_closure.cb = destroyed_port;
sp->destroyed_closure.cb_arg = s;
grpc_fd_orphan(sp->emfd, &sp->destroyed_closure, "udp_listener_shutdown");
}
gpr_mu_unlock(&s->mu);
} else {
gpr_mu_unlock(&s->mu);
finish_shutdown(s);
}
}
void grpc_udp_server_destroy(
grpc_udp_server *s, void (*shutdown_complete)(void *shutdown_complete_arg),
void *shutdown_complete_arg) {
size_t i;
gpr_mu_lock(&s->mu);
GPR_ASSERT(!s->shutdown);
s->shutdown = 1;
s->shutdown_complete = shutdown_complete
? shutdown_complete
: dont_care_about_shutdown_completion;
s->shutdown_complete_arg = shutdown_complete_arg;
/* shutdown all fd's */
if (s->active_ports) {
for (i = 0; i < s->nports; i++) {
grpc_fd_shutdown(s->ports[i].emfd);
}
gpr_mu_unlock(&s->mu);
} else {
gpr_mu_unlock(&s->mu);
deactivated_all_ports(s);
}
}
/* Prepare a recently-created socket for listening. */
static int prepare_socket(int fd, const struct sockaddr *addr, int addr_len) {
struct sockaddr_storage sockname_temp;
socklen_t sockname_len;
int get_local_ip;
int rc;
if (fd < 0) {
goto error;
}
get_local_ip = 1;
rc = setsockopt(fd, IPPROTO_IP, IP_PKTINFO,
&get_local_ip, sizeof(get_local_ip));
if (rc == 0 && addr->sa_family == AF_INET6) {
rc = setsockopt(fd, IPPROTO_IPV6, IPV6_RECVPKTINFO,
&get_local_ip, sizeof(get_local_ip));
}
if (bind(fd, addr, addr_len) < 0) {
char *addr_str;
grpc_sockaddr_to_string(&addr_str, addr, 0);
gpr_log(GPR_ERROR, "bind addr=%s: %s", addr_str, strerror(errno));
gpr_free(addr_str);
goto error;
}
sockname_len = sizeof(sockname_temp);
if (getsockname(fd, (struct sockaddr *)&sockname_temp, &sockname_len) < 0) {
goto error;
}
return grpc_sockaddr_get_port((struct sockaddr *)&sockname_temp);
error:
if (fd >= 0) {
close(fd);
}
return -1;
}
/* event manager callback when reads are ready */
static void on_read(void *arg, int success) {
server_port *sp = arg;
if (success == 0) {
gpr_mu_lock(&sp->server->mu);
if (0 == --sp->server->active_ports) {
gpr_mu_unlock(&sp->server->mu);
deactivated_all_ports(sp->server);
} else {
gpr_mu_unlock(&sp->server->mu);
}
return;
}
/* Tell the registered callback that data is available to read. */
GPR_ASSERT(sp->read_cb);
sp->read_cb(sp->fd, sp->server->cb, sp->server->cb_arg);
/* Re-arm the notification event so we get another chance to read. */
grpc_fd_notify_on_read(sp->emfd, &sp->read_closure);
}
static int add_socket_to_server(grpc_udp_server *s, int fd,
const struct sockaddr *addr, int addr_len,
grpc_udp_server_read_cb read_cb) {
server_port *sp;
int port;
char *addr_str;
char *name;
port = prepare_socket(fd, addr, addr_len);
if (port >= 0) {
grpc_sockaddr_to_string(&addr_str, (struct sockaddr *)&addr, 1);
gpr_asprintf(&name, "udp-server-listener:%s", addr_str);
gpr_mu_lock(&s->mu);
GPR_ASSERT(!s->cb && "must add ports before starting server");
/* append it to the list under a lock */
if (s->nports == s->port_capacity) {
s->port_capacity *= 2;
s->ports = gpr_realloc(s->ports, sizeof(server_port) * s->port_capacity);
}
sp = &s->ports[s->nports++];
sp->server = s;
sp->fd = fd;
sp->emfd = grpc_fd_create(fd, name);
memcpy(sp->addr.untyped, addr, addr_len);
sp->addr_len = addr_len;
sp->read_cb = read_cb;
GPR_ASSERT(sp->emfd);
gpr_mu_unlock(&s->mu);
}
return port;
}
int grpc_udp_server_add_port(grpc_udp_server *s, const void *addr,
int addr_len, grpc_udp_server_read_cb read_cb) {
int allocated_port1 = -1;
int allocated_port2 = -1;
unsigned i;
int fd;
grpc_dualstack_mode dsmode;
struct sockaddr_in6 addr6_v4mapped;
struct sockaddr_in wild4;
struct sockaddr_in6 wild6;
struct sockaddr_in addr4_copy;
struct sockaddr *allocated_addr = NULL;
struct sockaddr_storage sockname_temp;
socklen_t sockname_len;
int port;
if (((struct sockaddr *)addr)->sa_family == AF_UNIX) {
unlink_if_unix_domain_socket(addr);
}
/* Check if this is a wildcard port, and if so, try to keep the port the same
as some previously created listener. */
if (grpc_sockaddr_get_port(addr) == 0) {
for (i = 0; i < s->nports; i++) {
sockname_len = sizeof(sockname_temp);
if (0 == getsockname(s->ports[i].fd, (struct sockaddr *)&sockname_temp,
&sockname_len)) {
port = grpc_sockaddr_get_port((struct sockaddr *)&sockname_temp);
if (port > 0) {
allocated_addr = malloc(addr_len);
memcpy(allocated_addr, addr, addr_len);
grpc_sockaddr_set_port(allocated_addr, port);
addr = allocated_addr;
break;
}
}
}
}
if (grpc_sockaddr_to_v4mapped(addr, &addr6_v4mapped)) {
addr = (const struct sockaddr *)&addr6_v4mapped;
addr_len = sizeof(addr6_v4mapped);
}
/* Treat :: or 0.0.0.0 as a family-agnostic wildcard. */
if (grpc_sockaddr_is_wildcard(addr, &port)) {
grpc_sockaddr_make_wildcards(port, &wild4, &wild6);
/* Try listening on IPv6 first. */
addr = (struct sockaddr *)&wild6;
addr_len = sizeof(wild6);
fd = grpc_create_dualstack_socket(addr, SOCK_DGRAM, IPPROTO_UDP, &dsmode);
allocated_port1 = add_socket_to_server(s, fd, addr, addr_len, read_cb);
if (fd >= 0 && dsmode == GRPC_DSMODE_DUALSTACK) {
goto done;
}
/* If we didn't get a dualstack socket, also listen on 0.0.0.0. */
if (port == 0 && allocated_port1 > 0) {
grpc_sockaddr_set_port((struct sockaddr *)&wild4, allocated_port1);
}
addr = (struct sockaddr *)&wild4;
addr_len = sizeof(wild4);
}
fd = grpc_create_dualstack_socket(addr, SOCK_DGRAM, IPPROTO_UDP, &dsmode);
if (fd < 0) {
gpr_log(GPR_ERROR, "Unable to create socket: %s", strerror(errno));
}
if (dsmode == GRPC_DSMODE_IPV4 &&
grpc_sockaddr_is_v4mapped(addr, &addr4_copy)) {
addr = (struct sockaddr *)&addr4_copy;
addr_len = sizeof(addr4_copy);
}
allocated_port2 = add_socket_to_server(s, fd, addr, addr_len, read_cb);
done:
gpr_free(allocated_addr);
return allocated_port1 >= 0 ? allocated_port1 : allocated_port2;
}
int grpc_udp_server_get_fd(grpc_udp_server *s, unsigned index) {
return (index < s->nports) ? s->ports[index].fd : -1;
}
void grpc_udp_server_start(grpc_udp_server *s, grpc_pollset **pollsets,
size_t pollset_count,
grpc_udp_server_cb new_transport_cb, void *cb_arg) {
size_t i, j;
GPR_ASSERT(new_transport_cb);
gpr_mu_lock(&s->mu);
GPR_ASSERT(!s->cb);
GPR_ASSERT(s->active_ports == 0);
s->cb = new_transport_cb;
s->cb_arg = cb_arg;
s->pollsets = pollsets;
for (i = 0; i < s->nports; i++) {
for (j = 0; j < pollset_count; j++) {
grpc_pollset_add_fd(pollsets[j], s->ports[i].emfd);
}
s->ports[i].read_closure.cb = on_read;
s->ports[i].read_closure.cb_arg = &s->ports[i];
grpc_fd_notify_on_read(s->ports[i].emfd, &s->ports[i].read_closure);
s->active_ports++;
}
gpr_mu_unlock(&s->mu);
}
/* TODO(rjshade): Add a test for this method. */
void grpc_udp_server_write(server_port *sp, const char *buffer, size_t buf_len,
const struct sockaddr *peer_address) {
int rc;
rc = sendto(sp->fd, buffer, buf_len, 0, peer_address, sizeof(peer_address));
if (rc < 0) {
gpr_log(GPR_ERROR, "Unable to send data: %s", strerror(errno));
}
}
#endif

@ -0,0 +1,85 @@
/*
*
* Copyright 2015, Google Inc.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
* met:
*
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* * Redistributions in binary form must reproduce the above
* copyright notice, this list of conditions and the following disclaimer
* in the documentation and/or other materials provided with the
* distribution.
* * Neither the name of Google Inc. nor the names of its
* contributors may be used to endorse or promote products derived from
* this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
* OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
*/
#ifndef GRPC_INTERNAL_CORE_IOMGR_UDP_SERVER_H
#define GRPC_INTERNAL_CORE_IOMGR_UDP_SERVER_H
#include "src/core/iomgr/endpoint.h"
/* Forward decl of grpc_udp_server */
typedef struct grpc_udp_server grpc_udp_server;
/* New server callback: ep is the newly connected connection */
typedef void (*grpc_udp_server_cb)(void *arg, grpc_endpoint *ep);
/* Called when data is available to read from the socket. */
typedef void (*grpc_udp_server_read_cb)(int fd,
grpc_udp_server_cb new_transport_cb,
void *cb_arg);
/* Create a server, initially not bound to any ports */
grpc_udp_server *grpc_udp_server_create(void);
/* Start listening to bound ports */
void grpc_udp_server_start(grpc_udp_server *server, grpc_pollset **pollsets,
size_t pollset_count, grpc_udp_server_cb cb,
void *cb_arg);
int grpc_udp_server_get_fd(grpc_udp_server *s, unsigned index);
/* Add a port to the server, returning port number on success, or negative
on failure.
The :: and 0.0.0.0 wildcard addresses are treated identically, accepting
both IPv4 and IPv6 connections, but :: is the preferred style. This usually
creates one socket, but possibly two on systems which support IPv6,
but not dualstack sockets. */
/* TODO(ctiller): deprecate this, and make grpc_udp_server_add_ports to handle
all of the multiple socket port matching logic in one place */
int grpc_udp_server_add_port(grpc_udp_server *s, const void *addr, int addr_len,
grpc_udp_server_read_cb read_cb);
void grpc_udp_server_destroy(grpc_udp_server *server,
void (*shutdown_done)(void *shutdown_done_arg),
void *shutdown_done_arg);
/* Write the contents of buffer to the underlying UDP socket. */
/*
void grpc_udp_server_write(grpc_udp_server *s,
const char *buffer,
int buf_len,
const struct sockaddr* to);
*/
#endif /* GRPC_INTERNAL_CORE_IOMGR_UDP_SERVER_H */

@ -1,157 +0,0 @@
/*
*
* Copyright 2015, Google Inc.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
* met:
*
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* * Redistributions in binary form must reproduce the above
* copyright notice, this list of conditions and the following disclaimer
* in the documentation and/or other materials provided with the
* distribution.
* * Neither the name of Google Inc. nor the names of its
* contributors may be used to endorse or promote products derived from
* this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
* OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
*/
/* Implementation for gpr_cancellable */
#include <grpc/support/atm.h>
#include <grpc/support/sync.h>
#include <grpc/support/time.h>
void gpr_cancellable_init(gpr_cancellable *c) {
gpr_mu_init(&c->mu);
c->cancelled = 0;
c->waiters.next = &c->waiters;
c->waiters.prev = &c->waiters;
c->waiters.mu = NULL;
c->waiters.cv = NULL;
}
void gpr_cancellable_destroy(gpr_cancellable *c) { gpr_mu_destroy(&c->mu); }
int gpr_cancellable_is_cancelled(gpr_cancellable *c) {
return gpr_atm_acq_load(&c->cancelled) != 0;
}
/* Threads in gpr_cv_cancellable_wait(cv, mu, ..., c) place themselves on a
linked list c->waiters of gpr_cancellable_list_ before waiting on their
condition variables. They check for cancellation while holding *mu. Thus,
to wake a thread from gpr_cv_cancellable_wait(), it suffices to:
- set c->cancelled
- acquire and release *mu
- gpr_cv_broadcast(cv)
However, gpr_cancellable_cancel() may not use gpr_mu_lock(mu), since the
caller may already hold *mu---a possible deadlock. (If we knew the caller
did not hold *mu, care would still be needed, because c->mu follows *mu in
the locking order, so *mu could not be acquired while holding c->mu---which
is needed to iterate over c->waiters.)
Therefore, gpr_cancellable_cancel() uses gpr_mu_trylock() rather than
gpr_mu_lock(), and retries until either gpr_mu_trylock() succeeds or the
thread leaves gpr_cv_cancellable_wait() for other reasons. In the first
case, gpr_cancellable_cancel() removes the entry from the waiters list; in
the second, the waiting thread removes itself from the list.
A one-entry cache of mutexes and condition variables processed is kept to
avoid doing the same work again and again if many threads are blocked in the
same place. However, it's important to broadcast on a condition variable if
the corresponding mutex has been locked successfully, even if the condition
variable has been signalled before. */
void gpr_cancellable_cancel(gpr_cancellable *c) {
if (!gpr_cancellable_is_cancelled(c)) {
int failures;
int backoff = 1;
do {
struct gpr_cancellable_list_ *l;
struct gpr_cancellable_list_ *nl;
gpr_mu *omu = 0; /* one-element cache of a processed gpr_mu */
gpr_cv *ocv = 0; /* one-element cache of a processd gpr_cv */
gpr_mu_lock(&c->mu);
gpr_atm_rel_store(&c->cancelled, 1);
failures = 0;
for (l = c->waiters.next; l != &c->waiters; l = nl) {
nl = l->next;
if (omu != l->mu) {
omu = l->mu;
if (gpr_mu_trylock(l->mu)) {
gpr_mu_unlock(l->mu);
l->next->prev = l->prev; /* remove *l from list */
l->prev->next = l->next;
/* allow unconditional dequeue in gpr_cv_cancellable_wait() */
l->next = l;
l->prev = l;
ocv = 0; /* force broadcast */
} else {
failures++;
}
}
if (ocv != l->cv) {
ocv = l->cv;
gpr_cv_broadcast(l->cv);
}
}
gpr_mu_unlock(&c->mu);
if (failures != 0) {
if (backoff < 10) {
volatile int i;
for (i = 0; i != (1 << backoff); i++) {
}
backoff++;
} else {
gpr_event ev;
gpr_event_init(&ev);
gpr_event_wait(
&ev, gpr_time_add(gpr_now(GPR_CLOCK_REALTIME),
gpr_time_from_micros(1000, GPR_TIMESPAN)));
}
}
} while (failures != 0);
}
}
int gpr_cv_cancellable_wait(gpr_cv *cv, gpr_mu *mu, gpr_timespec abs_deadline,
gpr_cancellable *c) {
gpr_int32 timeout;
gpr_mu_lock(&c->mu);
timeout = gpr_cancellable_is_cancelled(c);
if (!timeout) {
struct gpr_cancellable_list_ le;
le.mu = mu;
le.cv = cv;
le.next = c->waiters.next;
le.prev = &c->waiters;
le.next->prev = &le;
le.prev->next = &le;
gpr_mu_unlock(&c->mu);
timeout = gpr_cv_wait(cv, mu, abs_deadline);
gpr_mu_lock(&c->mu);
le.next->prev = le.prev;
le.prev->next = le.next;
if (!timeout) {
timeout = gpr_cancellable_is_cancelled(c);
}
}
gpr_mu_unlock(&c->mu);
return timeout;
}

@ -94,21 +94,6 @@ void *gpr_event_wait(gpr_event *ev, gpr_timespec abs_deadline) {
return result;
}
void *gpr_event_cancellable_wait(gpr_event *ev, gpr_timespec abs_deadline,
gpr_cancellable *c) {
void *result = (void *)gpr_atm_acq_load(&ev->state);
if (result == NULL) {
struct sync_array_s *s = hash(ev);
gpr_mu_lock(&s->mu);
do {
result = (void *)gpr_atm_acq_load(&ev->state);
} while (result == NULL &&
!gpr_cv_cancellable_wait(&s->cv, &s->mu, abs_deadline, c));
gpr_mu_unlock(&s->mu);
}
return result;
}
void gpr_ref_init(gpr_refcount *r, int n) { gpr_atm_rel_store(&r->count, n); }
void gpr_ref(gpr_refcount *r) { gpr_atm_no_barrier_fetch_add(&r->count, 1); }

@ -964,7 +964,7 @@ static void call_on_done_recv(void *pc, int success) {
next_child_call = child_call->sibling_next;
if (child_call->cancellation_is_inherited) {
GRPC_CALL_INTERNAL_REF(child_call, "propagate_cancel");
grpc_call_cancel(child_call);
grpc_call_cancel(child_call, NULL);
GRPC_CALL_INTERNAL_UNREF(child_call, "propagate_cancel", 0);
}
child_call = next_child_call;
@ -1265,18 +1265,22 @@ void grpc_call_destroy(grpc_call *c) {
c->cancel_alarm |= c->have_alarm;
cancel = c->read_state != READ_STATE_STREAM_CLOSED;
unlock(c);
if (cancel) grpc_call_cancel(c);
if (cancel) grpc_call_cancel(c, NULL);
GRPC_CALL_INTERNAL_UNREF(c, "destroy", 1);
}
grpc_call_error grpc_call_cancel(grpc_call *call) {
return grpc_call_cancel_with_status(call, GRPC_STATUS_CANCELLED, "Cancelled");
grpc_call_error grpc_call_cancel(grpc_call *call, void *reserved) {
GPR_ASSERT(!reserved);
return grpc_call_cancel_with_status(call, GRPC_STATUS_CANCELLED, "Cancelled",
NULL);
}
grpc_call_error grpc_call_cancel_with_status(grpc_call *c,
grpc_status_code status,
const char *description) {
const char *description,
void *reserved) {
grpc_call_error r;
(void) reserved;
lock(c);
r = cancel_with_status(c, status, description);
unlock(c);
@ -1513,13 +1517,14 @@ static int are_write_flags_valid(gpr_uint32 flags) {
}
grpc_call_error grpc_call_start_batch(grpc_call *call, const grpc_op *ops,
size_t nops, void *tag) {
size_t nops, void *tag, void *reserved) {
grpc_ioreq reqs[GRPC_IOREQ_OP_COUNT];
size_t in;
size_t out;
const grpc_op *op;
grpc_ioreq *req;
void (*finish_func)(grpc_call *, int, void *) = finish_batch;
GPR_ASSERT(!reserved);
GRPC_CALL_LOG_BATCH(GPR_INFO, call, ops, nops, tag);

@ -168,7 +168,8 @@ grpc_call *grpc_channel_create_call(grpc_channel *channel,
gpr_uint32 propagation_mask,
grpc_completion_queue *cq,
const char *method, const char *host,
gpr_timespec deadline) {
gpr_timespec deadline, void *reserved) {
GPR_ASSERT(!reserved);
return grpc_channel_create_call_internal(
channel, parent_call, propagation_mask, cq,
grpc_mdelem_from_metadata_strings(
@ -182,8 +183,9 @@ grpc_call *grpc_channel_create_call(grpc_channel *channel,
}
void *grpc_channel_register_call(grpc_channel *channel, const char *method,
const char *host) {
const char *host, void *reserved) {
registered_call *rc = gpr_malloc(sizeof(registered_call));
GPR_ASSERT(!reserved);
rc->path = grpc_mdelem_from_metadata_strings(
channel->metadata_context, GRPC_MDSTR_REF(channel->path_string),
grpc_mdstr_from_string(channel->metadata_context, method, 0));
@ -200,8 +202,9 @@ void *grpc_channel_register_call(grpc_channel *channel, const char *method,
grpc_call *grpc_channel_create_registered_call(
grpc_channel *channel, grpc_call *parent_call, gpr_uint32 propagation_mask,
grpc_completion_queue *completion_queue, void *registered_call_handle,
gpr_timespec deadline) {
gpr_timespec deadline, void *reserved) {
registered_call *rc = registered_call_handle;
GPR_ASSERT(!reserved);
return grpc_channel_create_call_internal(
channel, parent_call, propagation_mask, completion_queue,
GRPC_MDELEM_REF(rc->path),

@ -155,7 +155,8 @@ static const grpc_subchannel_factory_vtable subchannel_factory_vtable = {
- connect to it (trying alternatives as presented)
- perform handshakes */
grpc_channel *grpc_insecure_channel_create(const char *target,
const grpc_channel_args *args) {
const grpc_channel_args *args,
void *reserved) {
grpc_channel *channel = NULL;
#define MAX_FILTERS 3
const grpc_channel_filter *filters[MAX_FILTERS];
@ -163,6 +164,7 @@ grpc_channel *grpc_insecure_channel_create(const char *target,
subchannel_factory *f;
grpc_mdctx *mdctx = grpc_mdctx_create();
int n = 0;
GPR_ASSERT(!reserved);
/* TODO(census)
if (grpc_channel_args_is_census_enabled(args)) {
filters[n++] = &grpc_client_census_filter;

@ -69,8 +69,9 @@ struct grpc_completion_queue {
plucker pluckers[GRPC_MAX_COMPLETION_QUEUE_PLUCKERS];
};
grpc_completion_queue *grpc_completion_queue_create(void) {
grpc_completion_queue *grpc_completion_queue_create(void *reserved) {
grpc_completion_queue *cc = gpr_malloc(sizeof(grpc_completion_queue));
GPR_ASSERT(!reserved);
memset(cc, 0, sizeof(*cc));
/* Initial ref is dropped by grpc_completion_queue_shutdown */
gpr_ref_init(&cc->pending_events, 1);
@ -166,9 +167,11 @@ void grpc_cq_end_op(grpc_completion_queue *cc, void *tag, int success,
}
grpc_event grpc_completion_queue_next(grpc_completion_queue *cc,
gpr_timespec deadline) {
gpr_timespec deadline,
void *reserved) {
grpc_event ret;
grpc_pollset_worker worker;
GPR_ASSERT(!reserved);
deadline = gpr_convert_clock_type(deadline, GPR_CLOCK_MONOTONIC);
@ -232,11 +235,12 @@ static void del_plucker(grpc_completion_queue *cc, void *tag,
}
grpc_event grpc_completion_queue_pluck(grpc_completion_queue *cc, void *tag,
gpr_timespec deadline) {
gpr_timespec deadline, void *reserved) {
grpc_event ret;
grpc_cq_completion *c;
grpc_cq_completion *prev;
grpc_pollset_worker worker;
GPR_ASSERT(!reserved);
deadline = gpr_convert_clock_type(deadline, GPR_CLOCK_MONOTONIC);

@ -33,8 +33,11 @@
#include <grpc/support/port_platform.h>
#include <memory.h>
#include <grpc/census.h>
#include <grpc/grpc.h>
#include <grpc/support/alloc.h>
#include <grpc/support/time.h>
#include "src/core/channel/channel_stack.h"
#include "src/core/client_config/resolver_registry.h"
@ -49,6 +52,8 @@
#include "src/core/transport/chttp2_transport.h"
#include "src/core/transport/connectivity_state.h"
#define MAX_PLUGINS 128
static gpr_once g_basic_init = GPR_ONCE_INIT;
static gpr_mu g_init_mu;
static int g_initializations;
@ -58,7 +63,23 @@ static void do_basic_init(void) {
g_initializations = 0;
}
typedef struct grpc_plugin {
void (*init)();
void (*destroy)();
} grpc_plugin;
static grpc_plugin g_all_of_the_plugins[MAX_PLUGINS];
static int g_number_of_plugins = 0;
void grpc_register_plugin(void (*init)(void), void (*destroy)(void)) {
GPR_ASSERT(g_number_of_plugins != MAX_PLUGINS);
g_all_of_the_plugins[g_number_of_plugins].init = init;
g_all_of_the_plugins[g_number_of_plugins].destroy = destroy;
g_number_of_plugins++;
}
void grpc_init(void) {
int i;
gpr_once_init(&g_basic_init, do_basic_init);
gpr_mu_lock(&g_init_mu);
@ -87,11 +108,17 @@ void grpc_init(void) {
}
}
grpc_timers_global_init();
for (i = 0; i < g_number_of_plugins; i++) {
if (g_all_of_the_plugins[i].init != NULL) {
g_all_of_the_plugins[i].init();
}
}
}
gpr_mu_unlock(&g_init_mu);
}
void grpc_shutdown(void) {
int i;
gpr_mu_lock(&g_init_mu);
if (--g_initializations == 0) {
grpc_iomgr_shutdown();
@ -99,6 +126,11 @@ void grpc_shutdown(void) {
grpc_timers_global_destroy();
grpc_tracer_shutdown();
grpc_resolver_registry_shutdown();
for (i = 0; i < g_number_of_plugins; i++) {
if (g_all_of_the_plugins[i].destroy != NULL) {
g_all_of_the_plugins[i].destroy();
}
}
}
gpr_mu_unlock(&g_init_mu);
}

@ -761,8 +761,10 @@ static const grpc_channel_filter server_surface_filter = {
};
void grpc_server_register_completion_queue(grpc_server *server,
grpc_completion_queue *cq) {
grpc_completion_queue *cq,
void *reserved) {
size_t i, n;
GPR_ASSERT(!reserved);
for (i = 0; i < server->cq_count; i++) {
if (server->cqs[i] == cq) return;
}

@ -36,8 +36,9 @@
#include "src/core/surface/server.h"
#include "src/core/channel/compress_filter.h"
grpc_server *grpc_server_create(const grpc_channel_args *args) {
grpc_server *grpc_server_create(const grpc_channel_args *args, void *reserved) {
const grpc_channel_filter *filters[] = {&grpc_compress_filter};
(void) reserved;
return grpc_server_create_from_filters(filters, GPR_ARRAY_SIZE(filters),
args);
}

@ -258,6 +258,7 @@ static void link_tail(grpc_mdelem_list *list, grpc_linked_mdelem *storage) {
GPR_ASSERT(storage->md);
storage->prev = list->tail;
storage->next = NULL;
storage->reserved = NULL;
if (list->tail != NULL) {
list->tail->next = storage;
} else {

@ -77,6 +77,7 @@ typedef struct grpc_linked_mdelem {
grpc_mdelem *md;
struct grpc_linked_mdelem *next;
struct grpc_linked_mdelem *prev;
void *reserved;
} grpc_linked_mdelem;
typedef struct grpc_mdelem_list {

@ -67,7 +67,7 @@ Call Channel::CreateCall(const RpcMethod& method, ClientContext* context,
c_call = grpc_channel_create_registered_call(
c_channel_, context->propagate_from_call_,
context->propagation_options_.c_bitmask(), cq->cq(),
method.channel_tag(), context->raw_deadline());
method.channel_tag(), context->raw_deadline(), nullptr);
} else {
const char* host_str = NULL;
if (!context->authority().empty()) {
@ -78,7 +78,7 @@ Call Channel::CreateCall(const RpcMethod& method, ClientContext* context,
c_call = grpc_channel_create_call(c_channel_, context->propagate_from_call_,
context->propagation_options_.c_bitmask(),
cq->cq(), method.name(), host_str,
context->raw_deadline());
context->raw_deadline(), nullptr);
}
grpc_census_call_set_context(c_call, context->census_context());
GRPC_TIMER_MARK(GRPC_PTAG_CPP_CALL_CREATED, c_call);
@ -93,13 +93,14 @@ void Channel::PerformOpsOnCall(CallOpSetInterface* ops, Call* call) {
GRPC_TIMER_BEGIN(GRPC_PTAG_CPP_PERFORM_OPS, call->call());
ops->FillOps(cops, &nops);
GPR_ASSERT(GRPC_CALL_OK ==
grpc_call_start_batch(call->call(), cops, nops, ops));
grpc_call_start_batch(call->call(), cops, nops, ops, nullptr));
GRPC_TIMER_END(GRPC_PTAG_CPP_PERFORM_OPS, call->call());
}
void* Channel::RegisterMethod(const char* method) {
return grpc_channel_register_call(c_channel_, method,
host_.empty() ? NULL : host_.c_str());
host_.empty() ? NULL : host_.c_str(),
nullptr);
}
grpc_connectivity_state Channel::GetState(bool try_to_connect) {

@ -77,19 +77,19 @@ void ClientContext::set_call(grpc_call* call,
channel_ = channel;
if (creds_ && !creds_->ApplyToCall(call_)) {
grpc_call_cancel_with_status(call, GRPC_STATUS_CANCELLED,
"Failed to set credentials to rpc.");
"Failed to set credentials to rpc.", nullptr);
}
}
void ClientContext::set_compression_algorithm(
grpc_compression_algorithm algorithm) {
char* algorithm_name = NULL;
char* algorithm_name = nullptr;
if (!grpc_compression_algorithm_name(algorithm, &algorithm_name)) {
gpr_log(GPR_ERROR, "Name for compression algorithm '%d' unknown.",
algorithm);
abort();
}
GPR_ASSERT(algorithm_name != NULL);
GPR_ASSERT(algorithm_name != nullptr);
AddMetadata(GRPC_COMPRESS_REQUEST_ALGORITHM_KEY, algorithm_name);
}
@ -102,7 +102,7 @@ std::shared_ptr<const AuthContext> ClientContext::auth_context() const {
void ClientContext::TryCancel() {
if (call_) {
grpc_call_cancel(call_);
grpc_call_cancel(call_, nullptr);
}
}

@ -49,7 +49,7 @@ class InsecureCredentialsImpl GRPC_FINAL : public Credentials {
grpc_channel_args channel_args;
args.SetChannelArgs(&channel_args);
return std::shared_ptr<ChannelInterface>(new Channel(
grpc_insecure_channel_create(target.c_str(), &channel_args)));
grpc_insecure_channel_create(target.c_str(), &channel_args, nullptr)));
}
// InsecureCredentials should not be applied to a call.

@ -40,7 +40,9 @@
namespace grpc {
CompletionQueue::CompletionQueue() { cq_ = grpc_completion_queue_create(); }
CompletionQueue::CompletionQueue() {
cq_ = grpc_completion_queue_create(nullptr);
}
CompletionQueue::CompletionQueue(grpc_completion_queue* take) : cq_(take) {}
@ -51,7 +53,7 @@ void CompletionQueue::Shutdown() { grpc_completion_queue_shutdown(cq_); }
CompletionQueue::NextStatus CompletionQueue::AsyncNextInternal(
void** tag, bool* ok, gpr_timespec deadline) {
for (;;) {
auto ev = grpc_completion_queue_next(cq_, deadline);
auto ev = grpc_completion_queue_next(cq_, deadline, nullptr);
switch (ev.type) {
case GRPC_QUEUE_TIMEOUT:
return TIMEOUT;
@ -70,8 +72,8 @@ CompletionQueue::NextStatus CompletionQueue::AsyncNextInternal(
}
bool CompletionQueue::Pluck(CompletionQueueTag* tag) {
auto ev =
grpc_completion_queue_pluck(cq_, tag, gpr_inf_future(GPR_CLOCK_REALTIME));
auto deadline = gpr_inf_future(GPR_CLOCK_REALTIME);
auto ev = grpc_completion_queue_pluck(cq_, tag, deadline, nullptr);
bool ok = ev.success != 0;
void* ignored = tag;
GPR_ASSERT(tag->FinalizeResult(&ignored, &ok));
@ -81,8 +83,8 @@ bool CompletionQueue::Pluck(CompletionQueueTag* tag) {
}
void CompletionQueue::TryPluck(CompletionQueueTag* tag) {
auto ev =
grpc_completion_queue_pluck(cq_, tag, gpr_time_0(GPR_CLOCK_REALTIME));
auto deadline = gpr_time_0(GPR_CLOCK_REALTIME);
auto ev = grpc_completion_queue_pluck(cq_, tag, deadline, nullptr);
if (ev.type == GRPC_QUEUE_TIMEOUT) return;
bool ok = ev.success != 0;
void* ignored = tag;

@ -67,11 +67,17 @@ class Server::SyncRequest GRPC_FINAL : public CompletionQueueTag {
has_request_payload_(method->method_type() == RpcMethod::NORMAL_RPC ||
method->method_type() ==
RpcMethod::SERVER_STREAMING),
call_details_(nullptr),
cq_(nullptr) {
grpc_metadata_array_init(&request_metadata_);
}
~SyncRequest() { grpc_metadata_array_destroy(&request_metadata_); }
~SyncRequest() {
if (call_details_) {
delete call_details_;
}
grpc_metadata_array_destroy(&request_metadata_);
}
static SyncRequest* Wait(CompletionQueue* cq, bool* ok) {
void* tag = nullptr;
@ -84,7 +90,7 @@ class Server::SyncRequest GRPC_FINAL : public CompletionQueueTag {
return mrd;
}
void SetupRequest() { cq_ = grpc_completion_queue_create(); }
void SetupRequest() { cq_ = grpc_completion_queue_create(nullptr); }
void TeardownRequest() {
grpc_completion_queue_destroy(cq_);
@ -94,17 +100,32 @@ class Server::SyncRequest GRPC_FINAL : public CompletionQueueTag {
void Request(grpc_server* server, grpc_completion_queue* notify_cq) {
GPR_ASSERT(cq_ && !in_flight_);
in_flight_ = true;
if (tag_) {
GPR_ASSERT(GRPC_CALL_OK ==
grpc_server_request_registered_call(
server, tag_, &call_, &deadline_, &request_metadata_,
has_request_payload_ ? &request_payload_ : nullptr, cq_,
notify_cq, this));
} else {
if (!call_details_) {
call_details_ = new grpc_call_details;
grpc_call_details_init(call_details_);
}
GPR_ASSERT(GRPC_CALL_OK == grpc_server_request_call(
server, &call_, call_details_,
&request_metadata_, cq_, notify_cq, this));
}
}
bool FinalizeResult(void** tag, bool* status) GRPC_OVERRIDE {
if (!*status) {
grpc_completion_queue_destroy(cq_);
}
if (call_details_) {
deadline_ = call_details_->deadline;
grpc_call_details_destroy(call_details_);
grpc_call_details_init(call_details_);
}
return true;
}
@ -157,6 +178,7 @@ class Server::SyncRequest GRPC_FINAL : public CompletionQueueTag {
bool in_flight_;
const bool has_request_payload_;
grpc_call* call_;
grpc_call_details* call_details_;
gpr_timespec deadline_;
grpc_metadata_array request_metadata_;
grpc_byte_buffer* request_payload_;
@ -170,9 +192,9 @@ static grpc_server* CreateServer(int max_message_size) {
arg.key = const_cast<char*>(GRPC_ARG_MAX_MESSAGE_LENGTH);
arg.value.integer = max_message_size;
grpc_channel_args args = {1, &arg};
return grpc_server_create(&args);
return grpc_server_create(&args, nullptr);
} else {
return grpc_server_create(nullptr);
return grpc_server_create(nullptr, nullptr);
}
}
@ -183,10 +205,11 @@ Server::Server(ThreadPoolInterface* thread_pool, bool thread_pool_owned,
shutdown_(false),
num_running_cb_(0),
sync_methods_(new std::list<SyncRequest>),
has_generic_service_(false),
server_(CreateServer(max_message_size)),
thread_pool_(thread_pool),
thread_pool_owned_(thread_pool_owned) {
grpc_server_register_completion_queue(server_, cq_.cq());
grpc_server_register_completion_queue(server_, cq_.cq(), nullptr);
}
Server::~Server() {
@ -223,7 +246,8 @@ bool Server::RegisterService(const grpc::string *host, RpcService* service) {
return true;
}
bool Server::RegisterAsyncService(const grpc::string *host, AsynchronousService* service) {
bool Server::RegisterAsyncService(const grpc::string* host,
AsynchronousService* service) {
GPR_ASSERT(service->server_ == nullptr &&
"Can only register an asynchronous service against one server.");
service->server_ = this;
@ -245,6 +269,7 @@ void Server::RegisterAsyncGenericService(AsyncGenericService* service) {
GPR_ASSERT(service->server_ == nullptr &&
"Can only register an async generic service against one server.");
service->server_ = this;
has_generic_service_ = true;
}
int Server::AddListeningPort(const grpc::string& addr,
@ -258,6 +283,11 @@ bool Server::Start() {
started_ = true;
grpc_server_start(server_);
if (!has_generic_service_) {
unknown_method_.reset(new RpcServiceMethod(
"unknown", RpcMethod::BIDI_STREAMING, new UnknownMethodHandler));
sync_methods_->emplace_back(unknown_method_.get(), nullptr);
}
// Start processing rpcs.
if (!sync_methods_->empty()) {
for (auto m = sync_methods_->begin(); m != sync_methods_->end(); m++) {
@ -297,8 +327,8 @@ void Server::PerformOpsOnCall(CallOpSetInterface* ops, Call* call) {
size_t nops = 0;
grpc_op cops[MAX_OPS];
ops->FillOps(cops, &nops);
GPR_ASSERT(GRPC_CALL_OK ==
grpc_call_start_batch(call->call(), cops, nops, ops));
auto result = grpc_call_start_batch(call->call(), cops, nops, ops, nullptr);
GPR_ASSERT(GRPC_CALL_OK == result);
}
Server::BaseAsyncRequest::BaseAsyncRequest(

@ -38,6 +38,7 @@
#include <grpc++/impl/service_type.h>
#include <grpc++/server.h>
#include <grpc++/thread_pool_interface.h>
#include <grpc++/fixed_size_thread_pool.h>
namespace grpc {
@ -100,10 +101,17 @@ std::unique_ptr<Server> ServerBuilder::BuildAndStart() {
thread_pool_ = CreateDefaultThreadPool();
thread_pool_owned = true;
}
// Async services only, create a thread pool to handle requests to unknown
// services.
if (!thread_pool_ && !generic_service_ && !async_services_.empty()) {
thread_pool_ = new FixedSizeThreadPool(1);
thread_pool_owned = true;
}
std::unique_ptr<Server> server(
new Server(thread_pool_, thread_pool_owned, max_message_size_));
for (auto cq = cqs_.begin(); cq != cqs_.end(); ++cq) {
grpc_server_register_completion_queue(server->server_, (*cq)->cq());
grpc_server_register_completion_queue(server->server_, (*cq)->cq(),
nullptr);
}
for (auto service = services_.begin(); service != services_.end();
service++) {

@ -91,6 +91,7 @@ void ServerContext::CompletionOp::FillOps(grpc_op* ops, size_t* nops) {
ops->op = GRPC_OP_RECV_CLOSE_ON_SERVER;
ops->data.recv_close_on_server.cancelled = &cancelled_;
ops->flags = 0;
ops->reserved = NULL;
*nops = 1;
}

@ -339,7 +339,7 @@ GPR_EXPORT void GPR_CALLTYPE grpcsharp_shutdown(void) { grpc_shutdown(); }
GPR_EXPORT grpc_completion_queue *GPR_CALLTYPE
grpcsharp_completion_queue_create(void) {
return grpc_completion_queue_create();
return grpc_completion_queue_create(NULL);
}
GPR_EXPORT void GPR_CALLTYPE
@ -354,13 +354,14 @@ grpcsharp_completion_queue_destroy(grpc_completion_queue *cq) {
GPR_EXPORT grpc_event GPR_CALLTYPE
grpcsharp_completion_queue_next(grpc_completion_queue *cq) {
return grpc_completion_queue_next(cq, gpr_inf_future(GPR_CLOCK_REALTIME));
return grpc_completion_queue_next(cq, gpr_inf_future(GPR_CLOCK_REALTIME),
NULL);
}
GPR_EXPORT grpc_event GPR_CALLTYPE
grpcsharp_completion_queue_pluck(grpc_completion_queue *cq, void *tag) {
return grpc_completion_queue_pluck(cq, tag,
gpr_inf_future(GPR_CLOCK_REALTIME));
gpr_inf_future(GPR_CLOCK_REALTIME), NULL);
}
/* Channel */
@ -368,7 +369,7 @@ grpcsharp_completion_queue_pluck(grpc_completion_queue *cq, void *tag) {
GPR_EXPORT grpc_channel *GPR_CALLTYPE
grpcsharp_insecure_channel_create(const char *target, const grpc_channel_args *args) {
return grpc_insecure_channel_create(target, args);
return grpc_insecure_channel_create(target, args, NULL);
}
GPR_EXPORT void GPR_CALLTYPE grpcsharp_channel_destroy(grpc_channel *channel) {
@ -382,7 +383,7 @@ grpcsharp_channel_create_call(grpc_channel *channel, grpc_call *parent_call,
const char *method, const char *host,
gpr_timespec deadline) {
return grpc_channel_create_call(channel, parent_call, propagation_mask, cq,
method, host, deadline);
method, host, deadline, NULL);
}
GPR_EXPORT grpc_connectivity_state GPR_CALLTYPE
@ -475,13 +476,13 @@ GPR_EXPORT gpr_int32 GPR_CALLTYPE gprsharp_sizeof_timespec(void) {
/* Call */
GPR_EXPORT grpc_call_error GPR_CALLTYPE grpcsharp_call_cancel(grpc_call *call) {
return grpc_call_cancel(call);
return grpc_call_cancel(call, NULL);
}
GPR_EXPORT grpc_call_error GPR_CALLTYPE
grpcsharp_call_cancel_with_status(grpc_call *call, grpc_status_code status,
const char *description) {
return grpc_call_cancel_with_status(call, status, description);
return grpc_call_cancel_with_status(call, status, description, NULL);
}
GPR_EXPORT char *GPR_CALLTYPE grpcsharp_call_get_peer(grpc_call *call) {
@ -538,7 +539,8 @@ grpcsharp_call_start_unary(grpc_call *call, grpcsharp_batch_context *ctx,
&(ctx->recv_status_on_client.status_details_capacity);
ops[5].flags = 0;
return grpc_call_start_batch(call, ops, sizeof(ops) / sizeof(ops[0]), ctx);
return grpc_call_start_batch(call, ops, sizeof(ops) / sizeof(ops[0]), ctx,
NULL);
}
GPR_EXPORT grpc_call_error GPR_CALLTYPE
@ -575,7 +577,8 @@ grpcsharp_call_start_client_streaming(grpc_call *call,
&(ctx->recv_status_on_client.status_details_capacity);
ops[3].flags = 0;
return grpc_call_start_batch(call, ops, sizeof(ops) / sizeof(ops[0]), ctx);
return grpc_call_start_batch(call, ops, sizeof(ops) / sizeof(ops[0]), ctx,
NULL);
}
GPR_EXPORT grpc_call_error GPR_CALLTYPE grpcsharp_call_start_server_streaming(
@ -615,7 +618,8 @@ GPR_EXPORT grpc_call_error GPR_CALLTYPE grpcsharp_call_start_server_streaming(
&(ctx->recv_status_on_client.status_details_capacity);
ops[4].flags = 0;
return grpc_call_start_batch(call, ops, sizeof(ops) / sizeof(ops[0]), ctx);
return grpc_call_start_batch(call, ops, sizeof(ops) / sizeof(ops[0]), ctx,
NULL);
}
GPR_EXPORT grpc_call_error GPR_CALLTYPE
@ -648,7 +652,8 @@ grpcsharp_call_start_duplex_streaming(grpc_call *call,
&(ctx->recv_status_on_client.status_details_capacity);
ops[2].flags = 0;
return grpc_call_start_batch(call, ops, sizeof(ops) / sizeof(ops[0]), ctx);
return grpc_call_start_batch(call, ops, sizeof(ops) / sizeof(ops[0]), ctx,
NULL);
}
GPR_EXPORT grpc_call_error GPR_CALLTYPE
@ -668,7 +673,7 @@ grpcsharp_call_send_message(grpc_call *call, grpcsharp_batch_context *ctx,
ops[1].data.send_initial_metadata.metadata = NULL;
ops[1].flags = 0;
return grpc_call_start_batch(call, ops, nops, ctx);
return grpc_call_start_batch(call, ops, nops, ctx, NULL);
}
GPR_EXPORT grpc_call_error GPR_CALLTYPE
@ -679,7 +684,8 @@ grpcsharp_call_send_close_from_client(grpc_call *call,
ops[0].op = GRPC_OP_SEND_CLOSE_FROM_CLIENT;
ops[0].flags = 0;
return grpc_call_start_batch(call, ops, sizeof(ops) / sizeof(ops[0]), ctx);
return grpc_call_start_batch(call, ops, sizeof(ops) / sizeof(ops[0]), ctx,
NULL);
}
GPR_EXPORT grpc_call_error GPR_CALLTYPE grpcsharp_call_send_status_from_server(
@ -705,7 +711,7 @@ GPR_EXPORT grpc_call_error GPR_CALLTYPE grpcsharp_call_send_status_from_server(
ops[1].data.send_initial_metadata.metadata = NULL;
ops[1].flags = 0;
return grpc_call_start_batch(call, ops, nops, ctx);
return grpc_call_start_batch(call, ops, nops, ctx, NULL);
}
GPR_EXPORT grpc_call_error GPR_CALLTYPE
@ -715,7 +721,8 @@ grpcsharp_call_recv_message(grpc_call *call, grpcsharp_batch_context *ctx) {
ops[0].op = GRPC_OP_RECV_MESSAGE;
ops[0].data.recv_message = &(ctx->recv_message);
ops[0].flags = 0;
return grpc_call_start_batch(call, ops, sizeof(ops) / sizeof(ops[0]), ctx);
return grpc_call_start_batch(call, ops, sizeof(ops) / sizeof(ops[0]), ctx,
NULL);
}
GPR_EXPORT grpc_call_error GPR_CALLTYPE
@ -727,7 +734,8 @@ grpcsharp_call_start_serverside(grpc_call *call, grpcsharp_batch_context *ctx) {
(&ctx->recv_close_on_server_cancelled);
ops[0].flags = 0;
return grpc_call_start_batch(call, ops, sizeof(ops) / sizeof(ops[0]), ctx);
return grpc_call_start_batch(call, ops, sizeof(ops) / sizeof(ops[0]), ctx,
NULL);
}
GPR_EXPORT grpc_call_error GPR_CALLTYPE
@ -744,7 +752,8 @@ grpcsharp_call_send_initial_metadata(grpc_call *call,
ctx->send_initial_metadata.metadata;
ops[0].flags = 0;
return grpc_call_start_batch(call, ops, sizeof(ops) / sizeof(ops[0]), ctx);
return grpc_call_start_batch(call, ops, sizeof(ops) / sizeof(ops[0]), ctx,
NULL);
}
/* Server */
@ -752,8 +761,8 @@ grpcsharp_call_send_initial_metadata(grpc_call *call,
GPR_EXPORT grpc_server *GPR_CALLTYPE
grpcsharp_server_create(grpc_completion_queue *cq,
const grpc_channel_args *args) {
grpc_server *server = grpc_server_create(args);
grpc_server_register_completion_queue(server, cq);
grpc_server *server = grpc_server_create(args, NULL);
grpc_server_register_completion_queue(server, cq, NULL);
return server;
}

@ -532,12 +532,12 @@ NAN_METHOD(Call::New) {
wrapped_call = grpc_channel_create_call(
wrapped_channel, parent_call, propagate_flags,
CompletionQueueAsyncWorker::GetQueue(), *method,
*host_override, MillisecondsToTimespec(deadline));
*host_override, MillisecondsToTimespec(deadline), NULL);
} else if (args[3]->IsUndefined() || args[3]->IsNull()) {
wrapped_call = grpc_channel_create_call(
wrapped_channel, parent_call, propagate_flags,
CompletionQueueAsyncWorker::GetQueue(), *method,
NULL, MillisecondsToTimespec(deadline));
NULL, MillisecondsToTimespec(deadline), NULL);
} else {
return NanThrowTypeError("Call's fourth argument must be a string");
}
@ -617,7 +617,7 @@ NAN_METHOD(Call::StartBatch) {
NanCallback *callback = new NanCallback(callback_func);
grpc_call_error error = grpc_call_start_batch(
call->wrapped_call, &ops[0], nops, new struct tag(
callback, op_vector.release(), resources));
callback, op_vector.release(), resources), NULL);
if (error != GRPC_CALL_OK) {
return NanThrowError("startBatch failed", error);
}
@ -631,7 +631,7 @@ NAN_METHOD(Call::Cancel) {
return NanThrowTypeError("cancel can only be called on Call objects");
}
Call *call = ObjectWrap::Unwrap<Call>(args.This());
grpc_call_error error = grpc_call_cancel(call->wrapped_call);
grpc_call_error error = grpc_call_cancel(call->wrapped_call, NULL);
if (error != GRPC_CALL_OK) {
return NanThrowError("cancel failed", error);
}

@ -33,12 +33,17 @@
#include <vector>
#include "grpc/support/log.h"
#include <node.h>
#include <nan.h>
#include "grpc/grpc.h"
#include "grpc/grpc_security.h"
#include "call.h"
#include "channel.h"
#include "completion_queue_async_worker.h"
#include "credentials.h"
#include "timeval.h"
namespace grpc {
namespace node {
@ -51,6 +56,7 @@ using v8::Handle;
using v8::HandleScope;
using v8::Integer;
using v8::Local;
using v8::Number;
using v8::Object;
using v8::Persistent;
using v8::String;
@ -76,6 +82,12 @@ void Channel::Init(Handle<Object> exports) {
NanNew<FunctionTemplate>(Close)->GetFunction());
NanSetPrototypeTemplate(tpl, "getTarget",
NanNew<FunctionTemplate>(GetTarget)->GetFunction());
NanSetPrototypeTemplate(
tpl, "getConnectivityState",
NanNew<FunctionTemplate>(GetConnectivityState)->GetFunction());
NanSetPrototypeTemplate(
tpl, "watchConnectivityState",
NanNew<FunctionTemplate>(WatchConnectivityState)->GetFunction());
NanAssignPersistent(fun_tpl, tpl);
Handle<Function> ctr = tpl->GetFunction();
constructor = new NanCallback(ctr);
@ -111,7 +123,7 @@ NAN_METHOD(Channel::New) {
grpc_channel_args *channel_args_ptr;
if (args[2]->IsUndefined()) {
channel_args_ptr = NULL;
wrapped_channel = grpc_insecure_channel_create(*host, NULL);
wrapped_channel = grpc_insecure_channel_create(*host, NULL, NULL);
} else if (args[2]->IsObject()) {
Handle<Object> args_hash(args[2]->ToObject()->Clone());
Handle<Array> keys(args_hash->GetOwnPropertyNames());
@ -145,7 +157,8 @@ NAN_METHOD(Channel::New) {
return NanThrowTypeError("Channel expects a string and an object");
}
if (creds == NULL) {
wrapped_channel = grpc_insecure_channel_create(*host, channel_args_ptr);
wrapped_channel = grpc_insecure_channel_create(*host, channel_args_ptr,
NULL);
} else {
wrapped_channel =
grpc_secure_channel_create(creds, *host, channel_args_ptr);
@ -185,5 +198,52 @@ NAN_METHOD(Channel::GetTarget) {
NanReturnValue(NanNew(grpc_channel_get_target(channel->wrapped_channel)));
}
NAN_METHOD(Channel::GetConnectivityState) {
NanScope();
if (!HasInstance(args.This())) {
return NanThrowTypeError(
"getConnectivityState can only be called on Channel objects");
}
Channel *channel = ObjectWrap::Unwrap<Channel>(args.This());
int try_to_connect = (int)args[0]->Equals(NanTrue());
NanReturnValue(grpc_channel_check_connectivity_state(channel->wrapped_channel,
try_to_connect));
}
NAN_METHOD(Channel::WatchConnectivityState) {
NanScope();
if (!HasInstance(args.This())) {
return NanThrowTypeError(
"watchConnectivityState can only be called on Channel objects");
}
if (!args[0]->IsUint32()) {
return NanThrowTypeError(
"watchConnectivityState's first argument must be a channel state");
}
if (!(args[1]->IsNumber() || args[1]->IsDate())) {
return NanThrowTypeError(
"watchConnectivityState's second argument must be a date or a number");
}
if (!args[2]->IsFunction()) {
return NanThrowTypeError(
"watchConnectivityState's third argument must be a callback");
}
grpc_connectivity_state last_state =
static_cast<grpc_connectivity_state>(args[0]->Uint32Value());
double deadline = args[1]->NumberValue();
Handle<Function> callback_func = args[2].As<Function>();
NanCallback *callback = new NanCallback(callback_func);
Channel *channel = ObjectWrap::Unwrap<Channel>(args.This());
unique_ptr<OpVec> ops(new OpVec());
grpc_channel_watch_connectivity_state(
channel->wrapped_channel, last_state, MillisecondsToTimespec(deadline),
CompletionQueueAsyncWorker::GetQueue(),
new struct tag(callback,
ops.release(),
shared_ptr<Resources>(nullptr)));
CompletionQueueAsyncWorker::Next();
NanReturnUndefined();
}
} // namespace node
} // namespace grpc

@ -64,6 +64,8 @@ class Channel : public ::node::ObjectWrap {
static NAN_METHOD(New);
static NAN_METHOD(Close);
static NAN_METHOD(GetTarget);
static NAN_METHOD(GetConnectivityState);
static NAN_METHOD(WatchConnectivityState);
static NanCallback *constructor;
static v8::Persistent<v8::FunctionTemplate> fun_tpl;

@ -63,9 +63,9 @@ CompletionQueueAsyncWorker::~CompletionQueueAsyncWorker() {}
void CompletionQueueAsyncWorker::Execute() {
result =
grpc_completion_queue_next(queue, gpr_inf_future(GPR_CLOCK_REALTIME));
grpc_completion_queue_next(queue, gpr_inf_future(GPR_CLOCK_REALTIME), NULL);
if (!result.success) {
SetErrorMessage("The batch encountered an error");
SetErrorMessage("The async function encountered an error");
}
}
@ -85,7 +85,7 @@ void CompletionQueueAsyncWorker::Init(Handle<Object> exports) {
NanScope();
current_threads = 0;
waiting_next_calls = 0;
queue = grpc_completion_queue_create();
queue = grpc_completion_queue_create(NULL);
}
void CompletionQueueAsyncWorker::HandleOKCallback() {

@ -178,6 +178,24 @@ void InitPropagateConstants(Handle<Object> exports) {
propagate->Set(NanNew("DEFAULTS"), DEFAULTS);
}
void InitConnectivityStateConstants(Handle<Object> exports) {
NanScope();
Handle<Object> channel_state = NanNew<Object>();
exports->Set(NanNew("connectivityState"), channel_state);
Handle<Value> IDLE(NanNew<Uint32, uint32_t>(GRPC_CHANNEL_IDLE));
channel_state->Set(NanNew("IDLE"), IDLE);
Handle<Value> CONNECTING(NanNew<Uint32, uint32_t>(GRPC_CHANNEL_CONNECTING));
channel_state->Set(NanNew("CONNECTING"), CONNECTING);
Handle<Value> READY(NanNew<Uint32, uint32_t>(GRPC_CHANNEL_READY));
channel_state->Set(NanNew("READY"), READY);
Handle<Value> TRANSIENT_FAILURE(
NanNew<Uint32, uint32_t>(GRPC_CHANNEL_TRANSIENT_FAILURE));
channel_state->Set(NanNew("TRANSIENT_FAILURE"), TRANSIENT_FAILURE);
Handle<Value> FATAL_FAILURE(
NanNew<Uint32, uint32_t>(GRPC_CHANNEL_FATAL_FAILURE));
channel_state->Set(NanNew("FATAL_FAILURE"), FATAL_FAILURE);
}
void init(Handle<Object> exports) {
NanScope();
grpc_init();
@ -185,6 +203,7 @@ void init(Handle<Object> exports) {
InitCallErrorConstants(exports);
InitOpTypeConstants(exports);
InitPropagateConstants(exports);
InitConnectivityStateConstants(exports);
grpc::node::Call::Init(exports);
grpc::node::Channel::Init(exports);

@ -113,8 +113,8 @@ class NewCallOp : public Op {
};
Server::Server(grpc_server *server) : wrapped_server(server) {
shutdown_queue = grpc_completion_queue_create();
grpc_server_register_completion_queue(server, shutdown_queue);
shutdown_queue = grpc_completion_queue_create(NULL);
grpc_server_register_completion_queue(server, shutdown_queue, NULL);
}
Server::~Server() {
@ -158,7 +158,7 @@ void Server::ShutdownServer() {
this->shutdown_queue,
NULL);
grpc_completion_queue_pluck(this->shutdown_queue, NULL,
gpr_inf_future(GPR_CLOCK_REALTIME));
gpr_inf_future(GPR_CLOCK_REALTIME), NULL);
this->wrapped_server = NULL;
}
}
@ -176,7 +176,7 @@ NAN_METHOD(Server::New) {
grpc_server *wrapped_server;
grpc_completion_queue *queue = CompletionQueueAsyncWorker::GetQueue();
if (args[0]->IsUndefined()) {
wrapped_server = grpc_server_create(NULL);
wrapped_server = grpc_server_create(NULL, NULL);
} else if (args[0]->IsObject()) {
Handle<Object> args_hash(args[0]->ToObject());
Handle<Array> keys(args_hash->GetOwnPropertyNames());
@ -205,12 +205,12 @@ NAN_METHOD(Server::New) {
return NanThrowTypeError("Arg values must be strings");
}
}
wrapped_server = grpc_server_create(&channel_args);
wrapped_server = grpc_server_create(&channel_args, NULL);
free(channel_args.args);
} else {
return NanThrowTypeError("Server expects an object");
}
grpc_server_register_completion_queue(wrapped_server, queue);
grpc_server_register_completion_queue(wrapped_server, queue, NULL);
Server *server = new Server(wrapped_server);
server->Wrap(args.This());
NanReturnValue(args.This());

@ -563,6 +563,35 @@ exports.makeClientConstructor = function(methods, serviceName) {
this.updateMetadata = updateMetadata;
}
/**
* Wait for the client to be ready. The callback will be called when the
* client has successfully connected to the server, and it will be called
* with an error if the attempt to connect to the server has unrecoverablly
* failed or if the deadline expires. This function will make the channel
* start connecting if it has not already done so.
* @param {(Date|Number)} deadline When to stop waiting for a connection. Pass
* Infinity to wait forever.
* @param {function(Error)} callback The callback to call when done attempting
* to connect.
*/
Client.prototype.$waitForReady = function(deadline, callback) {
var self = this;
var checkState = function(err) {
if (err) {
callback(new Error('Failed to connect before the deadline'));
}
var new_state = self.channel.getConnectivityState(true);
if (new_state === grpc.connectivityState.READY) {
callback();
} else if (new_state === grpc.connectivityState.FATAL_FAILURE) {
callback(new Error('Failed to connect to server'));
} else {
self.channel.watchConnectivityState(new_state, deadline, checkState);
}
};
checkState();
};
_.each(methods, function(attrs, name) {
var method_type;
if (attrs.requestStream) {

@ -36,6 +36,26 @@
var assert = require('assert');
var grpc = require('bindings')('grpc.node');
/**
* This is used for testing functions with multiple asynchronous calls that
* can happen in different orders. This should be passed the number of async
* function invocations that can occur last, and each of those should call this
* function's return value
* @param {function()} done The function that should be called when a test is
* complete.
* @param {number} count The number of calls to the resulting function if the
* test passes.
* @return {function()} The function that should be called at the end of each
* sequence of asynchronous functions.
*/
function multiDone(done, count) {
return function() {
count -= 1;
if (count <= 0) {
done();
}
};
}
var insecureCreds = grpc.Credentials.createInsecure();
describe('channel', function() {
@ -86,14 +106,16 @@ describe('channel', function() {
});
});
describe('close', function() {
var channel;
beforeEach(function() {
channel = new grpc.Channel('hostname', insecureCreds, {});
});
it('should succeed silently', function() {
var channel = new grpc.Channel('hostname', insecureCreds, {});
assert.doesNotThrow(function() {
channel.close();
});
});
it('should be idempotent', function() {
var channel = new grpc.Channel('hostname', insecureCreds, {});
assert.doesNotThrow(function() {
channel.close();
channel.close();
@ -101,9 +123,68 @@ describe('channel', function() {
});
});
describe('getTarget', function() {
var channel;
beforeEach(function() {
channel = new grpc.Channel('hostname', insecureCreds, {});
});
it('should return a string', function() {
var channel = new grpc.Channel('localhost', insecureCreds, {});
assert.strictEqual(typeof channel.getTarget(), 'string');
});
});
describe('getConnectivityState', function() {
var channel;
beforeEach(function() {
channel = new grpc.Channel('hostname', insecureCreds, {});
});
it('should return IDLE for a new channel', function() {
assert.strictEqual(channel.getConnectivityState(),
grpc.connectivityState.IDLE);
});
});
describe('watchConnectivityState', function() {
var channel;
beforeEach(function() {
channel = new grpc.Channel('localhost', insecureCreds, {});
});
afterEach(function() {
channel.close();
});
it('should time out if called alone', function(done) {
var old_state = channel.getConnectivityState();
var deadline = new Date();
deadline.setSeconds(deadline.getSeconds() + 1);
channel.watchConnectivityState(old_state, deadline, function(err, value) {
assert(err);
done();
});
});
it('should complete if a connection attempt is forced', function(done) {
var old_state = channel.getConnectivityState();
var deadline = new Date();
deadline.setSeconds(deadline.getSeconds() + 1);
channel.watchConnectivityState(old_state, deadline, function(err, value) {
assert.ifError(err);
assert.notEqual(value.new_state, old_state);
done();
});
channel.getConnectivityState(true);
});
it('should complete twice if called twice', function(done) {
done = multiDone(done, 2);
var old_state = channel.getConnectivityState();
var deadline = new Date();
deadline.setSeconds(deadline.getSeconds() + 1);
channel.watchConnectivityState(old_state, deadline, function(err, value) {
assert.ifError(err);
assert.notEqual(value.new_state, old_state);
done();
});
channel.watchConnectivityState(old_state, deadline, function(err, value) {
assert.ifError(err);
assert.notEqual(value.new_state, old_state);
done();
});
channel.getConnectivityState(true);
});
});
});

@ -90,6 +90,18 @@ var propagateFlagNames = [
'CANCELLATION',
'DEFAULTS'
];
/*
* List of all connectivity state names
* @const
* @type {Array.<string>}
*/
var connectivityStateNames = [
'IDLE',
'CONNECTING',
'READY',
'TRANSIENT_FAILURE',
'FATAL_FAILURE'
];
describe('constants', function() {
it('should have all of the status constants', function() {
@ -110,4 +122,10 @@ describe('constants', function() {
'call error missing: ' + propagateFlagNames[i]);
}
});
it('should have all of the connectivity states', function() {
for (var i = 0; i < connectivityStateNames.length; i++) {
assert(grpc.connectivityState.hasOwnProperty(connectivityStateNames[i]),
'connectivity status missing: ' + connectivityStateNames[i]);
}
});
});

@ -133,6 +133,58 @@ describe('Server.prototype.addProtoService', function() {
});
});
});
describe('Client#$waitForReady', function() {
var server;
var port;
var Client;
var client;
before(function() {
server = new grpc.Server();
port = server.bind('localhost:0', grpc.ServerCredentials.createInsecure());
server.start();
Client = surface_client.makeProtobufClientConstructor(mathService);
});
beforeEach(function() {
client = new Client('localhost:' + port, grpc.Credentials.createInsecure());
});
after(function() {
server.shutdown();
});
it('should complete when called alone', function(done) {
client.$waitForReady(Infinity, function(error) {
assert.ifError(error);
done();
});
});
it('should complete when a call is initiated', function(done) {
client.$waitForReady(Infinity, function(error) {
assert.ifError(error);
done();
});
var call = client.div({}, function(err, response) {});
call.cancel();
});
it('should complete if called more than once', function(done) {
done = multiDone(done, 2);
client.$waitForReady(Infinity, function(error) {
assert.ifError(error);
done();
});
client.$waitForReady(Infinity, function(error) {
assert.ifError(error);
done();
});
});
it('should complete if called when already ready', function(done) {
client.$waitForReady(Infinity, function(error) {
assert.ifError(error);
client.$waitForReady(Infinity, function(error) {
assert.ifError(error);
done();
});
});
});
});
describe('Echo service', function() {
var server;
var client;

@ -43,7 +43,7 @@
- (instancetype)init {
if ((self = [super init])) {
_unmanagedQueue = grpc_completion_queue_create();
_unmanagedQueue = grpc_completion_queue_create(NULL);
// This is for the following block to capture the pointer by value (instead
// of retaining self and doing self->_unmanagedQueue). This is essential
@ -64,7 +64,8 @@
while (YES) {
// The following call blocks until an event is available.
grpc_event event = grpc_completion_queue_next(unmanagedQueue,
gpr_inf_future(GPR_CLOCK_REALTIME));
gpr_inf_future(GPR_CLOCK_REALTIME),
NULL);
GRPCQueueCompletionHandler handler;
switch (event.type) {
case GRPC_OP_COMPLETE:

@ -97,7 +97,7 @@
queue.unmanagedQueue,
path.UTF8String,
self.hostName.UTF8String,
gpr_inf_future(GPR_CLOCK_REALTIME));
gpr_inf_future(GPR_CLOCK_REALTIME), NULL);
}
- (GRPCChannel *)channel {

@ -38,7 +38,7 @@
@implementation GRPCUnsecuredChannel
- (instancetype)initWithHost:(NSString *)host {
return (self = [super initWithChannel:grpc_insecure_channel_create(host.UTF8String, NULL)]);
return (self = [super initWithChannel:grpc_insecure_channel_create(host.UTF8String, NULL, NULL)]);
}
// TODO(jcanizales): GRPCSecureChannel and GRPCUnsecuredChannel are just convenience initializers

@ -282,7 +282,7 @@
for (GRPCOperation *operation in operations) {
[operation finish];
}
}));
}), NULL);
gpr_free(ops_array);
if (error != GRPC_CALL_OK) {
@ -293,7 +293,7 @@
}
- (void)cancel {
grpc_call_cancel(_call);
grpc_call_cancel(_call, NULL);
}
- (void)dealloc {

@ -241,7 +241,7 @@ PHP_METHOD(Call, __construct) {
deadline_obj TSRMLS_CC);
call->wrapped = grpc_channel_create_call(
channel->wrapped, NULL, GRPC_PROPAGATE_DEFAULTS, completion_queue, method,
channel->target, deadline->wrapped);
channel->target, deadline->wrapped, NULL);
}
/**
@ -400,7 +400,8 @@ PHP_METHOD(Call, startBatch) {
ops[op_num].flags = 0;
op_num++;
}
error = grpc_call_start_batch(call->wrapped, ops, op_num, call->wrapped);
error = grpc_call_start_batch(call->wrapped, ops, op_num, call->wrapped,
NULL);
if (error != GRPC_CALL_OK) {
zend_throw_exception(spl_ce_LogicException,
"start_batch was called incorrectly",
@ -408,7 +409,7 @@ PHP_METHOD(Call, startBatch) {
goto cleanup;
}
event = grpc_completion_queue_pluck(completion_queue, call->wrapped,
gpr_inf_future(GPR_CLOCK_REALTIME));
gpr_inf_future(GPR_CLOCK_REALTIME), NULL);
if (!event.success) {
zend_throw_exception(spl_ce_LogicException,
"The batch failed for some reason",
@ -489,7 +490,7 @@ PHP_METHOD(Call, getPeer) {
PHP_METHOD(Call, cancel) {
wrapped_grpc_call *call =
(wrapped_grpc_call *)zend_object_store_get_object(getThis() TSRMLS_CC);
grpc_call_cancel(call->wrapped);
grpc_call_cancel(call->wrapped, NULL);
}
static zend_function_entry call_methods[] = {

@ -154,7 +154,7 @@ PHP_METHOD(Channel, __construct) {
override = target;
override_len = target_length;
if (args_array == NULL) {
channel->wrapped = grpc_insecure_channel_create(target, NULL);
channel->wrapped = grpc_insecure_channel_create(target, NULL, NULL);
} else {
array_hash = Z_ARRVAL_P(args_array);
if (zend_hash_find(array_hash, "credentials", sizeof("credentials"),
@ -184,7 +184,7 @@ PHP_METHOD(Channel, __construct) {
}
php_grpc_read_args_array(args_array, &args);
if (creds == NULL) {
channel->wrapped = grpc_insecure_channel_create(target, &args);
channel->wrapped = grpc_insecure_channel_create(target, &args, NULL);
} else {
gpr_log(GPR_DEBUG, "Initialized secure channel");
channel->wrapped =
@ -255,7 +255,7 @@ PHP_METHOD(Channel, watchConnectivityState) {
deadline->wrapped, completion_queue, NULL);
grpc_event event = grpc_completion_queue_pluck(
completion_queue, NULL,
gpr_inf_future(GPR_CLOCK_REALTIME));
gpr_inf_future(GPR_CLOCK_REALTIME), NULL);
RETURN_BOOL(event.success);
}

@ -38,14 +38,13 @@
grpc_completion_queue *completion_queue;
void grpc_php_init_completion_queue(TSRMLS_D) {
completion_queue = grpc_completion_queue_create();
completion_queue = grpc_completion_queue_create(NULL);
}
void grpc_php_shutdown_completion_queue(TSRMLS_D) {
grpc_completion_queue_shutdown(completion_queue);
while (grpc_completion_queue_next(completion_queue,
gpr_inf_future(GPR_CLOCK_REALTIME))
.type != GRPC_QUEUE_SHUTDOWN)
;
gpr_inf_future(GPR_CLOCK_REALTIME),
NULL).type != GRPC_QUEUE_SHUTDOWN);
grpc_completion_queue_destroy(completion_queue);
}

@ -66,7 +66,7 @@ void free_wrapped_grpc_server(void *object TSRMLS_DC) {
grpc_server_shutdown_and_notify(server->wrapped, completion_queue, NULL);
grpc_server_cancel_all_calls(server->wrapped);
grpc_completion_queue_pluck(completion_queue, NULL,
gpr_inf_future(GPR_CLOCK_REALTIME));
gpr_inf_future(GPR_CLOCK_REALTIME), NULL);
grpc_server_destroy(server->wrapped);
}
efree(server);
@ -109,13 +109,14 @@ PHP_METHOD(Server, __construct) {
return;
}
if (args_array == NULL) {
server->wrapped = grpc_server_create(NULL);
server->wrapped = grpc_server_create(NULL, NULL);
} else {
php_grpc_read_args_array(args_array, &args);
server->wrapped = grpc_server_create(&args);
server->wrapped = grpc_server_create(&args, NULL);
efree(args.args);
}
grpc_server_register_completion_queue(server->wrapped, completion_queue);
grpc_server_register_completion_queue(server->wrapped, completion_queue,
NULL);
}
/**
@ -146,7 +147,7 @@ PHP_METHOD(Server, requestCall) {
goto cleanup;
}
event = grpc_completion_queue_pluck(completion_queue, NULL,
gpr_inf_future(GPR_CLOCK_REALTIME));
gpr_inf_future(GPR_CLOCK_REALTIME), NULL);
if (!event.success) {
zend_throw_exception(spl_ce_LogicException,
"Failed to request a call for some reason",

@ -132,7 +132,7 @@ PyObject *pygrpc_Call_start_batch(Call *self, PyObject *args, PyObject *kwargs)
}
}
tag = pygrpc_produce_batch_tag(user_tag, self, ops, nops);
errcode = grpc_call_start_batch(self->c_call, tag->ops, tag->nops, tag);
errcode = grpc_call_start_batch(self->c_call, tag->ops, tag->nops, tag, NULL);
gpr_free(ops);
return PyInt_FromLong(errcode);
}
@ -152,13 +152,13 @@ PyObject *pygrpc_Call_cancel(Call *self, PyObject *args, PyObject *kwargs) {
return NULL;
}
code = PyInt_AsLong(py_code);
errcode = grpc_call_cancel_with_status(self->c_call, code, details);
errcode = grpc_call_cancel_with_status(self->c_call, code, details, NULL);
} else if (py_code != NULL || details != NULL) {
PyErr_SetString(PyExc_ValueError,
"if `code` is specified, so must `details`");
return NULL;
} else {
errcode = grpc_call_cancel(self->c_call);
errcode = grpc_call_cancel(self->c_call, NULL);
}
return PyInt_FromLong(errcode);
}

@ -108,7 +108,7 @@ Channel *pygrpc_Channel_new(
if (creds) {
self->c_chan = grpc_secure_channel_create(creds->c_creds, target, &c_args);
} else {
self->c_chan = grpc_insecure_channel_create(target, &c_args);
self->c_chan = grpc_insecure_channel_create(target, &c_args, NULL);
}
pygrpc_discard_channel_args(c_args);
return self;
@ -133,7 +133,7 @@ Call *pygrpc_Channel_create_call(
call = pygrpc_Call_new_empty(cq);
call->c_call = grpc_channel_create_call(
self->c_chan, NULL, GRPC_PROPAGATE_DEFAULTS, cq->c_cq, method, host,
pygrpc_cast_double_to_gpr_timespec(deadline));
pygrpc_cast_double_to_gpr_timespec(deadline), NULL);
return call;
}

@ -90,7 +90,7 @@ PyTypeObject pygrpc_CompletionQueue_type = {
CompletionQueue *pygrpc_CompletionQueue_new(
PyTypeObject *type, PyObject *args, PyObject *kwargs) {
CompletionQueue *self = (CompletionQueue *)type->tp_alloc(type, 0);
self->c_cq = grpc_completion_queue_create();
self->c_cq = grpc_completion_queue_create(NULL);
return self;
}
@ -111,7 +111,7 @@ PyObject *pygrpc_CompletionQueue_next(
}
Py_BEGIN_ALLOW_THREADS;
event = grpc_completion_queue_next(
self->c_cq, pygrpc_cast_double_to_gpr_timespec(deadline));
self->c_cq, pygrpc_cast_double_to_gpr_timespec(deadline), NULL);
Py_END_ALLOW_THREADS;
transliterated_event = pygrpc_consume_event(event);
return transliterated_event;

@ -104,8 +104,8 @@ Server *pygrpc_Server_new(PyTypeObject *type, PyObject *args, PyObject *kwargs)
return NULL;
}
self = (Server *)type->tp_alloc(type, 0);
self->c_serv = grpc_server_create(&c_args);
grpc_server_register_completion_queue(self->c_serv, cq->c_cq);
self->c_serv = grpc_server_create(&c_args, NULL);
grpc_server_register_completion_queue(self->c_serv, cq->c_cq, NULL);
pygrpc_discard_channel_args(c_args);
self->cq = cq;
Py_INCREF(self->cq);

@ -170,7 +170,7 @@ static VALUE grpc_rb_call_cancel(VALUE self) {
grpc_call *call = NULL;
grpc_call_error err;
TypedData_Get_Struct(self, grpc_call, &grpc_call_data_type, call);
err = grpc_call_cancel(call);
err = grpc_call_cancel(call, NULL);
if (err != GRPC_CALL_OK) {
rb_raise(grpc_rb_eCallError, "cancel failed: %s (code=%d)",
grpc_call_error_detail_of(err), err);
@ -615,7 +615,7 @@ static VALUE grpc_rb_call_run_batch(VALUE self, VALUE cqueue, VALUE tag,
/* call grpc_call_start_batch, then wait for it to complete using
* pluck_event */
err = grpc_call_start_batch(call, st.ops, st.op_num, ROBJECT(tag));
err = grpc_call_start_batch(call, st.ops, st.op_num, ROBJECT(tag), NULL);
if (err != GRPC_CALL_OK) {
grpc_run_batch_stack_cleanup(&st);
rb_raise(grpc_rb_eCallError,

@ -147,7 +147,7 @@ static VALUE grpc_rb_channel_init(int argc, VALUE *argv, VALUE self) {
target_chars = StringValueCStr(target);
grpc_rb_hash_convert_to_channel_args(channel_args, &args);
if (credentials == Qnil) {
ch = grpc_insecure_channel_create(target_chars, &args);
ch = grpc_insecure_channel_create(target_chars, &args, NULL);
} else {
creds = grpc_rb_get_wrapped_credentials(credentials);
ch = grpc_secure_channel_create(creds, target_chars, &args);
@ -288,7 +288,7 @@ static VALUE grpc_rb_channel_create_call(VALUE self, VALUE cqueue,
call = grpc_channel_create_call(ch, parent_call, flags, cq, method_chars,
host_chars, grpc_rb_time_timeval(
deadline,
/* absolute time */ 0));
/* absolute time */ 0), NULL);
if (call == NULL) {
rb_raise(rb_eRuntimeError, "cannot create call with method %s",
method_chars);

@ -56,7 +56,7 @@ typedef struct next_call_stack {
static void *grpc_rb_completion_queue_next_no_gil(void *param) {
next_call_stack *const next_call = (next_call_stack*)param;
next_call->event =
grpc_completion_queue_next(next_call->cq, next_call->timeout);
grpc_completion_queue_next(next_call->cq, next_call->timeout, NULL);
return NULL;
}
@ -64,7 +64,7 @@ static void *grpc_rb_completion_queue_next_no_gil(void *param) {
static void *grpc_rb_completion_queue_pluck_no_gil(void *param) {
next_call_stack *const next_call = (next_call_stack*)param;
next_call->event = grpc_completion_queue_pluck(next_call->cq, next_call->tag,
next_call->timeout);
next_call->timeout, NULL);
return NULL;
}
@ -128,7 +128,7 @@ static rb_data_type_t grpc_rb_completion_queue_data_type = {
/* Allocates a completion queue. */
static VALUE grpc_rb_completion_queue_alloc(VALUE cls) {
grpc_completion_queue *cq = grpc_completion_queue_create();
grpc_completion_queue *cq = grpc_completion_queue_create(NULL);
if (cq == NULL) {
rb_raise(rb_eArgError, "could not create a completion queue: not sure why");
}

@ -128,7 +128,7 @@ static VALUE grpc_rb_server_init(VALUE self, VALUE cqueue, VALUE channel_args) {
TypedData_Get_Struct(self, grpc_rb_server, &grpc_rb_server_data_type,
wrapper);
grpc_rb_hash_convert_to_channel_args(channel_args, &args);
srv = grpc_server_create(&args);
srv = grpc_server_create(&args, NULL);
if (args.args != NULL) {
xfree(args.args); /* Allocated by grpc_rb_hash_convert_to_channel_args */
@ -136,7 +136,7 @@ static VALUE grpc_rb_server_init(VALUE self, VALUE cqueue, VALUE channel_args) {
if (srv == NULL) {
rb_raise(rb_eRuntimeError, "could not create a gRPC server, not sure why");
}
grpc_server_register_completion_queue(srv, cq);
grpc_server_register_completion_queue(srv, cq, NULL);
wrapper->wrapped = srv;
/* Add the cq as the server's mark object. This ensures the ruby cq can't be

@ -436,6 +436,7 @@ PROTOC_CHECK_CMD = which protoc > /dev/null
PROTOC_CHECK_VERSION_CMD = protoc --version | grep -q libprotoc.3
DTRACE_CHECK_CMD = which dtrace > /dev/null
SYSTEMTAP_HEADERS_CHECK_CMD = $(CC) $(CFLAGS) $(CPPFLAGS) -o $(TMPOUT) test/build/systemtap.c $(LDFLAGS)
ZOOKEEPER_CHECK_CMD = $(CC) $(CFLAGS) $(CPPFLAGS) -o $(TMPOUT) test/build/zookeeper.c $(LDFLAGS) -lzookeeper_mt
ifndef REQUIRE_CUSTOM_LIBRARIES_$(CONFIG)
HAS_SYSTEM_PERFTOOLS ?= $(shell $(PERFTOOLS_CHECK_CMD) 2> /dev/null && echo true || echo false)
@ -503,6 +504,8 @@ ifeq ($(HAS_SYSTEMTAP),true)
CACHE_MK += HAS_SYSTEMTAP = true,
endif
HAS_ZOOKEEPER = $(shell $(ZOOKEEPER_CHECK_CMD) 2> /dev/null && echo true || echo false)
# Note that for testing purposes, one can do:
# make HAS_EMBEDDED_OPENSSL_ALPN=false
# to emulate the fact we do not have OpenSSL in the third_party folder.
@ -621,6 +624,14 @@ PC_LIBS_PRIVATE = $(PC_LIBS_GRPC)
PC_LIB = -lgrpc
GRPC_UNSECURE_PC_FILE := $(PC_TEMPLATE)
# gprc_zookeeper .pc file
PC_NAME = gRPC zookeeper
PC_DESCRIPTION = gRPC's zookeeper plugin
PC_CFLAGS =
PC_REQUIRES_PRIVATE =
PC_LIBS_PRIVATE = -lzookeeper_mt
GRPC_ZOOKEEPER_PC_FILE := $(PC_TEMPLATE)
PROTOBUF_PKG_CONFIG = false
PC_REQUIRES_GRPCXX =
@ -813,6 +824,7 @@ run_dep_checks:
$(PERFTOOLS_CHECK_CMD) || true
$(PROTOBUF_CHECK_CMD) || true
$(PROTOC_CHECK_VERSION_CMD) || true
$(ZOOKEEPER_CHECK_CMD) || true
$(LIBDIR)/$(CONFIG)/zlib/libz.a:
$(E) "[MAKE] Building zlib"
@ -871,12 +883,13 @@ $(LIBDIR)/$(CONFIG)/protobuf/libprotobuf.a: third_party/protobuf/configure
static: static_c static_cxx
static_c: pc_c pc_c_unsecure cache.mk \
static_c: pc_c pc_c_unsecure cache.mk pc_gpr pc_c_zookeeper\
% for lib in libs:
% if lib.build == 'all' and lib.language == 'c':
% if lib.build == 'all' and lib.language == 'c' and not lib.get('external_deps', None):
$(LIBDIR)/$(CONFIG)/lib${lib.name}.a\
% endif
% endfor
static_zookeeper_libs
static_cxx: pc_cxx pc_cxx_unsecure pc_gpr cache.mk \
@ -889,13 +902,13 @@ static_cxx: pc_cxx pc_cxx_unsecure pc_gpr cache.mk \
shared: shared_c shared_cxx
shared_c: pc_c pc_c_unsecure pc_gpr cache.mk\
shared_c: pc_c pc_c_unsecure pc_gpr cache.mk pc_c_zookeeper\
% for lib in libs:
% if lib.build == 'all' and lib.language == 'c':
% if lib.build == 'all' and lib.language == 'c' and not lib.get('external_deps', None):
$(LIBDIR)/$(CONFIG)/lib${lib.name}.$(SHARED_EXT)\
% endif
% endfor
shared_zookeeper_libs
shared_cxx: pc_cxx pc_cxx_unsecure cache.mk\
% for lib in libs:
@ -912,6 +925,29 @@ shared_csharp: shared_c \
% endif
% endfor
ifeq ($(HAS_ZOOKEEPER),true)
static_zookeeper_libs:\
% for lib in libs:
% if lib.build == 'all' and lib.language == 'c' and 'zookeeper' in lib.get('external_deps', []):
$(LIBDIR)/$(CONFIG)/lib${lib.name}.a\
% endif
% endfor
shared_zookeeper_libs:\
% for lib in libs:
% if lib.build == 'all' and lib.language == 'c' and 'zookeeper' in lib.get('external_deps', []):
$(LIBDIR)/$(CONFIG)/lib${lib.name}.$(SHARED_EXT)\
% endif
% endfor
else
static_zookeeper_libs:
shared_zookeeper_libs:
endif
grpc_csharp_ext: shared_csharp
plugins: $(PROTOC_PLUGINS)
@ -920,7 +956,7 @@ privatelibs: privatelibs_c privatelibs_cxx
privatelibs_c: \
% for lib in libs:
% if lib.build == 'private' and lib.language == 'c':
% if lib.build == 'private' and lib.language == 'c' and not lib.get('external_deps', None):
$(LIBDIR)/$(CONFIG)/lib${lib.name}.a\
% endif
% endfor
@ -931,43 +967,75 @@ pc_c: $(LIBDIR)/$(CONFIG)/pkgconfig/grpc.pc
pc_c_unsecure: $(LIBDIR)/$(CONFIG)/pkgconfig/grpc_unsecure.pc
ifeq ($(HAS_ZOOKEEPER),true)
pc_c_zookeeper: $(LIBDIR)/$(CONFIG)/pkgconfig/grpc_zookeeper.pc
else
pc_c_zookeeper:
endif
pc_cxx: $(LIBDIR)/$(CONFIG)/pkgconfig/grpc++.pc
pc_cxx_unsecure: $(LIBDIR)/$(CONFIG)/pkgconfig/grpc++_unsecure.pc
privatelibs_cxx: \
% for lib in libs:
% if lib.build == 'private' and lib.language == 'c++':
% if lib.build == 'private' and lib.language == 'c++' and not lib.get('external_deps', None):
$(LIBDIR)/$(CONFIG)/lib${lib.name}.a\
% endif
% endfor
buildtests: buildtests_c buildtests_cxx
ifeq ($(HAS_ZOOKEEPER),true)
privatelibs_zookeeper: \
% for lib in libs:
% if lib.build == 'private' and lib.language == 'c++' and zookeeper in lib.get('external_deps', []):
$(LIBDIR)/$(CONFIG)/lib${lib.name}.a\
% endif
% endfor
else
privatelibs_zookeeper:
endif
buildtests: buildtests_c buildtests_cxx buildtests_zookeeper
buildtests_c: privatelibs_c\
% for tgt in targets:
% if tgt.build == 'test' and not tgt.language == 'c++':
% if tgt.build == 'test' and not tgt.language == 'c++' and not tgt.get('external_deps', None):
$(BINDIR)/$(CONFIG)/${tgt.name}\
% endif
% endfor
buildtests_cxx: buildtests_zookeeper privatelibs_cxx\
% for tgt in targets:
% if tgt.build == 'test' and tgt.language == 'c++' and not tgt.get('external_deps', None):
$(BINDIR)/$(CONFIG)/${tgt.name}\
% endif
% endfor
buildtests_cxx: privatelibs_cxx\
ifeq ($(HAS_ZOOKEEPER),true)
buildtests_zookeeper: privatelibs_zookeeper\
% for tgt in targets:
% if tgt.build == 'test' and tgt.language == 'c++':
% if tgt.build == 'test' and tgt.language == 'c++' and 'zookeeper' in tgt.get('external_deps', []):
$(BINDIR)/$(CONFIG)/${tgt.name}\
% endif
% endfor
else
buildtests_zookeeper:
endif
test: test_c test_cxx
flaky_test: flaky_test_c flaky_test_cxx
test: test_c test_cxx test_zookeeper
flaky_test: flaky_test_c flaky_test_cxx flaky_test_zookeeper
test_c: buildtests_c
% for tgt in targets:
% if tgt.build == 'test' and tgt.get('run', True) and not tgt.language == 'c++' and not tgt.get('flaky', False):
% if tgt.build == 'test' and tgt.get('run', True) and not tgt.language == 'c++' and not tgt.get('flaky', False) and not tgt.get('external_deps', None):
$(E) "[RUN] Testing ${tgt.name}"
$(Q) $(BINDIR)/$(CONFIG)/${tgt.name} || ( echo test ${tgt.name} failed ; exit 1 )
% endif
@ -976,16 +1044,16 @@ test_c: buildtests_c
flaky_test_c: buildtests_c
% for tgt in targets:
% if tgt.build == 'test' and tgt.get('run', True) and not tgt.language == 'c++' and tgt.get('flaky', False):
% if tgt.build == 'test' and tgt.get('run', True) and not tgt.language == 'c++' and tgt.get('flaky', False) and not tgt.get('external_deps', None):
$(E) "[RUN] Testing ${tgt.name}"
$(Q) $(BINDIR)/$(CONFIG)/${tgt.name} || ( echo test ${tgt.name} failed ; exit 1 )
% endif
% endfor
test_cxx: buildtests_cxx
test_cxx: test_zookeeper buildtests_cxx
% for tgt in targets:
% if tgt.build == 'test' and tgt.get('run', True) and tgt.language == 'c++' and not tgt.get('flaky', False):
% if tgt.build == 'test' and tgt.get('run', True) and tgt.language == 'c++' and not tgt.get('flaky', False) and not tgt.get('external_deps', None):
$(E) "[RUN] Testing ${tgt.name}"
$(Q) $(BINDIR)/$(CONFIG)/${tgt.name} || ( echo test ${tgt.name} failed ; exit 1 )
% endif
@ -994,13 +1062,37 @@ test_cxx: buildtests_cxx
flaky_test_cxx: buildtests_cxx
% for tgt in targets:
% if tgt.build == 'test' and tgt.get('run', True) and tgt.language == 'c++' and tgt.get('flaky', False):
% if tgt.build == 'test' and tgt.get('run', True) and tgt.language == 'c++' and tgt.get('flaky', False) and not tgt.get('external_deps', None):
$(E) "[RUN] Testing ${tgt.name}"
$(Q) $(BINDIR)/$(CONFIG)/${tgt.name} || ( echo test ${tgt.name} failed ; exit 1 )
% endif
% endfor
ifeq ($(HAS_ZOOKEEPER),true)
test_zookeeper: buildtests_zookeeper
% for tgt in targets:
% if tgt.build == 'test' and tgt.get('run', True) and tgt.language == 'c++' and not tgt.get('flaky', False) and 'zookeeper' in tgt.get('external_deps', []):
$(E) "[RUN] Testing ${tgt.name}"
$(Q) $(BINDIR)/$(CONFIG)/${tgt.name} || ( echo test ${tgt.name} failed ; exit 1 )
% endif
% endfor
flaky_test_zookeeper: buildtests_zookeeper
% for tgt in targets:
% if tgt.build == 'test' and tgt.get('run', True) and tgt.language == 'c++' and tgt.get('flaky', False) and 'zookeeper' in tgt.get('external_deps', []):
$(E) "[RUN] Testing ${tgt.name}"
$(Q) $(BINDIR)/$(CONFIG)/${tgt.name} || ( echo test ${tgt.name} failed ; exit 1 )
% endif
% endfor
else
test_zookeeper:
flaky_test_zookeeper:
endif
test_python: static_c
$(E) "[RUN] Testing python code"
$(Q) tools/run_tests/run_tests.py -lpython -c$(CONFIG)
@ -1063,23 +1155,52 @@ ifeq ($(CONFIG),opt)
% for lib in libs:
% if lib.language == "c++":
% if lib.build == "all":
% if not lib.get('external_deps', None):
$(E) "[STRIP] Stripping lib${lib.name}.a"
$(Q) $(STRIP) $(LIBDIR)/$(CONFIG)/lib${lib.name}.a
% endif
% endif
% endif
% endfor
ifeq ($(HAS_ZOOKEEPER),true)
% for lib in libs:
% if lib.language == "c++":
% if lib.build == "all":
% if 'zookeeper' in lib.get('external_deps', []):
$(E) "[STRIP] Stripping lib${lib.name}.a"
$(Q) $(STRIP) $(LIBDIR)/$(CONFIG)/lib${lib.name}.a
% endif
% endif
% endif
% endfor
endif
endif
strip-shared_c: shared_c
ifeq ($(CONFIG),opt)
% for lib in libs:
% if lib.language == "c":
% if lib.build == "all":
% if not lib.get('external_deps', None):
$(E) "[STRIP] Stripping lib${lib.name}.so"
$(Q) $(STRIP) $(LIBDIR)/$(CONFIG)/lib${lib.name}.$(SHARED_EXT)
% endif
% endif
% endif
% endfor
ifeq ($(HAS_ZOOKEEPER),true)
% for lib in libs:
% if lib.language == "c":
% if lib.build == "all":
% if 'zookeeper' in lib.get('external_deps', []):
$(E) "[STRIP] Stripping lib${lib.name}.so"
$(Q) $(STRIP) $(LIBDIR)/$(CONFIG)/lib${lib.name}.$(SHARED_EXT)
% endif
% endif
% endif
% endfor
endif
endif
strip-shared_cxx: shared_cxx
@ -1125,6 +1246,11 @@ $(LIBDIR)/$(CONFIG)/pkgconfig/grpc_unsecure.pc:
$(Q) mkdir -p $(@D)
$(Q) echo "$(GRPC_UNSECURE_PC_FILE)" | tr , '\n' >$@
$(LIBDIR)/$(CONFIG)/pkgconfig/grpc_zookeeper.pc:
$(E) "[MAKE] Generating $@"
$(Q) mkdir -p $(@D)
$(Q) echo -e "$(GRPC_ZOOKEEPER_PC_FILE)" >$@
$(LIBDIR)/$(CONFIG)/pkgconfig/grpc++.pc:
$(E) "[MAKE] Generating $@"
$(Q) mkdir -p $(@D)
@ -1213,12 +1339,27 @@ install-static_c: static_c strip-static_c install-pkg-config_c
% for lib in libs:
% if lib.language == "c":
% if lib.build == "all":
% if not lib.get('external_deps', None):
$(E) "[INSTALL] Installing lib${lib.name}.a"
$(Q) $(INSTALL) -d $(prefix)/lib
$(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/lib${lib.name}.a $(prefix)/lib/lib${lib.name}.a
% endif
% endif
% endif
% endfor
ifeq ($(HAS_ZOOKEEPER),true)
% for lib in libs:
% if lib.language == "c":
% if lib.build == "all":
% if 'zookeeper' in lib.get('external_deps', []):
$(E) "[INSTALL] Installing lib${lib.name}.a"
$(Q) $(INSTALL) -d $(prefix)/lib
$(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/lib${lib.name}.a $(prefix)/lib/lib${lib.name}.a
% endif
% endif
% endif
% endfor
endif
install-static_cxx: static_cxx strip-static_cxx install-pkg-config_cxx
% for lib in libs:
@ -1235,6 +1376,30 @@ install-static_cxx: static_cxx strip-static_cxx install-pkg-config_cxx
% for lib in libs:
% if lib.language == lang_filter:
% if lib.build == "all":
% if not lib.get('external_deps', None):
ifeq ($(SYSTEM),MINGW32)
$(E) "[INSTALL] Installing ${lib.name}.$(SHARED_EXT)"
$(Q) $(INSTALL) -d $(prefix)/lib
$(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/${lib.name}.$(SHARED_EXT) $(prefix)/lib/${lib.name}.$(SHARED_EXT)
$(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/lib${lib.name}-imp.a $(prefix)/lib/lib${lib.name}-imp.a
else
$(E) "[INSTALL] Installing lib${lib.name}.$(SHARED_EXT)"
$(Q) $(INSTALL) -d $(prefix)/lib
$(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/lib${lib.name}.$(SHARED_EXT) $(prefix)/lib/lib${lib.name}.$(SHARED_EXT)
ifneq ($(SYSTEM),Darwin)
$(Q) ln -sf lib${lib.name}.$(SHARED_EXT) $(prefix)/lib/lib${lib.name}.so.${settings.version.major}
$(Q) ln -sf lib${lib.name}.$(SHARED_EXT) $(prefix)/lib/lib${lib.name}.so
endif
endif
% endif
% endif
% endif
% endfor
ifeq ($(HAS_ZOOKEEPER),true)
% for lib in libs:
% if lib.language == lang_filter:
% if lib.build == "all":
% if 'zookeeper' in lib.get('external_deps', []):
ifeq ($(SYSTEM),MINGW32)
$(E) "[INSTALL] Installing ${lib.name}.$(SHARED_EXT)"
$(Q) $(INSTALL) -d $(prefix)/lib
@ -1251,7 +1416,9 @@ endif
endif
% endif
% endif
% endif
% endfor
endif
ifneq ($(SYSTEM),MINGW32)
ifneq ($(SYSTEM),Darwin)
$(Q) ldconfig || true
@ -1281,12 +1448,15 @@ else
% endfor
endif
install-pkg-config_c: pc_gpr pc_c pc_c_unsecure
install-pkg-config_c: pc_gpr pc_c pc_c_unsecure pc_c_zookeeper
$(E) "[INSTALL] Installing C pkg-config files"
$(Q) $(INSTALL) -d $(prefix)/lib/pkgconfig
$(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/pkgconfig/gpr.pc $(prefix)/lib/pkgconfig/gpr.pc
$(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/pkgconfig/grpc.pc $(prefix)/lib/pkgconfig/grpc.pc
$(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/pkgconfig/grpc_unsecure.pc $(prefix)/lib/pkgconfig/grpc_unsecure.pc
ifeq ($(HAS_ZOOKEEPER),true)
$(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/pkgconfig/grpc_zookeeper.pc $(prefix)/lib/pkgconfig/grpc_zookeeper.pc
endif
install-pkg-config_cxx: pc_cxx pc_cxx_unsecure
$(E) "[INSTALL] Installing C++ pkg-config files"
@ -1480,6 +1650,9 @@ endif
for src in lib.src:
sources_that_don_t_need_openssl.add(src)
if 'zookeeper' in lib.get('external_deps', []):
libs = libs + ' -lzookeeper_mt'
if lib.get('secure', 'check') == 'yes' or lib.get('secure', 'check') == 'check':
lib_deps = lib_deps + ' $(OPENSSL_DEP)'
mingw_lib_deps = mingw_lib_deps + ' $(OPENSSL_DEP)'
@ -1619,6 +1792,9 @@ $(${tgt.name.upper()}_OBJS)\
% for dep in tgt.deps:
$(LIBDIR)/$(CONFIG)/lib${dep}.a\
% endfor
% if 'zookeeper' in tgt.get('external_deps', []):
-lzookeeper_mt\
% endif
% if tgt.language == "c++":
% if tgt.build == 'protoc':
$(HOST_LDLIBSXX) $(HOST_LDLIBS_PROTOC)\

@ -0,0 +1,2 @@
<%namespace file="../vcxproj_defs.include" import="gen_project"/>\
${gen_project('grpc_test_util_unsecure', libs)}

@ -0,0 +1,43 @@
/*
*
* Copyright 2015, Google Inc.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
* met:
*
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* * Redistributions in binary form must reproduce the above
* copyright notice, this list of conditions and the following disclaimer
* in the documentation and/or other materials provided with the
* distribution.
* * Neither the name of Google Inc. nor the names of its
* contributors may be used to endorse or promote products derived from
* this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
* OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
*/
/* This is just a compilation test, to see if we have Zookeeper C client
library installed. */
#include <stdlib.h>
#include <zookeeper/zookeeper.h>
int main() {
zookeeper_init(NULL, NULL, 0, 0, 0, 0);
return 0;
}

@ -102,11 +102,11 @@ void grpc_run_bad_client_test(grpc_bad_client_server_side_validator validator,
/* Create server, completion events */
a.server = grpc_server_create_from_filters(NULL, 0, NULL);
a.cq = grpc_completion_queue_create();
a.cq = grpc_completion_queue_create(NULL);
gpr_event_init(&a.done_thd);
gpr_event_init(&a.done_write);
a.validator = validator;
grpc_server_register_completion_queue(a.server, a.cq);
grpc_server_register_completion_queue(a.server, a.cq, NULL);
grpc_server_start(a.server);
transport = grpc_create_chttp2_transport(NULL, sfd.server, mdctx, 0);
server_setup_transport(&a, transport, mdctx);
@ -151,7 +151,8 @@ void grpc_run_bad_client_test(grpc_bad_client_server_side_validator validator,
}
grpc_server_shutdown_and_notify(a.server, a.cq, NULL);
GPR_ASSERT(grpc_completion_queue_pluck(a.cq, NULL,
GRPC_TIMEOUT_SECONDS_TO_DEADLINE(1))
GRPC_TIMEOUT_SECONDS_TO_DEADLINE(1),
NULL)
.type == GRPC_OP_COMPLETE);
grpc_server_destroy(a.server);
grpc_completion_queue_destroy(a.cq);

@ -37,8 +37,8 @@
static void verifier(grpc_server *server, grpc_completion_queue *cq) {
while (grpc_server_has_open_connections(server)) {
GPR_ASSERT(
grpc_completion_queue_next(cq, GRPC_TIMEOUT_MILLIS_TO_DEADLINE(20))
.type == GRPC_QUEUE_TIMEOUT);
grpc_completion_queue_next(cq, GRPC_TIMEOUT_MILLIS_TO_DEADLINE(20),
NULL).type == GRPC_QUEUE_TIMEOUT);
}
}

@ -39,8 +39,8 @@
static void verifier(grpc_server *server, grpc_completion_queue *cq) {
while (grpc_server_has_open_connections(server)) {
GPR_ASSERT(
grpc_completion_queue_next(cq, GRPC_TIMEOUT_MILLIS_TO_DEADLINE(20))
.type == GRPC_QUEUE_TIMEOUT);
grpc_completion_queue_next(cq, GRPC_TIMEOUT_MILLIS_TO_DEADLINE(20),
NULL).type == GRPC_QUEUE_TIMEOUT);
}
}

@ -226,7 +226,7 @@ void cq_verify(cq_verifier *v) {
gpr_strvec_init(&have_tags);
while (v->expect.next != &v->expect) {
ev = grpc_completion_queue_next(v->cq, deadline);
ev = grpc_completion_queue_next(v->cq, deadline, NULL);
if (ev.type == GRPC_QUEUE_TIMEOUT) {
fail_no_event_received(v);
break;
@ -265,7 +265,7 @@ void cq_verify_empty(cq_verifier *v) {
GPR_ASSERT(v->expect.next == &v->expect && "expectation queue must be empty");
ev = grpc_completion_queue_next(v->cq, deadline);
ev = grpc_completion_queue_next(v->cq, deadline, NULL);
if (ev.type != GRPC_QUEUE_TIMEOUT) {
char *s = grpc_event_string(&ev);
gpr_log(GPR_ERROR, "unexpected event (expected nothing): %s", s);

@ -53,7 +53,7 @@ static gpr_timespec ms_from_now(int ms) {
static void drain_cq(grpc_completion_queue *cq) {
grpc_event ev;
do {
ev = grpc_completion_queue_next(cq, ms_from_now(5000));
ev = grpc_completion_queue_next(cq, ms_from_now(5000), NULL);
} while (ev.type != GRPC_QUEUE_SHUTDOWN);
}
@ -75,6 +75,7 @@ void test_connect(const char *server_host, const char *client_host, int port,
grpc_metadata_array trailing_metadata_recv;
grpc_metadata_array request_metadata_recv;
grpc_status_code status;
grpc_call_error error;
char *details = NULL;
size_t details_capacity = 0;
int was_cancelled = 2;
@ -93,9 +94,9 @@ void test_connect(const char *server_host, const char *client_host, int port,
grpc_call_details_init(&call_details);
/* Create server. */
cq = grpc_completion_queue_create();
server = grpc_server_create(NULL);
grpc_server_register_completion_queue(server, cq);
cq = grpc_completion_queue_create(NULL);
server = grpc_server_create(NULL, NULL);
grpc_server_register_completion_queue(server, cq, NULL);
GPR_ASSERT((got_port = grpc_server_add_insecure_http2_port(
server, server_hostport)) > 0);
if (port == 0) {
@ -113,7 +114,7 @@ void test_connect(const char *server_host, const char *client_host, int port,
} else {
gpr_join_host_port(&client_hostport, client_host, port);
}
client = grpc_insecure_channel_create(client_hostport, NULL);
client = grpc_insecure_channel_create(client_hostport, NULL, NULL);
gpr_log(GPR_INFO, "Testing with server=%s client=%s (expecting %s)",
server_hostport, client_hostport, expect_ok ? "success" : "failure");
@ -132,20 +133,23 @@ void test_connect(const char *server_host, const char *client_host, int port,
/* Send a trivial request. */
c = grpc_channel_create_call(client, NULL, GRPC_PROPAGATE_DEFAULTS, cq,
"/foo", "foo.test.google.fr", deadline);
"/foo", "foo.test.google.fr", deadline, NULL);
GPR_ASSERT(c);
op = ops;
op->op = GRPC_OP_SEND_INITIAL_METADATA;
op->data.send_initial_metadata.count = 0;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_SEND_CLOSE_FROM_CLIENT;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_RECV_INITIAL_METADATA;
op->data.recv_initial_metadata = &initial_metadata_recv;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_RECV_STATUS_ON_CLIENT;
op->data.recv_status_on_client.trailing_metadata = &trailing_metadata_recv;
@ -153,14 +157,16 @@ void test_connect(const char *server_host, const char *client_host, int port,
op->data.recv_status_on_client.status_details = &details;
op->data.recv_status_on_client.status_details_capacity = &details_capacity;
op->flags = 0;
op->reserved = NULL;
op++;
GPR_ASSERT(GRPC_CALL_OK == grpc_call_start_batch(c, ops, op - ops, tag(1)));
error = grpc_call_start_batch(c, ops, op - ops, tag(1), NULL);
GPR_ASSERT(GRPC_CALL_OK == error);
if (expect_ok) {
/* Check for a successful request. */
GPR_ASSERT(GRPC_CALL_OK == grpc_server_request_call(
server, &s, &call_details,
&request_metadata_recv, cq, cq, tag(101)));
error = grpc_server_request_call(server, &s, &call_details,
&request_metadata_recv, cq, cq, tag(101));
GPR_ASSERT(GRPC_CALL_OK == error);
cq_expect_completion(cqv, tag(101), 1);
cq_verify(cqv);
@ -179,8 +185,8 @@ void test_connect(const char *server_host, const char *client_host, int port,
op->data.recv_close_on_server.cancelled = &was_cancelled;
op->flags = 0;
op++;
GPR_ASSERT(GRPC_CALL_OK ==
grpc_call_start_batch(s, ops, op - ops, tag(102)));
error = grpc_call_start_batch(s, ops, op - ops, tag(102), NULL);
GPR_ASSERT(GRPC_CALL_OK == error);
cq_expect_completion(cqv, tag(102), 1);
cq_expect_completion(cqv, tag(1), 1);
@ -215,7 +221,8 @@ void test_connect(const char *server_host, const char *client_host, int port,
/* Destroy server. */
grpc_server_shutdown_and_notify(server, cq, tag(1000));
GPR_ASSERT(grpc_completion_queue_pluck(cq, tag(1000),
GRPC_TIMEOUT_SECONDS_TO_DEADLINE(5))
GRPC_TIMEOUT_SECONDS_TO_DEADLINE(5),
NULL)
.type == GRPC_OP_COMPLETE);
grpc_server_destroy(server);
grpc_completion_queue_shutdown(cq);

@ -60,7 +60,7 @@ static grpc_end2end_test_fixture chttp2_create_fixture_secure_fullstack(
gpr_join_host_port(&ffd->localaddr, "localhost", port);
f.fixture_data = ffd;
f.cq = grpc_completion_queue_create();
f.cq = grpc_completion_queue_create(NULL);
return f;
}
@ -89,8 +89,8 @@ static void chttp2_init_server_secure_fullstack(
if (f->server) {
grpc_server_destroy(f->server);
}
f->server = grpc_server_create(server_args);
grpc_server_register_completion_queue(f->server, f->cq);
f->server = grpc_server_create(server_args, NULL);
grpc_server_register_completion_queue(f->server, f->cq, NULL);
GPR_ASSERT(grpc_server_add_secure_http2_port(f->server, ffd->localaddr,
server_creds));
grpc_server_credentials_release(server_creds);

@ -64,7 +64,7 @@ static grpc_end2end_test_fixture chttp2_create_fixture_fullstack(
gpr_join_host_port(&ffd->localaddr, "localhost", port);
f.fixture_data = ffd;
f.cq = grpc_completion_queue_create();
f.cq = grpc_completion_queue_create(NULL);
return f;
}
@ -72,7 +72,7 @@ static grpc_end2end_test_fixture chttp2_create_fixture_fullstack(
void chttp2_init_client_fullstack(grpc_end2end_test_fixture *f,
grpc_channel_args *client_args) {
fullstack_fixture_data *ffd = f->fixture_data;
f->client = grpc_insecure_channel_create(ffd->localaddr, client_args);
f->client = grpc_insecure_channel_create(ffd->localaddr, client_args, NULL);
GPR_ASSERT(f->client);
}
@ -82,8 +82,8 @@ void chttp2_init_server_fullstack(grpc_end2end_test_fixture *f,
if (f->server) {
grpc_server_destroy(f->server);
}
f->server = grpc_server_create(server_args);
grpc_server_register_completion_queue(f->server, f->cq);
f->server = grpc_server_create(server_args, NULL);
grpc_server_register_completion_queue(f->server, f->cq, NULL);
GPR_ASSERT(grpc_server_add_insecure_http2_port(f->server, ffd->localaddr));
grpc_server_start(f->server);
}

@ -69,7 +69,7 @@ static grpc_end2end_test_fixture chttp2_create_fixture_fullstack_compression(
memset(&f, 0, sizeof(f));
f.fixture_data = ffd;
f.cq = grpc_completion_queue_create();
f.cq = grpc_completion_queue_create(NULL);
return f;
}
@ -83,7 +83,7 @@ void chttp2_init_client_fullstack_compression(grpc_end2end_test_fixture *f,
ffd->client_args_compression = grpc_channel_args_set_compression_algorithm(
client_args, GRPC_COMPRESS_GZIP);
f->client = grpc_insecure_channel_create(ffd->localaddr,
ffd->client_args_compression);
ffd->client_args_compression, NULL);
}
void chttp2_init_server_fullstack_compression(grpc_end2end_test_fixture *f,
@ -97,8 +97,8 @@ void chttp2_init_server_fullstack_compression(grpc_end2end_test_fixture *f,
if (f->server) {
grpc_server_destroy(f->server);
}
f->server = grpc_server_create(ffd->server_args_compression);
grpc_server_register_completion_queue(f->server, f->cq);
f->server = grpc_server_create(ffd->server_args_compression, NULL);
grpc_server_register_completion_queue(f->server, f->cq, NULL);
GPR_ASSERT(grpc_server_add_insecure_http2_port(f->server, ffd->localaddr));
grpc_server_start(f->server);
}

@ -70,7 +70,7 @@ static grpc_end2end_test_fixture chttp2_create_fixture_fullstack(
unique++);
f.fixture_data = ffd;
f.cq = grpc_completion_queue_create();
f.cq = grpc_completion_queue_create(NULL);
return f;
}
@ -78,7 +78,7 @@ static grpc_end2end_test_fixture chttp2_create_fixture_fullstack(
void chttp2_init_client_fullstack(grpc_end2end_test_fixture *f,
grpc_channel_args *client_args) {
fullstack_fixture_data *ffd = f->fixture_data;
f->client = grpc_insecure_channel_create(ffd->localaddr, client_args);
f->client = grpc_insecure_channel_create(ffd->localaddr, client_args, NULL);
}
void chttp2_init_server_fullstack(grpc_end2end_test_fixture *f,
@ -87,8 +87,8 @@ void chttp2_init_server_fullstack(grpc_end2end_test_fixture *f,
if (f->server) {
grpc_server_destroy(f->server);
}
f->server = grpc_server_create(server_args);
grpc_server_register_completion_queue(f->server, f->cq);
f->server = grpc_server_create(server_args, NULL);
grpc_server_register_completion_queue(f->server, f->cq, NULL);
GPR_ASSERT(grpc_server_add_insecure_http2_port(f->server, ffd->localaddr));
grpc_server_start(f->server);
}

@ -70,7 +70,7 @@ static grpc_end2end_test_fixture chttp2_create_fixture_fullstack(
unique++);
f.fixture_data = ffd;
f.cq = grpc_completion_queue_create();
f.cq = grpc_completion_queue_create(NULL);
return f;
}
@ -78,7 +78,7 @@ static grpc_end2end_test_fixture chttp2_create_fixture_fullstack(
void chttp2_init_client_fullstack(grpc_end2end_test_fixture *f,
grpc_channel_args *client_args) {
fullstack_fixture_data *ffd = f->fixture_data;
f->client = grpc_insecure_channel_create(ffd->localaddr, client_args);
f->client = grpc_insecure_channel_create(ffd->localaddr, client_args, NULL);
}
void chttp2_init_server_fullstack(grpc_end2end_test_fixture *f,
@ -87,8 +87,8 @@ void chttp2_init_server_fullstack(grpc_end2end_test_fixture *f,
if (f->server) {
grpc_server_destroy(f->server);
}
f->server = grpc_server_create(server_args);
grpc_server_register_completion_queue(f->server, f->cq);
f->server = grpc_server_create(server_args, NULL);
grpc_server_register_completion_queue(f->server, f->cq, NULL);
GPR_ASSERT(grpc_server_add_insecure_http2_port(f->server, ffd->localaddr));
grpc_server_start(f->server);
}

@ -64,7 +64,7 @@ static grpc_end2end_test_fixture chttp2_create_fixture_fullstack(
gpr_join_host_port(&ffd->localaddr, "localhost", port);
f.fixture_data = ffd;
f.cq = grpc_completion_queue_create();
f.cq = grpc_completion_queue_create(NULL);
return f;
}
@ -72,7 +72,7 @@ static grpc_end2end_test_fixture chttp2_create_fixture_fullstack(
void chttp2_init_client_fullstack(grpc_end2end_test_fixture *f,
grpc_channel_args *client_args) {
fullstack_fixture_data *ffd = f->fixture_data;
f->client = grpc_insecure_channel_create(ffd->localaddr, client_args);
f->client = grpc_insecure_channel_create(ffd->localaddr, client_args, NULL);
}
void chttp2_init_server_fullstack(grpc_end2end_test_fixture *f,
@ -81,8 +81,8 @@ void chttp2_init_server_fullstack(grpc_end2end_test_fixture *f,
if (f->server) {
grpc_server_destroy(f->server);
}
f->server = grpc_server_create(server_args);
grpc_server_register_completion_queue(f->server, f->cq);
f->server = grpc_server_create(server_args, NULL);
grpc_server_register_completion_queue(f->server, f->cq, NULL);
GPR_ASSERT(grpc_server_add_insecure_http2_port(f->server, ffd->localaddr));
grpc_server_start(f->server);
}

@ -56,13 +56,13 @@ typedef struct fullstack_fixture_data {
} fullstack_fixture_data;
static grpc_server *create_proxy_server(const char *port) {
grpc_server *s = grpc_server_create(NULL);
grpc_server *s = grpc_server_create(NULL, NULL);
GPR_ASSERT(grpc_server_add_insecure_http2_port(s, port));
return s;
}
static grpc_channel *create_proxy_client(const char *target) {
return grpc_insecure_channel_create(target, NULL);
return grpc_insecure_channel_create(target, NULL, NULL);
}
static const grpc_end2end_proxy_def proxy_def = {create_proxy_server,
@ -77,7 +77,7 @@ static grpc_end2end_test_fixture chttp2_create_fixture_fullstack(
ffd->proxy = grpc_end2end_proxy_create(&proxy_def);
f.fixture_data = ffd;
f.cq = grpc_completion_queue_create();
f.cq = grpc_completion_queue_create(NULL);
return f;
}
@ -86,7 +86,7 @@ void chttp2_init_client_fullstack(grpc_end2end_test_fixture *f,
grpc_channel_args *client_args) {
fullstack_fixture_data *ffd = f->fixture_data;
f->client = grpc_insecure_channel_create(
grpc_end2end_proxy_get_client_target(ffd->proxy), client_args);
grpc_end2end_proxy_get_client_target(ffd->proxy), client_args, NULL);
GPR_ASSERT(f->client);
}
@ -96,8 +96,8 @@ void chttp2_init_server_fullstack(grpc_end2end_test_fixture *f,
if (f->server) {
grpc_server_destroy(f->server);
}
f->server = grpc_server_create(server_args);
grpc_server_register_completion_queue(f->server, f->cq);
f->server = grpc_server_create(server_args, NULL);
grpc_server_register_completion_queue(f->server, f->cq, NULL);
GPR_ASSERT(grpc_server_add_insecure_http2_port(
f->server, grpc_end2end_proxy_get_server_port(ffd->proxy)));
grpc_server_start(f->server);

@ -63,7 +63,7 @@ static grpc_end2end_test_fixture chttp2_create_fixture_secure_fullstack(
gpr_join_host_port(&ffd->localaddr, "localhost", port);
f.fixture_data = ffd;
f.cq = grpc_completion_queue_create();
f.cq = grpc_completion_queue_create(NULL);
return f;
}
@ -92,8 +92,8 @@ static void chttp2_init_server_secure_fullstack(
if (f->server) {
grpc_server_destroy(f->server);
}
f->server = grpc_server_create(server_args);
grpc_server_register_completion_queue(f->server, f->cq);
f->server = grpc_server_create(server_args, NULL);
grpc_server_register_completion_queue(f->server, f->cq, NULL);
GPR_ASSERT(grpc_server_add_secure_http2_port(f->server, ffd->localaddr,
server_creds));
grpc_server_credentials_release(server_creds);

@ -63,7 +63,7 @@ static grpc_end2end_test_fixture chttp2_create_fixture_secure_fullstack(
gpr_join_host_port(&ffd->localaddr, "localhost", port);
f.fixture_data = ffd;
f.cq = grpc_completion_queue_create();
f.cq = grpc_completion_queue_create(NULL);
return f;
}
@ -92,8 +92,8 @@ static void chttp2_init_server_secure_fullstack(
if (f->server) {
grpc_server_destroy(f->server);
}
f->server = grpc_server_create(server_args);
grpc_server_register_completion_queue(f->server, f->cq);
f->server = grpc_server_create(server_args, NULL);
grpc_server_register_completion_queue(f->server, f->cq, NULL);
GPR_ASSERT(grpc_server_add_secure_http2_port(f->server, ffd->localaddr,
server_creds));
grpc_server_credentials_release(server_creds);

@ -54,7 +54,7 @@ typedef struct fullstack_secure_fixture_data {
} fullstack_secure_fixture_data;
static grpc_server *create_proxy_server(const char *port) {
grpc_server *s = grpc_server_create(NULL);
grpc_server *s = grpc_server_create(NULL, NULL);
grpc_ssl_pem_key_cert_pair pem_cert_key_pair = {test_server1_key,
test_server1_cert};
grpc_server_credentials *ssl_creds =
@ -91,7 +91,7 @@ static grpc_end2end_test_fixture chttp2_create_fixture_secure_fullstack(
ffd->proxy = grpc_end2end_proxy_create(&proxy_def);
f.fixture_data = ffd;
f.cq = grpc_completion_queue_create();
f.cq = grpc_completion_queue_create(NULL);
return f;
}
@ -121,8 +121,8 @@ static void chttp2_init_server_secure_fullstack(
if (f->server) {
grpc_server_destroy(f->server);
}
f->server = grpc_server_create(server_args);
grpc_server_register_completion_queue(f->server, f->cq);
f->server = grpc_server_create(server_args, NULL);
grpc_server_register_completion_queue(f->server, f->cq, NULL);
GPR_ASSERT(grpc_server_add_secure_http2_port(
f->server, grpc_end2end_proxy_get_server_port(ffd->proxy), server_creds));
grpc_server_credentials_release(server_creds);

@ -105,7 +105,7 @@ static grpc_end2end_test_fixture chttp2_create_fixture_secure_fullstack(
gpr_join_host_port(&ffd->localaddr, "localhost", port);
f.fixture_data = ffd;
f.cq = grpc_completion_queue_create();
f.cq = grpc_completion_queue_create(NULL);
return f;
}
@ -126,8 +126,8 @@ static void chttp2_init_server_secure_fullstack(
if (f->server) {
grpc_server_destroy(f->server);
}
f->server = grpc_server_create(server_args);
grpc_server_register_completion_queue(f->server, f->cq);
f->server = grpc_server_create(server_args, NULL);
grpc_server_register_completion_queue(f->server, f->cq, NULL);
GPR_ASSERT(grpc_server_add_secure_http2_port(f->server, ffd->localaddr,
server_creds));
grpc_server_credentials_release(server_creds);

@ -95,7 +95,7 @@ static grpc_end2end_test_fixture chttp2_create_fixture_socketpair(
grpc_end2end_test_fixture f;
memset(&f, 0, sizeof(f));
f.fixture_data = sfd;
f.cq = grpc_completion_queue_create();
f.cq = grpc_completion_queue_create(NULL);
*sfd = grpc_iomgr_create_endpoint_pair("fixture", 65536);
@ -123,7 +123,7 @@ static void chttp2_init_server_socketpair(grpc_end2end_test_fixture *f,
grpc_transport *transport;
GPR_ASSERT(!f->server);
f->server = grpc_server_create_from_filters(NULL, 0, server_args);
grpc_server_register_completion_queue(f->server, f->cq);
grpc_server_register_completion_queue(f->server, f->cq, NULL);
grpc_server_start(f->server);
transport = grpc_create_chttp2_transport(server_args, sfd->server, mdctx, 0);
server_setup_transport(f, transport, mdctx);

@ -95,7 +95,7 @@ static grpc_end2end_test_fixture chttp2_create_fixture_socketpair(
grpc_end2end_test_fixture f;
memset(&f, 0, sizeof(f));
f.fixture_data = sfd;
f.cq = grpc_completion_queue_create();
f.cq = grpc_completion_queue_create(NULL);
*sfd = grpc_iomgr_create_endpoint_pair("fixture", 1);
@ -123,7 +123,7 @@ static void chttp2_init_server_socketpair(grpc_end2end_test_fixture *f,
grpc_transport *transport;
GPR_ASSERT(!f->server);
f->server = grpc_server_create_from_filters(NULL, 0, server_args);
grpc_server_register_completion_queue(f->server, f->cq);
grpc_server_register_completion_queue(f->server, f->cq, NULL);
grpc_server_start(f->server);
transport = grpc_create_chttp2_transport(server_args, sfd->server, mdctx, 0);
server_setup_transport(f, transport, mdctx);

@ -96,7 +96,7 @@ static grpc_end2end_test_fixture chttp2_create_fixture_socketpair(
grpc_end2end_test_fixture f;
memset(&f, 0, sizeof(f));
f.fixture_data = sfd;
f.cq = grpc_completion_queue_create();
f.cq = grpc_completion_queue_create(NULL);
*sfd = grpc_iomgr_create_endpoint_pair("fixture", 65536);
@ -124,7 +124,7 @@ static void chttp2_init_server_socketpair(grpc_end2end_test_fixture *f,
grpc_transport *transport;
GPR_ASSERT(!f->server);
f->server = grpc_server_create_from_filters(NULL, 0, server_args);
grpc_server_register_completion_queue(f->server, f->cq);
grpc_server_register_completion_queue(f->server, f->cq, NULL);
grpc_server_start(f->server);
transport = grpc_create_chttp2_transport(server_args, sfd->server, mdctx, 0);
server_setup_transport(f, transport, mdctx);

@ -100,11 +100,11 @@ grpc_end2end_proxy *grpc_end2end_proxy_create(
gpr_join_host_port(&proxy->proxy_port, "localhost", proxy_port);
gpr_join_host_port(&proxy->server_port, "localhost", server_port);
proxy->cq = grpc_completion_queue_create();
proxy->cq = grpc_completion_queue_create(NULL);
proxy->server = def->create_server(proxy->proxy_port);
proxy->client = def->create_client(proxy->server_port);
grpc_server_register_completion_queue(proxy->server, proxy->cq);
grpc_server_register_completion_queue(proxy->server, proxy->cq, NULL);
grpc_server_start(proxy->server);
gpr_thd_options_set_joinable(&opt);
@ -178,7 +178,8 @@ static void on_p2s_recv_initial_metadata(void *arg, int success) {
op.data.send_initial_metadata.metadata = pc->p2s_initial_metadata.metadata;
refpc(pc, "on_c2p_sent_initial_metadata");
err = grpc_call_start_batch(pc->c2p, &op, 1,
new_closure(on_c2p_sent_initial_metadata, pc));
new_closure(on_c2p_sent_initial_metadata, pc),
NULL);
GPR_ASSERT(err == GRPC_CALL_OK);
}
@ -204,7 +205,7 @@ static void on_p2s_sent_message(void *arg, int success) {
op.data.recv_message = &pc->c2p_msg;
refpc(pc, "on_c2p_recv_msg");
err = grpc_call_start_batch(pc->c2p, &op, 1,
new_closure(on_c2p_recv_msg, pc));
new_closure(on_c2p_recv_msg, pc), NULL);
GPR_ASSERT(err == GRPC_CALL_OK);
}
@ -228,14 +229,14 @@ static void on_c2p_recv_msg(void *arg, int success) {
op.data.send_message = pc->c2p_msg;
refpc(pc, "on_p2s_sent_message");
err = grpc_call_start_batch(pc->p2s, &op, 1,
new_closure(on_p2s_sent_message, pc));
new_closure(on_p2s_sent_message, pc), NULL);
GPR_ASSERT(err == GRPC_CALL_OK);
} else {
op.op = GRPC_OP_SEND_CLOSE_FROM_CLIENT;
op.flags = 0;
refpc(pc, "on_p2s_sent_close");
err = grpc_call_start_batch(pc->p2s, &op, 1,
new_closure(on_p2s_sent_close, pc));
new_closure(on_p2s_sent_close, pc), NULL);
GPR_ASSERT(err == GRPC_CALL_OK);
}
}
@ -257,7 +258,7 @@ static void on_c2p_sent_message(void *arg, int success) {
op.data.recv_message = &pc->p2s_msg;
refpc(pc, "on_p2s_recv_msg");
err = grpc_call_start_batch(pc->p2s, &op, 1,
new_closure(on_p2s_recv_msg, pc));
new_closure(on_p2s_recv_msg, pc), NULL);
GPR_ASSERT(err == GRPC_CALL_OK);
}
@ -275,7 +276,7 @@ static void on_p2s_recv_msg(void *arg, int success) {
op.data.send_message = pc->p2s_msg;
refpc(pc, "on_c2p_sent_message");
err = grpc_call_start_batch(pc->c2p, &op, 1,
new_closure(on_c2p_sent_message, pc));
new_closure(on_c2p_sent_message, pc), NULL);
GPR_ASSERT(err == GRPC_CALL_OK);
}
unrefpc(pc, "on_p2s_recv_msg");
@ -303,7 +304,7 @@ static void on_p2s_status(void *arg, int success) {
op.data.send_status_from_server.status_details = pc->p2s_status_details;
refpc(pc, "on_c2p_sent_status");
err = grpc_call_start_batch(pc->c2p, &op, 1,
new_closure(on_c2p_sent_status, pc));
new_closure(on_c2p_sent_status, pc), NULL);
GPR_ASSERT(err == GRPC_CALL_OK);
}
@ -330,7 +331,7 @@ static void on_new_call(void *arg, int success) {
pc->p2s = grpc_channel_create_call(
proxy->client, pc->c2p, GRPC_PROPAGATE_DEFAULTS, proxy->cq,
proxy->new_call_details.method, proxy->new_call_details.host,
proxy->new_call_details.deadline);
proxy->new_call_details.deadline, NULL);
gpr_ref_init(&pc->refs, 1);
op.flags = 0;
@ -339,7 +340,8 @@ static void on_new_call(void *arg, int success) {
op.data.recv_initial_metadata = &pc->p2s_initial_metadata;
refpc(pc, "on_p2s_recv_initial_metadata");
err = grpc_call_start_batch(pc->p2s, &op, 1,
new_closure(on_p2s_recv_initial_metadata, pc));
new_closure(on_p2s_recv_initial_metadata, pc),
NULL);
GPR_ASSERT(err == GRPC_CALL_OK);
op.op = GRPC_OP_SEND_INITIAL_METADATA;
@ -347,21 +349,22 @@ static void on_new_call(void *arg, int success) {
op.data.send_initial_metadata.metadata = pc->c2p_initial_metadata.metadata;
refpc(pc, "on_p2s_sent_initial_metadata");
err = grpc_call_start_batch(pc->p2s, &op, 1,
new_closure(on_p2s_sent_initial_metadata, pc));
new_closure(on_p2s_sent_initial_metadata, pc),
NULL);
GPR_ASSERT(err == GRPC_CALL_OK);
op.op = GRPC_OP_RECV_MESSAGE;
op.data.recv_message = &pc->c2p_msg;
refpc(pc, "on_c2p_recv_msg");
err = grpc_call_start_batch(pc->c2p, &op, 1,
new_closure(on_c2p_recv_msg, pc));
new_closure(on_c2p_recv_msg, pc), NULL);
GPR_ASSERT(err == GRPC_CALL_OK);
op.op = GRPC_OP_RECV_MESSAGE;
op.data.recv_message = &pc->p2s_msg;
refpc(pc, "on_p2s_recv_msg");
err = grpc_call_start_batch(pc->p2s, &op, 1,
new_closure(on_p2s_recv_msg, pc));
new_closure(on_p2s_recv_msg, pc), NULL);
GPR_ASSERT(err == GRPC_CALL_OK);
op.op = GRPC_OP_RECV_STATUS_ON_CLIENT;
@ -372,15 +375,15 @@ static void on_new_call(void *arg, int success) {
op.data.recv_status_on_client.status_details_capacity =
&pc->p2s_status_details_capacity;
refpc(pc, "on_p2s_status");
err =
grpc_call_start_batch(pc->p2s, &op, 1, new_closure(on_p2s_status, pc));
err = grpc_call_start_batch(pc->p2s, &op, 1,
new_closure(on_p2s_status, pc), NULL);
GPR_ASSERT(err == GRPC_CALL_OK);
op.op = GRPC_OP_RECV_CLOSE_ON_SERVER;
op.data.recv_close_on_server.cancelled = &pc->c2p_server_cancelled;
refpc(pc, "on_c2p_closed");
err =
grpc_call_start_batch(pc->c2p, &op, 1, new_closure(on_c2p_closed, pc));
err = grpc_call_start_batch(pc->c2p, &op, 1,
new_closure(on_c2p_closed, pc), NULL);
GPR_ASSERT(err == GRPC_CALL_OK);
request_call(proxy);
@ -405,7 +408,7 @@ static void thread_main(void *arg) {
closure *cl;
for (;;) {
grpc_event ev = grpc_completion_queue_next(
proxy->cq, gpr_inf_future(GPR_CLOCK_MONOTONIC));
proxy->cq, gpr_inf_future(GPR_CLOCK_MONOTONIC), NULL);
switch (ev.type) {
case GRPC_QUEUE_TIMEOUT:
gpr_log(GPR_ERROR, "Should never reach here");

@ -41,20 +41,20 @@ int main(int argc, char **argv) {
grpc_test_init(argc, argv);
grpc_init();
cq1 = grpc_completion_queue_create();
cq2 = grpc_completion_queue_create();
server = grpc_server_create(NULL);
grpc_server_register_completion_queue(server, cq1);
cq1 = grpc_completion_queue_create(NULL);
cq2 = grpc_completion_queue_create(NULL);
server = grpc_server_create(NULL, NULL);
grpc_server_register_completion_queue(server, cq1, NULL);
grpc_server_add_insecure_http2_port(server, "[::]:0");
grpc_server_register_completion_queue(server, cq2);
grpc_server_register_completion_queue(server, cq2, NULL);
grpc_server_start(server);
grpc_server_shutdown_and_notify(server, cq2, NULL);
grpc_completion_queue_next(
cq2, gpr_inf_future(GPR_CLOCK_REALTIME)); /* cue queue hang */
cq2, gpr_inf_future(GPR_CLOCK_REALTIME), NULL); /* cue queue hang */
grpc_completion_queue_shutdown(cq1);
grpc_completion_queue_shutdown(cq2);
grpc_completion_queue_next(cq1, gpr_inf_future(GPR_CLOCK_REALTIME));
grpc_completion_queue_next(cq2, gpr_inf_future(GPR_CLOCK_REALTIME));
grpc_completion_queue_next(cq1, gpr_inf_future(GPR_CLOCK_REALTIME), NULL);
grpc_completion_queue_next(cq2, gpr_inf_future(GPR_CLOCK_REALTIME), NULL);
grpc_server_destroy(server);
grpc_completion_queue_destroy(cq1);
grpc_completion_queue_destroy(cq2);

@ -57,18 +57,19 @@ int main(int argc, char **argv) {
grpc_metadata_array_init(&trailing_metadata_recv);
cq = grpc_completion_queue_create();
cq = grpc_completion_queue_create(NULL);
cqv = cq_verifier_create(cq);
/* create a call, channel to a non existant server */
chan = grpc_insecure_channel_create("nonexistant:54321", NULL);
chan = grpc_insecure_channel_create("nonexistant:54321", NULL, NULL);
call = grpc_channel_create_call(chan, NULL, GRPC_PROPAGATE_DEFAULTS, cq,
"/Foo", "nonexistant", deadline);
"/Foo", "nonexistant", deadline, NULL);
op = ops;
op->op = GRPC_OP_SEND_INITIAL_METADATA;
op->data.send_initial_metadata.count = 0;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_RECV_STATUS_ON_CLIENT;
op->data.recv_status_on_client.trailing_metadata = &trailing_metadata_recv;
@ -76,9 +77,10 @@ int main(int argc, char **argv) {
op->data.recv_status_on_client.status_details = &details;
op->data.recv_status_on_client.status_details_capacity = &details_capacity;
op->flags = 0;
op->reserved = NULL;
op++;
GPR_ASSERT(GRPC_CALL_OK ==
grpc_call_start_batch(call, ops, op - ops, tag(1)));
grpc_call_start_batch(call, ops, op - ops, tag(1), NULL));
/* verify that all tags get completed */
cq_expect_completion(cqv, tag(1), 1);
cq_verify(cqv);
@ -86,8 +88,8 @@ int main(int argc, char **argv) {
GPR_ASSERT(status == GRPC_STATUS_DEADLINE_EXCEEDED);
grpc_completion_queue_shutdown(cq);
while (grpc_completion_queue_next(cq, gpr_inf_future(GPR_CLOCK_REALTIME))
.type != GRPC_QUEUE_SHUTDOWN)
while (grpc_completion_queue_next(cq, gpr_inf_future(GPR_CLOCK_REALTIME),
NULL).type != GRPC_QUEUE_SHUTDOWN)
;
grpc_completion_queue_destroy(cq);
grpc_call_destroy(call);

@ -70,7 +70,7 @@ static gpr_timespec five_seconds_time(void) { return n_seconds_time(5); }
static void drain_cq(grpc_completion_queue *cq) {
grpc_event ev;
do {
ev = grpc_completion_queue_next(cq, five_seconds_time());
ev = grpc_completion_queue_next(cq, five_seconds_time(), NULL);
} while (ev.type != GRPC_QUEUE_SHUTDOWN);
}
@ -78,7 +78,8 @@ static void shutdown_server(grpc_end2end_test_fixture *f) {
if (!f->server) return;
grpc_server_shutdown_and_notify(f->server, f->cq, tag(1000));
GPR_ASSERT(grpc_completion_queue_pluck(f->cq, tag(1000),
GRPC_TIMEOUT_SECONDS_TO_DEADLINE(5))
GRPC_TIMEOUT_SECONDS_TO_DEADLINE(5),
NULL)
.type == GRPC_OP_COMPLETE);
grpc_server_destroy(f->server);
f->server = NULL;
@ -110,11 +111,12 @@ static void simple_request_body(grpc_end2end_test_fixture f) {
grpc_metadata_array request_metadata_recv;
grpc_call_details call_details;
grpc_status_code status;
grpc_call_error error;
char *details = NULL;
size_t details_capacity = 0;
c = grpc_channel_create_call(f.client, NULL, GRPC_PROPAGATE_DEFAULTS, f.cq,
"/foo", "slartibartfast.local", deadline);
"/foo", "slartibartfast.local", deadline, NULL);
GPR_ASSERT(c);
grpc_metadata_array_init(&initial_metadata_recv);
@ -126,13 +128,16 @@ static void simple_request_body(grpc_end2end_test_fixture f) {
op->op = GRPC_OP_SEND_INITIAL_METADATA;
op->data.send_initial_metadata.count = 0;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_SEND_CLOSE_FROM_CLIENT;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_RECV_INITIAL_METADATA;
op->data.recv_initial_metadata = &initial_metadata_recv;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_RECV_STATUS_ON_CLIENT;
op->data.recv_status_on_client.trailing_metadata = &trailing_metadata_recv;
@ -140,8 +145,10 @@ static void simple_request_body(grpc_end2end_test_fixture f) {
op->data.recv_status_on_client.status_details = &details;
op->data.recv_status_on_client.status_details_capacity = &details_capacity;
op->flags = 0;
op->reserved = NULL;
op++;
GPR_ASSERT(GRPC_CALL_OK == grpc_call_start_batch(c, ops, op - ops, tag(1)));
error = grpc_call_start_batch(c, ops, op - ops, tag(1), NULL);
GPR_ASSERT(GRPC_CALL_OK == error);
cq_expect_completion(cqv, tag(1), 1);
cq_verify(cqv);

@ -69,7 +69,7 @@ static gpr_timespec five_seconds_time(void) { return n_seconds_time(5); }
static void drain_cq(grpc_completion_queue *cq) {
grpc_event ev;
do {
ev = grpc_completion_queue_next(cq, five_seconds_time());
ev = grpc_completion_queue_next(cq, five_seconds_time(), NULL);
} while (ev.type != GRPC_QUEUE_SHUTDOWN);
}
@ -77,7 +77,8 @@ static void shutdown_server(grpc_end2end_test_fixture *f) {
if (!f->server) return;
grpc_server_shutdown_and_notify(f->server, f->cq, tag(1000));
GPR_ASSERT(grpc_completion_queue_pluck(f->cq, tag(1000),
GRPC_TIMEOUT_SECONDS_TO_DEADLINE(5))
GRPC_TIMEOUT_SECONDS_TO_DEADLINE(5),
NULL)
.type == GRPC_OP_COMPLETE);
grpc_server_destroy(f->server);
f->server = NULL;
@ -114,6 +115,7 @@ static void test_cancel_after_accept(grpc_end2end_test_config config,
grpc_metadata_array request_metadata_recv;
grpc_call_details call_details;
grpc_status_code status;
grpc_call_error error;
char *details = NULL;
size_t details_capacity = 0;
grpc_byte_buffer *request_payload_recv = NULL;
@ -127,7 +129,7 @@ static void test_cancel_after_accept(grpc_end2end_test_config config,
int was_cancelled = 2;
c = grpc_channel_create_call(f.client, NULL, GRPC_PROPAGATE_DEFAULTS, f.cq,
"/foo", "foo.test.google.fr", deadline);
"/foo", "foo.test.google.fr", deadline, NULL);
GPR_ASSERT(c);
grpc_metadata_array_init(&initial_metadata_recv);
@ -142,28 +144,34 @@ static void test_cancel_after_accept(grpc_end2end_test_config config,
op->data.recv_status_on_client.status_details = &details;
op->data.recv_status_on_client.status_details_capacity = &details_capacity;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_SEND_INITIAL_METADATA;
op->data.send_initial_metadata.count = 0;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_SEND_MESSAGE;
op->data.send_message = request_payload;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_RECV_INITIAL_METADATA;
op->data.recv_initial_metadata = &initial_metadata_recv;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_RECV_MESSAGE;
op->data.recv_message = &response_payload_recv;
op->flags = 0;
op->reserved = NULL;
op++;
GPR_ASSERT(GRPC_CALL_OK == grpc_call_start_batch(c, ops, op - ops, tag(1)));
error = grpc_call_start_batch(c, ops, op - ops, tag(1), NULL);
GPR_ASSERT(GRPC_CALL_OK == error);
GPR_ASSERT(GRPC_CALL_OK == grpc_server_request_call(
f.server, &s, &call_details,
&request_metadata_recv, f.cq, f.cq, tag(2)));
error = grpc_server_request_call(f.server, &s, &call_details,
&request_metadata_recv, f.cq, f.cq, tag(2));
GPR_ASSERT(GRPC_CALL_OK == error);
cq_expect_completion(cqv, tag(2), 1);
cq_verify(cqv);
@ -171,22 +179,27 @@ static void test_cancel_after_accept(grpc_end2end_test_config config,
op->op = GRPC_OP_RECV_MESSAGE;
op->data.recv_message = &request_payload_recv;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_SEND_INITIAL_METADATA;
op->data.send_initial_metadata.count = 0;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_SEND_MESSAGE;
op->data.send_message = response_payload;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_RECV_CLOSE_ON_SERVER;
op->data.recv_close_on_server.cancelled = &was_cancelled;
op->flags = 0;
op->reserved = NULL;
op++;
GPR_ASSERT(GRPC_CALL_OK == grpc_call_start_batch(s, ops, op - ops, tag(3)));
error = grpc_call_start_batch(s, ops, op - ops, tag(3), NULL);
GPR_ASSERT(GRPC_CALL_OK == error);
GPR_ASSERT(GRPC_CALL_OK == mode.initiate_cancel(c));
GPR_ASSERT(GRPC_CALL_OK == mode.initiate_cancel(c, NULL));
cq_expect_completion(cqv, tag(3), 1);
cq_expect_completion(cqv, tag(1), 1);

@ -69,7 +69,7 @@ static gpr_timespec five_seconds_time(void) { return n_seconds_time(5); }
static void drain_cq(grpc_completion_queue *cq) {
grpc_event ev;
do {
ev = grpc_completion_queue_next(cq, five_seconds_time());
ev = grpc_completion_queue_next(cq, five_seconds_time(), NULL);
} while (ev.type != GRPC_QUEUE_SHUTDOWN);
}
@ -77,7 +77,8 @@ static void shutdown_server(grpc_end2end_test_fixture *f) {
if (!f->server) return;
grpc_server_shutdown_and_notify(f->server, f->cq, tag(1000));
GPR_ASSERT(grpc_completion_queue_pluck(f->cq, tag(1000),
GRPC_TIMEOUT_SECONDS_TO_DEADLINE(5))
GRPC_TIMEOUT_SECONDS_TO_DEADLINE(5),
NULL)
.type == GRPC_OP_COMPLETE);
grpc_server_destroy(f->server);
f->server = NULL;
@ -114,6 +115,7 @@ static void test_cancel_after_accept_and_writes_closed(
grpc_metadata_array request_metadata_recv;
grpc_call_details call_details;
grpc_status_code status;
grpc_call_error error;
char *details = NULL;
size_t details_capacity = 0;
grpc_byte_buffer *request_payload_recv = NULL;
@ -127,7 +129,7 @@ static void test_cancel_after_accept_and_writes_closed(
int was_cancelled = 2;
c = grpc_channel_create_call(f.client, NULL, GRPC_PROPAGATE_DEFAULTS, f.cq,
"/foo", "foo.test.google.fr", deadline);
"/foo", "foo.test.google.fr", deadline, NULL);
GPR_ASSERT(c);
grpc_metadata_array_init(&initial_metadata_recv);
@ -142,31 +144,38 @@ static void test_cancel_after_accept_and_writes_closed(
op->data.recv_status_on_client.status_details = &details;
op->data.recv_status_on_client.status_details_capacity = &details_capacity;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_SEND_INITIAL_METADATA;
op->data.send_initial_metadata.count = 0;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_SEND_MESSAGE;
op->data.send_message = request_payload;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_SEND_CLOSE_FROM_CLIENT;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_RECV_INITIAL_METADATA;
op->data.recv_initial_metadata = &initial_metadata_recv;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_RECV_MESSAGE;
op->data.recv_message = &response_payload_recv;
op->flags = 0;
op->reserved = NULL;
op++;
GPR_ASSERT(GRPC_CALL_OK == grpc_call_start_batch(c, ops, op - ops, tag(1)));
error = grpc_call_start_batch(c, ops, op - ops, tag(1), NULL);
GPR_ASSERT(GRPC_CALL_OK == error);
GPR_ASSERT(GRPC_CALL_OK == grpc_server_request_call(
f.server, &s, &call_details,
&request_metadata_recv, f.cq, f.cq, tag(2)));
error = grpc_server_request_call(f.server, &s, &call_details,
&request_metadata_recv, f.cq, f.cq, tag(2));
GPR_ASSERT(GRPC_CALL_OK == error);
cq_expect_completion(cqv, tag(2), 1);
cq_verify(cqv);
@ -174,22 +183,27 @@ static void test_cancel_after_accept_and_writes_closed(
op->op = GRPC_OP_RECV_MESSAGE;
op->data.recv_message = &request_payload_recv;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_RECV_CLOSE_ON_SERVER;
op->data.recv_close_on_server.cancelled = &was_cancelled;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_SEND_INITIAL_METADATA;
op->data.send_initial_metadata.count = 0;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_SEND_MESSAGE;
op->data.send_message = response_payload;
op->flags = 0;
op->reserved = NULL;
op++;
GPR_ASSERT(GRPC_CALL_OK == grpc_call_start_batch(s, ops, op - ops, tag(3)));
error = grpc_call_start_batch(s, ops, op - ops, tag(3), NULL);
GPR_ASSERT(GRPC_CALL_OK == error);
GPR_ASSERT(GRPC_CALL_OK == mode.initiate_cancel(c));
GPR_ASSERT(GRPC_CALL_OK == mode.initiate_cancel(c, NULL));
cq_expect_completion(cqv, tag(3), 1);
cq_expect_completion(cqv, tag(1), 1);

@ -70,7 +70,7 @@ static gpr_timespec five_seconds_time(void) { return n_seconds_time(5); }
static void drain_cq(grpc_completion_queue *cq) {
grpc_event ev;
do {
ev = grpc_completion_queue_next(cq, five_seconds_time());
ev = grpc_completion_queue_next(cq, five_seconds_time(), NULL);
} while (ev.type != GRPC_QUEUE_SHUTDOWN);
}
@ -78,7 +78,8 @@ static void shutdown_server(grpc_end2end_test_fixture *f) {
if (!f->server) return;
grpc_server_shutdown_and_notify(f->server, f->cq, tag(1000));
GPR_ASSERT(grpc_completion_queue_pluck(f->cq, tag(1000),
GRPC_TIMEOUT_SECONDS_TO_DEADLINE(5))
GRPC_TIMEOUT_SECONDS_TO_DEADLINE(5),
NULL)
.type == GRPC_OP_COMPLETE);
grpc_server_destroy(f->server);
f->server = NULL;
@ -114,6 +115,7 @@ static void test_cancel_after_invoke(grpc_end2end_test_config config,
grpc_metadata_array request_metadata_recv;
grpc_call_details call_details;
grpc_status_code status;
grpc_call_error error;
char *details = NULL;
size_t details_capacity = 0;
grpc_byte_buffer *response_payload_recv = NULL;
@ -122,7 +124,7 @@ static void test_cancel_after_invoke(grpc_end2end_test_config config,
grpc_raw_byte_buffer_create(&request_payload_slice, 1);
c = grpc_channel_create_call(f.client, NULL, GRPC_PROPAGATE_DEFAULTS, f.cq,
"/foo", "foo.test.google.fr", deadline);
"/foo", "foo.test.google.fr", deadline, NULL);
GPR_ASSERT(c);
grpc_metadata_array_init(&initial_metadata_recv);
@ -137,29 +139,36 @@ static void test_cancel_after_invoke(grpc_end2end_test_config config,
op->data.recv_status_on_client.status_details = &details;
op->data.recv_status_on_client.status_details_capacity = &details_capacity;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_SEND_INITIAL_METADATA;
op->data.send_initial_metadata.count = 0;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_SEND_MESSAGE;
op->data.send_message = request_payload;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_SEND_CLOSE_FROM_CLIENT;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_RECV_INITIAL_METADATA;
op->data.recv_initial_metadata = &initial_metadata_recv;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_RECV_MESSAGE;
op->data.recv_message = &response_payload_recv;
op->flags = 0;
op->reserved = NULL;
op++;
GPR_ASSERT(GRPC_CALL_OK == grpc_call_start_batch(c, ops, test_ops, tag(1)));
error = grpc_call_start_batch(c, ops, test_ops, tag(1), NULL);
GPR_ASSERT(GRPC_CALL_OK == error);
GPR_ASSERT(GRPC_CALL_OK == mode.initiate_cancel(c));
GPR_ASSERT(GRPC_CALL_OK == mode.initiate_cancel(c, NULL));
cq_expect_completion(cqv, tag(1), 1);
cq_verify(cqv);

@ -68,7 +68,7 @@ static gpr_timespec five_seconds_time(void) { return n_seconds_time(5); }
static void drain_cq(grpc_completion_queue *cq) {
grpc_event ev;
do {
ev = grpc_completion_queue_next(cq, five_seconds_time());
ev = grpc_completion_queue_next(cq, five_seconds_time(), NULL);
} while (ev.type != GRPC_QUEUE_SHUTDOWN);
}
@ -76,7 +76,8 @@ static void shutdown_server(grpc_end2end_test_fixture *f) {
if (!f->server) return;
grpc_server_shutdown_and_notify(f->server, f->cq, tag(1000));
GPR_ASSERT(grpc_completion_queue_pluck(f->cq, tag(1000),
GRPC_TIMEOUT_SECONDS_TO_DEADLINE(5))
GRPC_TIMEOUT_SECONDS_TO_DEADLINE(5),
NULL)
.type == GRPC_OP_COMPLETE);
grpc_server_destroy(f->server);
f->server = NULL;
@ -112,6 +113,7 @@ static void test_cancel_before_invoke(grpc_end2end_test_config config,
grpc_metadata_array request_metadata_recv;
grpc_call_details call_details;
grpc_status_code status;
grpc_call_error error;
char *details = NULL;
size_t details_capacity = 0;
grpc_byte_buffer *response_payload_recv = NULL;
@ -120,10 +122,10 @@ static void test_cancel_before_invoke(grpc_end2end_test_config config,
grpc_raw_byte_buffer_create(&request_payload_slice, 1);
c = grpc_channel_create_call(f.client, NULL, GRPC_PROPAGATE_DEFAULTS, f.cq,
"/foo", "foo.test.google.fr", deadline);
"/foo", "foo.test.google.fr", deadline, NULL);
GPR_ASSERT(c);
GPR_ASSERT(GRPC_CALL_OK == grpc_call_cancel(c));
GPR_ASSERT(GRPC_CALL_OK == grpc_call_cancel(c, NULL));
grpc_metadata_array_init(&initial_metadata_recv);
grpc_metadata_array_init(&trailing_metadata_recv);
@ -137,27 +139,34 @@ static void test_cancel_before_invoke(grpc_end2end_test_config config,
op->data.recv_status_on_client.status_details = &details;
op->data.recv_status_on_client.status_details_capacity = &details_capacity;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_SEND_INITIAL_METADATA;
op->data.send_initial_metadata.count = 0;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_SEND_MESSAGE;
op->data.send_message = request_payload;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_SEND_CLOSE_FROM_CLIENT;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_RECV_INITIAL_METADATA;
op->data.recv_initial_metadata = &initial_metadata_recv;
op->flags = 0;
op->reserved = NULL;
op++;
op->op = GRPC_OP_RECV_MESSAGE;
op->data.recv_message = &response_payload_recv;
op->flags = 0;
op->reserved = NULL;
op++;
GPR_ASSERT(GRPC_CALL_OK == grpc_call_start_batch(c, ops, test_ops, tag(1)));
error = grpc_call_start_batch(c, ops, test_ops, tag(1), NULL);
GPR_ASSERT(GRPC_CALL_OK == error);
cq_expect_completion(cqv, tag(1), 1);
cq_verify(cqv);

@ -69,7 +69,7 @@ static gpr_timespec five_seconds_time(void) { return n_seconds_time(5); }
static void drain_cq(grpc_completion_queue *cq) {
grpc_event ev;
do {
ev = grpc_completion_queue_next(cq, five_seconds_time());
ev = grpc_completion_queue_next(cq, five_seconds_time(), NULL);
} while (ev.type != GRPC_QUEUE_SHUTDOWN);
}
@ -77,7 +77,8 @@ static void shutdown_server(grpc_end2end_test_fixture *f) {
if (!f->server) return;
grpc_server_shutdown_and_notify(f->server, f->cq, tag(1000));
GPR_ASSERT(grpc_completion_queue_pluck(f->cq, tag(1000),
GRPC_TIMEOUT_SECONDS_TO_DEADLINE(5))
GRPC_TIMEOUT_SECONDS_TO_DEADLINE(5),
NULL)
.type == GRPC_OP_COMPLETE);
grpc_server_destroy(f->server);
f->server = NULL;
@ -108,10 +109,10 @@ static void test_cancel_in_a_vacuum(grpc_end2end_test_config config,
cq_verifier *v_client = cq_verifier_create(f.cq);
c = grpc_channel_create_call(f.client, NULL, GRPC_PROPAGATE_DEFAULTS, f.cq,
"/foo", "foo.test.google.fr", deadline);
"/foo", "foo.test.google.fr", deadline, NULL);
GPR_ASSERT(c);
GPR_ASSERT(GRPC_CALL_OK == mode.initiate_cancel(c));
GPR_ASSERT(GRPC_CALL_OK == mode.initiate_cancel(c, NULL));
grpc_call_destroy(c);

@ -36,12 +36,13 @@
typedef struct {
const char *name;
grpc_call_error (*initiate_cancel)(grpc_call *call);
grpc_call_error (*initiate_cancel)(grpc_call *call, void *reserved);
grpc_status_code expect_status;
const char *expect_details;
} cancellation_mode;
static grpc_call_error wait_for_deadline(grpc_call *call) {
static grpc_call_error wait_for_deadline(grpc_call *call, void *reserved) {
(void) reserved;
return GRPC_CALL_OK;
}

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

Loading…
Cancel
Save