diff options
author | Muxi Yan <mxyan@google.com> | 2017-12-13 14:04:45 -0800 |
---|---|---|
committer | Muxi Yan <mxyan@google.com> | 2017-12-13 14:04:45 -0800 |
commit | 032e9b32dc5978a042bdda5c3031ae6cbd928973 (patch) | |
tree | 9a9102f17700c05003cb2c85801913e48637ddf5 /include/grpc++ | |
parent | 86ece2c8f6740bf046cddbe66e6cec12d50fb29b (diff) | |
parent | 91a851c6e1f6bc7c1dbf84ea12558d535c911252 (diff) |
Merge remote-tracking branch 'upstream/master' into fix-stream-compression-config-interface
Diffstat (limited to 'include/grpc++')
-rw-r--r-- | include/grpc++/generic/async_generic_service.h | 17 | ||||
-rw-r--r-- | include/grpc++/impl/codegen/async_unary_call.h | 7 | ||||
-rw-r--r-- | include/grpc++/impl/codegen/call.h | 15 | ||||
-rw-r--r-- | include/grpc++/impl/codegen/client_context.h | 14 |
4 files changed, 50 insertions, 3 deletions
diff --git a/include/grpc++/generic/async_generic_service.h b/include/grpc++/generic/async_generic_service.h index cd9a65e3cb..b1ea4f3909 100644 --- a/include/grpc++/generic/async_generic_service.h +++ b/include/grpc++/generic/async_generic_service.h @@ -42,6 +42,23 @@ class GenericServerContext final : public ServerContext { grpc::string host_; }; +// A generic service at the server side accepts all RPC methods and hosts. It is +// typically used in proxies. The generic service can be registered to a server +// which also has other services. +// Sample usage: +// ServerBuilder builder; +// auto cq = builder.AddCompletionQueue(); +// AsyncGenericService generic_service; +// builder.RegisterAsyncGeneicService(&generic_service); +// auto server = builder.BuildAndStart(); +// +// // request a new call +// GenericServerContext context; +// GenericAsyncReaderWriter stream; +// generic_service.RequestCall(&context, &stream, cq.get(), cq.get(), tag); +// +// When tag is retrieved from cq->Next(), context.method() can be used to look +// at the method and the RPC can be handled accordingly. class AsyncGenericService final { public: AsyncGenericService() : server_(nullptr) {} diff --git a/include/grpc++/impl/codegen/async_unary_call.h b/include/grpc++/impl/codegen/async_unary_call.h index b9ea5fd19c..fb573004cb 100644 --- a/include/grpc++/impl/codegen/async_unary_call.h +++ b/include/grpc++/impl/codegen/async_unary_call.h @@ -103,6 +103,13 @@ class ClientAsyncResponseReader final assert(size == sizeof(ClientAsyncResponseReader)); } + // This operator should never be called as the memory should be freed as part + // of the arena destruction. It only exists to provide a matching operator + // delete to the operator new so that some compilers will not complain (see + // https://github.com/grpc/grpc/issues/11301) Note at the time of adding this + // there are no tests catching the compiler warning. + static void operator delete(void*, void*) { assert(0); } + void StartCall() override { assert(!started_); started_ = true; diff --git a/include/grpc++/impl/codegen/call.h b/include/grpc++/impl/codegen/call.h index 1c7f9b3d00..2758e94c5e 100644 --- a/include/grpc++/impl/codegen/call.h +++ b/include/grpc++/impl/codegen/call.h @@ -541,10 +541,12 @@ class CallOpRecvInitialMetadata { class CallOpClientRecvStatus { public: - CallOpClientRecvStatus() : recv_status_(nullptr) {} + CallOpClientRecvStatus() + : recv_status_(nullptr), debug_error_string_(nullptr) {} void ClientRecvStatus(ClientContext* context, Status* status) { - metadata_map_ = &context->trailing_metadata_; + client_context_ = context; + metadata_map_ = &client_context_->trailing_metadata_; recv_status_ = status; error_message_ = g_core_codegen_interface->grpc_empty_slice(); } @@ -557,7 +559,7 @@ class CallOpClientRecvStatus { op->data.recv_status_on_client.trailing_metadata = metadata_map_->arr(); op->data.recv_status_on_client.status = &status_code_; op->data.recv_status_on_client.status_details = &error_message_; - op->data.recv_status_on_client.error_string = nullptr; + op->data.recv_status_on_client.error_string = &debug_error_string_; op->flags = 0; op->reserved = NULL; } @@ -575,13 +577,20 @@ class CallOpClientRecvStatus { grpc::string(GRPC_SLICE_START_PTR(error_message_), GRPC_SLICE_END_PTR(error_message_)), binary_error_details); + client_context_->set_debug_error_string( + debug_error_string_ != nullptr ? debug_error_string_ : ""); g_core_codegen_interface->grpc_slice_unref(error_message_); + if (debug_error_string_ != nullptr) { + g_core_codegen_interface->gpr_free((void*)debug_error_string_); + } recv_status_ = nullptr; } private: + ClientContext* client_context_; MetadataMap* metadata_map_; Status* recv_status_; + const char* debug_error_string_; grpc_status_code status_code_; grpc_slice error_message_; }; diff --git a/include/grpc++/impl/codegen/client_context.h b/include/grpc++/impl/codegen/client_context.h index 22b581cbc5..61d97ce818 100644 --- a/include/grpc++/impl/codegen/client_context.h +++ b/include/grpc++/impl/codegen/client_context.h @@ -348,6 +348,13 @@ class ClientContext { /// Applications never need to call this method. grpc_call* c_call() { return call_; } + /// EXPERIMENTAL debugging API + /// + /// if status is not ok() for an RPC, this will return a detailed string + /// of the gRPC Core error that led to the failure. It should not be relied + /// upon for anything other than gaining more debug data in failure cases. + grpc::string debug_error_string() const { return debug_error_string_; } + private: // Disallow copy and assign. ClientContext(const ClientContext&); @@ -374,6 +381,11 @@ class ClientContext { template <class InputMessage, class OutputMessage> friend class ::grpc::internal::BlockingUnaryCallImpl; + // Used by friend class CallOpClientRecvStatus + void set_debug_error_string(const grpc::string& debug_error_string) { + debug_error_string_ = debug_error_string; + } + grpc_call* call() const { return call_; } void set_call(grpc_call* call, const std::shared_ptr<Channel>& channel); @@ -412,6 +424,8 @@ class ClientContext { grpc_compression_algorithm compression_algorithm_; bool initial_metadata_corked_; + + grpc::string debug_error_string_; }; } // namespace grpc |