diff --git a/cpp/dmi/hw_management_service.grpc.pb.h b/cpp/dmi/hw_management_service.grpc.pb.h
new file mode 100644
index 0000000..db23956
--- /dev/null
+++ b/cpp/dmi/hw_management_service.grpc.pb.h
@@ -0,0 +1,2893 @@
+// Generated by the gRPC C++ plugin.
+// If you make any local change, they will be lost.
+// source: dmi/hw_management_service.proto
+#ifndef GRPC_dmi_2fhw_5fmanagement_5fservice_2eproto__INCLUDED
+#define GRPC_dmi_2fhw_5fmanagement_5fservice_2eproto__INCLUDED
+
+#include "dmi/hw_management_service.pb.h"
+
+#include <functional>
+#include <grpc/impl/codegen/port_platform.h>
+#include <grpcpp/impl/codegen/async_generic_service.h>
+#include <grpcpp/impl/codegen/async_stream.h>
+#include <grpcpp/impl/codegen/async_unary_call.h>
+#include <grpcpp/impl/codegen/client_callback.h>
+#include <grpcpp/impl/codegen/client_context.h>
+#include <grpcpp/impl/codegen/completion_queue.h>
+#include <grpcpp/impl/codegen/message_allocator.h>
+#include <grpcpp/impl/codegen/method_handler.h>
+#include <grpcpp/impl/codegen/proto_utils.h>
+#include <grpcpp/impl/codegen/rpc_method.h>
+#include <grpcpp/impl/codegen/server_callback.h>
+#include <grpcpp/impl/codegen/server_callback_handlers.h>
+#include <grpcpp/impl/codegen/server_context.h>
+#include <grpcpp/impl/codegen/service_type.h>
+#include <grpcpp/impl/codegen/status.h>
+#include <grpcpp/impl/codegen/stub_options.h>
+#include <grpcpp/impl/codegen/sync_stream.h>
+
+namespace dmi {
+
+class NativeHWManagementService final {
+ public:
+  static constexpr char const* service_full_name() {
+    return "dmi.NativeHWManagementService";
+  }
+  class StubInterface {
+   public:
+    virtual ~StubInterface() {}
+    // Initializes context for a device and sets up required states
+    // In the call to StartManagingDevice, the fields of ModifiableComponent which are relevant
+    // and their meanings in this context is mentioned below:
+    // name = The unique name that needs to be assigned to this hardware;
+    // class = COMPONENT_TYPE_UNDEFINED;
+    // parent = nil;
+    // alias = Optional;
+    // asset_id = Optional;
+    // uri = IP Address of the Hardware;
+    std::unique_ptr< ::grpc::ClientReaderInterface< ::dmi::StartManagingDeviceResponse>> StartManagingDevice(::grpc::ClientContext* context, const ::dmi::ModifiableComponent& request) {
+      return std::unique_ptr< ::grpc::ClientReaderInterface< ::dmi::StartManagingDeviceResponse>>(StartManagingDeviceRaw(context, request));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncReaderInterface< ::dmi::StartManagingDeviceResponse>> AsyncStartManagingDevice(::grpc::ClientContext* context, const ::dmi::ModifiableComponent& request, ::grpc::CompletionQueue* cq, void* tag) {
+      return std::unique_ptr< ::grpc::ClientAsyncReaderInterface< ::dmi::StartManagingDeviceResponse>>(AsyncStartManagingDeviceRaw(context, request, cq, tag));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncReaderInterface< ::dmi::StartManagingDeviceResponse>> PrepareAsyncStartManagingDevice(::grpc::ClientContext* context, const ::dmi::ModifiableComponent& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncReaderInterface< ::dmi::StartManagingDeviceResponse>>(PrepareAsyncStartManagingDeviceRaw(context, request, cq));
+    }
+    // Stop management of a device and clean up any context and caches for that device
+    // This rpc can be called at any time, even before the StartManagingDevice operation
+    // has completed, and should be able to cleanup.
+    virtual ::grpc::Status StopManagingDevice(::grpc::ClientContext* context, const ::dmi::StopManagingDeviceRequest& request, ::dmi::StopManagingDeviceResponse* response) = 0;
+    std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::StopManagingDeviceResponse>> AsyncStopManagingDevice(::grpc::ClientContext* context, const ::dmi::StopManagingDeviceRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::StopManagingDeviceResponse>>(AsyncStopManagingDeviceRaw(context, request, cq));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::StopManagingDeviceResponse>> PrepareAsyncStopManagingDevice(::grpc::ClientContext* context, const ::dmi::StopManagingDeviceRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::StopManagingDeviceResponse>>(PrepareAsyncStopManagingDeviceRaw(context, request, cq));
+    }
+    // Returns an object containing a list of devices managed by this entity
+    virtual ::grpc::Status GetManagedDevices(::grpc::ClientContext* context, const ::google::protobuf::Empty& request, ::dmi::ManagedDevicesResponse* response) = 0;
+    std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::ManagedDevicesResponse>> AsyncGetManagedDevices(::grpc::ClientContext* context, const ::google::protobuf::Empty& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::ManagedDevicesResponse>>(AsyncGetManagedDevicesRaw(context, request, cq));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::ManagedDevicesResponse>> PrepareAsyncGetManagedDevices(::grpc::ClientContext* context, const ::google::protobuf::Empty& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::ManagedDevicesResponse>>(PrepareAsyncGetManagedDevicesRaw(context, request, cq));
+    }
+    // Get the HW inventory details of the Device
+    std::unique_ptr< ::grpc::ClientReaderInterface< ::dmi::PhysicalInventoryResponse>> GetPhysicalInventory(::grpc::ClientContext* context, const ::dmi::PhysicalInventoryRequest& request) {
+      return std::unique_ptr< ::grpc::ClientReaderInterface< ::dmi::PhysicalInventoryResponse>>(GetPhysicalInventoryRaw(context, request));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncReaderInterface< ::dmi::PhysicalInventoryResponse>> AsyncGetPhysicalInventory(::grpc::ClientContext* context, const ::dmi::PhysicalInventoryRequest& request, ::grpc::CompletionQueue* cq, void* tag) {
+      return std::unique_ptr< ::grpc::ClientAsyncReaderInterface< ::dmi::PhysicalInventoryResponse>>(AsyncGetPhysicalInventoryRaw(context, request, cq, tag));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncReaderInterface< ::dmi::PhysicalInventoryResponse>> PrepareAsyncGetPhysicalInventory(::grpc::ClientContext* context, const ::dmi::PhysicalInventoryRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncReaderInterface< ::dmi::PhysicalInventoryResponse>>(PrepareAsyncGetPhysicalInventoryRaw(context, request, cq));
+    }
+    // Get the details of a particular HW component
+    std::unique_ptr< ::grpc::ClientReaderInterface< ::dmi::HWComponentInfoGetResponse>> GetHWComponentInfo(::grpc::ClientContext* context, const ::dmi::HWComponentInfoGetRequest& request) {
+      return std::unique_ptr< ::grpc::ClientReaderInterface< ::dmi::HWComponentInfoGetResponse>>(GetHWComponentInfoRaw(context, request));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncReaderInterface< ::dmi::HWComponentInfoGetResponse>> AsyncGetHWComponentInfo(::grpc::ClientContext* context, const ::dmi::HWComponentInfoGetRequest& request, ::grpc::CompletionQueue* cq, void* tag) {
+      return std::unique_ptr< ::grpc::ClientAsyncReaderInterface< ::dmi::HWComponentInfoGetResponse>>(AsyncGetHWComponentInfoRaw(context, request, cq, tag));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncReaderInterface< ::dmi::HWComponentInfoGetResponse>> PrepareAsyncGetHWComponentInfo(::grpc::ClientContext* context, const ::dmi::HWComponentInfoGetRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncReaderInterface< ::dmi::HWComponentInfoGetResponse>>(PrepareAsyncGetHWComponentInfoRaw(context, request, cq));
+    }
+    // Sets the permissible attributes of a HW component
+    virtual ::grpc::Status SetHWComponentInfo(::grpc::ClientContext* context, const ::dmi::HWComponentInfoSetRequest& request, ::dmi::HWComponentInfoSetResponse* response) = 0;
+    std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::HWComponentInfoSetResponse>> AsyncSetHWComponentInfo(::grpc::ClientContext* context, const ::dmi::HWComponentInfoSetRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::HWComponentInfoSetResponse>>(AsyncSetHWComponentInfoRaw(context, request, cq));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::HWComponentInfoSetResponse>> PrepareAsyncSetHWComponentInfo(::grpc::ClientContext* context, const ::dmi::HWComponentInfoSetRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::HWComponentInfoSetResponse>>(PrepareAsyncSetHWComponentInfoRaw(context, request, cq));
+    }
+    // Sets the location to which logs need to be shipped
+    virtual ::grpc::Status SetLoggingEndpoint(::grpc::ClientContext* context, const ::dmi::SetLoggingEndpointRequest& request, ::dmi::SetRemoteEndpointResponse* response) = 0;
+    std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::SetRemoteEndpointResponse>> AsyncSetLoggingEndpoint(::grpc::ClientContext* context, const ::dmi::SetLoggingEndpointRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::SetRemoteEndpointResponse>>(AsyncSetLoggingEndpointRaw(context, request, cq));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::SetRemoteEndpointResponse>> PrepareAsyncSetLoggingEndpoint(::grpc::ClientContext* context, const ::dmi::SetLoggingEndpointRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::SetRemoteEndpointResponse>>(PrepareAsyncSetLoggingEndpointRaw(context, request, cq));
+    }
+    // Gets the configured location to which the logs are being shipped
+    virtual ::grpc::Status GetLoggingEndpoint(::grpc::ClientContext* context, const ::dmi::HardwareID& request, ::dmi::GetLoggingEndpointResponse* response) = 0;
+    std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::GetLoggingEndpointResponse>> AsyncGetLoggingEndpoint(::grpc::ClientContext* context, const ::dmi::HardwareID& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::GetLoggingEndpointResponse>>(AsyncGetLoggingEndpointRaw(context, request, cq));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::GetLoggingEndpointResponse>> PrepareAsyncGetLoggingEndpoint(::grpc::ClientContext* context, const ::dmi::HardwareID& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::GetLoggingEndpointResponse>>(PrepareAsyncGetLoggingEndpointRaw(context, request, cq));
+    }
+    // Sets the location of the Message Bus to which events and metrics are shipped
+    virtual ::grpc::Status SetMsgBusEndpoint(::grpc::ClientContext* context, const ::dmi::SetMsgBusEndpointRequest& request, ::dmi::SetRemoteEndpointResponse* response) = 0;
+    std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::SetRemoteEndpointResponse>> AsyncSetMsgBusEndpoint(::grpc::ClientContext* context, const ::dmi::SetMsgBusEndpointRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::SetRemoteEndpointResponse>>(AsyncSetMsgBusEndpointRaw(context, request, cq));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::SetRemoteEndpointResponse>> PrepareAsyncSetMsgBusEndpoint(::grpc::ClientContext* context, const ::dmi::SetMsgBusEndpointRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::SetRemoteEndpointResponse>>(PrepareAsyncSetMsgBusEndpointRaw(context, request, cq));
+    }
+    // Gets the configured location to which the events and metrics are being shipped
+    virtual ::grpc::Status GetMsgBusEndpoint(::grpc::ClientContext* context, const ::google::protobuf::Empty& request, ::dmi::GetMsgBusEndpointResponse* response) = 0;
+    std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::GetMsgBusEndpointResponse>> AsyncGetMsgBusEndpoint(::grpc::ClientContext* context, const ::google::protobuf::Empty& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::GetMsgBusEndpointResponse>>(AsyncGetMsgBusEndpointRaw(context, request, cq));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::GetMsgBusEndpointResponse>> PrepareAsyncGetMsgBusEndpoint(::grpc::ClientContext* context, const ::google::protobuf::Empty& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::GetMsgBusEndpointResponse>>(PrepareAsyncGetMsgBusEndpointRaw(context, request, cq));
+    }
+    // Gets the entities of a device on which log can be configured. A few are expected, like OS, PON Management etc.
+    // In general an entity is any item within an hardware system that can emit logs, e.g. service, process, subsystem,
+    // interface, package etc.
+    virtual ::grpc::Status GetLoggableEntities(::grpc::ClientContext* context, const ::dmi::GetLoggableEntitiesRequest& request, ::dmi::GetLogLevelResponse* response) = 0;
+    std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::GetLogLevelResponse>> AsyncGetLoggableEntities(::grpc::ClientContext* context, const ::dmi::GetLoggableEntitiesRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::GetLogLevelResponse>>(AsyncGetLoggableEntitiesRaw(context, request, cq));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::GetLogLevelResponse>> PrepareAsyncGetLoggableEntities(::grpc::ClientContext* context, const ::dmi::GetLoggableEntitiesRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::GetLogLevelResponse>>(PrepareAsyncGetLoggableEntitiesRaw(context, request, cq));
+    }
+    // Sets the log level of the device, for each given entity to a certain level.
+    // If only one EntitiesLogLevel is provided for the device and that request contains only a log level with
+    // no entity in the list it's assumed that the caller wants to set that level for all the entities.
+    virtual ::grpc::Status SetLogLevel(::grpc::ClientContext* context, const ::dmi::SetLogLevelRequest& request, ::dmi::SetLogLevelResponse* response) = 0;
+    std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::SetLogLevelResponse>> AsyncSetLogLevel(::grpc::ClientContext* context, const ::dmi::SetLogLevelRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::SetLogLevelResponse>>(AsyncSetLogLevelRaw(context, request, cq));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::SetLogLevelResponse>> PrepareAsyncSetLogLevel(::grpc::ClientContext* context, const ::dmi::SetLogLevelRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::SetLogLevelResponse>>(PrepareAsyncSetLogLevelRaw(context, request, cq));
+    }
+    // Gets the configured log level for a certain entity on a certain device.
+    // If no entity is specified in the request all the entities with their log level should be returned.
+    virtual ::grpc::Status GetLogLevel(::grpc::ClientContext* context, const ::dmi::GetLogLevelRequest& request, ::dmi::GetLogLevelResponse* response) = 0;
+    std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::GetLogLevelResponse>> AsyncGetLogLevel(::grpc::ClientContext* context, const ::dmi::GetLogLevelRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::GetLogLevelResponse>>(AsyncGetLogLevelRaw(context, request, cq));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::GetLogLevelResponse>> PrepareAsyncGetLogLevel(::grpc::ClientContext* context, const ::dmi::GetLogLevelRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::dmi::GetLogLevelResponse>>(PrepareAsyncGetLogLevelRaw(context, request, cq));
+    }
+    class experimental_async_interface {
+     public:
+      virtual ~experimental_async_interface() {}
+      // Initializes context for a device and sets up required states
+      // In the call to StartManagingDevice, the fields of ModifiableComponent which are relevant
+      // and their meanings in this context is mentioned below:
+      // name = The unique name that needs to be assigned to this hardware;
+      // class = COMPONENT_TYPE_UNDEFINED;
+      // parent = nil;
+      // alias = Optional;
+      // asset_id = Optional;
+      // uri = IP Address of the Hardware;
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      virtual void StartManagingDevice(::grpc::ClientContext* context, ::dmi::ModifiableComponent* request, ::grpc::ClientReadReactor< ::dmi::StartManagingDeviceResponse>* reactor) = 0;
+      #else
+      virtual void StartManagingDevice(::grpc::ClientContext* context, ::dmi::ModifiableComponent* request, ::grpc::experimental::ClientReadReactor< ::dmi::StartManagingDeviceResponse>* reactor) = 0;
+      #endif
+      // Stop management of a device and clean up any context and caches for that device
+      // This rpc can be called at any time, even before the StartManagingDevice operation
+      // has completed, and should be able to cleanup.
+      virtual void StopManagingDevice(::grpc::ClientContext* context, const ::dmi::StopManagingDeviceRequest* request, ::dmi::StopManagingDeviceResponse* response, std::function<void(::grpc::Status)>) = 0;
+      virtual void StopManagingDevice(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::StopManagingDeviceResponse* response, std::function<void(::grpc::Status)>) = 0;
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      virtual void StopManagingDevice(::grpc::ClientContext* context, const ::dmi::StopManagingDeviceRequest* request, ::dmi::StopManagingDeviceResponse* response, ::grpc::ClientUnaryReactor* reactor) = 0;
+      #else
+      virtual void StopManagingDevice(::grpc::ClientContext* context, const ::dmi::StopManagingDeviceRequest* request, ::dmi::StopManagingDeviceResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) = 0;
+      #endif
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      virtual void StopManagingDevice(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::StopManagingDeviceResponse* response, ::grpc::ClientUnaryReactor* reactor) = 0;
+      #else
+      virtual void StopManagingDevice(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::StopManagingDeviceResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) = 0;
+      #endif
+      // Returns an object containing a list of devices managed by this entity
+      virtual void GetManagedDevices(::grpc::ClientContext* context, const ::google::protobuf::Empty* request, ::dmi::ManagedDevicesResponse* response, std::function<void(::grpc::Status)>) = 0;
+      virtual void GetManagedDevices(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::ManagedDevicesResponse* response, std::function<void(::grpc::Status)>) = 0;
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      virtual void GetManagedDevices(::grpc::ClientContext* context, const ::google::protobuf::Empty* request, ::dmi::ManagedDevicesResponse* response, ::grpc::ClientUnaryReactor* reactor) = 0;
+      #else
+      virtual void GetManagedDevices(::grpc::ClientContext* context, const ::google::protobuf::Empty* request, ::dmi::ManagedDevicesResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) = 0;
+      #endif
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      virtual void GetManagedDevices(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::ManagedDevicesResponse* response, ::grpc::ClientUnaryReactor* reactor) = 0;
+      #else
+      virtual void GetManagedDevices(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::ManagedDevicesResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) = 0;
+      #endif
+      // Get the HW inventory details of the Device
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      virtual void GetPhysicalInventory(::grpc::ClientContext* context, ::dmi::PhysicalInventoryRequest* request, ::grpc::ClientReadReactor< ::dmi::PhysicalInventoryResponse>* reactor) = 0;
+      #else
+      virtual void GetPhysicalInventory(::grpc::ClientContext* context, ::dmi::PhysicalInventoryRequest* request, ::grpc::experimental::ClientReadReactor< ::dmi::PhysicalInventoryResponse>* reactor) = 0;
+      #endif
+      // Get the details of a particular HW component
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      virtual void GetHWComponentInfo(::grpc::ClientContext* context, ::dmi::HWComponentInfoGetRequest* request, ::grpc::ClientReadReactor< ::dmi::HWComponentInfoGetResponse>* reactor) = 0;
+      #else
+      virtual void GetHWComponentInfo(::grpc::ClientContext* context, ::dmi::HWComponentInfoGetRequest* request, ::grpc::experimental::ClientReadReactor< ::dmi::HWComponentInfoGetResponse>* reactor) = 0;
+      #endif
+      // Sets the permissible attributes of a HW component
+      virtual void SetHWComponentInfo(::grpc::ClientContext* context, const ::dmi::HWComponentInfoSetRequest* request, ::dmi::HWComponentInfoSetResponse* response, std::function<void(::grpc::Status)>) = 0;
+      virtual void SetHWComponentInfo(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::HWComponentInfoSetResponse* response, std::function<void(::grpc::Status)>) = 0;
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      virtual void SetHWComponentInfo(::grpc::ClientContext* context, const ::dmi::HWComponentInfoSetRequest* request, ::dmi::HWComponentInfoSetResponse* response, ::grpc::ClientUnaryReactor* reactor) = 0;
+      #else
+      virtual void SetHWComponentInfo(::grpc::ClientContext* context, const ::dmi::HWComponentInfoSetRequest* request, ::dmi::HWComponentInfoSetResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) = 0;
+      #endif
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      virtual void SetHWComponentInfo(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::HWComponentInfoSetResponse* response, ::grpc::ClientUnaryReactor* reactor) = 0;
+      #else
+      virtual void SetHWComponentInfo(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::HWComponentInfoSetResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) = 0;
+      #endif
+      // Sets the location to which logs need to be shipped
+      virtual void SetLoggingEndpoint(::grpc::ClientContext* context, const ::dmi::SetLoggingEndpointRequest* request, ::dmi::SetRemoteEndpointResponse* response, std::function<void(::grpc::Status)>) = 0;
+      virtual void SetLoggingEndpoint(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::SetRemoteEndpointResponse* response, std::function<void(::grpc::Status)>) = 0;
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      virtual void SetLoggingEndpoint(::grpc::ClientContext* context, const ::dmi::SetLoggingEndpointRequest* request, ::dmi::SetRemoteEndpointResponse* response, ::grpc::ClientUnaryReactor* reactor) = 0;
+      #else
+      virtual void SetLoggingEndpoint(::grpc::ClientContext* context, const ::dmi::SetLoggingEndpointRequest* request, ::dmi::SetRemoteEndpointResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) = 0;
+      #endif
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      virtual void SetLoggingEndpoint(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::SetRemoteEndpointResponse* response, ::grpc::ClientUnaryReactor* reactor) = 0;
+      #else
+      virtual void SetLoggingEndpoint(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::SetRemoteEndpointResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) = 0;
+      #endif
+      // Gets the configured location to which the logs are being shipped
+      virtual void GetLoggingEndpoint(::grpc::ClientContext* context, const ::dmi::HardwareID* request, ::dmi::GetLoggingEndpointResponse* response, std::function<void(::grpc::Status)>) = 0;
+      virtual void GetLoggingEndpoint(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::GetLoggingEndpointResponse* response, std::function<void(::grpc::Status)>) = 0;
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      virtual void GetLoggingEndpoint(::grpc::ClientContext* context, const ::dmi::HardwareID* request, ::dmi::GetLoggingEndpointResponse* response, ::grpc::ClientUnaryReactor* reactor) = 0;
+      #else
+      virtual void GetLoggingEndpoint(::grpc::ClientContext* context, const ::dmi::HardwareID* request, ::dmi::GetLoggingEndpointResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) = 0;
+      #endif
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      virtual void GetLoggingEndpoint(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::GetLoggingEndpointResponse* response, ::grpc::ClientUnaryReactor* reactor) = 0;
+      #else
+      virtual void GetLoggingEndpoint(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::GetLoggingEndpointResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) = 0;
+      #endif
+      // Sets the location of the Message Bus to which events and metrics are shipped
+      virtual void SetMsgBusEndpoint(::grpc::ClientContext* context, const ::dmi::SetMsgBusEndpointRequest* request, ::dmi::SetRemoteEndpointResponse* response, std::function<void(::grpc::Status)>) = 0;
+      virtual void SetMsgBusEndpoint(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::SetRemoteEndpointResponse* response, std::function<void(::grpc::Status)>) = 0;
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      virtual void SetMsgBusEndpoint(::grpc::ClientContext* context, const ::dmi::SetMsgBusEndpointRequest* request, ::dmi::SetRemoteEndpointResponse* response, ::grpc::ClientUnaryReactor* reactor) = 0;
+      #else
+      virtual void SetMsgBusEndpoint(::grpc::ClientContext* context, const ::dmi::SetMsgBusEndpointRequest* request, ::dmi::SetRemoteEndpointResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) = 0;
+      #endif
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      virtual void SetMsgBusEndpoint(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::SetRemoteEndpointResponse* response, ::grpc::ClientUnaryReactor* reactor) = 0;
+      #else
+      virtual void SetMsgBusEndpoint(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::SetRemoteEndpointResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) = 0;
+      #endif
+      // Gets the configured location to which the events and metrics are being shipped
+      virtual void GetMsgBusEndpoint(::grpc::ClientContext* context, const ::google::protobuf::Empty* request, ::dmi::GetMsgBusEndpointResponse* response, std::function<void(::grpc::Status)>) = 0;
+      virtual void GetMsgBusEndpoint(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::GetMsgBusEndpointResponse* response, std::function<void(::grpc::Status)>) = 0;
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      virtual void GetMsgBusEndpoint(::grpc::ClientContext* context, const ::google::protobuf::Empty* request, ::dmi::GetMsgBusEndpointResponse* response, ::grpc::ClientUnaryReactor* reactor) = 0;
+      #else
+      virtual void GetMsgBusEndpoint(::grpc::ClientContext* context, const ::google::protobuf::Empty* request, ::dmi::GetMsgBusEndpointResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) = 0;
+      #endif
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      virtual void GetMsgBusEndpoint(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::GetMsgBusEndpointResponse* response, ::grpc::ClientUnaryReactor* reactor) = 0;
+      #else
+      virtual void GetMsgBusEndpoint(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::GetMsgBusEndpointResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) = 0;
+      #endif
+      // Gets the entities of a device on which log can be configured. A few are expected, like OS, PON Management etc.
+      // In general an entity is any item within an hardware system that can emit logs, e.g. service, process, subsystem,
+      // interface, package etc.
+      virtual void GetLoggableEntities(::grpc::ClientContext* context, const ::dmi::GetLoggableEntitiesRequest* request, ::dmi::GetLogLevelResponse* response, std::function<void(::grpc::Status)>) = 0;
+      virtual void GetLoggableEntities(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::GetLogLevelResponse* response, std::function<void(::grpc::Status)>) = 0;
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      virtual void GetLoggableEntities(::grpc::ClientContext* context, const ::dmi::GetLoggableEntitiesRequest* request, ::dmi::GetLogLevelResponse* response, ::grpc::ClientUnaryReactor* reactor) = 0;
+      #else
+      virtual void GetLoggableEntities(::grpc::ClientContext* context, const ::dmi::GetLoggableEntitiesRequest* request, ::dmi::GetLogLevelResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) = 0;
+      #endif
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      virtual void GetLoggableEntities(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::GetLogLevelResponse* response, ::grpc::ClientUnaryReactor* reactor) = 0;
+      #else
+      virtual void GetLoggableEntities(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::GetLogLevelResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) = 0;
+      #endif
+      // Sets the log level of the device, for each given entity to a certain level.
+      // If only one EntitiesLogLevel is provided for the device and that request contains only a log level with
+      // no entity in the list it's assumed that the caller wants to set that level for all the entities.
+      virtual void SetLogLevel(::grpc::ClientContext* context, const ::dmi::SetLogLevelRequest* request, ::dmi::SetLogLevelResponse* response, std::function<void(::grpc::Status)>) = 0;
+      virtual void SetLogLevel(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::SetLogLevelResponse* response, std::function<void(::grpc::Status)>) = 0;
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      virtual void SetLogLevel(::grpc::ClientContext* context, const ::dmi::SetLogLevelRequest* request, ::dmi::SetLogLevelResponse* response, ::grpc::ClientUnaryReactor* reactor) = 0;
+      #else
+      virtual void SetLogLevel(::grpc::ClientContext* context, const ::dmi::SetLogLevelRequest* request, ::dmi::SetLogLevelResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) = 0;
+      #endif
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      virtual void SetLogLevel(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::SetLogLevelResponse* response, ::grpc::ClientUnaryReactor* reactor) = 0;
+      #else
+      virtual void SetLogLevel(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::SetLogLevelResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) = 0;
+      #endif
+      // Gets the configured log level for a certain entity on a certain device.
+      // If no entity is specified in the request all the entities with their log level should be returned.
+      virtual void GetLogLevel(::grpc::ClientContext* context, const ::dmi::GetLogLevelRequest* request, ::dmi::GetLogLevelResponse* response, std::function<void(::grpc::Status)>) = 0;
+      virtual void GetLogLevel(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::GetLogLevelResponse* response, std::function<void(::grpc::Status)>) = 0;
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      virtual void GetLogLevel(::grpc::ClientContext* context, const ::dmi::GetLogLevelRequest* request, ::dmi::GetLogLevelResponse* response, ::grpc::ClientUnaryReactor* reactor) = 0;
+      #else
+      virtual void GetLogLevel(::grpc::ClientContext* context, const ::dmi::GetLogLevelRequest* request, ::dmi::GetLogLevelResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) = 0;
+      #endif
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      virtual void GetLogLevel(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::GetLogLevelResponse* response, ::grpc::ClientUnaryReactor* reactor) = 0;
+      #else
+      virtual void GetLogLevel(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::GetLogLevelResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) = 0;
+      #endif
+    };
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+    typedef class experimental_async_interface async_interface;
+    #endif
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+    async_interface* async() { return experimental_async(); }
+    #endif
+    virtual class experimental_async_interface* experimental_async() { return nullptr; }
+  private:
+    virtual ::grpc::ClientReaderInterface< ::dmi::StartManagingDeviceResponse>* StartManagingDeviceRaw(::grpc::ClientContext* context, const ::dmi::ModifiableComponent& request) = 0;
+    virtual ::grpc::ClientAsyncReaderInterface< ::dmi::StartManagingDeviceResponse>* AsyncStartManagingDeviceRaw(::grpc::ClientContext* context, const ::dmi::ModifiableComponent& request, ::grpc::CompletionQueue* cq, void* tag) = 0;
+    virtual ::grpc::ClientAsyncReaderInterface< ::dmi::StartManagingDeviceResponse>* PrepareAsyncStartManagingDeviceRaw(::grpc::ClientContext* context, const ::dmi::ModifiableComponent& request, ::grpc::CompletionQueue* cq) = 0;
+    virtual ::grpc::ClientAsyncResponseReaderInterface< ::dmi::StopManagingDeviceResponse>* AsyncStopManagingDeviceRaw(::grpc::ClientContext* context, const ::dmi::StopManagingDeviceRequest& request, ::grpc::CompletionQueue* cq) = 0;
+    virtual ::grpc::ClientAsyncResponseReaderInterface< ::dmi::StopManagingDeviceResponse>* PrepareAsyncStopManagingDeviceRaw(::grpc::ClientContext* context, const ::dmi::StopManagingDeviceRequest& request, ::grpc::CompletionQueue* cq) = 0;
+    virtual ::grpc::ClientAsyncResponseReaderInterface< ::dmi::ManagedDevicesResponse>* AsyncGetManagedDevicesRaw(::grpc::ClientContext* context, const ::google::protobuf::Empty& request, ::grpc::CompletionQueue* cq) = 0;
+    virtual ::grpc::ClientAsyncResponseReaderInterface< ::dmi::ManagedDevicesResponse>* PrepareAsyncGetManagedDevicesRaw(::grpc::ClientContext* context, const ::google::protobuf::Empty& request, ::grpc::CompletionQueue* cq) = 0;
+    virtual ::grpc::ClientReaderInterface< ::dmi::PhysicalInventoryResponse>* GetPhysicalInventoryRaw(::grpc::ClientContext* context, const ::dmi::PhysicalInventoryRequest& request) = 0;
+    virtual ::grpc::ClientAsyncReaderInterface< ::dmi::PhysicalInventoryResponse>* AsyncGetPhysicalInventoryRaw(::grpc::ClientContext* context, const ::dmi::PhysicalInventoryRequest& request, ::grpc::CompletionQueue* cq, void* tag) = 0;
+    virtual ::grpc::ClientAsyncReaderInterface< ::dmi::PhysicalInventoryResponse>* PrepareAsyncGetPhysicalInventoryRaw(::grpc::ClientContext* context, const ::dmi::PhysicalInventoryRequest& request, ::grpc::CompletionQueue* cq) = 0;
+    virtual ::grpc::ClientReaderInterface< ::dmi::HWComponentInfoGetResponse>* GetHWComponentInfoRaw(::grpc::ClientContext* context, const ::dmi::HWComponentInfoGetRequest& request) = 0;
+    virtual ::grpc::ClientAsyncReaderInterface< ::dmi::HWComponentInfoGetResponse>* AsyncGetHWComponentInfoRaw(::grpc::ClientContext* context, const ::dmi::HWComponentInfoGetRequest& request, ::grpc::CompletionQueue* cq, void* tag) = 0;
+    virtual ::grpc::ClientAsyncReaderInterface< ::dmi::HWComponentInfoGetResponse>* PrepareAsyncGetHWComponentInfoRaw(::grpc::ClientContext* context, const ::dmi::HWComponentInfoGetRequest& request, ::grpc::CompletionQueue* cq) = 0;
+    virtual ::grpc::ClientAsyncResponseReaderInterface< ::dmi::HWComponentInfoSetResponse>* AsyncSetHWComponentInfoRaw(::grpc::ClientContext* context, const ::dmi::HWComponentInfoSetRequest& request, ::grpc::CompletionQueue* cq) = 0;
+    virtual ::grpc::ClientAsyncResponseReaderInterface< ::dmi::HWComponentInfoSetResponse>* PrepareAsyncSetHWComponentInfoRaw(::grpc::ClientContext* context, const ::dmi::HWComponentInfoSetRequest& request, ::grpc::CompletionQueue* cq) = 0;
+    virtual ::grpc::ClientAsyncResponseReaderInterface< ::dmi::SetRemoteEndpointResponse>* AsyncSetLoggingEndpointRaw(::grpc::ClientContext* context, const ::dmi::SetLoggingEndpointRequest& request, ::grpc::CompletionQueue* cq) = 0;
+    virtual ::grpc::ClientAsyncResponseReaderInterface< ::dmi::SetRemoteEndpointResponse>* PrepareAsyncSetLoggingEndpointRaw(::grpc::ClientContext* context, const ::dmi::SetLoggingEndpointRequest& request, ::grpc::CompletionQueue* cq) = 0;
+    virtual ::grpc::ClientAsyncResponseReaderInterface< ::dmi::GetLoggingEndpointResponse>* AsyncGetLoggingEndpointRaw(::grpc::ClientContext* context, const ::dmi::HardwareID& request, ::grpc::CompletionQueue* cq) = 0;
+    virtual ::grpc::ClientAsyncResponseReaderInterface< ::dmi::GetLoggingEndpointResponse>* PrepareAsyncGetLoggingEndpointRaw(::grpc::ClientContext* context, const ::dmi::HardwareID& request, ::grpc::CompletionQueue* cq) = 0;
+    virtual ::grpc::ClientAsyncResponseReaderInterface< ::dmi::SetRemoteEndpointResponse>* AsyncSetMsgBusEndpointRaw(::grpc::ClientContext* context, const ::dmi::SetMsgBusEndpointRequest& request, ::grpc::CompletionQueue* cq) = 0;
+    virtual ::grpc::ClientAsyncResponseReaderInterface< ::dmi::SetRemoteEndpointResponse>* PrepareAsyncSetMsgBusEndpointRaw(::grpc::ClientContext* context, const ::dmi::SetMsgBusEndpointRequest& request, ::grpc::CompletionQueue* cq) = 0;
+    virtual ::grpc::ClientAsyncResponseReaderInterface< ::dmi::GetMsgBusEndpointResponse>* AsyncGetMsgBusEndpointRaw(::grpc::ClientContext* context, const ::google::protobuf::Empty& request, ::grpc::CompletionQueue* cq) = 0;
+    virtual ::grpc::ClientAsyncResponseReaderInterface< ::dmi::GetMsgBusEndpointResponse>* PrepareAsyncGetMsgBusEndpointRaw(::grpc::ClientContext* context, const ::google::protobuf::Empty& request, ::grpc::CompletionQueue* cq) = 0;
+    virtual ::grpc::ClientAsyncResponseReaderInterface< ::dmi::GetLogLevelResponse>* AsyncGetLoggableEntitiesRaw(::grpc::ClientContext* context, const ::dmi::GetLoggableEntitiesRequest& request, ::grpc::CompletionQueue* cq) = 0;
+    virtual ::grpc::ClientAsyncResponseReaderInterface< ::dmi::GetLogLevelResponse>* PrepareAsyncGetLoggableEntitiesRaw(::grpc::ClientContext* context, const ::dmi::GetLoggableEntitiesRequest& request, ::grpc::CompletionQueue* cq) = 0;
+    virtual ::grpc::ClientAsyncResponseReaderInterface< ::dmi::SetLogLevelResponse>* AsyncSetLogLevelRaw(::grpc::ClientContext* context, const ::dmi::SetLogLevelRequest& request, ::grpc::CompletionQueue* cq) = 0;
+    virtual ::grpc::ClientAsyncResponseReaderInterface< ::dmi::SetLogLevelResponse>* PrepareAsyncSetLogLevelRaw(::grpc::ClientContext* context, const ::dmi::SetLogLevelRequest& request, ::grpc::CompletionQueue* cq) = 0;
+    virtual ::grpc::ClientAsyncResponseReaderInterface< ::dmi::GetLogLevelResponse>* AsyncGetLogLevelRaw(::grpc::ClientContext* context, const ::dmi::GetLogLevelRequest& request, ::grpc::CompletionQueue* cq) = 0;
+    virtual ::grpc::ClientAsyncResponseReaderInterface< ::dmi::GetLogLevelResponse>* PrepareAsyncGetLogLevelRaw(::grpc::ClientContext* context, const ::dmi::GetLogLevelRequest& request, ::grpc::CompletionQueue* cq) = 0;
+  };
+  class Stub final : public StubInterface {
+   public:
+    Stub(const std::shared_ptr< ::grpc::ChannelInterface>& channel);
+    std::unique_ptr< ::grpc::ClientReader< ::dmi::StartManagingDeviceResponse>> StartManagingDevice(::grpc::ClientContext* context, const ::dmi::ModifiableComponent& request) {
+      return std::unique_ptr< ::grpc::ClientReader< ::dmi::StartManagingDeviceResponse>>(StartManagingDeviceRaw(context, request));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncReader< ::dmi::StartManagingDeviceResponse>> AsyncStartManagingDevice(::grpc::ClientContext* context, const ::dmi::ModifiableComponent& request, ::grpc::CompletionQueue* cq, void* tag) {
+      return std::unique_ptr< ::grpc::ClientAsyncReader< ::dmi::StartManagingDeviceResponse>>(AsyncStartManagingDeviceRaw(context, request, cq, tag));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncReader< ::dmi::StartManagingDeviceResponse>> PrepareAsyncStartManagingDevice(::grpc::ClientContext* context, const ::dmi::ModifiableComponent& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncReader< ::dmi::StartManagingDeviceResponse>>(PrepareAsyncStartManagingDeviceRaw(context, request, cq));
+    }
+    ::grpc::Status StopManagingDevice(::grpc::ClientContext* context, const ::dmi::StopManagingDeviceRequest& request, ::dmi::StopManagingDeviceResponse* response) override;
+    std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::StopManagingDeviceResponse>> AsyncStopManagingDevice(::grpc::ClientContext* context, const ::dmi::StopManagingDeviceRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::StopManagingDeviceResponse>>(AsyncStopManagingDeviceRaw(context, request, cq));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::StopManagingDeviceResponse>> PrepareAsyncStopManagingDevice(::grpc::ClientContext* context, const ::dmi::StopManagingDeviceRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::StopManagingDeviceResponse>>(PrepareAsyncStopManagingDeviceRaw(context, request, cq));
+    }
+    ::grpc::Status GetManagedDevices(::grpc::ClientContext* context, const ::google::protobuf::Empty& request, ::dmi::ManagedDevicesResponse* response) override;
+    std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::ManagedDevicesResponse>> AsyncGetManagedDevices(::grpc::ClientContext* context, const ::google::protobuf::Empty& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::ManagedDevicesResponse>>(AsyncGetManagedDevicesRaw(context, request, cq));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::ManagedDevicesResponse>> PrepareAsyncGetManagedDevices(::grpc::ClientContext* context, const ::google::protobuf::Empty& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::ManagedDevicesResponse>>(PrepareAsyncGetManagedDevicesRaw(context, request, cq));
+    }
+    std::unique_ptr< ::grpc::ClientReader< ::dmi::PhysicalInventoryResponse>> GetPhysicalInventory(::grpc::ClientContext* context, const ::dmi::PhysicalInventoryRequest& request) {
+      return std::unique_ptr< ::grpc::ClientReader< ::dmi::PhysicalInventoryResponse>>(GetPhysicalInventoryRaw(context, request));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncReader< ::dmi::PhysicalInventoryResponse>> AsyncGetPhysicalInventory(::grpc::ClientContext* context, const ::dmi::PhysicalInventoryRequest& request, ::grpc::CompletionQueue* cq, void* tag) {
+      return std::unique_ptr< ::grpc::ClientAsyncReader< ::dmi::PhysicalInventoryResponse>>(AsyncGetPhysicalInventoryRaw(context, request, cq, tag));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncReader< ::dmi::PhysicalInventoryResponse>> PrepareAsyncGetPhysicalInventory(::grpc::ClientContext* context, const ::dmi::PhysicalInventoryRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncReader< ::dmi::PhysicalInventoryResponse>>(PrepareAsyncGetPhysicalInventoryRaw(context, request, cq));
+    }
+    std::unique_ptr< ::grpc::ClientReader< ::dmi::HWComponentInfoGetResponse>> GetHWComponentInfo(::grpc::ClientContext* context, const ::dmi::HWComponentInfoGetRequest& request) {
+      return std::unique_ptr< ::grpc::ClientReader< ::dmi::HWComponentInfoGetResponse>>(GetHWComponentInfoRaw(context, request));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncReader< ::dmi::HWComponentInfoGetResponse>> AsyncGetHWComponentInfo(::grpc::ClientContext* context, const ::dmi::HWComponentInfoGetRequest& request, ::grpc::CompletionQueue* cq, void* tag) {
+      return std::unique_ptr< ::grpc::ClientAsyncReader< ::dmi::HWComponentInfoGetResponse>>(AsyncGetHWComponentInfoRaw(context, request, cq, tag));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncReader< ::dmi::HWComponentInfoGetResponse>> PrepareAsyncGetHWComponentInfo(::grpc::ClientContext* context, const ::dmi::HWComponentInfoGetRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncReader< ::dmi::HWComponentInfoGetResponse>>(PrepareAsyncGetHWComponentInfoRaw(context, request, cq));
+    }
+    ::grpc::Status SetHWComponentInfo(::grpc::ClientContext* context, const ::dmi::HWComponentInfoSetRequest& request, ::dmi::HWComponentInfoSetResponse* response) override;
+    std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::HWComponentInfoSetResponse>> AsyncSetHWComponentInfo(::grpc::ClientContext* context, const ::dmi::HWComponentInfoSetRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::HWComponentInfoSetResponse>>(AsyncSetHWComponentInfoRaw(context, request, cq));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::HWComponentInfoSetResponse>> PrepareAsyncSetHWComponentInfo(::grpc::ClientContext* context, const ::dmi::HWComponentInfoSetRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::HWComponentInfoSetResponse>>(PrepareAsyncSetHWComponentInfoRaw(context, request, cq));
+    }
+    ::grpc::Status SetLoggingEndpoint(::grpc::ClientContext* context, const ::dmi::SetLoggingEndpointRequest& request, ::dmi::SetRemoteEndpointResponse* response) override;
+    std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::SetRemoteEndpointResponse>> AsyncSetLoggingEndpoint(::grpc::ClientContext* context, const ::dmi::SetLoggingEndpointRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::SetRemoteEndpointResponse>>(AsyncSetLoggingEndpointRaw(context, request, cq));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::SetRemoteEndpointResponse>> PrepareAsyncSetLoggingEndpoint(::grpc::ClientContext* context, const ::dmi::SetLoggingEndpointRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::SetRemoteEndpointResponse>>(PrepareAsyncSetLoggingEndpointRaw(context, request, cq));
+    }
+    ::grpc::Status GetLoggingEndpoint(::grpc::ClientContext* context, const ::dmi::HardwareID& request, ::dmi::GetLoggingEndpointResponse* response) override;
+    std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::GetLoggingEndpointResponse>> AsyncGetLoggingEndpoint(::grpc::ClientContext* context, const ::dmi::HardwareID& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::GetLoggingEndpointResponse>>(AsyncGetLoggingEndpointRaw(context, request, cq));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::GetLoggingEndpointResponse>> PrepareAsyncGetLoggingEndpoint(::grpc::ClientContext* context, const ::dmi::HardwareID& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::GetLoggingEndpointResponse>>(PrepareAsyncGetLoggingEndpointRaw(context, request, cq));
+    }
+    ::grpc::Status SetMsgBusEndpoint(::grpc::ClientContext* context, const ::dmi::SetMsgBusEndpointRequest& request, ::dmi::SetRemoteEndpointResponse* response) override;
+    std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::SetRemoteEndpointResponse>> AsyncSetMsgBusEndpoint(::grpc::ClientContext* context, const ::dmi::SetMsgBusEndpointRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::SetRemoteEndpointResponse>>(AsyncSetMsgBusEndpointRaw(context, request, cq));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::SetRemoteEndpointResponse>> PrepareAsyncSetMsgBusEndpoint(::grpc::ClientContext* context, const ::dmi::SetMsgBusEndpointRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::SetRemoteEndpointResponse>>(PrepareAsyncSetMsgBusEndpointRaw(context, request, cq));
+    }
+    ::grpc::Status GetMsgBusEndpoint(::grpc::ClientContext* context, const ::google::protobuf::Empty& request, ::dmi::GetMsgBusEndpointResponse* response) override;
+    std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::GetMsgBusEndpointResponse>> AsyncGetMsgBusEndpoint(::grpc::ClientContext* context, const ::google::protobuf::Empty& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::GetMsgBusEndpointResponse>>(AsyncGetMsgBusEndpointRaw(context, request, cq));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::GetMsgBusEndpointResponse>> PrepareAsyncGetMsgBusEndpoint(::grpc::ClientContext* context, const ::google::protobuf::Empty& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::GetMsgBusEndpointResponse>>(PrepareAsyncGetMsgBusEndpointRaw(context, request, cq));
+    }
+    ::grpc::Status GetLoggableEntities(::grpc::ClientContext* context, const ::dmi::GetLoggableEntitiesRequest& request, ::dmi::GetLogLevelResponse* response) override;
+    std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::GetLogLevelResponse>> AsyncGetLoggableEntities(::grpc::ClientContext* context, const ::dmi::GetLoggableEntitiesRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::GetLogLevelResponse>>(AsyncGetLoggableEntitiesRaw(context, request, cq));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::GetLogLevelResponse>> PrepareAsyncGetLoggableEntities(::grpc::ClientContext* context, const ::dmi::GetLoggableEntitiesRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::GetLogLevelResponse>>(PrepareAsyncGetLoggableEntitiesRaw(context, request, cq));
+    }
+    ::grpc::Status SetLogLevel(::grpc::ClientContext* context, const ::dmi::SetLogLevelRequest& request, ::dmi::SetLogLevelResponse* response) override;
+    std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::SetLogLevelResponse>> AsyncSetLogLevel(::grpc::ClientContext* context, const ::dmi::SetLogLevelRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::SetLogLevelResponse>>(AsyncSetLogLevelRaw(context, request, cq));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::SetLogLevelResponse>> PrepareAsyncSetLogLevel(::grpc::ClientContext* context, const ::dmi::SetLogLevelRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::SetLogLevelResponse>>(PrepareAsyncSetLogLevelRaw(context, request, cq));
+    }
+    ::grpc::Status GetLogLevel(::grpc::ClientContext* context, const ::dmi::GetLogLevelRequest& request, ::dmi::GetLogLevelResponse* response) override;
+    std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::GetLogLevelResponse>> AsyncGetLogLevel(::grpc::ClientContext* context, const ::dmi::GetLogLevelRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::GetLogLevelResponse>>(AsyncGetLogLevelRaw(context, request, cq));
+    }
+    std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::GetLogLevelResponse>> PrepareAsyncGetLogLevel(::grpc::ClientContext* context, const ::dmi::GetLogLevelRequest& request, ::grpc::CompletionQueue* cq) {
+      return std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::dmi::GetLogLevelResponse>>(PrepareAsyncGetLogLevelRaw(context, request, cq));
+    }
+    class experimental_async final :
+      public StubInterface::experimental_async_interface {
+     public:
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      void StartManagingDevice(::grpc::ClientContext* context, ::dmi::ModifiableComponent* request, ::grpc::ClientReadReactor< ::dmi::StartManagingDeviceResponse>* reactor) override;
+      #else
+      void StartManagingDevice(::grpc::ClientContext* context, ::dmi::ModifiableComponent* request, ::grpc::experimental::ClientReadReactor< ::dmi::StartManagingDeviceResponse>* reactor) override;
+      #endif
+      void StopManagingDevice(::grpc::ClientContext* context, const ::dmi::StopManagingDeviceRequest* request, ::dmi::StopManagingDeviceResponse* response, std::function<void(::grpc::Status)>) override;
+      void StopManagingDevice(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::StopManagingDeviceResponse* response, std::function<void(::grpc::Status)>) override;
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      void StopManagingDevice(::grpc::ClientContext* context, const ::dmi::StopManagingDeviceRequest* request, ::dmi::StopManagingDeviceResponse* response, ::grpc::ClientUnaryReactor* reactor) override;
+      #else
+      void StopManagingDevice(::grpc::ClientContext* context, const ::dmi::StopManagingDeviceRequest* request, ::dmi::StopManagingDeviceResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) override;
+      #endif
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      void StopManagingDevice(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::StopManagingDeviceResponse* response, ::grpc::ClientUnaryReactor* reactor) override;
+      #else
+      void StopManagingDevice(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::StopManagingDeviceResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) override;
+      #endif
+      void GetManagedDevices(::grpc::ClientContext* context, const ::google::protobuf::Empty* request, ::dmi::ManagedDevicesResponse* response, std::function<void(::grpc::Status)>) override;
+      void GetManagedDevices(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::ManagedDevicesResponse* response, std::function<void(::grpc::Status)>) override;
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      void GetManagedDevices(::grpc::ClientContext* context, const ::google::protobuf::Empty* request, ::dmi::ManagedDevicesResponse* response, ::grpc::ClientUnaryReactor* reactor) override;
+      #else
+      void GetManagedDevices(::grpc::ClientContext* context, const ::google::protobuf::Empty* request, ::dmi::ManagedDevicesResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) override;
+      #endif
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      void GetManagedDevices(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::ManagedDevicesResponse* response, ::grpc::ClientUnaryReactor* reactor) override;
+      #else
+      void GetManagedDevices(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::ManagedDevicesResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) override;
+      #endif
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      void GetPhysicalInventory(::grpc::ClientContext* context, ::dmi::PhysicalInventoryRequest* request, ::grpc::ClientReadReactor< ::dmi::PhysicalInventoryResponse>* reactor) override;
+      #else
+      void GetPhysicalInventory(::grpc::ClientContext* context, ::dmi::PhysicalInventoryRequest* request, ::grpc::experimental::ClientReadReactor< ::dmi::PhysicalInventoryResponse>* reactor) override;
+      #endif
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      void GetHWComponentInfo(::grpc::ClientContext* context, ::dmi::HWComponentInfoGetRequest* request, ::grpc::ClientReadReactor< ::dmi::HWComponentInfoGetResponse>* reactor) override;
+      #else
+      void GetHWComponentInfo(::grpc::ClientContext* context, ::dmi::HWComponentInfoGetRequest* request, ::grpc::experimental::ClientReadReactor< ::dmi::HWComponentInfoGetResponse>* reactor) override;
+      #endif
+      void SetHWComponentInfo(::grpc::ClientContext* context, const ::dmi::HWComponentInfoSetRequest* request, ::dmi::HWComponentInfoSetResponse* response, std::function<void(::grpc::Status)>) override;
+      void SetHWComponentInfo(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::HWComponentInfoSetResponse* response, std::function<void(::grpc::Status)>) override;
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      void SetHWComponentInfo(::grpc::ClientContext* context, const ::dmi::HWComponentInfoSetRequest* request, ::dmi::HWComponentInfoSetResponse* response, ::grpc::ClientUnaryReactor* reactor) override;
+      #else
+      void SetHWComponentInfo(::grpc::ClientContext* context, const ::dmi::HWComponentInfoSetRequest* request, ::dmi::HWComponentInfoSetResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) override;
+      #endif
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      void SetHWComponentInfo(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::HWComponentInfoSetResponse* response, ::grpc::ClientUnaryReactor* reactor) override;
+      #else
+      void SetHWComponentInfo(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::HWComponentInfoSetResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) override;
+      #endif
+      void SetLoggingEndpoint(::grpc::ClientContext* context, const ::dmi::SetLoggingEndpointRequest* request, ::dmi::SetRemoteEndpointResponse* response, std::function<void(::grpc::Status)>) override;
+      void SetLoggingEndpoint(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::SetRemoteEndpointResponse* response, std::function<void(::grpc::Status)>) override;
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      void SetLoggingEndpoint(::grpc::ClientContext* context, const ::dmi::SetLoggingEndpointRequest* request, ::dmi::SetRemoteEndpointResponse* response, ::grpc::ClientUnaryReactor* reactor) override;
+      #else
+      void SetLoggingEndpoint(::grpc::ClientContext* context, const ::dmi::SetLoggingEndpointRequest* request, ::dmi::SetRemoteEndpointResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) override;
+      #endif
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      void SetLoggingEndpoint(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::SetRemoteEndpointResponse* response, ::grpc::ClientUnaryReactor* reactor) override;
+      #else
+      void SetLoggingEndpoint(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::SetRemoteEndpointResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) override;
+      #endif
+      void GetLoggingEndpoint(::grpc::ClientContext* context, const ::dmi::HardwareID* request, ::dmi::GetLoggingEndpointResponse* response, std::function<void(::grpc::Status)>) override;
+      void GetLoggingEndpoint(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::GetLoggingEndpointResponse* response, std::function<void(::grpc::Status)>) override;
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      void GetLoggingEndpoint(::grpc::ClientContext* context, const ::dmi::HardwareID* request, ::dmi::GetLoggingEndpointResponse* response, ::grpc::ClientUnaryReactor* reactor) override;
+      #else
+      void GetLoggingEndpoint(::grpc::ClientContext* context, const ::dmi::HardwareID* request, ::dmi::GetLoggingEndpointResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) override;
+      #endif
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      void GetLoggingEndpoint(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::GetLoggingEndpointResponse* response, ::grpc::ClientUnaryReactor* reactor) override;
+      #else
+      void GetLoggingEndpoint(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::GetLoggingEndpointResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) override;
+      #endif
+      void SetMsgBusEndpoint(::grpc::ClientContext* context, const ::dmi::SetMsgBusEndpointRequest* request, ::dmi::SetRemoteEndpointResponse* response, std::function<void(::grpc::Status)>) override;
+      void SetMsgBusEndpoint(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::SetRemoteEndpointResponse* response, std::function<void(::grpc::Status)>) override;
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      void SetMsgBusEndpoint(::grpc::ClientContext* context, const ::dmi::SetMsgBusEndpointRequest* request, ::dmi::SetRemoteEndpointResponse* response, ::grpc::ClientUnaryReactor* reactor) override;
+      #else
+      void SetMsgBusEndpoint(::grpc::ClientContext* context, const ::dmi::SetMsgBusEndpointRequest* request, ::dmi::SetRemoteEndpointResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) override;
+      #endif
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      void SetMsgBusEndpoint(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::SetRemoteEndpointResponse* response, ::grpc::ClientUnaryReactor* reactor) override;
+      #else
+      void SetMsgBusEndpoint(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::SetRemoteEndpointResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) override;
+      #endif
+      void GetMsgBusEndpoint(::grpc::ClientContext* context, const ::google::protobuf::Empty* request, ::dmi::GetMsgBusEndpointResponse* response, std::function<void(::grpc::Status)>) override;
+      void GetMsgBusEndpoint(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::GetMsgBusEndpointResponse* response, std::function<void(::grpc::Status)>) override;
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      void GetMsgBusEndpoint(::grpc::ClientContext* context, const ::google::protobuf::Empty* request, ::dmi::GetMsgBusEndpointResponse* response, ::grpc::ClientUnaryReactor* reactor) override;
+      #else
+      void GetMsgBusEndpoint(::grpc::ClientContext* context, const ::google::protobuf::Empty* request, ::dmi::GetMsgBusEndpointResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) override;
+      #endif
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      void GetMsgBusEndpoint(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::GetMsgBusEndpointResponse* response, ::grpc::ClientUnaryReactor* reactor) override;
+      #else
+      void GetMsgBusEndpoint(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::GetMsgBusEndpointResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) override;
+      #endif
+      void GetLoggableEntities(::grpc::ClientContext* context, const ::dmi::GetLoggableEntitiesRequest* request, ::dmi::GetLogLevelResponse* response, std::function<void(::grpc::Status)>) override;
+      void GetLoggableEntities(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::GetLogLevelResponse* response, std::function<void(::grpc::Status)>) override;
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      void GetLoggableEntities(::grpc::ClientContext* context, const ::dmi::GetLoggableEntitiesRequest* request, ::dmi::GetLogLevelResponse* response, ::grpc::ClientUnaryReactor* reactor) override;
+      #else
+      void GetLoggableEntities(::grpc::ClientContext* context, const ::dmi::GetLoggableEntitiesRequest* request, ::dmi::GetLogLevelResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) override;
+      #endif
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      void GetLoggableEntities(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::GetLogLevelResponse* response, ::grpc::ClientUnaryReactor* reactor) override;
+      #else
+      void GetLoggableEntities(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::GetLogLevelResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) override;
+      #endif
+      void SetLogLevel(::grpc::ClientContext* context, const ::dmi::SetLogLevelRequest* request, ::dmi::SetLogLevelResponse* response, std::function<void(::grpc::Status)>) override;
+      void SetLogLevel(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::SetLogLevelResponse* response, std::function<void(::grpc::Status)>) override;
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      void SetLogLevel(::grpc::ClientContext* context, const ::dmi::SetLogLevelRequest* request, ::dmi::SetLogLevelResponse* response, ::grpc::ClientUnaryReactor* reactor) override;
+      #else
+      void SetLogLevel(::grpc::ClientContext* context, const ::dmi::SetLogLevelRequest* request, ::dmi::SetLogLevelResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) override;
+      #endif
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      void SetLogLevel(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::SetLogLevelResponse* response, ::grpc::ClientUnaryReactor* reactor) override;
+      #else
+      void SetLogLevel(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::SetLogLevelResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) override;
+      #endif
+      void GetLogLevel(::grpc::ClientContext* context, const ::dmi::GetLogLevelRequest* request, ::dmi::GetLogLevelResponse* response, std::function<void(::grpc::Status)>) override;
+      void GetLogLevel(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::GetLogLevelResponse* response, std::function<void(::grpc::Status)>) override;
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      void GetLogLevel(::grpc::ClientContext* context, const ::dmi::GetLogLevelRequest* request, ::dmi::GetLogLevelResponse* response, ::grpc::ClientUnaryReactor* reactor) override;
+      #else
+      void GetLogLevel(::grpc::ClientContext* context, const ::dmi::GetLogLevelRequest* request, ::dmi::GetLogLevelResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) override;
+      #endif
+      #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      void GetLogLevel(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::GetLogLevelResponse* response, ::grpc::ClientUnaryReactor* reactor) override;
+      #else
+      void GetLogLevel(::grpc::ClientContext* context, const ::grpc::ByteBuffer* request, ::dmi::GetLogLevelResponse* response, ::grpc::experimental::ClientUnaryReactor* reactor) override;
+      #endif
+     private:
+      friend class Stub;
+      explicit experimental_async(Stub* stub): stub_(stub) { }
+      Stub* stub() { return stub_; }
+      Stub* stub_;
+    };
+    class experimental_async_interface* experimental_async() override { return &async_stub_; }
+
+   private:
+    std::shared_ptr< ::grpc::ChannelInterface> channel_;
+    class experimental_async async_stub_{this};
+    ::grpc::ClientReader< ::dmi::StartManagingDeviceResponse>* StartManagingDeviceRaw(::grpc::ClientContext* context, const ::dmi::ModifiableComponent& request) override;
+    ::grpc::ClientAsyncReader< ::dmi::StartManagingDeviceResponse>* AsyncStartManagingDeviceRaw(::grpc::ClientContext* context, const ::dmi::ModifiableComponent& request, ::grpc::CompletionQueue* cq, void* tag) override;
+    ::grpc::ClientAsyncReader< ::dmi::StartManagingDeviceResponse>* PrepareAsyncStartManagingDeviceRaw(::grpc::ClientContext* context, const ::dmi::ModifiableComponent& request, ::grpc::CompletionQueue* cq) override;
+    ::grpc::ClientAsyncResponseReader< ::dmi::StopManagingDeviceResponse>* AsyncStopManagingDeviceRaw(::grpc::ClientContext* context, const ::dmi::StopManagingDeviceRequest& request, ::grpc::CompletionQueue* cq) override;
+    ::grpc::ClientAsyncResponseReader< ::dmi::StopManagingDeviceResponse>* PrepareAsyncStopManagingDeviceRaw(::grpc::ClientContext* context, const ::dmi::StopManagingDeviceRequest& request, ::grpc::CompletionQueue* cq) override;
+    ::grpc::ClientAsyncResponseReader< ::dmi::ManagedDevicesResponse>* AsyncGetManagedDevicesRaw(::grpc::ClientContext* context, const ::google::protobuf::Empty& request, ::grpc::CompletionQueue* cq) override;
+    ::grpc::ClientAsyncResponseReader< ::dmi::ManagedDevicesResponse>* PrepareAsyncGetManagedDevicesRaw(::grpc::ClientContext* context, const ::google::protobuf::Empty& request, ::grpc::CompletionQueue* cq) override;
+    ::grpc::ClientReader< ::dmi::PhysicalInventoryResponse>* GetPhysicalInventoryRaw(::grpc::ClientContext* context, const ::dmi::PhysicalInventoryRequest& request) override;
+    ::grpc::ClientAsyncReader< ::dmi::PhysicalInventoryResponse>* AsyncGetPhysicalInventoryRaw(::grpc::ClientContext* context, const ::dmi::PhysicalInventoryRequest& request, ::grpc::CompletionQueue* cq, void* tag) override;
+    ::grpc::ClientAsyncReader< ::dmi::PhysicalInventoryResponse>* PrepareAsyncGetPhysicalInventoryRaw(::grpc::ClientContext* context, const ::dmi::PhysicalInventoryRequest& request, ::grpc::CompletionQueue* cq) override;
+    ::grpc::ClientReader< ::dmi::HWComponentInfoGetResponse>* GetHWComponentInfoRaw(::grpc::ClientContext* context, const ::dmi::HWComponentInfoGetRequest& request) override;
+    ::grpc::ClientAsyncReader< ::dmi::HWComponentInfoGetResponse>* AsyncGetHWComponentInfoRaw(::grpc::ClientContext* context, const ::dmi::HWComponentInfoGetRequest& request, ::grpc::CompletionQueue* cq, void* tag) override;
+    ::grpc::ClientAsyncReader< ::dmi::HWComponentInfoGetResponse>* PrepareAsyncGetHWComponentInfoRaw(::grpc::ClientContext* context, const ::dmi::HWComponentInfoGetRequest& request, ::grpc::CompletionQueue* cq) override;
+    ::grpc::ClientAsyncResponseReader< ::dmi::HWComponentInfoSetResponse>* AsyncSetHWComponentInfoRaw(::grpc::ClientContext* context, const ::dmi::HWComponentInfoSetRequest& request, ::grpc::CompletionQueue* cq) override;
+    ::grpc::ClientAsyncResponseReader< ::dmi::HWComponentInfoSetResponse>* PrepareAsyncSetHWComponentInfoRaw(::grpc::ClientContext* context, const ::dmi::HWComponentInfoSetRequest& request, ::grpc::CompletionQueue* cq) override;
+    ::grpc::ClientAsyncResponseReader< ::dmi::SetRemoteEndpointResponse>* AsyncSetLoggingEndpointRaw(::grpc::ClientContext* context, const ::dmi::SetLoggingEndpointRequest& request, ::grpc::CompletionQueue* cq) override;
+    ::grpc::ClientAsyncResponseReader< ::dmi::SetRemoteEndpointResponse>* PrepareAsyncSetLoggingEndpointRaw(::grpc::ClientContext* context, const ::dmi::SetLoggingEndpointRequest& request, ::grpc::CompletionQueue* cq) override;
+    ::grpc::ClientAsyncResponseReader< ::dmi::GetLoggingEndpointResponse>* AsyncGetLoggingEndpointRaw(::grpc::ClientContext* context, const ::dmi::HardwareID& request, ::grpc::CompletionQueue* cq) override;
+    ::grpc::ClientAsyncResponseReader< ::dmi::GetLoggingEndpointResponse>* PrepareAsyncGetLoggingEndpointRaw(::grpc::ClientContext* context, const ::dmi::HardwareID& request, ::grpc::CompletionQueue* cq) override;
+    ::grpc::ClientAsyncResponseReader< ::dmi::SetRemoteEndpointResponse>* AsyncSetMsgBusEndpointRaw(::grpc::ClientContext* context, const ::dmi::SetMsgBusEndpointRequest& request, ::grpc::CompletionQueue* cq) override;
+    ::grpc::ClientAsyncResponseReader< ::dmi::SetRemoteEndpointResponse>* PrepareAsyncSetMsgBusEndpointRaw(::grpc::ClientContext* context, const ::dmi::SetMsgBusEndpointRequest& request, ::grpc::CompletionQueue* cq) override;
+    ::grpc::ClientAsyncResponseReader< ::dmi::GetMsgBusEndpointResponse>* AsyncGetMsgBusEndpointRaw(::grpc::ClientContext* context, const ::google::protobuf::Empty& request, ::grpc::CompletionQueue* cq) override;
+    ::grpc::ClientAsyncResponseReader< ::dmi::GetMsgBusEndpointResponse>* PrepareAsyncGetMsgBusEndpointRaw(::grpc::ClientContext* context, const ::google::protobuf::Empty& request, ::grpc::CompletionQueue* cq) override;
+    ::grpc::ClientAsyncResponseReader< ::dmi::GetLogLevelResponse>* AsyncGetLoggableEntitiesRaw(::grpc::ClientContext* context, const ::dmi::GetLoggableEntitiesRequest& request, ::grpc::CompletionQueue* cq) override;
+    ::grpc::ClientAsyncResponseReader< ::dmi::GetLogLevelResponse>* PrepareAsyncGetLoggableEntitiesRaw(::grpc::ClientContext* context, const ::dmi::GetLoggableEntitiesRequest& request, ::grpc::CompletionQueue* cq) override;
+    ::grpc::ClientAsyncResponseReader< ::dmi::SetLogLevelResponse>* AsyncSetLogLevelRaw(::grpc::ClientContext* context, const ::dmi::SetLogLevelRequest& request, ::grpc::CompletionQueue* cq) override;
+    ::grpc::ClientAsyncResponseReader< ::dmi::SetLogLevelResponse>* PrepareAsyncSetLogLevelRaw(::grpc::ClientContext* context, const ::dmi::SetLogLevelRequest& request, ::grpc::CompletionQueue* cq) override;
+    ::grpc::ClientAsyncResponseReader< ::dmi::GetLogLevelResponse>* AsyncGetLogLevelRaw(::grpc::ClientContext* context, const ::dmi::GetLogLevelRequest& request, ::grpc::CompletionQueue* cq) override;
+    ::grpc::ClientAsyncResponseReader< ::dmi::GetLogLevelResponse>* PrepareAsyncGetLogLevelRaw(::grpc::ClientContext* context, const ::dmi::GetLogLevelRequest& request, ::grpc::CompletionQueue* cq) override;
+    const ::grpc::internal::RpcMethod rpcmethod_StartManagingDevice_;
+    const ::grpc::internal::RpcMethod rpcmethod_StopManagingDevice_;
+    const ::grpc::internal::RpcMethod rpcmethod_GetManagedDevices_;
+    const ::grpc::internal::RpcMethod rpcmethod_GetPhysicalInventory_;
+    const ::grpc::internal::RpcMethod rpcmethod_GetHWComponentInfo_;
+    const ::grpc::internal::RpcMethod rpcmethod_SetHWComponentInfo_;
+    const ::grpc::internal::RpcMethod rpcmethod_SetLoggingEndpoint_;
+    const ::grpc::internal::RpcMethod rpcmethod_GetLoggingEndpoint_;
+    const ::grpc::internal::RpcMethod rpcmethod_SetMsgBusEndpoint_;
+    const ::grpc::internal::RpcMethod rpcmethod_GetMsgBusEndpoint_;
+    const ::grpc::internal::RpcMethod rpcmethod_GetLoggableEntities_;
+    const ::grpc::internal::RpcMethod rpcmethod_SetLogLevel_;
+    const ::grpc::internal::RpcMethod rpcmethod_GetLogLevel_;
+  };
+  static std::unique_ptr<Stub> NewStub(const std::shared_ptr< ::grpc::ChannelInterface>& channel, const ::grpc::StubOptions& options = ::grpc::StubOptions());
+
+  class Service : public ::grpc::Service {
+   public:
+    Service();
+    virtual ~Service();
+    // Initializes context for a device and sets up required states
+    // In the call to StartManagingDevice, the fields of ModifiableComponent which are relevant
+    // and their meanings in this context is mentioned below:
+    // name = The unique name that needs to be assigned to this hardware;
+    // class = COMPONENT_TYPE_UNDEFINED;
+    // parent = nil;
+    // alias = Optional;
+    // asset_id = Optional;
+    // uri = IP Address of the Hardware;
+    virtual ::grpc::Status StartManagingDevice(::grpc::ServerContext* context, const ::dmi::ModifiableComponent* request, ::grpc::ServerWriter< ::dmi::StartManagingDeviceResponse>* writer);
+    // Stop management of a device and clean up any context and caches for that device
+    // This rpc can be called at any time, even before the StartManagingDevice operation
+    // has completed, and should be able to cleanup.
+    virtual ::grpc::Status StopManagingDevice(::grpc::ServerContext* context, const ::dmi::StopManagingDeviceRequest* request, ::dmi::StopManagingDeviceResponse* response);
+    // Returns an object containing a list of devices managed by this entity
+    virtual ::grpc::Status GetManagedDevices(::grpc::ServerContext* context, const ::google::protobuf::Empty* request, ::dmi::ManagedDevicesResponse* response);
+    // Get the HW inventory details of the Device
+    virtual ::grpc::Status GetPhysicalInventory(::grpc::ServerContext* context, const ::dmi::PhysicalInventoryRequest* request, ::grpc::ServerWriter< ::dmi::PhysicalInventoryResponse>* writer);
+    // Get the details of a particular HW component
+    virtual ::grpc::Status GetHWComponentInfo(::grpc::ServerContext* context, const ::dmi::HWComponentInfoGetRequest* request, ::grpc::ServerWriter< ::dmi::HWComponentInfoGetResponse>* writer);
+    // Sets the permissible attributes of a HW component
+    virtual ::grpc::Status SetHWComponentInfo(::grpc::ServerContext* context, const ::dmi::HWComponentInfoSetRequest* request, ::dmi::HWComponentInfoSetResponse* response);
+    // Sets the location to which logs need to be shipped
+    virtual ::grpc::Status SetLoggingEndpoint(::grpc::ServerContext* context, const ::dmi::SetLoggingEndpointRequest* request, ::dmi::SetRemoteEndpointResponse* response);
+    // Gets the configured location to which the logs are being shipped
+    virtual ::grpc::Status GetLoggingEndpoint(::grpc::ServerContext* context, const ::dmi::HardwareID* request, ::dmi::GetLoggingEndpointResponse* response);
+    // Sets the location of the Message Bus to which events and metrics are shipped
+    virtual ::grpc::Status SetMsgBusEndpoint(::grpc::ServerContext* context, const ::dmi::SetMsgBusEndpointRequest* request, ::dmi::SetRemoteEndpointResponse* response);
+    // Gets the configured location to which the events and metrics are being shipped
+    virtual ::grpc::Status GetMsgBusEndpoint(::grpc::ServerContext* context, const ::google::protobuf::Empty* request, ::dmi::GetMsgBusEndpointResponse* response);
+    // Gets the entities of a device on which log can be configured. A few are expected, like OS, PON Management etc.
+    // In general an entity is any item within an hardware system that can emit logs, e.g. service, process, subsystem,
+    // interface, package etc.
+    virtual ::grpc::Status GetLoggableEntities(::grpc::ServerContext* context, const ::dmi::GetLoggableEntitiesRequest* request, ::dmi::GetLogLevelResponse* response);
+    // Sets the log level of the device, for each given entity to a certain level.
+    // If only one EntitiesLogLevel is provided for the device and that request contains only a log level with
+    // no entity in the list it's assumed that the caller wants to set that level for all the entities.
+    virtual ::grpc::Status SetLogLevel(::grpc::ServerContext* context, const ::dmi::SetLogLevelRequest* request, ::dmi::SetLogLevelResponse* response);
+    // Gets the configured log level for a certain entity on a certain device.
+    // If no entity is specified in the request all the entities with their log level should be returned.
+    virtual ::grpc::Status GetLogLevel(::grpc::ServerContext* context, const ::dmi::GetLogLevelRequest* request, ::dmi::GetLogLevelResponse* response);
+  };
+  template <class BaseClass>
+  class WithAsyncMethod_StartManagingDevice : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithAsyncMethod_StartManagingDevice() {
+      ::grpc::Service::MarkMethodAsync(0);
+    }
+    ~WithAsyncMethod_StartManagingDevice() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status StartManagingDevice(::grpc::ServerContext* /*context*/, const ::dmi::ModifiableComponent* /*request*/, ::grpc::ServerWriter< ::dmi::StartManagingDeviceResponse>* /*writer*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    void RequestStartManagingDevice(::grpc::ServerContext* context, ::dmi::ModifiableComponent* request, ::grpc::ServerAsyncWriter< ::dmi::StartManagingDeviceResponse>* writer, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) {
+      ::grpc::Service::RequestAsyncServerStreaming(0, context, request, writer, new_call_cq, notification_cq, tag);
+    }
+  };
+  template <class BaseClass>
+  class WithAsyncMethod_StopManagingDevice : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithAsyncMethod_StopManagingDevice() {
+      ::grpc::Service::MarkMethodAsync(1);
+    }
+    ~WithAsyncMethod_StopManagingDevice() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status StopManagingDevice(::grpc::ServerContext* /*context*/, const ::dmi::StopManagingDeviceRequest* /*request*/, ::dmi::StopManagingDeviceResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    void RequestStopManagingDevice(::grpc::ServerContext* context, ::dmi::StopManagingDeviceRequest* request, ::grpc::ServerAsyncResponseWriter< ::dmi::StopManagingDeviceResponse>* response, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) {
+      ::grpc::Service::RequestAsyncUnary(1, context, request, response, new_call_cq, notification_cq, tag);
+    }
+  };
+  template <class BaseClass>
+  class WithAsyncMethod_GetManagedDevices : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithAsyncMethod_GetManagedDevices() {
+      ::grpc::Service::MarkMethodAsync(2);
+    }
+    ~WithAsyncMethod_GetManagedDevices() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetManagedDevices(::grpc::ServerContext* /*context*/, const ::google::protobuf::Empty* /*request*/, ::dmi::ManagedDevicesResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    void RequestGetManagedDevices(::grpc::ServerContext* context, ::google::protobuf::Empty* request, ::grpc::ServerAsyncResponseWriter< ::dmi::ManagedDevicesResponse>* response, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) {
+      ::grpc::Service::RequestAsyncUnary(2, context, request, response, new_call_cq, notification_cq, tag);
+    }
+  };
+  template <class BaseClass>
+  class WithAsyncMethod_GetPhysicalInventory : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithAsyncMethod_GetPhysicalInventory() {
+      ::grpc::Service::MarkMethodAsync(3);
+    }
+    ~WithAsyncMethod_GetPhysicalInventory() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetPhysicalInventory(::grpc::ServerContext* /*context*/, const ::dmi::PhysicalInventoryRequest* /*request*/, ::grpc::ServerWriter< ::dmi::PhysicalInventoryResponse>* /*writer*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    void RequestGetPhysicalInventory(::grpc::ServerContext* context, ::dmi::PhysicalInventoryRequest* request, ::grpc::ServerAsyncWriter< ::dmi::PhysicalInventoryResponse>* writer, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) {
+      ::grpc::Service::RequestAsyncServerStreaming(3, context, request, writer, new_call_cq, notification_cq, tag);
+    }
+  };
+  template <class BaseClass>
+  class WithAsyncMethod_GetHWComponentInfo : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithAsyncMethod_GetHWComponentInfo() {
+      ::grpc::Service::MarkMethodAsync(4);
+    }
+    ~WithAsyncMethod_GetHWComponentInfo() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetHWComponentInfo(::grpc::ServerContext* /*context*/, const ::dmi::HWComponentInfoGetRequest* /*request*/, ::grpc::ServerWriter< ::dmi::HWComponentInfoGetResponse>* /*writer*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    void RequestGetHWComponentInfo(::grpc::ServerContext* context, ::dmi::HWComponentInfoGetRequest* request, ::grpc::ServerAsyncWriter< ::dmi::HWComponentInfoGetResponse>* writer, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) {
+      ::grpc::Service::RequestAsyncServerStreaming(4, context, request, writer, new_call_cq, notification_cq, tag);
+    }
+  };
+  template <class BaseClass>
+  class WithAsyncMethod_SetHWComponentInfo : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithAsyncMethod_SetHWComponentInfo() {
+      ::grpc::Service::MarkMethodAsync(5);
+    }
+    ~WithAsyncMethod_SetHWComponentInfo() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status SetHWComponentInfo(::grpc::ServerContext* /*context*/, const ::dmi::HWComponentInfoSetRequest* /*request*/, ::dmi::HWComponentInfoSetResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    void RequestSetHWComponentInfo(::grpc::ServerContext* context, ::dmi::HWComponentInfoSetRequest* request, ::grpc::ServerAsyncResponseWriter< ::dmi::HWComponentInfoSetResponse>* response, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) {
+      ::grpc::Service::RequestAsyncUnary(5, context, request, response, new_call_cq, notification_cq, tag);
+    }
+  };
+  template <class BaseClass>
+  class WithAsyncMethod_SetLoggingEndpoint : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithAsyncMethod_SetLoggingEndpoint() {
+      ::grpc::Service::MarkMethodAsync(6);
+    }
+    ~WithAsyncMethod_SetLoggingEndpoint() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status SetLoggingEndpoint(::grpc::ServerContext* /*context*/, const ::dmi::SetLoggingEndpointRequest* /*request*/, ::dmi::SetRemoteEndpointResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    void RequestSetLoggingEndpoint(::grpc::ServerContext* context, ::dmi::SetLoggingEndpointRequest* request, ::grpc::ServerAsyncResponseWriter< ::dmi::SetRemoteEndpointResponse>* response, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) {
+      ::grpc::Service::RequestAsyncUnary(6, context, request, response, new_call_cq, notification_cq, tag);
+    }
+  };
+  template <class BaseClass>
+  class WithAsyncMethod_GetLoggingEndpoint : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithAsyncMethod_GetLoggingEndpoint() {
+      ::grpc::Service::MarkMethodAsync(7);
+    }
+    ~WithAsyncMethod_GetLoggingEndpoint() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetLoggingEndpoint(::grpc::ServerContext* /*context*/, const ::dmi::HardwareID* /*request*/, ::dmi::GetLoggingEndpointResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    void RequestGetLoggingEndpoint(::grpc::ServerContext* context, ::dmi::HardwareID* request, ::grpc::ServerAsyncResponseWriter< ::dmi::GetLoggingEndpointResponse>* response, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) {
+      ::grpc::Service::RequestAsyncUnary(7, context, request, response, new_call_cq, notification_cq, tag);
+    }
+  };
+  template <class BaseClass>
+  class WithAsyncMethod_SetMsgBusEndpoint : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithAsyncMethod_SetMsgBusEndpoint() {
+      ::grpc::Service::MarkMethodAsync(8);
+    }
+    ~WithAsyncMethod_SetMsgBusEndpoint() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status SetMsgBusEndpoint(::grpc::ServerContext* /*context*/, const ::dmi::SetMsgBusEndpointRequest* /*request*/, ::dmi::SetRemoteEndpointResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    void RequestSetMsgBusEndpoint(::grpc::ServerContext* context, ::dmi::SetMsgBusEndpointRequest* request, ::grpc::ServerAsyncResponseWriter< ::dmi::SetRemoteEndpointResponse>* response, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) {
+      ::grpc::Service::RequestAsyncUnary(8, context, request, response, new_call_cq, notification_cq, tag);
+    }
+  };
+  template <class BaseClass>
+  class WithAsyncMethod_GetMsgBusEndpoint : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithAsyncMethod_GetMsgBusEndpoint() {
+      ::grpc::Service::MarkMethodAsync(9);
+    }
+    ~WithAsyncMethod_GetMsgBusEndpoint() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetMsgBusEndpoint(::grpc::ServerContext* /*context*/, const ::google::protobuf::Empty* /*request*/, ::dmi::GetMsgBusEndpointResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    void RequestGetMsgBusEndpoint(::grpc::ServerContext* context, ::google::protobuf::Empty* request, ::grpc::ServerAsyncResponseWriter< ::dmi::GetMsgBusEndpointResponse>* response, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) {
+      ::grpc::Service::RequestAsyncUnary(9, context, request, response, new_call_cq, notification_cq, tag);
+    }
+  };
+  template <class BaseClass>
+  class WithAsyncMethod_GetLoggableEntities : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithAsyncMethod_GetLoggableEntities() {
+      ::grpc::Service::MarkMethodAsync(10);
+    }
+    ~WithAsyncMethod_GetLoggableEntities() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetLoggableEntities(::grpc::ServerContext* /*context*/, const ::dmi::GetLoggableEntitiesRequest* /*request*/, ::dmi::GetLogLevelResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    void RequestGetLoggableEntities(::grpc::ServerContext* context, ::dmi::GetLoggableEntitiesRequest* request, ::grpc::ServerAsyncResponseWriter< ::dmi::GetLogLevelResponse>* response, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) {
+      ::grpc::Service::RequestAsyncUnary(10, context, request, response, new_call_cq, notification_cq, tag);
+    }
+  };
+  template <class BaseClass>
+  class WithAsyncMethod_SetLogLevel : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithAsyncMethod_SetLogLevel() {
+      ::grpc::Service::MarkMethodAsync(11);
+    }
+    ~WithAsyncMethod_SetLogLevel() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status SetLogLevel(::grpc::ServerContext* /*context*/, const ::dmi::SetLogLevelRequest* /*request*/, ::dmi::SetLogLevelResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    void RequestSetLogLevel(::grpc::ServerContext* context, ::dmi::SetLogLevelRequest* request, ::grpc::ServerAsyncResponseWriter< ::dmi::SetLogLevelResponse>* response, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) {
+      ::grpc::Service::RequestAsyncUnary(11, context, request, response, new_call_cq, notification_cq, tag);
+    }
+  };
+  template <class BaseClass>
+  class WithAsyncMethod_GetLogLevel : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithAsyncMethod_GetLogLevel() {
+      ::grpc::Service::MarkMethodAsync(12);
+    }
+    ~WithAsyncMethod_GetLogLevel() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetLogLevel(::grpc::ServerContext* /*context*/, const ::dmi::GetLogLevelRequest* /*request*/, ::dmi::GetLogLevelResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    void RequestGetLogLevel(::grpc::ServerContext* context, ::dmi::GetLogLevelRequest* request, ::grpc::ServerAsyncResponseWriter< ::dmi::GetLogLevelResponse>* response, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) {
+      ::grpc::Service::RequestAsyncUnary(12, context, request, response, new_call_cq, notification_cq, tag);
+    }
+  };
+  typedef WithAsyncMethod_StartManagingDevice<WithAsyncMethod_StopManagingDevice<WithAsyncMethod_GetManagedDevices<WithAsyncMethod_GetPhysicalInventory<WithAsyncMethod_GetHWComponentInfo<WithAsyncMethod_SetHWComponentInfo<WithAsyncMethod_SetLoggingEndpoint<WithAsyncMethod_GetLoggingEndpoint<WithAsyncMethod_SetMsgBusEndpoint<WithAsyncMethod_GetMsgBusEndpoint<WithAsyncMethod_GetLoggableEntities<WithAsyncMethod_SetLogLevel<WithAsyncMethod_GetLogLevel<Service > > > > > > > > > > > > > AsyncService;
+  template <class BaseClass>
+  class ExperimentalWithCallbackMethod_StartManagingDevice : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    ExperimentalWithCallbackMethod_StartManagingDevice() {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::Service::
+    #else
+      ::grpc::Service::experimental().
+    #endif
+        MarkMethodCallback(0,
+          new ::grpc_impl::internal::CallbackServerStreamingHandler< ::dmi::ModifiableComponent, ::dmi::StartManagingDeviceResponse>(
+            [this](
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+                   ::grpc::CallbackServerContext*
+    #else
+                   ::grpc::experimental::CallbackServerContext*
+    #endif
+                     context, const ::dmi::ModifiableComponent* request) { return this->StartManagingDevice(context, request); }));
+    }
+    ~ExperimentalWithCallbackMethod_StartManagingDevice() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status StartManagingDevice(::grpc::ServerContext* /*context*/, const ::dmi::ModifiableComponent* /*request*/, ::grpc::ServerWriter< ::dmi::StartManagingDeviceResponse>* /*writer*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+    virtual ::grpc::ServerWriteReactor< ::dmi::StartManagingDeviceResponse>* StartManagingDevice(
+      ::grpc::CallbackServerContext* /*context*/, const ::dmi::ModifiableComponent* /*request*/)
+    #else
+    virtual ::grpc::experimental::ServerWriteReactor< ::dmi::StartManagingDeviceResponse>* StartManagingDevice(
+      ::grpc::experimental::CallbackServerContext* /*context*/, const ::dmi::ModifiableComponent* /*request*/)
+    #endif
+      { return nullptr; }
+  };
+  template <class BaseClass>
+  class ExperimentalWithCallbackMethod_StopManagingDevice : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    ExperimentalWithCallbackMethod_StopManagingDevice() {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::Service::
+    #else
+      ::grpc::Service::experimental().
+    #endif
+        MarkMethodCallback(1,
+          new ::grpc_impl::internal::CallbackUnaryHandler< ::dmi::StopManagingDeviceRequest, ::dmi::StopManagingDeviceResponse>(
+            [this](
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+                   ::grpc::CallbackServerContext*
+    #else
+                   ::grpc::experimental::CallbackServerContext*
+    #endif
+                     context, const ::dmi::StopManagingDeviceRequest* request, ::dmi::StopManagingDeviceResponse* response) { return this->StopManagingDevice(context, request, response); }));}
+    void SetMessageAllocatorFor_StopManagingDevice(
+        ::grpc::experimental::MessageAllocator< ::dmi::StopManagingDeviceRequest, ::dmi::StopManagingDeviceResponse>* allocator) {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::internal::MethodHandler* const handler = ::grpc::Service::GetHandler(1);
+    #else
+      ::grpc::internal::MethodHandler* const handler = ::grpc::Service::experimental().GetHandler(1);
+    #endif
+      static_cast<::grpc_impl::internal::CallbackUnaryHandler< ::dmi::StopManagingDeviceRequest, ::dmi::StopManagingDeviceResponse>*>(handler)
+              ->SetMessageAllocator(allocator);
+    }
+    ~ExperimentalWithCallbackMethod_StopManagingDevice() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status StopManagingDevice(::grpc::ServerContext* /*context*/, const ::dmi::StopManagingDeviceRequest* /*request*/, ::dmi::StopManagingDeviceResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+    virtual ::grpc::ServerUnaryReactor* StopManagingDevice(
+      ::grpc::CallbackServerContext* /*context*/, const ::dmi::StopManagingDeviceRequest* /*request*/, ::dmi::StopManagingDeviceResponse* /*response*/)
+    #else
+    virtual ::grpc::experimental::ServerUnaryReactor* StopManagingDevice(
+      ::grpc::experimental::CallbackServerContext* /*context*/, const ::dmi::StopManagingDeviceRequest* /*request*/, ::dmi::StopManagingDeviceResponse* /*response*/)
+    #endif
+      { return nullptr; }
+  };
+  template <class BaseClass>
+  class ExperimentalWithCallbackMethod_GetManagedDevices : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    ExperimentalWithCallbackMethod_GetManagedDevices() {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::Service::
+    #else
+      ::grpc::Service::experimental().
+    #endif
+        MarkMethodCallback(2,
+          new ::grpc_impl::internal::CallbackUnaryHandler< ::google::protobuf::Empty, ::dmi::ManagedDevicesResponse>(
+            [this](
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+                   ::grpc::CallbackServerContext*
+    #else
+                   ::grpc::experimental::CallbackServerContext*
+    #endif
+                     context, const ::google::protobuf::Empty* request, ::dmi::ManagedDevicesResponse* response) { return this->GetManagedDevices(context, request, response); }));}
+    void SetMessageAllocatorFor_GetManagedDevices(
+        ::grpc::experimental::MessageAllocator< ::google::protobuf::Empty, ::dmi::ManagedDevicesResponse>* allocator) {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::internal::MethodHandler* const handler = ::grpc::Service::GetHandler(2);
+    #else
+      ::grpc::internal::MethodHandler* const handler = ::grpc::Service::experimental().GetHandler(2);
+    #endif
+      static_cast<::grpc_impl::internal::CallbackUnaryHandler< ::google::protobuf::Empty, ::dmi::ManagedDevicesResponse>*>(handler)
+              ->SetMessageAllocator(allocator);
+    }
+    ~ExperimentalWithCallbackMethod_GetManagedDevices() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetManagedDevices(::grpc::ServerContext* /*context*/, const ::google::protobuf::Empty* /*request*/, ::dmi::ManagedDevicesResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+    virtual ::grpc::ServerUnaryReactor* GetManagedDevices(
+      ::grpc::CallbackServerContext* /*context*/, const ::google::protobuf::Empty* /*request*/, ::dmi::ManagedDevicesResponse* /*response*/)
+    #else
+    virtual ::grpc::experimental::ServerUnaryReactor* GetManagedDevices(
+      ::grpc::experimental::CallbackServerContext* /*context*/, const ::google::protobuf::Empty* /*request*/, ::dmi::ManagedDevicesResponse* /*response*/)
+    #endif
+      { return nullptr; }
+  };
+  template <class BaseClass>
+  class ExperimentalWithCallbackMethod_GetPhysicalInventory : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    ExperimentalWithCallbackMethod_GetPhysicalInventory() {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::Service::
+    #else
+      ::grpc::Service::experimental().
+    #endif
+        MarkMethodCallback(3,
+          new ::grpc_impl::internal::CallbackServerStreamingHandler< ::dmi::PhysicalInventoryRequest, ::dmi::PhysicalInventoryResponse>(
+            [this](
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+                   ::grpc::CallbackServerContext*
+    #else
+                   ::grpc::experimental::CallbackServerContext*
+    #endif
+                     context, const ::dmi::PhysicalInventoryRequest* request) { return this->GetPhysicalInventory(context, request); }));
+    }
+    ~ExperimentalWithCallbackMethod_GetPhysicalInventory() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetPhysicalInventory(::grpc::ServerContext* /*context*/, const ::dmi::PhysicalInventoryRequest* /*request*/, ::grpc::ServerWriter< ::dmi::PhysicalInventoryResponse>* /*writer*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+    virtual ::grpc::ServerWriteReactor< ::dmi::PhysicalInventoryResponse>* GetPhysicalInventory(
+      ::grpc::CallbackServerContext* /*context*/, const ::dmi::PhysicalInventoryRequest* /*request*/)
+    #else
+    virtual ::grpc::experimental::ServerWriteReactor< ::dmi::PhysicalInventoryResponse>* GetPhysicalInventory(
+      ::grpc::experimental::CallbackServerContext* /*context*/, const ::dmi::PhysicalInventoryRequest* /*request*/)
+    #endif
+      { return nullptr; }
+  };
+  template <class BaseClass>
+  class ExperimentalWithCallbackMethod_GetHWComponentInfo : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    ExperimentalWithCallbackMethod_GetHWComponentInfo() {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::Service::
+    #else
+      ::grpc::Service::experimental().
+    #endif
+        MarkMethodCallback(4,
+          new ::grpc_impl::internal::CallbackServerStreamingHandler< ::dmi::HWComponentInfoGetRequest, ::dmi::HWComponentInfoGetResponse>(
+            [this](
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+                   ::grpc::CallbackServerContext*
+    #else
+                   ::grpc::experimental::CallbackServerContext*
+    #endif
+                     context, const ::dmi::HWComponentInfoGetRequest* request) { return this->GetHWComponentInfo(context, request); }));
+    }
+    ~ExperimentalWithCallbackMethod_GetHWComponentInfo() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetHWComponentInfo(::grpc::ServerContext* /*context*/, const ::dmi::HWComponentInfoGetRequest* /*request*/, ::grpc::ServerWriter< ::dmi::HWComponentInfoGetResponse>* /*writer*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+    virtual ::grpc::ServerWriteReactor< ::dmi::HWComponentInfoGetResponse>* GetHWComponentInfo(
+      ::grpc::CallbackServerContext* /*context*/, const ::dmi::HWComponentInfoGetRequest* /*request*/)
+    #else
+    virtual ::grpc::experimental::ServerWriteReactor< ::dmi::HWComponentInfoGetResponse>* GetHWComponentInfo(
+      ::grpc::experimental::CallbackServerContext* /*context*/, const ::dmi::HWComponentInfoGetRequest* /*request*/)
+    #endif
+      { return nullptr; }
+  };
+  template <class BaseClass>
+  class ExperimentalWithCallbackMethod_SetHWComponentInfo : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    ExperimentalWithCallbackMethod_SetHWComponentInfo() {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::Service::
+    #else
+      ::grpc::Service::experimental().
+    #endif
+        MarkMethodCallback(5,
+          new ::grpc_impl::internal::CallbackUnaryHandler< ::dmi::HWComponentInfoSetRequest, ::dmi::HWComponentInfoSetResponse>(
+            [this](
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+                   ::grpc::CallbackServerContext*
+    #else
+                   ::grpc::experimental::CallbackServerContext*
+    #endif
+                     context, const ::dmi::HWComponentInfoSetRequest* request, ::dmi::HWComponentInfoSetResponse* response) { return this->SetHWComponentInfo(context, request, response); }));}
+    void SetMessageAllocatorFor_SetHWComponentInfo(
+        ::grpc::experimental::MessageAllocator< ::dmi::HWComponentInfoSetRequest, ::dmi::HWComponentInfoSetResponse>* allocator) {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::internal::MethodHandler* const handler = ::grpc::Service::GetHandler(5);
+    #else
+      ::grpc::internal::MethodHandler* const handler = ::grpc::Service::experimental().GetHandler(5);
+    #endif
+      static_cast<::grpc_impl::internal::CallbackUnaryHandler< ::dmi::HWComponentInfoSetRequest, ::dmi::HWComponentInfoSetResponse>*>(handler)
+              ->SetMessageAllocator(allocator);
+    }
+    ~ExperimentalWithCallbackMethod_SetHWComponentInfo() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status SetHWComponentInfo(::grpc::ServerContext* /*context*/, const ::dmi::HWComponentInfoSetRequest* /*request*/, ::dmi::HWComponentInfoSetResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+    virtual ::grpc::ServerUnaryReactor* SetHWComponentInfo(
+      ::grpc::CallbackServerContext* /*context*/, const ::dmi::HWComponentInfoSetRequest* /*request*/, ::dmi::HWComponentInfoSetResponse* /*response*/)
+    #else
+    virtual ::grpc::experimental::ServerUnaryReactor* SetHWComponentInfo(
+      ::grpc::experimental::CallbackServerContext* /*context*/, const ::dmi::HWComponentInfoSetRequest* /*request*/, ::dmi::HWComponentInfoSetResponse* /*response*/)
+    #endif
+      { return nullptr; }
+  };
+  template <class BaseClass>
+  class ExperimentalWithCallbackMethod_SetLoggingEndpoint : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    ExperimentalWithCallbackMethod_SetLoggingEndpoint() {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::Service::
+    #else
+      ::grpc::Service::experimental().
+    #endif
+        MarkMethodCallback(6,
+          new ::grpc_impl::internal::CallbackUnaryHandler< ::dmi::SetLoggingEndpointRequest, ::dmi::SetRemoteEndpointResponse>(
+            [this](
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+                   ::grpc::CallbackServerContext*
+    #else
+                   ::grpc::experimental::CallbackServerContext*
+    #endif
+                     context, const ::dmi::SetLoggingEndpointRequest* request, ::dmi::SetRemoteEndpointResponse* response) { return this->SetLoggingEndpoint(context, request, response); }));}
+    void SetMessageAllocatorFor_SetLoggingEndpoint(
+        ::grpc::experimental::MessageAllocator< ::dmi::SetLoggingEndpointRequest, ::dmi::SetRemoteEndpointResponse>* allocator) {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::internal::MethodHandler* const handler = ::grpc::Service::GetHandler(6);
+    #else
+      ::grpc::internal::MethodHandler* const handler = ::grpc::Service::experimental().GetHandler(6);
+    #endif
+      static_cast<::grpc_impl::internal::CallbackUnaryHandler< ::dmi::SetLoggingEndpointRequest, ::dmi::SetRemoteEndpointResponse>*>(handler)
+              ->SetMessageAllocator(allocator);
+    }
+    ~ExperimentalWithCallbackMethod_SetLoggingEndpoint() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status SetLoggingEndpoint(::grpc::ServerContext* /*context*/, const ::dmi::SetLoggingEndpointRequest* /*request*/, ::dmi::SetRemoteEndpointResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+    virtual ::grpc::ServerUnaryReactor* SetLoggingEndpoint(
+      ::grpc::CallbackServerContext* /*context*/, const ::dmi::SetLoggingEndpointRequest* /*request*/, ::dmi::SetRemoteEndpointResponse* /*response*/)
+    #else
+    virtual ::grpc::experimental::ServerUnaryReactor* SetLoggingEndpoint(
+      ::grpc::experimental::CallbackServerContext* /*context*/, const ::dmi::SetLoggingEndpointRequest* /*request*/, ::dmi::SetRemoteEndpointResponse* /*response*/)
+    #endif
+      { return nullptr; }
+  };
+  template <class BaseClass>
+  class ExperimentalWithCallbackMethod_GetLoggingEndpoint : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    ExperimentalWithCallbackMethod_GetLoggingEndpoint() {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::Service::
+    #else
+      ::grpc::Service::experimental().
+    #endif
+        MarkMethodCallback(7,
+          new ::grpc_impl::internal::CallbackUnaryHandler< ::dmi::HardwareID, ::dmi::GetLoggingEndpointResponse>(
+            [this](
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+                   ::grpc::CallbackServerContext*
+    #else
+                   ::grpc::experimental::CallbackServerContext*
+    #endif
+                     context, const ::dmi::HardwareID* request, ::dmi::GetLoggingEndpointResponse* response) { return this->GetLoggingEndpoint(context, request, response); }));}
+    void SetMessageAllocatorFor_GetLoggingEndpoint(
+        ::grpc::experimental::MessageAllocator< ::dmi::HardwareID, ::dmi::GetLoggingEndpointResponse>* allocator) {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::internal::MethodHandler* const handler = ::grpc::Service::GetHandler(7);
+    #else
+      ::grpc::internal::MethodHandler* const handler = ::grpc::Service::experimental().GetHandler(7);
+    #endif
+      static_cast<::grpc_impl::internal::CallbackUnaryHandler< ::dmi::HardwareID, ::dmi::GetLoggingEndpointResponse>*>(handler)
+              ->SetMessageAllocator(allocator);
+    }
+    ~ExperimentalWithCallbackMethod_GetLoggingEndpoint() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetLoggingEndpoint(::grpc::ServerContext* /*context*/, const ::dmi::HardwareID* /*request*/, ::dmi::GetLoggingEndpointResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+    virtual ::grpc::ServerUnaryReactor* GetLoggingEndpoint(
+      ::grpc::CallbackServerContext* /*context*/, const ::dmi::HardwareID* /*request*/, ::dmi::GetLoggingEndpointResponse* /*response*/)
+    #else
+    virtual ::grpc::experimental::ServerUnaryReactor* GetLoggingEndpoint(
+      ::grpc::experimental::CallbackServerContext* /*context*/, const ::dmi::HardwareID* /*request*/, ::dmi::GetLoggingEndpointResponse* /*response*/)
+    #endif
+      { return nullptr; }
+  };
+  template <class BaseClass>
+  class ExperimentalWithCallbackMethod_SetMsgBusEndpoint : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    ExperimentalWithCallbackMethod_SetMsgBusEndpoint() {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::Service::
+    #else
+      ::grpc::Service::experimental().
+    #endif
+        MarkMethodCallback(8,
+          new ::grpc_impl::internal::CallbackUnaryHandler< ::dmi::SetMsgBusEndpointRequest, ::dmi::SetRemoteEndpointResponse>(
+            [this](
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+                   ::grpc::CallbackServerContext*
+    #else
+                   ::grpc::experimental::CallbackServerContext*
+    #endif
+                     context, const ::dmi::SetMsgBusEndpointRequest* request, ::dmi::SetRemoteEndpointResponse* response) { return this->SetMsgBusEndpoint(context, request, response); }));}
+    void SetMessageAllocatorFor_SetMsgBusEndpoint(
+        ::grpc::experimental::MessageAllocator< ::dmi::SetMsgBusEndpointRequest, ::dmi::SetRemoteEndpointResponse>* allocator) {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::internal::MethodHandler* const handler = ::grpc::Service::GetHandler(8);
+    #else
+      ::grpc::internal::MethodHandler* const handler = ::grpc::Service::experimental().GetHandler(8);
+    #endif
+      static_cast<::grpc_impl::internal::CallbackUnaryHandler< ::dmi::SetMsgBusEndpointRequest, ::dmi::SetRemoteEndpointResponse>*>(handler)
+              ->SetMessageAllocator(allocator);
+    }
+    ~ExperimentalWithCallbackMethod_SetMsgBusEndpoint() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status SetMsgBusEndpoint(::grpc::ServerContext* /*context*/, const ::dmi::SetMsgBusEndpointRequest* /*request*/, ::dmi::SetRemoteEndpointResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+    virtual ::grpc::ServerUnaryReactor* SetMsgBusEndpoint(
+      ::grpc::CallbackServerContext* /*context*/, const ::dmi::SetMsgBusEndpointRequest* /*request*/, ::dmi::SetRemoteEndpointResponse* /*response*/)
+    #else
+    virtual ::grpc::experimental::ServerUnaryReactor* SetMsgBusEndpoint(
+      ::grpc::experimental::CallbackServerContext* /*context*/, const ::dmi::SetMsgBusEndpointRequest* /*request*/, ::dmi::SetRemoteEndpointResponse* /*response*/)
+    #endif
+      { return nullptr; }
+  };
+  template <class BaseClass>
+  class ExperimentalWithCallbackMethod_GetMsgBusEndpoint : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    ExperimentalWithCallbackMethod_GetMsgBusEndpoint() {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::Service::
+    #else
+      ::grpc::Service::experimental().
+    #endif
+        MarkMethodCallback(9,
+          new ::grpc_impl::internal::CallbackUnaryHandler< ::google::protobuf::Empty, ::dmi::GetMsgBusEndpointResponse>(
+            [this](
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+                   ::grpc::CallbackServerContext*
+    #else
+                   ::grpc::experimental::CallbackServerContext*
+    #endif
+                     context, const ::google::protobuf::Empty* request, ::dmi::GetMsgBusEndpointResponse* response) { return this->GetMsgBusEndpoint(context, request, response); }));}
+    void SetMessageAllocatorFor_GetMsgBusEndpoint(
+        ::grpc::experimental::MessageAllocator< ::google::protobuf::Empty, ::dmi::GetMsgBusEndpointResponse>* allocator) {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::internal::MethodHandler* const handler = ::grpc::Service::GetHandler(9);
+    #else
+      ::grpc::internal::MethodHandler* const handler = ::grpc::Service::experimental().GetHandler(9);
+    #endif
+      static_cast<::grpc_impl::internal::CallbackUnaryHandler< ::google::protobuf::Empty, ::dmi::GetMsgBusEndpointResponse>*>(handler)
+              ->SetMessageAllocator(allocator);
+    }
+    ~ExperimentalWithCallbackMethod_GetMsgBusEndpoint() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetMsgBusEndpoint(::grpc::ServerContext* /*context*/, const ::google::protobuf::Empty* /*request*/, ::dmi::GetMsgBusEndpointResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+    virtual ::grpc::ServerUnaryReactor* GetMsgBusEndpoint(
+      ::grpc::CallbackServerContext* /*context*/, const ::google::protobuf::Empty* /*request*/, ::dmi::GetMsgBusEndpointResponse* /*response*/)
+    #else
+    virtual ::grpc::experimental::ServerUnaryReactor* GetMsgBusEndpoint(
+      ::grpc::experimental::CallbackServerContext* /*context*/, const ::google::protobuf::Empty* /*request*/, ::dmi::GetMsgBusEndpointResponse* /*response*/)
+    #endif
+      { return nullptr; }
+  };
+  template <class BaseClass>
+  class ExperimentalWithCallbackMethod_GetLoggableEntities : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    ExperimentalWithCallbackMethod_GetLoggableEntities() {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::Service::
+    #else
+      ::grpc::Service::experimental().
+    #endif
+        MarkMethodCallback(10,
+          new ::grpc_impl::internal::CallbackUnaryHandler< ::dmi::GetLoggableEntitiesRequest, ::dmi::GetLogLevelResponse>(
+            [this](
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+                   ::grpc::CallbackServerContext*
+    #else
+                   ::grpc::experimental::CallbackServerContext*
+    #endif
+                     context, const ::dmi::GetLoggableEntitiesRequest* request, ::dmi::GetLogLevelResponse* response) { return this->GetLoggableEntities(context, request, response); }));}
+    void SetMessageAllocatorFor_GetLoggableEntities(
+        ::grpc::experimental::MessageAllocator< ::dmi::GetLoggableEntitiesRequest, ::dmi::GetLogLevelResponse>* allocator) {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::internal::MethodHandler* const handler = ::grpc::Service::GetHandler(10);
+    #else
+      ::grpc::internal::MethodHandler* const handler = ::grpc::Service::experimental().GetHandler(10);
+    #endif
+      static_cast<::grpc_impl::internal::CallbackUnaryHandler< ::dmi::GetLoggableEntitiesRequest, ::dmi::GetLogLevelResponse>*>(handler)
+              ->SetMessageAllocator(allocator);
+    }
+    ~ExperimentalWithCallbackMethod_GetLoggableEntities() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetLoggableEntities(::grpc::ServerContext* /*context*/, const ::dmi::GetLoggableEntitiesRequest* /*request*/, ::dmi::GetLogLevelResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+    virtual ::grpc::ServerUnaryReactor* GetLoggableEntities(
+      ::grpc::CallbackServerContext* /*context*/, const ::dmi::GetLoggableEntitiesRequest* /*request*/, ::dmi::GetLogLevelResponse* /*response*/)
+    #else
+    virtual ::grpc::experimental::ServerUnaryReactor* GetLoggableEntities(
+      ::grpc::experimental::CallbackServerContext* /*context*/, const ::dmi::GetLoggableEntitiesRequest* /*request*/, ::dmi::GetLogLevelResponse* /*response*/)
+    #endif
+      { return nullptr; }
+  };
+  template <class BaseClass>
+  class ExperimentalWithCallbackMethod_SetLogLevel : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    ExperimentalWithCallbackMethod_SetLogLevel() {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::Service::
+    #else
+      ::grpc::Service::experimental().
+    #endif
+        MarkMethodCallback(11,
+          new ::grpc_impl::internal::CallbackUnaryHandler< ::dmi::SetLogLevelRequest, ::dmi::SetLogLevelResponse>(
+            [this](
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+                   ::grpc::CallbackServerContext*
+    #else
+                   ::grpc::experimental::CallbackServerContext*
+    #endif
+                     context, const ::dmi::SetLogLevelRequest* request, ::dmi::SetLogLevelResponse* response) { return this->SetLogLevel(context, request, response); }));}
+    void SetMessageAllocatorFor_SetLogLevel(
+        ::grpc::experimental::MessageAllocator< ::dmi::SetLogLevelRequest, ::dmi::SetLogLevelResponse>* allocator) {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::internal::MethodHandler* const handler = ::grpc::Service::GetHandler(11);
+    #else
+      ::grpc::internal::MethodHandler* const handler = ::grpc::Service::experimental().GetHandler(11);
+    #endif
+      static_cast<::grpc_impl::internal::CallbackUnaryHandler< ::dmi::SetLogLevelRequest, ::dmi::SetLogLevelResponse>*>(handler)
+              ->SetMessageAllocator(allocator);
+    }
+    ~ExperimentalWithCallbackMethod_SetLogLevel() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status SetLogLevel(::grpc::ServerContext* /*context*/, const ::dmi::SetLogLevelRequest* /*request*/, ::dmi::SetLogLevelResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+    virtual ::grpc::ServerUnaryReactor* SetLogLevel(
+      ::grpc::CallbackServerContext* /*context*/, const ::dmi::SetLogLevelRequest* /*request*/, ::dmi::SetLogLevelResponse* /*response*/)
+    #else
+    virtual ::grpc::experimental::ServerUnaryReactor* SetLogLevel(
+      ::grpc::experimental::CallbackServerContext* /*context*/, const ::dmi::SetLogLevelRequest* /*request*/, ::dmi::SetLogLevelResponse* /*response*/)
+    #endif
+      { return nullptr; }
+  };
+  template <class BaseClass>
+  class ExperimentalWithCallbackMethod_GetLogLevel : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    ExperimentalWithCallbackMethod_GetLogLevel() {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::Service::
+    #else
+      ::grpc::Service::experimental().
+    #endif
+        MarkMethodCallback(12,
+          new ::grpc_impl::internal::CallbackUnaryHandler< ::dmi::GetLogLevelRequest, ::dmi::GetLogLevelResponse>(
+            [this](
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+                   ::grpc::CallbackServerContext*
+    #else
+                   ::grpc::experimental::CallbackServerContext*
+    #endif
+                     context, const ::dmi::GetLogLevelRequest* request, ::dmi::GetLogLevelResponse* response) { return this->GetLogLevel(context, request, response); }));}
+    void SetMessageAllocatorFor_GetLogLevel(
+        ::grpc::experimental::MessageAllocator< ::dmi::GetLogLevelRequest, ::dmi::GetLogLevelResponse>* allocator) {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::internal::MethodHandler* const handler = ::grpc::Service::GetHandler(12);
+    #else
+      ::grpc::internal::MethodHandler* const handler = ::grpc::Service::experimental().GetHandler(12);
+    #endif
+      static_cast<::grpc_impl::internal::CallbackUnaryHandler< ::dmi::GetLogLevelRequest, ::dmi::GetLogLevelResponse>*>(handler)
+              ->SetMessageAllocator(allocator);
+    }
+    ~ExperimentalWithCallbackMethod_GetLogLevel() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetLogLevel(::grpc::ServerContext* /*context*/, const ::dmi::GetLogLevelRequest* /*request*/, ::dmi::GetLogLevelResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+    virtual ::grpc::ServerUnaryReactor* GetLogLevel(
+      ::grpc::CallbackServerContext* /*context*/, const ::dmi::GetLogLevelRequest* /*request*/, ::dmi::GetLogLevelResponse* /*response*/)
+    #else
+    virtual ::grpc::experimental::ServerUnaryReactor* GetLogLevel(
+      ::grpc::experimental::CallbackServerContext* /*context*/, const ::dmi::GetLogLevelRequest* /*request*/, ::dmi::GetLogLevelResponse* /*response*/)
+    #endif
+      { return nullptr; }
+  };
+  #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+  typedef ExperimentalWithCallbackMethod_StartManagingDevice<ExperimentalWithCallbackMethod_StopManagingDevice<ExperimentalWithCallbackMethod_GetManagedDevices<ExperimentalWithCallbackMethod_GetPhysicalInventory<ExperimentalWithCallbackMethod_GetHWComponentInfo<ExperimentalWithCallbackMethod_SetHWComponentInfo<ExperimentalWithCallbackMethod_SetLoggingEndpoint<ExperimentalWithCallbackMethod_GetLoggingEndpoint<ExperimentalWithCallbackMethod_SetMsgBusEndpoint<ExperimentalWithCallbackMethod_GetMsgBusEndpoint<ExperimentalWithCallbackMethod_GetLoggableEntities<ExperimentalWithCallbackMethod_SetLogLevel<ExperimentalWithCallbackMethod_GetLogLevel<Service > > > > > > > > > > > > > CallbackService;
+  #endif
+
+  typedef ExperimentalWithCallbackMethod_StartManagingDevice<ExperimentalWithCallbackMethod_StopManagingDevice<ExperimentalWithCallbackMethod_GetManagedDevices<ExperimentalWithCallbackMethod_GetPhysicalInventory<ExperimentalWithCallbackMethod_GetHWComponentInfo<ExperimentalWithCallbackMethod_SetHWComponentInfo<ExperimentalWithCallbackMethod_SetLoggingEndpoint<ExperimentalWithCallbackMethod_GetLoggingEndpoint<ExperimentalWithCallbackMethod_SetMsgBusEndpoint<ExperimentalWithCallbackMethod_GetMsgBusEndpoint<ExperimentalWithCallbackMethod_GetLoggableEntities<ExperimentalWithCallbackMethod_SetLogLevel<ExperimentalWithCallbackMethod_GetLogLevel<Service > > > > > > > > > > > > > ExperimentalCallbackService;
+  template <class BaseClass>
+  class WithGenericMethod_StartManagingDevice : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithGenericMethod_StartManagingDevice() {
+      ::grpc::Service::MarkMethodGeneric(0);
+    }
+    ~WithGenericMethod_StartManagingDevice() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status StartManagingDevice(::grpc::ServerContext* /*context*/, const ::dmi::ModifiableComponent* /*request*/, ::grpc::ServerWriter< ::dmi::StartManagingDeviceResponse>* /*writer*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+  };
+  template <class BaseClass>
+  class WithGenericMethod_StopManagingDevice : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithGenericMethod_StopManagingDevice() {
+      ::grpc::Service::MarkMethodGeneric(1);
+    }
+    ~WithGenericMethod_StopManagingDevice() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status StopManagingDevice(::grpc::ServerContext* /*context*/, const ::dmi::StopManagingDeviceRequest* /*request*/, ::dmi::StopManagingDeviceResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+  };
+  template <class BaseClass>
+  class WithGenericMethod_GetManagedDevices : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithGenericMethod_GetManagedDevices() {
+      ::grpc::Service::MarkMethodGeneric(2);
+    }
+    ~WithGenericMethod_GetManagedDevices() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetManagedDevices(::grpc::ServerContext* /*context*/, const ::google::protobuf::Empty* /*request*/, ::dmi::ManagedDevicesResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+  };
+  template <class BaseClass>
+  class WithGenericMethod_GetPhysicalInventory : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithGenericMethod_GetPhysicalInventory() {
+      ::grpc::Service::MarkMethodGeneric(3);
+    }
+    ~WithGenericMethod_GetPhysicalInventory() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetPhysicalInventory(::grpc::ServerContext* /*context*/, const ::dmi::PhysicalInventoryRequest* /*request*/, ::grpc::ServerWriter< ::dmi::PhysicalInventoryResponse>* /*writer*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+  };
+  template <class BaseClass>
+  class WithGenericMethod_GetHWComponentInfo : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithGenericMethod_GetHWComponentInfo() {
+      ::grpc::Service::MarkMethodGeneric(4);
+    }
+    ~WithGenericMethod_GetHWComponentInfo() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetHWComponentInfo(::grpc::ServerContext* /*context*/, const ::dmi::HWComponentInfoGetRequest* /*request*/, ::grpc::ServerWriter< ::dmi::HWComponentInfoGetResponse>* /*writer*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+  };
+  template <class BaseClass>
+  class WithGenericMethod_SetHWComponentInfo : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithGenericMethod_SetHWComponentInfo() {
+      ::grpc::Service::MarkMethodGeneric(5);
+    }
+    ~WithGenericMethod_SetHWComponentInfo() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status SetHWComponentInfo(::grpc::ServerContext* /*context*/, const ::dmi::HWComponentInfoSetRequest* /*request*/, ::dmi::HWComponentInfoSetResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+  };
+  template <class BaseClass>
+  class WithGenericMethod_SetLoggingEndpoint : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithGenericMethod_SetLoggingEndpoint() {
+      ::grpc::Service::MarkMethodGeneric(6);
+    }
+    ~WithGenericMethod_SetLoggingEndpoint() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status SetLoggingEndpoint(::grpc::ServerContext* /*context*/, const ::dmi::SetLoggingEndpointRequest* /*request*/, ::dmi::SetRemoteEndpointResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+  };
+  template <class BaseClass>
+  class WithGenericMethod_GetLoggingEndpoint : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithGenericMethod_GetLoggingEndpoint() {
+      ::grpc::Service::MarkMethodGeneric(7);
+    }
+    ~WithGenericMethod_GetLoggingEndpoint() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetLoggingEndpoint(::grpc::ServerContext* /*context*/, const ::dmi::HardwareID* /*request*/, ::dmi::GetLoggingEndpointResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+  };
+  template <class BaseClass>
+  class WithGenericMethod_SetMsgBusEndpoint : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithGenericMethod_SetMsgBusEndpoint() {
+      ::grpc::Service::MarkMethodGeneric(8);
+    }
+    ~WithGenericMethod_SetMsgBusEndpoint() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status SetMsgBusEndpoint(::grpc::ServerContext* /*context*/, const ::dmi::SetMsgBusEndpointRequest* /*request*/, ::dmi::SetRemoteEndpointResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+  };
+  template <class BaseClass>
+  class WithGenericMethod_GetMsgBusEndpoint : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithGenericMethod_GetMsgBusEndpoint() {
+      ::grpc::Service::MarkMethodGeneric(9);
+    }
+    ~WithGenericMethod_GetMsgBusEndpoint() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetMsgBusEndpoint(::grpc::ServerContext* /*context*/, const ::google::protobuf::Empty* /*request*/, ::dmi::GetMsgBusEndpointResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+  };
+  template <class BaseClass>
+  class WithGenericMethod_GetLoggableEntities : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithGenericMethod_GetLoggableEntities() {
+      ::grpc::Service::MarkMethodGeneric(10);
+    }
+    ~WithGenericMethod_GetLoggableEntities() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetLoggableEntities(::grpc::ServerContext* /*context*/, const ::dmi::GetLoggableEntitiesRequest* /*request*/, ::dmi::GetLogLevelResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+  };
+  template <class BaseClass>
+  class WithGenericMethod_SetLogLevel : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithGenericMethod_SetLogLevel() {
+      ::grpc::Service::MarkMethodGeneric(11);
+    }
+    ~WithGenericMethod_SetLogLevel() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status SetLogLevel(::grpc::ServerContext* /*context*/, const ::dmi::SetLogLevelRequest* /*request*/, ::dmi::SetLogLevelResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+  };
+  template <class BaseClass>
+  class WithGenericMethod_GetLogLevel : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithGenericMethod_GetLogLevel() {
+      ::grpc::Service::MarkMethodGeneric(12);
+    }
+    ~WithGenericMethod_GetLogLevel() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetLogLevel(::grpc::ServerContext* /*context*/, const ::dmi::GetLogLevelRequest* /*request*/, ::dmi::GetLogLevelResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+  };
+  template <class BaseClass>
+  class WithRawMethod_StartManagingDevice : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithRawMethod_StartManagingDevice() {
+      ::grpc::Service::MarkMethodRaw(0);
+    }
+    ~WithRawMethod_StartManagingDevice() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status StartManagingDevice(::grpc::ServerContext* /*context*/, const ::dmi::ModifiableComponent* /*request*/, ::grpc::ServerWriter< ::dmi::StartManagingDeviceResponse>* /*writer*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    void RequestStartManagingDevice(::grpc::ServerContext* context, ::grpc::ByteBuffer* request, ::grpc::ServerAsyncWriter< ::grpc::ByteBuffer>* writer, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) {
+      ::grpc::Service::RequestAsyncServerStreaming(0, context, request, writer, new_call_cq, notification_cq, tag);
+    }
+  };
+  template <class BaseClass>
+  class WithRawMethod_StopManagingDevice : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithRawMethod_StopManagingDevice() {
+      ::grpc::Service::MarkMethodRaw(1);
+    }
+    ~WithRawMethod_StopManagingDevice() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status StopManagingDevice(::grpc::ServerContext* /*context*/, const ::dmi::StopManagingDeviceRequest* /*request*/, ::dmi::StopManagingDeviceResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    void RequestStopManagingDevice(::grpc::ServerContext* context, ::grpc::ByteBuffer* request, ::grpc::ServerAsyncResponseWriter< ::grpc::ByteBuffer>* response, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) {
+      ::grpc::Service::RequestAsyncUnary(1, context, request, response, new_call_cq, notification_cq, tag);
+    }
+  };
+  template <class BaseClass>
+  class WithRawMethod_GetManagedDevices : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithRawMethod_GetManagedDevices() {
+      ::grpc::Service::MarkMethodRaw(2);
+    }
+    ~WithRawMethod_GetManagedDevices() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetManagedDevices(::grpc::ServerContext* /*context*/, const ::google::protobuf::Empty* /*request*/, ::dmi::ManagedDevicesResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    void RequestGetManagedDevices(::grpc::ServerContext* context, ::grpc::ByteBuffer* request, ::grpc::ServerAsyncResponseWriter< ::grpc::ByteBuffer>* response, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) {
+      ::grpc::Service::RequestAsyncUnary(2, context, request, response, new_call_cq, notification_cq, tag);
+    }
+  };
+  template <class BaseClass>
+  class WithRawMethod_GetPhysicalInventory : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithRawMethod_GetPhysicalInventory() {
+      ::grpc::Service::MarkMethodRaw(3);
+    }
+    ~WithRawMethod_GetPhysicalInventory() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetPhysicalInventory(::grpc::ServerContext* /*context*/, const ::dmi::PhysicalInventoryRequest* /*request*/, ::grpc::ServerWriter< ::dmi::PhysicalInventoryResponse>* /*writer*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    void RequestGetPhysicalInventory(::grpc::ServerContext* context, ::grpc::ByteBuffer* request, ::grpc::ServerAsyncWriter< ::grpc::ByteBuffer>* writer, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) {
+      ::grpc::Service::RequestAsyncServerStreaming(3, context, request, writer, new_call_cq, notification_cq, tag);
+    }
+  };
+  template <class BaseClass>
+  class WithRawMethod_GetHWComponentInfo : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithRawMethod_GetHWComponentInfo() {
+      ::grpc::Service::MarkMethodRaw(4);
+    }
+    ~WithRawMethod_GetHWComponentInfo() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetHWComponentInfo(::grpc::ServerContext* /*context*/, const ::dmi::HWComponentInfoGetRequest* /*request*/, ::grpc::ServerWriter< ::dmi::HWComponentInfoGetResponse>* /*writer*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    void RequestGetHWComponentInfo(::grpc::ServerContext* context, ::grpc::ByteBuffer* request, ::grpc::ServerAsyncWriter< ::grpc::ByteBuffer>* writer, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) {
+      ::grpc::Service::RequestAsyncServerStreaming(4, context, request, writer, new_call_cq, notification_cq, tag);
+    }
+  };
+  template <class BaseClass>
+  class WithRawMethod_SetHWComponentInfo : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithRawMethod_SetHWComponentInfo() {
+      ::grpc::Service::MarkMethodRaw(5);
+    }
+    ~WithRawMethod_SetHWComponentInfo() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status SetHWComponentInfo(::grpc::ServerContext* /*context*/, const ::dmi::HWComponentInfoSetRequest* /*request*/, ::dmi::HWComponentInfoSetResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    void RequestSetHWComponentInfo(::grpc::ServerContext* context, ::grpc::ByteBuffer* request, ::grpc::ServerAsyncResponseWriter< ::grpc::ByteBuffer>* response, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) {
+      ::grpc::Service::RequestAsyncUnary(5, context, request, response, new_call_cq, notification_cq, tag);
+    }
+  };
+  template <class BaseClass>
+  class WithRawMethod_SetLoggingEndpoint : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithRawMethod_SetLoggingEndpoint() {
+      ::grpc::Service::MarkMethodRaw(6);
+    }
+    ~WithRawMethod_SetLoggingEndpoint() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status SetLoggingEndpoint(::grpc::ServerContext* /*context*/, const ::dmi::SetLoggingEndpointRequest* /*request*/, ::dmi::SetRemoteEndpointResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    void RequestSetLoggingEndpoint(::grpc::ServerContext* context, ::grpc::ByteBuffer* request, ::grpc::ServerAsyncResponseWriter< ::grpc::ByteBuffer>* response, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) {
+      ::grpc::Service::RequestAsyncUnary(6, context, request, response, new_call_cq, notification_cq, tag);
+    }
+  };
+  template <class BaseClass>
+  class WithRawMethod_GetLoggingEndpoint : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithRawMethod_GetLoggingEndpoint() {
+      ::grpc::Service::MarkMethodRaw(7);
+    }
+    ~WithRawMethod_GetLoggingEndpoint() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetLoggingEndpoint(::grpc::ServerContext* /*context*/, const ::dmi::HardwareID* /*request*/, ::dmi::GetLoggingEndpointResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    void RequestGetLoggingEndpoint(::grpc::ServerContext* context, ::grpc::ByteBuffer* request, ::grpc::ServerAsyncResponseWriter< ::grpc::ByteBuffer>* response, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) {
+      ::grpc::Service::RequestAsyncUnary(7, context, request, response, new_call_cq, notification_cq, tag);
+    }
+  };
+  template <class BaseClass>
+  class WithRawMethod_SetMsgBusEndpoint : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithRawMethod_SetMsgBusEndpoint() {
+      ::grpc::Service::MarkMethodRaw(8);
+    }
+    ~WithRawMethod_SetMsgBusEndpoint() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status SetMsgBusEndpoint(::grpc::ServerContext* /*context*/, const ::dmi::SetMsgBusEndpointRequest* /*request*/, ::dmi::SetRemoteEndpointResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    void RequestSetMsgBusEndpoint(::grpc::ServerContext* context, ::grpc::ByteBuffer* request, ::grpc::ServerAsyncResponseWriter< ::grpc::ByteBuffer>* response, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) {
+      ::grpc::Service::RequestAsyncUnary(8, context, request, response, new_call_cq, notification_cq, tag);
+    }
+  };
+  template <class BaseClass>
+  class WithRawMethod_GetMsgBusEndpoint : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithRawMethod_GetMsgBusEndpoint() {
+      ::grpc::Service::MarkMethodRaw(9);
+    }
+    ~WithRawMethod_GetMsgBusEndpoint() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetMsgBusEndpoint(::grpc::ServerContext* /*context*/, const ::google::protobuf::Empty* /*request*/, ::dmi::GetMsgBusEndpointResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    void RequestGetMsgBusEndpoint(::grpc::ServerContext* context, ::grpc::ByteBuffer* request, ::grpc::ServerAsyncResponseWriter< ::grpc::ByteBuffer>* response, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) {
+      ::grpc::Service::RequestAsyncUnary(9, context, request, response, new_call_cq, notification_cq, tag);
+    }
+  };
+  template <class BaseClass>
+  class WithRawMethod_GetLoggableEntities : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithRawMethod_GetLoggableEntities() {
+      ::grpc::Service::MarkMethodRaw(10);
+    }
+    ~WithRawMethod_GetLoggableEntities() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetLoggableEntities(::grpc::ServerContext* /*context*/, const ::dmi::GetLoggableEntitiesRequest* /*request*/, ::dmi::GetLogLevelResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    void RequestGetLoggableEntities(::grpc::ServerContext* context, ::grpc::ByteBuffer* request, ::grpc::ServerAsyncResponseWriter< ::grpc::ByteBuffer>* response, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) {
+      ::grpc::Service::RequestAsyncUnary(10, context, request, response, new_call_cq, notification_cq, tag);
+    }
+  };
+  template <class BaseClass>
+  class WithRawMethod_SetLogLevel : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithRawMethod_SetLogLevel() {
+      ::grpc::Service::MarkMethodRaw(11);
+    }
+    ~WithRawMethod_SetLogLevel() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status SetLogLevel(::grpc::ServerContext* /*context*/, const ::dmi::SetLogLevelRequest* /*request*/, ::dmi::SetLogLevelResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    void RequestSetLogLevel(::grpc::ServerContext* context, ::grpc::ByteBuffer* request, ::grpc::ServerAsyncResponseWriter< ::grpc::ByteBuffer>* response, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) {
+      ::grpc::Service::RequestAsyncUnary(11, context, request, response, new_call_cq, notification_cq, tag);
+    }
+  };
+  template <class BaseClass>
+  class WithRawMethod_GetLogLevel : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithRawMethod_GetLogLevel() {
+      ::grpc::Service::MarkMethodRaw(12);
+    }
+    ~WithRawMethod_GetLogLevel() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetLogLevel(::grpc::ServerContext* /*context*/, const ::dmi::GetLogLevelRequest* /*request*/, ::dmi::GetLogLevelResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    void RequestGetLogLevel(::grpc::ServerContext* context, ::grpc::ByteBuffer* request, ::grpc::ServerAsyncResponseWriter< ::grpc::ByteBuffer>* response, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) {
+      ::grpc::Service::RequestAsyncUnary(12, context, request, response, new_call_cq, notification_cq, tag);
+    }
+  };
+  template <class BaseClass>
+  class ExperimentalWithRawCallbackMethod_StartManagingDevice : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    ExperimentalWithRawCallbackMethod_StartManagingDevice() {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::Service::
+    #else
+      ::grpc::Service::experimental().
+    #endif
+        MarkMethodRawCallback(0,
+          new ::grpc_impl::internal::CallbackServerStreamingHandler< ::grpc::ByteBuffer, ::grpc::ByteBuffer>(
+            [this](
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+                   ::grpc::CallbackServerContext*
+    #else
+                   ::grpc::experimental::CallbackServerContext*
+    #endif
+                     context, const::grpc::ByteBuffer* request) { return this->StartManagingDevice(context, request); }));
+    }
+    ~ExperimentalWithRawCallbackMethod_StartManagingDevice() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status StartManagingDevice(::grpc::ServerContext* /*context*/, const ::dmi::ModifiableComponent* /*request*/, ::grpc::ServerWriter< ::dmi::StartManagingDeviceResponse>* /*writer*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+    virtual ::grpc::ServerWriteReactor< ::grpc::ByteBuffer>* StartManagingDevice(
+      ::grpc::CallbackServerContext* /*context*/, const ::grpc::ByteBuffer* /*request*/)
+    #else
+    virtual ::grpc::experimental::ServerWriteReactor< ::grpc::ByteBuffer>* StartManagingDevice(
+      ::grpc::experimental::CallbackServerContext* /*context*/, const ::grpc::ByteBuffer* /*request*/)
+    #endif
+      { return nullptr; }
+  };
+  template <class BaseClass>
+  class ExperimentalWithRawCallbackMethod_StopManagingDevice : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    ExperimentalWithRawCallbackMethod_StopManagingDevice() {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::Service::
+    #else
+      ::grpc::Service::experimental().
+    #endif
+        MarkMethodRawCallback(1,
+          new ::grpc_impl::internal::CallbackUnaryHandler< ::grpc::ByteBuffer, ::grpc::ByteBuffer>(
+            [this](
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+                   ::grpc::CallbackServerContext*
+    #else
+                   ::grpc::experimental::CallbackServerContext*
+    #endif
+                     context, const ::grpc::ByteBuffer* request, ::grpc::ByteBuffer* response) { return this->StopManagingDevice(context, request, response); }));
+    }
+    ~ExperimentalWithRawCallbackMethod_StopManagingDevice() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status StopManagingDevice(::grpc::ServerContext* /*context*/, const ::dmi::StopManagingDeviceRequest* /*request*/, ::dmi::StopManagingDeviceResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+    virtual ::grpc::ServerUnaryReactor* StopManagingDevice(
+      ::grpc::CallbackServerContext* /*context*/, const ::grpc::ByteBuffer* /*request*/, ::grpc::ByteBuffer* /*response*/)
+    #else
+    virtual ::grpc::experimental::ServerUnaryReactor* StopManagingDevice(
+      ::grpc::experimental::CallbackServerContext* /*context*/, const ::grpc::ByteBuffer* /*request*/, ::grpc::ByteBuffer* /*response*/)
+    #endif
+      { return nullptr; }
+  };
+  template <class BaseClass>
+  class ExperimentalWithRawCallbackMethod_GetManagedDevices : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    ExperimentalWithRawCallbackMethod_GetManagedDevices() {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::Service::
+    #else
+      ::grpc::Service::experimental().
+    #endif
+        MarkMethodRawCallback(2,
+          new ::grpc_impl::internal::CallbackUnaryHandler< ::grpc::ByteBuffer, ::grpc::ByteBuffer>(
+            [this](
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+                   ::grpc::CallbackServerContext*
+    #else
+                   ::grpc::experimental::CallbackServerContext*
+    #endif
+                     context, const ::grpc::ByteBuffer* request, ::grpc::ByteBuffer* response) { return this->GetManagedDevices(context, request, response); }));
+    }
+    ~ExperimentalWithRawCallbackMethod_GetManagedDevices() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetManagedDevices(::grpc::ServerContext* /*context*/, const ::google::protobuf::Empty* /*request*/, ::dmi::ManagedDevicesResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+    virtual ::grpc::ServerUnaryReactor* GetManagedDevices(
+      ::grpc::CallbackServerContext* /*context*/, const ::grpc::ByteBuffer* /*request*/, ::grpc::ByteBuffer* /*response*/)
+    #else
+    virtual ::grpc::experimental::ServerUnaryReactor* GetManagedDevices(
+      ::grpc::experimental::CallbackServerContext* /*context*/, const ::grpc::ByteBuffer* /*request*/, ::grpc::ByteBuffer* /*response*/)
+    #endif
+      { return nullptr; }
+  };
+  template <class BaseClass>
+  class ExperimentalWithRawCallbackMethod_GetPhysicalInventory : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    ExperimentalWithRawCallbackMethod_GetPhysicalInventory() {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::Service::
+    #else
+      ::grpc::Service::experimental().
+    #endif
+        MarkMethodRawCallback(3,
+          new ::grpc_impl::internal::CallbackServerStreamingHandler< ::grpc::ByteBuffer, ::grpc::ByteBuffer>(
+            [this](
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+                   ::grpc::CallbackServerContext*
+    #else
+                   ::grpc::experimental::CallbackServerContext*
+    #endif
+                     context, const::grpc::ByteBuffer* request) { return this->GetPhysicalInventory(context, request); }));
+    }
+    ~ExperimentalWithRawCallbackMethod_GetPhysicalInventory() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetPhysicalInventory(::grpc::ServerContext* /*context*/, const ::dmi::PhysicalInventoryRequest* /*request*/, ::grpc::ServerWriter< ::dmi::PhysicalInventoryResponse>* /*writer*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+    virtual ::grpc::ServerWriteReactor< ::grpc::ByteBuffer>* GetPhysicalInventory(
+      ::grpc::CallbackServerContext* /*context*/, const ::grpc::ByteBuffer* /*request*/)
+    #else
+    virtual ::grpc::experimental::ServerWriteReactor< ::grpc::ByteBuffer>* GetPhysicalInventory(
+      ::grpc::experimental::CallbackServerContext* /*context*/, const ::grpc::ByteBuffer* /*request*/)
+    #endif
+      { return nullptr; }
+  };
+  template <class BaseClass>
+  class ExperimentalWithRawCallbackMethod_GetHWComponentInfo : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    ExperimentalWithRawCallbackMethod_GetHWComponentInfo() {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::Service::
+    #else
+      ::grpc::Service::experimental().
+    #endif
+        MarkMethodRawCallback(4,
+          new ::grpc_impl::internal::CallbackServerStreamingHandler< ::grpc::ByteBuffer, ::grpc::ByteBuffer>(
+            [this](
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+                   ::grpc::CallbackServerContext*
+    #else
+                   ::grpc::experimental::CallbackServerContext*
+    #endif
+                     context, const::grpc::ByteBuffer* request) { return this->GetHWComponentInfo(context, request); }));
+    }
+    ~ExperimentalWithRawCallbackMethod_GetHWComponentInfo() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetHWComponentInfo(::grpc::ServerContext* /*context*/, const ::dmi::HWComponentInfoGetRequest* /*request*/, ::grpc::ServerWriter< ::dmi::HWComponentInfoGetResponse>* /*writer*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+    virtual ::grpc::ServerWriteReactor< ::grpc::ByteBuffer>* GetHWComponentInfo(
+      ::grpc::CallbackServerContext* /*context*/, const ::grpc::ByteBuffer* /*request*/)
+    #else
+    virtual ::grpc::experimental::ServerWriteReactor< ::grpc::ByteBuffer>* GetHWComponentInfo(
+      ::grpc::experimental::CallbackServerContext* /*context*/, const ::grpc::ByteBuffer* /*request*/)
+    #endif
+      { return nullptr; }
+  };
+  template <class BaseClass>
+  class ExperimentalWithRawCallbackMethod_SetHWComponentInfo : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    ExperimentalWithRawCallbackMethod_SetHWComponentInfo() {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::Service::
+    #else
+      ::grpc::Service::experimental().
+    #endif
+        MarkMethodRawCallback(5,
+          new ::grpc_impl::internal::CallbackUnaryHandler< ::grpc::ByteBuffer, ::grpc::ByteBuffer>(
+            [this](
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+                   ::grpc::CallbackServerContext*
+    #else
+                   ::grpc::experimental::CallbackServerContext*
+    #endif
+                     context, const ::grpc::ByteBuffer* request, ::grpc::ByteBuffer* response) { return this->SetHWComponentInfo(context, request, response); }));
+    }
+    ~ExperimentalWithRawCallbackMethod_SetHWComponentInfo() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status SetHWComponentInfo(::grpc::ServerContext* /*context*/, const ::dmi::HWComponentInfoSetRequest* /*request*/, ::dmi::HWComponentInfoSetResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+    virtual ::grpc::ServerUnaryReactor* SetHWComponentInfo(
+      ::grpc::CallbackServerContext* /*context*/, const ::grpc::ByteBuffer* /*request*/, ::grpc::ByteBuffer* /*response*/)
+    #else
+    virtual ::grpc::experimental::ServerUnaryReactor* SetHWComponentInfo(
+      ::grpc::experimental::CallbackServerContext* /*context*/, const ::grpc::ByteBuffer* /*request*/, ::grpc::ByteBuffer* /*response*/)
+    #endif
+      { return nullptr; }
+  };
+  template <class BaseClass>
+  class ExperimentalWithRawCallbackMethod_SetLoggingEndpoint : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    ExperimentalWithRawCallbackMethod_SetLoggingEndpoint() {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::Service::
+    #else
+      ::grpc::Service::experimental().
+    #endif
+        MarkMethodRawCallback(6,
+          new ::grpc_impl::internal::CallbackUnaryHandler< ::grpc::ByteBuffer, ::grpc::ByteBuffer>(
+            [this](
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+                   ::grpc::CallbackServerContext*
+    #else
+                   ::grpc::experimental::CallbackServerContext*
+    #endif
+                     context, const ::grpc::ByteBuffer* request, ::grpc::ByteBuffer* response) { return this->SetLoggingEndpoint(context, request, response); }));
+    }
+    ~ExperimentalWithRawCallbackMethod_SetLoggingEndpoint() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status SetLoggingEndpoint(::grpc::ServerContext* /*context*/, const ::dmi::SetLoggingEndpointRequest* /*request*/, ::dmi::SetRemoteEndpointResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+    virtual ::grpc::ServerUnaryReactor* SetLoggingEndpoint(
+      ::grpc::CallbackServerContext* /*context*/, const ::grpc::ByteBuffer* /*request*/, ::grpc::ByteBuffer* /*response*/)
+    #else
+    virtual ::grpc::experimental::ServerUnaryReactor* SetLoggingEndpoint(
+      ::grpc::experimental::CallbackServerContext* /*context*/, const ::grpc::ByteBuffer* /*request*/, ::grpc::ByteBuffer* /*response*/)
+    #endif
+      { return nullptr; }
+  };
+  template <class BaseClass>
+  class ExperimentalWithRawCallbackMethod_GetLoggingEndpoint : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    ExperimentalWithRawCallbackMethod_GetLoggingEndpoint() {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::Service::
+    #else
+      ::grpc::Service::experimental().
+    #endif
+        MarkMethodRawCallback(7,
+          new ::grpc_impl::internal::CallbackUnaryHandler< ::grpc::ByteBuffer, ::grpc::ByteBuffer>(
+            [this](
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+                   ::grpc::CallbackServerContext*
+    #else
+                   ::grpc::experimental::CallbackServerContext*
+    #endif
+                     context, const ::grpc::ByteBuffer* request, ::grpc::ByteBuffer* response) { return this->GetLoggingEndpoint(context, request, response); }));
+    }
+    ~ExperimentalWithRawCallbackMethod_GetLoggingEndpoint() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetLoggingEndpoint(::grpc::ServerContext* /*context*/, const ::dmi::HardwareID* /*request*/, ::dmi::GetLoggingEndpointResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+    virtual ::grpc::ServerUnaryReactor* GetLoggingEndpoint(
+      ::grpc::CallbackServerContext* /*context*/, const ::grpc::ByteBuffer* /*request*/, ::grpc::ByteBuffer* /*response*/)
+    #else
+    virtual ::grpc::experimental::ServerUnaryReactor* GetLoggingEndpoint(
+      ::grpc::experimental::CallbackServerContext* /*context*/, const ::grpc::ByteBuffer* /*request*/, ::grpc::ByteBuffer* /*response*/)
+    #endif
+      { return nullptr; }
+  };
+  template <class BaseClass>
+  class ExperimentalWithRawCallbackMethod_SetMsgBusEndpoint : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    ExperimentalWithRawCallbackMethod_SetMsgBusEndpoint() {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::Service::
+    #else
+      ::grpc::Service::experimental().
+    #endif
+        MarkMethodRawCallback(8,
+          new ::grpc_impl::internal::CallbackUnaryHandler< ::grpc::ByteBuffer, ::grpc::ByteBuffer>(
+            [this](
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+                   ::grpc::CallbackServerContext*
+    #else
+                   ::grpc::experimental::CallbackServerContext*
+    #endif
+                     context, const ::grpc::ByteBuffer* request, ::grpc::ByteBuffer* response) { return this->SetMsgBusEndpoint(context, request, response); }));
+    }
+    ~ExperimentalWithRawCallbackMethod_SetMsgBusEndpoint() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status SetMsgBusEndpoint(::grpc::ServerContext* /*context*/, const ::dmi::SetMsgBusEndpointRequest* /*request*/, ::dmi::SetRemoteEndpointResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+    virtual ::grpc::ServerUnaryReactor* SetMsgBusEndpoint(
+      ::grpc::CallbackServerContext* /*context*/, const ::grpc::ByteBuffer* /*request*/, ::grpc::ByteBuffer* /*response*/)
+    #else
+    virtual ::grpc::experimental::ServerUnaryReactor* SetMsgBusEndpoint(
+      ::grpc::experimental::CallbackServerContext* /*context*/, const ::grpc::ByteBuffer* /*request*/, ::grpc::ByteBuffer* /*response*/)
+    #endif
+      { return nullptr; }
+  };
+  template <class BaseClass>
+  class ExperimentalWithRawCallbackMethod_GetMsgBusEndpoint : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    ExperimentalWithRawCallbackMethod_GetMsgBusEndpoint() {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::Service::
+    #else
+      ::grpc::Service::experimental().
+    #endif
+        MarkMethodRawCallback(9,
+          new ::grpc_impl::internal::CallbackUnaryHandler< ::grpc::ByteBuffer, ::grpc::ByteBuffer>(
+            [this](
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+                   ::grpc::CallbackServerContext*
+    #else
+                   ::grpc::experimental::CallbackServerContext*
+    #endif
+                     context, const ::grpc::ByteBuffer* request, ::grpc::ByteBuffer* response) { return this->GetMsgBusEndpoint(context, request, response); }));
+    }
+    ~ExperimentalWithRawCallbackMethod_GetMsgBusEndpoint() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetMsgBusEndpoint(::grpc::ServerContext* /*context*/, const ::google::protobuf::Empty* /*request*/, ::dmi::GetMsgBusEndpointResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+    virtual ::grpc::ServerUnaryReactor* GetMsgBusEndpoint(
+      ::grpc::CallbackServerContext* /*context*/, const ::grpc::ByteBuffer* /*request*/, ::grpc::ByteBuffer* /*response*/)
+    #else
+    virtual ::grpc::experimental::ServerUnaryReactor* GetMsgBusEndpoint(
+      ::grpc::experimental::CallbackServerContext* /*context*/, const ::grpc::ByteBuffer* /*request*/, ::grpc::ByteBuffer* /*response*/)
+    #endif
+      { return nullptr; }
+  };
+  template <class BaseClass>
+  class ExperimentalWithRawCallbackMethod_GetLoggableEntities : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    ExperimentalWithRawCallbackMethod_GetLoggableEntities() {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::Service::
+    #else
+      ::grpc::Service::experimental().
+    #endif
+        MarkMethodRawCallback(10,
+          new ::grpc_impl::internal::CallbackUnaryHandler< ::grpc::ByteBuffer, ::grpc::ByteBuffer>(
+            [this](
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+                   ::grpc::CallbackServerContext*
+    #else
+                   ::grpc::experimental::CallbackServerContext*
+    #endif
+                     context, const ::grpc::ByteBuffer* request, ::grpc::ByteBuffer* response) { return this->GetLoggableEntities(context, request, response); }));
+    }
+    ~ExperimentalWithRawCallbackMethod_GetLoggableEntities() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetLoggableEntities(::grpc::ServerContext* /*context*/, const ::dmi::GetLoggableEntitiesRequest* /*request*/, ::dmi::GetLogLevelResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+    virtual ::grpc::ServerUnaryReactor* GetLoggableEntities(
+      ::grpc::CallbackServerContext* /*context*/, const ::grpc::ByteBuffer* /*request*/, ::grpc::ByteBuffer* /*response*/)
+    #else
+    virtual ::grpc::experimental::ServerUnaryReactor* GetLoggableEntities(
+      ::grpc::experimental::CallbackServerContext* /*context*/, const ::grpc::ByteBuffer* /*request*/, ::grpc::ByteBuffer* /*response*/)
+    #endif
+      { return nullptr; }
+  };
+  template <class BaseClass>
+  class ExperimentalWithRawCallbackMethod_SetLogLevel : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    ExperimentalWithRawCallbackMethod_SetLogLevel() {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::Service::
+    #else
+      ::grpc::Service::experimental().
+    #endif
+        MarkMethodRawCallback(11,
+          new ::grpc_impl::internal::CallbackUnaryHandler< ::grpc::ByteBuffer, ::grpc::ByteBuffer>(
+            [this](
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+                   ::grpc::CallbackServerContext*
+    #else
+                   ::grpc::experimental::CallbackServerContext*
+    #endif
+                     context, const ::grpc::ByteBuffer* request, ::grpc::ByteBuffer* response) { return this->SetLogLevel(context, request, response); }));
+    }
+    ~ExperimentalWithRawCallbackMethod_SetLogLevel() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status SetLogLevel(::grpc::ServerContext* /*context*/, const ::dmi::SetLogLevelRequest* /*request*/, ::dmi::SetLogLevelResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+    virtual ::grpc::ServerUnaryReactor* SetLogLevel(
+      ::grpc::CallbackServerContext* /*context*/, const ::grpc::ByteBuffer* /*request*/, ::grpc::ByteBuffer* /*response*/)
+    #else
+    virtual ::grpc::experimental::ServerUnaryReactor* SetLogLevel(
+      ::grpc::experimental::CallbackServerContext* /*context*/, const ::grpc::ByteBuffer* /*request*/, ::grpc::ByteBuffer* /*response*/)
+    #endif
+      { return nullptr; }
+  };
+  template <class BaseClass>
+  class ExperimentalWithRawCallbackMethod_GetLogLevel : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    ExperimentalWithRawCallbackMethod_GetLogLevel() {
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+      ::grpc::Service::
+    #else
+      ::grpc::Service::experimental().
+    #endif
+        MarkMethodRawCallback(12,
+          new ::grpc_impl::internal::CallbackUnaryHandler< ::grpc::ByteBuffer, ::grpc::ByteBuffer>(
+            [this](
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+                   ::grpc::CallbackServerContext*
+    #else
+                   ::grpc::experimental::CallbackServerContext*
+    #endif
+                     context, const ::grpc::ByteBuffer* request, ::grpc::ByteBuffer* response) { return this->GetLogLevel(context, request, response); }));
+    }
+    ~ExperimentalWithRawCallbackMethod_GetLogLevel() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable synchronous version of this method
+    ::grpc::Status GetLogLevel(::grpc::ServerContext* /*context*/, const ::dmi::GetLogLevelRequest* /*request*/, ::dmi::GetLogLevelResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    #ifdef GRPC_CALLBACK_API_NONEXPERIMENTAL
+    virtual ::grpc::ServerUnaryReactor* GetLogLevel(
+      ::grpc::CallbackServerContext* /*context*/, const ::grpc::ByteBuffer* /*request*/, ::grpc::ByteBuffer* /*response*/)
+    #else
+    virtual ::grpc::experimental::ServerUnaryReactor* GetLogLevel(
+      ::grpc::experimental::CallbackServerContext* /*context*/, const ::grpc::ByteBuffer* /*request*/, ::grpc::ByteBuffer* /*response*/)
+    #endif
+      { return nullptr; }
+  };
+  template <class BaseClass>
+  class WithStreamedUnaryMethod_StopManagingDevice : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithStreamedUnaryMethod_StopManagingDevice() {
+      ::grpc::Service::MarkMethodStreamed(1,
+        new ::grpc::internal::StreamedUnaryHandler<
+          ::dmi::StopManagingDeviceRequest, ::dmi::StopManagingDeviceResponse>(
+            [this](::grpc_impl::ServerContext* context,
+                   ::grpc_impl::ServerUnaryStreamer<
+                     ::dmi::StopManagingDeviceRequest, ::dmi::StopManagingDeviceResponse>* streamer) {
+                       return this->StreamedStopManagingDevice(context,
+                         streamer);
+                  }));
+    }
+    ~WithStreamedUnaryMethod_StopManagingDevice() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable regular version of this method
+    ::grpc::Status StopManagingDevice(::grpc::ServerContext* /*context*/, const ::dmi::StopManagingDeviceRequest* /*request*/, ::dmi::StopManagingDeviceResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    // replace default version of method with streamed unary
+    virtual ::grpc::Status StreamedStopManagingDevice(::grpc::ServerContext* context, ::grpc::ServerUnaryStreamer< ::dmi::StopManagingDeviceRequest,::dmi::StopManagingDeviceResponse>* server_unary_streamer) = 0;
+  };
+  template <class BaseClass>
+  class WithStreamedUnaryMethod_GetManagedDevices : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithStreamedUnaryMethod_GetManagedDevices() {
+      ::grpc::Service::MarkMethodStreamed(2,
+        new ::grpc::internal::StreamedUnaryHandler<
+          ::google::protobuf::Empty, ::dmi::ManagedDevicesResponse>(
+            [this](::grpc_impl::ServerContext* context,
+                   ::grpc_impl::ServerUnaryStreamer<
+                     ::google::protobuf::Empty, ::dmi::ManagedDevicesResponse>* streamer) {
+                       return this->StreamedGetManagedDevices(context,
+                         streamer);
+                  }));
+    }
+    ~WithStreamedUnaryMethod_GetManagedDevices() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable regular version of this method
+    ::grpc::Status GetManagedDevices(::grpc::ServerContext* /*context*/, const ::google::protobuf::Empty* /*request*/, ::dmi::ManagedDevicesResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    // replace default version of method with streamed unary
+    virtual ::grpc::Status StreamedGetManagedDevices(::grpc::ServerContext* context, ::grpc::ServerUnaryStreamer< ::google::protobuf::Empty,::dmi::ManagedDevicesResponse>* server_unary_streamer) = 0;
+  };
+  template <class BaseClass>
+  class WithStreamedUnaryMethod_SetHWComponentInfo : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithStreamedUnaryMethod_SetHWComponentInfo() {
+      ::grpc::Service::MarkMethodStreamed(5,
+        new ::grpc::internal::StreamedUnaryHandler<
+          ::dmi::HWComponentInfoSetRequest, ::dmi::HWComponentInfoSetResponse>(
+            [this](::grpc_impl::ServerContext* context,
+                   ::grpc_impl::ServerUnaryStreamer<
+                     ::dmi::HWComponentInfoSetRequest, ::dmi::HWComponentInfoSetResponse>* streamer) {
+                       return this->StreamedSetHWComponentInfo(context,
+                         streamer);
+                  }));
+    }
+    ~WithStreamedUnaryMethod_SetHWComponentInfo() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable regular version of this method
+    ::grpc::Status SetHWComponentInfo(::grpc::ServerContext* /*context*/, const ::dmi::HWComponentInfoSetRequest* /*request*/, ::dmi::HWComponentInfoSetResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    // replace default version of method with streamed unary
+    virtual ::grpc::Status StreamedSetHWComponentInfo(::grpc::ServerContext* context, ::grpc::ServerUnaryStreamer< ::dmi::HWComponentInfoSetRequest,::dmi::HWComponentInfoSetResponse>* server_unary_streamer) = 0;
+  };
+  template <class BaseClass>
+  class WithStreamedUnaryMethod_SetLoggingEndpoint : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithStreamedUnaryMethod_SetLoggingEndpoint() {
+      ::grpc::Service::MarkMethodStreamed(6,
+        new ::grpc::internal::StreamedUnaryHandler<
+          ::dmi::SetLoggingEndpointRequest, ::dmi::SetRemoteEndpointResponse>(
+            [this](::grpc_impl::ServerContext* context,
+                   ::grpc_impl::ServerUnaryStreamer<
+                     ::dmi::SetLoggingEndpointRequest, ::dmi::SetRemoteEndpointResponse>* streamer) {
+                       return this->StreamedSetLoggingEndpoint(context,
+                         streamer);
+                  }));
+    }
+    ~WithStreamedUnaryMethod_SetLoggingEndpoint() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable regular version of this method
+    ::grpc::Status SetLoggingEndpoint(::grpc::ServerContext* /*context*/, const ::dmi::SetLoggingEndpointRequest* /*request*/, ::dmi::SetRemoteEndpointResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    // replace default version of method with streamed unary
+    virtual ::grpc::Status StreamedSetLoggingEndpoint(::grpc::ServerContext* context, ::grpc::ServerUnaryStreamer< ::dmi::SetLoggingEndpointRequest,::dmi::SetRemoteEndpointResponse>* server_unary_streamer) = 0;
+  };
+  template <class BaseClass>
+  class WithStreamedUnaryMethod_GetLoggingEndpoint : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithStreamedUnaryMethod_GetLoggingEndpoint() {
+      ::grpc::Service::MarkMethodStreamed(7,
+        new ::grpc::internal::StreamedUnaryHandler<
+          ::dmi::HardwareID, ::dmi::GetLoggingEndpointResponse>(
+            [this](::grpc_impl::ServerContext* context,
+                   ::grpc_impl::ServerUnaryStreamer<
+                     ::dmi::HardwareID, ::dmi::GetLoggingEndpointResponse>* streamer) {
+                       return this->StreamedGetLoggingEndpoint(context,
+                         streamer);
+                  }));
+    }
+    ~WithStreamedUnaryMethod_GetLoggingEndpoint() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable regular version of this method
+    ::grpc::Status GetLoggingEndpoint(::grpc::ServerContext* /*context*/, const ::dmi::HardwareID* /*request*/, ::dmi::GetLoggingEndpointResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    // replace default version of method with streamed unary
+    virtual ::grpc::Status StreamedGetLoggingEndpoint(::grpc::ServerContext* context, ::grpc::ServerUnaryStreamer< ::dmi::HardwareID,::dmi::GetLoggingEndpointResponse>* server_unary_streamer) = 0;
+  };
+  template <class BaseClass>
+  class WithStreamedUnaryMethod_SetMsgBusEndpoint : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithStreamedUnaryMethod_SetMsgBusEndpoint() {
+      ::grpc::Service::MarkMethodStreamed(8,
+        new ::grpc::internal::StreamedUnaryHandler<
+          ::dmi::SetMsgBusEndpointRequest, ::dmi::SetRemoteEndpointResponse>(
+            [this](::grpc_impl::ServerContext* context,
+                   ::grpc_impl::ServerUnaryStreamer<
+                     ::dmi::SetMsgBusEndpointRequest, ::dmi::SetRemoteEndpointResponse>* streamer) {
+                       return this->StreamedSetMsgBusEndpoint(context,
+                         streamer);
+                  }));
+    }
+    ~WithStreamedUnaryMethod_SetMsgBusEndpoint() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable regular version of this method
+    ::grpc::Status SetMsgBusEndpoint(::grpc::ServerContext* /*context*/, const ::dmi::SetMsgBusEndpointRequest* /*request*/, ::dmi::SetRemoteEndpointResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    // replace default version of method with streamed unary
+    virtual ::grpc::Status StreamedSetMsgBusEndpoint(::grpc::ServerContext* context, ::grpc::ServerUnaryStreamer< ::dmi::SetMsgBusEndpointRequest,::dmi::SetRemoteEndpointResponse>* server_unary_streamer) = 0;
+  };
+  template <class BaseClass>
+  class WithStreamedUnaryMethod_GetMsgBusEndpoint : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithStreamedUnaryMethod_GetMsgBusEndpoint() {
+      ::grpc::Service::MarkMethodStreamed(9,
+        new ::grpc::internal::StreamedUnaryHandler<
+          ::google::protobuf::Empty, ::dmi::GetMsgBusEndpointResponse>(
+            [this](::grpc_impl::ServerContext* context,
+                   ::grpc_impl::ServerUnaryStreamer<
+                     ::google::protobuf::Empty, ::dmi::GetMsgBusEndpointResponse>* streamer) {
+                       return this->StreamedGetMsgBusEndpoint(context,
+                         streamer);
+                  }));
+    }
+    ~WithStreamedUnaryMethod_GetMsgBusEndpoint() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable regular version of this method
+    ::grpc::Status GetMsgBusEndpoint(::grpc::ServerContext* /*context*/, const ::google::protobuf::Empty* /*request*/, ::dmi::GetMsgBusEndpointResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    // replace default version of method with streamed unary
+    virtual ::grpc::Status StreamedGetMsgBusEndpoint(::grpc::ServerContext* context, ::grpc::ServerUnaryStreamer< ::google::protobuf::Empty,::dmi::GetMsgBusEndpointResponse>* server_unary_streamer) = 0;
+  };
+  template <class BaseClass>
+  class WithStreamedUnaryMethod_GetLoggableEntities : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithStreamedUnaryMethod_GetLoggableEntities() {
+      ::grpc::Service::MarkMethodStreamed(10,
+        new ::grpc::internal::StreamedUnaryHandler<
+          ::dmi::GetLoggableEntitiesRequest, ::dmi::GetLogLevelResponse>(
+            [this](::grpc_impl::ServerContext* context,
+                   ::grpc_impl::ServerUnaryStreamer<
+                     ::dmi::GetLoggableEntitiesRequest, ::dmi::GetLogLevelResponse>* streamer) {
+                       return this->StreamedGetLoggableEntities(context,
+                         streamer);
+                  }));
+    }
+    ~WithStreamedUnaryMethod_GetLoggableEntities() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable regular version of this method
+    ::grpc::Status GetLoggableEntities(::grpc::ServerContext* /*context*/, const ::dmi::GetLoggableEntitiesRequest* /*request*/, ::dmi::GetLogLevelResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    // replace default version of method with streamed unary
+    virtual ::grpc::Status StreamedGetLoggableEntities(::grpc::ServerContext* context, ::grpc::ServerUnaryStreamer< ::dmi::GetLoggableEntitiesRequest,::dmi::GetLogLevelResponse>* server_unary_streamer) = 0;
+  };
+  template <class BaseClass>
+  class WithStreamedUnaryMethod_SetLogLevel : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithStreamedUnaryMethod_SetLogLevel() {
+      ::grpc::Service::MarkMethodStreamed(11,
+        new ::grpc::internal::StreamedUnaryHandler<
+          ::dmi::SetLogLevelRequest, ::dmi::SetLogLevelResponse>(
+            [this](::grpc_impl::ServerContext* context,
+                   ::grpc_impl::ServerUnaryStreamer<
+                     ::dmi::SetLogLevelRequest, ::dmi::SetLogLevelResponse>* streamer) {
+                       return this->StreamedSetLogLevel(context,
+                         streamer);
+                  }));
+    }
+    ~WithStreamedUnaryMethod_SetLogLevel() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable regular version of this method
+    ::grpc::Status SetLogLevel(::grpc::ServerContext* /*context*/, const ::dmi::SetLogLevelRequest* /*request*/, ::dmi::SetLogLevelResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    // replace default version of method with streamed unary
+    virtual ::grpc::Status StreamedSetLogLevel(::grpc::ServerContext* context, ::grpc::ServerUnaryStreamer< ::dmi::SetLogLevelRequest,::dmi::SetLogLevelResponse>* server_unary_streamer) = 0;
+  };
+  template <class BaseClass>
+  class WithStreamedUnaryMethod_GetLogLevel : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithStreamedUnaryMethod_GetLogLevel() {
+      ::grpc::Service::MarkMethodStreamed(12,
+        new ::grpc::internal::StreamedUnaryHandler<
+          ::dmi::GetLogLevelRequest, ::dmi::GetLogLevelResponse>(
+            [this](::grpc_impl::ServerContext* context,
+                   ::grpc_impl::ServerUnaryStreamer<
+                     ::dmi::GetLogLevelRequest, ::dmi::GetLogLevelResponse>* streamer) {
+                       return this->StreamedGetLogLevel(context,
+                         streamer);
+                  }));
+    }
+    ~WithStreamedUnaryMethod_GetLogLevel() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable regular version of this method
+    ::grpc::Status GetLogLevel(::grpc::ServerContext* /*context*/, const ::dmi::GetLogLevelRequest* /*request*/, ::dmi::GetLogLevelResponse* /*response*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    // replace default version of method with streamed unary
+    virtual ::grpc::Status StreamedGetLogLevel(::grpc::ServerContext* context, ::grpc::ServerUnaryStreamer< ::dmi::GetLogLevelRequest,::dmi::GetLogLevelResponse>* server_unary_streamer) = 0;
+  };
+  typedef WithStreamedUnaryMethod_StopManagingDevice<WithStreamedUnaryMethod_GetManagedDevices<WithStreamedUnaryMethod_SetHWComponentInfo<WithStreamedUnaryMethod_SetLoggingEndpoint<WithStreamedUnaryMethod_GetLoggingEndpoint<WithStreamedUnaryMethod_SetMsgBusEndpoint<WithStreamedUnaryMethod_GetMsgBusEndpoint<WithStreamedUnaryMethod_GetLoggableEntities<WithStreamedUnaryMethod_SetLogLevel<WithStreamedUnaryMethod_GetLogLevel<Service > > > > > > > > > > StreamedUnaryService;
+  template <class BaseClass>
+  class WithSplitStreamingMethod_StartManagingDevice : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithSplitStreamingMethod_StartManagingDevice() {
+      ::grpc::Service::MarkMethodStreamed(0,
+        new ::grpc::internal::SplitServerStreamingHandler<
+          ::dmi::ModifiableComponent, ::dmi::StartManagingDeviceResponse>(
+            [this](::grpc_impl::ServerContext* context,
+                   ::grpc_impl::ServerSplitStreamer<
+                     ::dmi::ModifiableComponent, ::dmi::StartManagingDeviceResponse>* streamer) {
+                       return this->StreamedStartManagingDevice(context,
+                         streamer);
+                  }));
+    }
+    ~WithSplitStreamingMethod_StartManagingDevice() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable regular version of this method
+    ::grpc::Status StartManagingDevice(::grpc::ServerContext* /*context*/, const ::dmi::ModifiableComponent* /*request*/, ::grpc::ServerWriter< ::dmi::StartManagingDeviceResponse>* /*writer*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    // replace default version of method with split streamed
+    virtual ::grpc::Status StreamedStartManagingDevice(::grpc::ServerContext* context, ::grpc::ServerSplitStreamer< ::dmi::ModifiableComponent,::dmi::StartManagingDeviceResponse>* server_split_streamer) = 0;
+  };
+  template <class BaseClass>
+  class WithSplitStreamingMethod_GetPhysicalInventory : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithSplitStreamingMethod_GetPhysicalInventory() {
+      ::grpc::Service::MarkMethodStreamed(3,
+        new ::grpc::internal::SplitServerStreamingHandler<
+          ::dmi::PhysicalInventoryRequest, ::dmi::PhysicalInventoryResponse>(
+            [this](::grpc_impl::ServerContext* context,
+                   ::grpc_impl::ServerSplitStreamer<
+                     ::dmi::PhysicalInventoryRequest, ::dmi::PhysicalInventoryResponse>* streamer) {
+                       return this->StreamedGetPhysicalInventory(context,
+                         streamer);
+                  }));
+    }
+    ~WithSplitStreamingMethod_GetPhysicalInventory() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable regular version of this method
+    ::grpc::Status GetPhysicalInventory(::grpc::ServerContext* /*context*/, const ::dmi::PhysicalInventoryRequest* /*request*/, ::grpc::ServerWriter< ::dmi::PhysicalInventoryResponse>* /*writer*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    // replace default version of method with split streamed
+    virtual ::grpc::Status StreamedGetPhysicalInventory(::grpc::ServerContext* context, ::grpc::ServerSplitStreamer< ::dmi::PhysicalInventoryRequest,::dmi::PhysicalInventoryResponse>* server_split_streamer) = 0;
+  };
+  template <class BaseClass>
+  class WithSplitStreamingMethod_GetHWComponentInfo : public BaseClass {
+   private:
+    void BaseClassMustBeDerivedFromService(const Service* /*service*/) {}
+   public:
+    WithSplitStreamingMethod_GetHWComponentInfo() {
+      ::grpc::Service::MarkMethodStreamed(4,
+        new ::grpc::internal::SplitServerStreamingHandler<
+          ::dmi::HWComponentInfoGetRequest, ::dmi::HWComponentInfoGetResponse>(
+            [this](::grpc_impl::ServerContext* context,
+                   ::grpc_impl::ServerSplitStreamer<
+                     ::dmi::HWComponentInfoGetRequest, ::dmi::HWComponentInfoGetResponse>* streamer) {
+                       return this->StreamedGetHWComponentInfo(context,
+                         streamer);
+                  }));
+    }
+    ~WithSplitStreamingMethod_GetHWComponentInfo() override {
+      BaseClassMustBeDerivedFromService(this);
+    }
+    // disable regular version of this method
+    ::grpc::Status GetHWComponentInfo(::grpc::ServerContext* /*context*/, const ::dmi::HWComponentInfoGetRequest* /*request*/, ::grpc::ServerWriter< ::dmi::HWComponentInfoGetResponse>* /*writer*/) override {
+      abort();
+      return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, "");
+    }
+    // replace default version of method with split streamed
+    virtual ::grpc::Status StreamedGetHWComponentInfo(::grpc::ServerContext* context, ::grpc::ServerSplitStreamer< ::dmi::HWComponentInfoGetRequest,::dmi::HWComponentInfoGetResponse>* server_split_streamer) = 0;
+  };
+  typedef WithSplitStreamingMethod_StartManagingDevice<WithSplitStreamingMethod_GetPhysicalInventory<WithSplitStreamingMethod_GetHWComponentInfo<Service > > > SplitStreamedService;
+  typedef WithSplitStreamingMethod_StartManagingDevice<WithStreamedUnaryMethod_StopManagingDevice<WithStreamedUnaryMethod_GetManagedDevices<WithSplitStreamingMethod_GetPhysicalInventory<WithSplitStreamingMethod_GetHWComponentInfo<WithStreamedUnaryMethod_SetHWComponentInfo<WithStreamedUnaryMethod_SetLoggingEndpoint<WithStreamedUnaryMethod_GetLoggingEndpoint<WithStreamedUnaryMethod_SetMsgBusEndpoint<WithStreamedUnaryMethod_GetMsgBusEndpoint<WithStreamedUnaryMethod_GetLoggableEntities<WithStreamedUnaryMethod_SetLogLevel<WithStreamedUnaryMethod_GetLogLevel<Service > > > > > > > > > > > > > StreamedService;
+};
+
+}  // namespace dmi
+
+
+#endif  // GRPC_dmi_2fhw_5fmanagement_5fservice_2eproto__INCLUDED
