// WARNING: This file is machine generated by fidlgen.

#pragma once

#include <fidl/test.anonymous/cpp/markers.h>
#include <fidl/test.anonymous/cpp/wire_types.h>
#include <lib/fidl/llcpp/wire_messaging.h>

#ifdef __Fuchsia__

#include <lib/fidl/llcpp/client.h>
#include <lib/fidl/llcpp/connect_service.h>
#include <lib/fidl/llcpp/server.h>
#include <lib/fidl/llcpp/service_handler_interface.h>
#include <lib/fidl/llcpp/sync_call.h>

#endif  // __Fuchsia__

namespace test_anonymous {
class SomeProtocol;

__LOCAL extern "C" const fidl_type_t
    test_anonymous_SomeProtocolSomeMethodRequestTable;
__LOCAL extern "C" const fidl_type_t
    test_anonymous_SomeProtocolSomeMethodTopResponseTable;
}  // namespace test_anonymous
template <>
struct ::fidl::internal::WireOrdinal<::test_anonymous::SomeProtocol::SomeMethod>
    final {
  static constexpr uint64_t value = 2515914517457749720lu;
};

namespace test_anonymous {}  // namespace test_anonymous
#ifdef __Fuchsia__

template <>
struct ::fidl::internal::ProtocolDetails<::test_anonymous::SomeProtocol> {};
#endif  // __Fuchsia__

#ifdef __Fuchsia__

template <>
struct ::fidl::internal::WireServerDispatcher<::test_anonymous::SomeProtocol>
    final {
  WireServerDispatcher() = delete;
  static ::fidl::DispatchResult TryDispatch(
      ::fidl::WireServer<::test_anonymous::SomeProtocol>* impl,
      ::fidl::IncomingMessage& msg,
      internal::IncomingTransportContext transport_context,
      ::fidl::Transaction* txn);
  static void Dispatch(::fidl::WireServer<::test_anonymous::SomeProtocol>* impl,
                       ::fidl::IncomingMessage&& msg,
                       internal::IncomingTransportContext transport_context,
                       ::fidl::Transaction* txn);

 private:
  static const ::fidl::internal::MethodEntry entries_[];
  static const ::fidl::internal::MethodEntry* entries_end_;
};
#endif  // __Fuchsia__

template <>
struct ::fidl::WireRequest<::test_anonymous::SomeProtocol::SomeMethod> final
    : public ::test_anonymous::wire::SomeProtocolSomeMethodRequest {
  using UnionMember = test_anonymous::wire::UnionMember;
  using TableMember = test_anonymous::wire::TableMember;

  explicit WireRequest(
      ::test_anonymous::wire::SomeProtocolSomeMethodRequest base)
      : ::test_anonymous::wire::SomeProtocolSomeMethodRequest(std::move(base)) {
  }
  explicit WireRequest(::test_anonymous::wire::UnionMember union_member,
                       ::test_anonymous::wire::TableMember table_member)
      : ::test_anonymous::wire::SomeProtocolSomeMethodRequest{
            .union_member = std::move(union_member),
            .table_member = std::move(table_member)} {}
  WireRequest() = default;
  using ResponseType =
      ::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod>;
};

template <>
struct ::fidl::internal::TransactionalRequest<
    ::test_anonymous::SomeProtocol::SomeMethod>
    final {
  FIDL_ALIGNDECL
  fidl_message_header_t header;

  ::fidl::WireRequest<::test_anonymous::SomeProtocol::SomeMethod> body;
  explicit TransactionalRequest(
      ::test_anonymous::wire::UnionMember union_member,
      ::test_anonymous::wire::TableMember table_member)
      : body(::fidl::WireRequest<::test_anonymous::SomeProtocol::SomeMethod>(
            union_member, table_member)) {
    _InitHeader();
  }
  TransactionalRequest() { _InitHeader(); }
  using ResponseType = ::fidl::internal::TransactionalResponse<
      ::test_anonymous::SomeProtocol::SomeMethod>;

 private:
  void _InitHeader();
};

template <>
struct ::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod> final
    : public ::test_anonymous::wire::SomeProtocolSomeMethodTopResponse {
  using Result = test_anonymous::wire::SomeProtocolSomeMethodResult;

  explicit WireResponse(
      ::test_anonymous::wire::SomeProtocolSomeMethodTopResponse base)
      : ::test_anonymous::wire::SomeProtocolSomeMethodTopResponse(
            std::move(base)) {}
  explicit WireResponse(
      ::test_anonymous::wire::SomeProtocolSomeMethodResult result)
      : ::test_anonymous::wire::SomeProtocolSomeMethodTopResponse{
            .result = std::move(result)} {}
  WireResponse() = default;
};

template <>
struct ::fidl::internal::TransactionalResponse<
    ::test_anonymous::SomeProtocol::SomeMethod>
    final {
  FIDL_ALIGNDECL
  fidl_message_header_t header;

  ::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod> body;
  explicit TransactionalResponse(
      ::test_anonymous::wire::SomeProtocolSomeMethodResult result)
      : body(::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod>(
            result)) {
    _InitHeader();
  }
  TransactionalResponse() { _InitHeader(); }

 private:
  void _InitHeader();
};

#ifdef __Fuchsia__

template <>
struct ::fidl::internal::WireMethodTypes<
    ::test_anonymous::SomeProtocol::SomeMethod> {
  using Completer = fidl::Completer<::fidl::internal::WireCompleterBase<
      ::test_anonymous::SomeProtocol::SomeMethod>>;

  using ApplicationError = ::test_anonymous::wire::SomeProtocolSomeMethodError;

  using Thenable = ::fidl::internal::WireThenableImpl<
      ::test_anonymous::SomeProtocol::SomeMethod,
      ::fidl::unstable::OwnedEncodedMessage<
          ::fidl::internal::TransactionalRequest<
              ::test_anonymous::SomeProtocol::SomeMethod>,
          ::fidl::internal::ChannelTransport>>;

  using BufferThenable = ::fidl::internal::WireThenableImpl<
      ::test_anonymous::SomeProtocol::SomeMethod,
      ::fidl::unstable::UnownedEncodedMessage<
          ::fidl::internal::TransactionalRequest<
              ::test_anonymous::SomeProtocol::SomeMethod>,
          ::fidl::internal::ChannelTransport>>;
};

#endif  // __Fuchsia__

namespace fidl {

template <>
struct IsFidlType<::fidl::internal::TransactionalRequest<
    ::test_anonymous::SomeProtocol::SomeMethod>> : public std::true_type {};
template <>
struct IsFidlType<
    ::fidl::WireRequest<::test_anonymous::SomeProtocol::SomeMethod>>
    : public std::true_type {};
template <>
struct IsFidlTransactionalMessage<::fidl::internal::TransactionalRequest<
    ::test_anonymous::SomeProtocol::SomeMethod>> : public std::true_type {};
template <>
struct IsFidlTransactionalMessage<
    ::fidl::WireRequest<::test_anonymous::SomeProtocol::SomeMethod>>
    : public std::false_type {};

template <>
struct TypeTraits<::fidl::internal::TransactionalRequest<
    ::test_anonymous::SomeProtocol::SomeMethod>> {
  static constexpr const fidl_type_t* kType =
      &::test_anonymous::test_anonymous_SomeProtocolSomeMethodRequestTable;
  static constexpr uint32_t kMaxNumHandles = 0;
  static constexpr uint32_t kPrimarySize =
      FIDL_ALIGN(32 + sizeof(fidl_message_header_t));
  static constexpr uint32_t kPrimarySizeV1 =
      FIDL_ALIGN(40 + sizeof(fidl_message_header_t));
  static constexpr uint32_t kMaxOutOfLine = 48;
  static constexpr uint32_t kMaxOutOfLineV1 = 72;
  static constexpr bool kHasFlexibleEnvelope = true;
  static constexpr bool kHasPointer = true;
  static constexpr ::fidl::internal::TransactionalMessageKind kMessageKind =
      ::fidl::internal::TransactionalMessageKind::kRequest;
};

static_assert(sizeof(::fidl::internal::TransactionalRequest<
                     ::test_anonymous::SomeProtocol::SomeMethod>) ==
              TypeTraits<::fidl::internal::TransactionalRequest<
                  ::test_anonymous::SomeProtocol::SomeMethod>>::kPrimarySize);
static_assert(offsetof(::fidl::internal::TransactionalRequest<
                           ::test_anonymous::SomeProtocol::SomeMethod>,
                       header) == 0);
static_assert(offsetof(::fidl::internal::TransactionalRequest<
                           ::test_anonymous::SomeProtocol::SomeMethod>,
                       body) == sizeof(fidl_message_header_t));

template <>
struct TypeTraits<
    ::fidl::WireRequest<::test_anonymous::SomeProtocol::SomeMethod>> {
  static constexpr const fidl_type_t* kType =
      &::test_anonymous::test_anonymous_SomeProtocolSomeMethodRequestTable;
  static constexpr uint32_t kMaxNumHandles = 0;
  static constexpr uint32_t kPrimarySize = 32;
  static constexpr uint32_t kPrimarySizeV1 = 40;
  static constexpr uint32_t kMaxOutOfLine = 48;
  static constexpr uint32_t kMaxOutOfLineV1 = 72;
  static constexpr bool kHasFlexibleEnvelope = true;
  static constexpr bool kHasPointer = true;
  static constexpr ::fidl::internal::TransactionalMessageKind kMessageKind =
      ::fidl::internal::TransactionalMessageKind::kRequest;
};
static_assert(
    sizeof(::fidl::WireRequest<::test_anonymous::SomeProtocol::SomeMethod>) ==
    TypeTraits<::fidl::WireRequest<
        ::test_anonymous::SomeProtocol::SomeMethod>>::kPrimarySize);
static_assert(
    offsetof(::fidl::WireRequest<::test_anonymous::SomeProtocol::SomeMethod>,
             union_member) == 0);
static_assert(
    offsetof(::fidl::WireRequest<::test_anonymous::SomeProtocol::SomeMethod>,
             table_member) == 16);

template <>
struct IsFidlType<::fidl::internal::TransactionalResponse<
    ::test_anonymous::SomeProtocol::SomeMethod>> : public std::true_type {};
template <>
struct IsFidlType<
    ::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod>>
    : public std::true_type {};
template <>
struct IsFidlTransactionalMessage<::fidl::internal::TransactionalResponse<
    ::test_anonymous::SomeProtocol::SomeMethod>> : public std::true_type {};
template <>
struct IsFidlTransactionalMessage<
    ::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod>>
    : public std::false_type {};

template <>
struct TypeTraits<::fidl::internal::TransactionalResponse<
    ::test_anonymous::SomeProtocol::SomeMethod>> {
  static constexpr const fidl_type_t* kType =
      &::test_anonymous::test_anonymous_SomeProtocolSomeMethodTopResponseTable;
  static constexpr uint32_t kMaxNumHandles = 0;
  static constexpr uint32_t kPrimarySize =
      FIDL_ALIGN(16 + sizeof(fidl_message_header_t));
  static constexpr uint32_t kPrimarySizeV1 =
      FIDL_ALIGN(24 + sizeof(fidl_message_header_t));
  static constexpr uint32_t kMaxOutOfLine = 0;
  static constexpr uint32_t kMaxOutOfLineV1 = 8;
  static constexpr bool kHasFlexibleEnvelope = false;
  static constexpr bool kHasPointer = true;
  static constexpr ::fidl::internal::TransactionalMessageKind kMessageKind =
      ::fidl::internal::TransactionalMessageKind::kResponse;
};

static_assert(sizeof(::fidl::internal::TransactionalResponse<
                     ::test_anonymous::SomeProtocol::SomeMethod>) ==
              TypeTraits<::fidl::internal::TransactionalResponse<
                  ::test_anonymous::SomeProtocol::SomeMethod>>::kPrimarySize);
static_assert(offsetof(::fidl::internal::TransactionalResponse<
                           ::test_anonymous::SomeProtocol::SomeMethod>,
                       header) == 0);
static_assert(offsetof(::fidl::internal::TransactionalResponse<
                           ::test_anonymous::SomeProtocol::SomeMethod>,
                       body) == sizeof(fidl_message_header_t));

template <>
struct TypeTraits<
    ::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod>> {
  static constexpr const fidl_type_t* kType =
      &::test_anonymous::test_anonymous_SomeProtocolSomeMethodTopResponseTable;
  static constexpr uint32_t kMaxNumHandles = 0;
  static constexpr uint32_t kPrimarySize = 16;
  static constexpr uint32_t kPrimarySizeV1 = 24;
  static constexpr uint32_t kMaxOutOfLine = 0;
  static constexpr uint32_t kMaxOutOfLineV1 = 8;
  static constexpr bool kHasFlexibleEnvelope = false;
  static constexpr bool kHasPointer = true;
  static constexpr ::fidl::internal::TransactionalMessageKind kMessageKind =
      ::fidl::internal::TransactionalMessageKind::kResponse;
};
static_assert(
    sizeof(::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod>) ==
    TypeTraits<::fidl::WireResponse<
        ::test_anonymous::SomeProtocol::SomeMethod>>::kPrimarySize);
static_assert(
    offsetof(::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod>,
             result) == 0);
#ifdef __Fuchsia__
}  // namespace fidl

template <>
struct ::fidl::internal::IncomingMessageStorage<
    ::fidl::internal::TransactionalResponse<
        ::test_anonymous::SomeProtocol::SomeMethod>>
    final : public ::fidl::internal::ChannelMessageStorageBase<
                ::fidl::internal::IncomingMessageStorage<
                    ::fidl::internal::TransactionalResponse<
                        ::test_anonymous::SomeProtocol::SomeMethod>>> {
  static constexpr uint32_t kNumHandles = fidl::internal::ClampedHandleCount<
      ::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod>,
      fidl::MessageDirection::kReceiving>();

  ::fidl::internal::InlineMessageBuffer<48> bytes_;
  ::std::array<zx_handle_t, kNumHandles> handles_;
  ::std::array<fidl_channel_handle_metadata_t, kNumHandles> handle_metadata_;
};
template <>
class [[nodiscard]] ::fidl::WireResult<
    ::test_anonymous::SomeProtocol::SomeMethod>
    final : public ::fidl::Status {
 public:
  WireResult(::fidl::UnownedClientEnd<::test_anonymous::SomeProtocol> client,
             ::fidl::internal::TransactionalRequest<
                 ::test_anonymous::SomeProtocol::SomeMethod>* request);
  WireResult(::fidl::UnownedClientEnd<::test_anonymous::SomeProtocol> client,
             ::fidl::internal::TransactionalRequest<
                 ::test_anonymous::SomeProtocol::SomeMethod>* request,
             zx_time_t _deadline);
  explicit WireResult(const ::fidl::Status& result) : ::fidl::Status(result) {}
  WireResult(WireResult&&) = delete;
  WireResult(const WireResult&) = delete;
  WireResult* operator=(WireResult&&) = delete;
  WireResult* operator=(const WireResult&) = delete;
  ~WireResult() = default;
  ::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod>* Unwrap() {
    ZX_DEBUG_ASSERT(ok());
    return reinterpret_cast<
        ::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod>*>(
        bytes_.data() + sizeof(fidl_message_header_t));
  }
  const ::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod>*
  Unwrap() const {
    ZX_DEBUG_ASSERT(ok());
    return reinterpret_cast<const ::fidl::WireResponse<
        ::test_anonymous::SomeProtocol::SomeMethod>*>(
        bytes_.data() + sizeof(fidl_message_header_t));
  }

  ::fitx::result<::test_anonymous::wire::SomeProtocolSomeMethodError,
                 ::test_anonymous::wire::SomeProtocolSomeMethodResponse*>*
  Unwrap_NEW() {
    return &result_.value();
  }
  const ::fitx::result<::test_anonymous::wire::SomeProtocolSomeMethodError,
                       ::test_anonymous::wire::SomeProtocolSomeMethodResponse*>*
  Unwrap_NEW() const {
    return &result_.value();
  }

  ::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod>& value() {
    return *Unwrap();
  }
  const ::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod>&
  value() const {
    return *Unwrap();
  }

  ::fitx::result<::test_anonymous::wire::SomeProtocolSomeMethodError,
                 ::test_anonymous::wire::SomeProtocolSomeMethodResponse*>&
  value_NEW() {
    return *Unwrap_NEW();
  }
  const ::fitx::result<::test_anonymous::wire::SomeProtocolSomeMethodError,
                       ::test_anonymous::wire::SomeProtocolSomeMethodResponse*>&
  value_NEW() const {
    return *Unwrap_NEW();
  }

  ::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod>*
  operator->() {
    return &value();
  }
  const ::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod>*
  operator->() const {
    return &value();
  }

  ::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod>&
  operator*() {
    return value();
  }
  const ::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod>&
  operator*() const {
    return value();
  }

 private:
  ::fidl::internal::InlineMessageBuffer<48> bytes_;
  std::optional<
      ::fitx::result<::test_anonymous::wire::SomeProtocolSomeMethodError,
                     ::test_anonymous::wire::SomeProtocolSomeMethodResponse*>>
      result_ = std::nullopt;
};
template <>
class [[nodiscard]] ::fidl::WireUnownedResult<
    ::test_anonymous::SomeProtocol::SomeMethod>
    final : public ::fidl::Status {
 public:
  explicit WireUnownedResult(
      ::fidl::UnownedClientEnd<::test_anonymous::SomeProtocol> client_end,
      ::fidl::internal::AnyBufferAllocator& allocator,
      ::fidl::internal::TransactionalRequest<
          ::test_anonymous::SomeProtocol::SomeMethod>* request);
  explicit WireUnownedResult(
      ::fidl::internal::TransactionalResponse<
          ::test_anonymous::SomeProtocol::SomeMethod>* response)
      : bytes_(reinterpret_cast<uint8_t*>(response)) {
    auto* raw_response = reinterpret_cast<
        ::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod>*>(
        bytes_ + sizeof(fidl_message_header_t));
    if (raw_response->result.is_err()) {
      result_ = fitx::error(raw_response->result.err());
    } else {
      result_ = fitx::ok(&(raw_response->result.response()));
    }
  }
  explicit WireUnownedResult(const ::fidl::Status& result)
      : ::fidl::Status(result) {}
  explicit WireUnownedResult(
      ::fidl::unstable::DecodedMessage<::fidl::internal::TransactionalResponse<
          ::test_anonymous::SomeProtocol::SomeMethod>>&& decoded,
      ::fidl::internal::IncomingTransportContext context)
      : ::fidl::Status(decoded) {
    if (decoded.ok()) {
      bytes_ = reinterpret_cast<uint8_t*>(decoded.PrimaryObject());
      auto* raw_response = reinterpret_cast<
          ::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod>*>(
          bytes_ + sizeof(fidl_message_header_t));
      if (raw_response->result.is_err()) {
        result_ = fitx::error(raw_response->result.err());
      } else if (raw_response->result.is_response()) {
        result_ = fitx::ok(&(raw_response->result.response()));
      }
    } else {
      bytes_ = nullptr;
    }
    decoded.ReleasePrimaryObject();
  }
  WireUnownedResult(WireUnownedResult&&) = delete;
  WireUnownedResult(const WireUnownedResult&) = delete;
  WireUnownedResult* operator=(WireUnownedResult&&) = delete;
  WireUnownedResult* operator=(const WireUnownedResult&) = delete;
  ~WireUnownedResult() = default;
  ::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod>* Unwrap() {
    ZX_DEBUG_ASSERT(ok());
    return &(reinterpret_cast<::fidl::internal::TransactionalResponse<
                 ::test_anonymous::SomeProtocol::SomeMethod>*>(bytes_)
                 ->body);
  }
  const ::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod>*
  Unwrap() const {
    ZX_DEBUG_ASSERT(ok());
    return &(reinterpret_cast<const ::fidl::internal::TransactionalResponse<
                 ::test_anonymous::SomeProtocol::SomeMethod>*>(bytes_)
                 ->body);
  }

  ::fitx::result<::test_anonymous::wire::SomeProtocolSomeMethodError,
                 ::test_anonymous::wire::SomeProtocolSomeMethodResponse*>*
  Unwrap_NEW() {
    return &result_.value();
  }
  const ::fitx::result<::test_anonymous::wire::SomeProtocolSomeMethodError,
                       ::test_anonymous::wire::SomeProtocolSomeMethodResponse*>*
  Unwrap_NEW() const {
    return &result_.value();
  }

  ::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod>& value() {
    return *Unwrap();
  }
  const ::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod>&
  value() const {
    return *Unwrap();
  }

  ::fitx::result<::test_anonymous::wire::SomeProtocolSomeMethodError,
                 ::test_anonymous::wire::SomeProtocolSomeMethodResponse*>&
  value_NEW() {
    return *Unwrap_NEW();
  }
  const ::fitx::result<::test_anonymous::wire::SomeProtocolSomeMethodError,
                       ::test_anonymous::wire::SomeProtocolSomeMethodResponse*>&
  value_NEW() const {
    return *Unwrap_NEW();
  }

  ::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod>*
  operator->() {
    return &value();
  }
  const ::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod>*
  operator->() const {
    return &value();
  }

  ::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod>&
  operator*() {
    return value();
  }
  const ::fidl::WireResponse<::test_anonymous::SomeProtocol::SomeMethod>&
  operator*() const {
    return value();
  }

 private:
  uint8_t* bytes_;
  std::optional<
      ::fitx::result<::test_anonymous::wire::SomeProtocolSomeMethodError,
                     ::test_anonymous::wire::SomeProtocolSomeMethodResponse*>>
      result_ = std::nullopt;
};
template <>
class ::fidl::internal::WireEventHandlerInterface<
    ::test_anonymous::SomeProtocol> {
 public:
  WireEventHandlerInterface() = default;
  virtual ~WireEventHandlerInterface() = default;
};

template <>
class ::fidl::WireAsyncEventHandler<::test_anonymous::SomeProtocol>
    : public ::fidl::internal::WireEventHandlerInterface<
          ::test_anonymous::SomeProtocol>,
      public ::fidl::internal::AsyncEventHandler {
 public:
  WireAsyncEventHandler() = default;
};

template <>
class ::fidl::WireSyncEventHandler<::test_anonymous::SomeProtocol>
    : public ::fidl::internal::WireEventHandlerInterface<
          ::test_anonymous::SomeProtocol> {
 public:
  WireSyncEventHandler() = default;

  // Handle all possible events defined in this protocol.
  // Blocks to consume exactly one message from the channel, then call the
  // corresponding virtual method.
  ::fidl::Status HandleOneEvent(
      ::fidl::UnownedClientEnd<::test_anonymous::SomeProtocol> client_end);

 private:
  [[maybe_unused]] bool got_transitional_ = false;
};

template <>
class ::fidl::internal::WireEventDispatcher<::test_anonymous::SomeProtocol>
    final : public ::fidl::internal::IncomingEventDispatcher<
                ::fidl::WireAsyncEventHandler<::test_anonymous::SomeProtocol>> {
 public:
  explicit WireEventDispatcher(
      ::fidl::WireAsyncEventHandler<::test_anonymous::SomeProtocol>*
          event_handler)
      : IncomingEventDispatcher(event_handler) {}

 private:
  std::optional<::fidl::UnbindInfo> DispatchEvent(
      ::fidl::IncomingMessage& msg,
      ::fidl::internal::IncomingTransportContext transport_context) override;
};

// Methods to make a sync FIDL call directly on an unowned handle or a
// const reference to a |fidl::ClientEnd<::test_anonymous::SomeProtocol>|,
// avoiding setting up a client.
template <>
class ::fidl::internal::WireSyncClientImpl<::test_anonymous::SomeProtocol> final
    : public ::fidl::internal::SyncEndpointManagedVeneer<
          ::fidl::internal::WireSyncClientImpl<
              ::test_anonymous::SomeProtocol>> {
 public:
  // Allocates 128 bytes of message buffer on the stack. No heap allocation
  // necessary.
  ::fidl::WireResult<::test_anonymous::SomeProtocol::SomeMethod> SomeMethod(
      ::test_anonymous::wire::UnionMember union_member,
      ::test_anonymous::wire::TableMember table_member) {
    ::fidl::internal::TransactionalRequest<
        ::test_anonymous::SomeProtocol::SomeMethod>
        _request{union_member, table_member};
    return ::fidl::WireResult<::test_anonymous::SomeProtocol::SomeMethod>(
        _client_end(), &_request);
  }

 private:
  ::fidl::UnownedClientEnd<::test_anonymous::SomeProtocol> _client_end() const {
    return ::fidl::UnownedClientEnd<::test_anonymous::SomeProtocol>(
        _transport().get<::fidl::internal::ChannelTransport>());
  }
};

template <>
class ::fidl::internal::WireSyncBufferClientImpl<::test_anonymous::SomeProtocol>
    final : public ::fidl::internal::SyncEndpointBufferVeneer<
                ::fidl::internal::WireSyncBufferClientImpl<
                    ::test_anonymous::SomeProtocol>> {
 public:
  // Caller provides the backing storage for FIDL message via an argument to
  // `.buffer()`.
  ::fidl::WireUnownedResult<::test_anonymous::SomeProtocol::SomeMethod>
  SomeMethod(::test_anonymous::wire::UnionMember union_member,
             ::test_anonymous::wire::TableMember table_member) {
    ::fidl::internal::TransactionalRequest<
        ::test_anonymous::SomeProtocol::SomeMethod>
        _request{union_member, table_member};
    return ::fidl::WireUnownedResult<
        ::test_anonymous::SomeProtocol::SomeMethod>(_client_end(), _allocator(),
                                                    &_request);
  }

 private:
  ::fidl::UnownedClientEnd<::test_anonymous::SomeProtocol> _client_end() const {
    return ::fidl::UnownedClientEnd<::test_anonymous::SomeProtocol>(
        _transport().get<::fidl::internal::ChannelTransport>());
  }
};

template <>
class ::fidl::internal::WireCompleterImpl<
    ::test_anonymous::SomeProtocol::SomeMethod>
    : public ::fidl::internal::CompleterImplBase<
          ::test_anonymous::SomeProtocol::SomeMethod> {
 public:
  using CompleterImplBase::CompleterImplBase;

  void Reply(::test_anonymous::wire::SomeProtocolSomeMethodResult result);
  void ReplySuccess(::test_anonymous::wire::BitsMember bits_member);
  void ReplyError(::test_anonymous::wire::SomeProtocolSomeMethodError error);
};

template <>
class ::fidl::internal::WireBufferCompleterImpl<
    ::test_anonymous::SomeProtocol::SomeMethod>
    : public ::fidl::internal::BufferCompleterImplBase {
 public:
  using BufferCompleterImplBase::BufferCompleterImplBase;

  void Reply(::test_anonymous::wire::SomeProtocolSomeMethodResult result);
  void ReplySuccess(::test_anonymous::wire::BitsMember bits_member);
  void ReplyError(::test_anonymous::wire::SomeProtocolSomeMethodError error);
};

template <>
class ::fidl::internal::WireCompleterBase<
    ::test_anonymous::SomeProtocol::SomeMethod>
    : public ::fidl::CompleterBase,
      public ::fidl::internal::WireCompleterImpl<
          ::test_anonymous::SomeProtocol::SomeMethod> {
 public:
  WireCompleterBase(::fidl::Transaction* transaction, bool owned,
                    bool expects_reply)
      : CompleterBase(transaction, owned, expects_reply),
        WireCompleterImpl(this) {}
  WireCompleterBase(WireCompleterBase&& other) noexcept
      : CompleterBase(std::move(other)), WireCompleterImpl(this) {}
  WireCompleterBase& operator=(WireCompleterBase&& other) noexcept {
    CompleterBase::operator=(std::move(other));
    WireCompleterImpl::_set_core(this);
    return *this;
  }
};

// Pure-virtual interface to be implemented by a server.
// This interface uses typed channels (i.e. |fidl::ClientEnd<SomeProtocol>|
// and |fidl::ServerEnd<SomeProtocol>|).
template <>
class ::fidl::WireServer<::test_anonymous::SomeProtocol>
    : public ::fidl::internal::IncomingMessageDispatcher {
 public:
  WireServer() = default;
  virtual ~WireServer() = default;

  // The FIDL protocol type that is implemented by this server.
  using _EnclosingProtocol = ::test_anonymous::SomeProtocol;

  using SomeMethodCompleter = ::fidl::internal::WireCompleter<
      ::test_anonymous::SomeProtocol::SomeMethod>;
  using SomeMethodRequestView = ::fidl::internal::WireRequestView<
      ::test_anonymous::SomeProtocol::SomeMethod>;

  virtual void SomeMethod(SomeMethodRequestView request,
                          SomeMethodCompleter::Sync& completer) = 0;

 private:
  void dispatch_message(
      ::fidl::IncomingMessage&& msg, ::fidl::Transaction* txn,
      ::fidl::internal::IncomingTransportContext transport_context) final;
};
namespace fidl {
#endif  // __Fuchsia__

#ifdef __Fuchsia__
}  // namespace fidl
template <>
class ::fidl::internal::WireWeakOnewayClientImpl<::test_anonymous::SomeProtocol>
    : public ::fidl::internal::ClientImplBase {
 public:
  using ClientImplBase::ClientImplBase;
};

template <>
class ::fidl::internal::WireWeakAsyncClientImpl<::test_anonymous::SomeProtocol>
    final : public ::fidl::internal::WireWeakOnewayClientImpl<
                ::test_anonymous::SomeProtocol> {
 public:
  using WireWeakOnewayClientImpl::WireWeakOnewayClientImpl;
  // Allocates 96 bytes of request buffer on the stack. The callback is stored
  // on the heap.
  ::fidl::internal::WireThenable<::test_anonymous::SomeProtocol::SomeMethod>
  SomeMethod(::test_anonymous::wire::UnionMember union_member,
             ::test_anonymous::wire::TableMember table_member);
};

template <>
class ::fidl::internal::WireWeakOnewayBufferClientImpl<
    ::test_anonymous::SomeProtocol>
    : public ::fidl::internal::BufferClientImplBase {
 public:
  using BufferClientImplBase::BufferClientImplBase;
};

template <>
class ::fidl::internal::WireWeakAsyncBufferClientImpl<
    ::test_anonymous::SomeProtocol>
    final : public ::fidl::internal::WireWeakOnewayBufferClientImpl<
                ::test_anonymous::SomeProtocol> {
 public:
  using WireWeakOnewayBufferClientImpl::WireWeakOnewayBufferClientImpl;

  // Caller provides the backing storage for FIDL message.
  ::fidl::internal::WireBufferThenable<
      ::test_anonymous::SomeProtocol::SomeMethod>
  SomeMethod(::test_anonymous::wire::UnionMember union_member,
             ::test_anonymous::wire::TableMember table_member);
};
template <>
class ::fidl::internal::WireWeakSyncClientImpl<::test_anonymous::SomeProtocol>
    final : public ::fidl::internal::WireWeakOnewayClientImpl<
                ::test_anonymous::SomeProtocol> {
 public:
  using WireWeakOnewayClientImpl::WireWeakOnewayClientImpl;

  // Allocates 128 bytes of message buffer on the stack. No heap allocation
  // necessary.
  ::fidl::WireResult<::test_anonymous::SomeProtocol::SomeMethod> SomeMethod(
      ::test_anonymous::wire::UnionMember union_member,
      ::test_anonymous::wire::TableMember table_member);
};
namespace fidl {
#endif  // __Fuchsia__

}  // namespace fidl
#ifdef __Fuchsia__
template <>
class ::fidl::internal::WireWeakEventSender<::test_anonymous::SomeProtocol>
    : public ::fidl::internal::WeakEventSenderBase {
 public:
  using WeakEventSenderBase::WeakEventSenderBase;
};

template <>
class ::fidl::internal::WireWeakBufferEventSender<
    ::test_anonymous::SomeProtocol>
    : public ::fidl::internal::WeakBufferEventSenderBase {
 public:
  using WeakBufferEventSenderBase::WeakBufferEventSenderBase;
};

template <>
class ::fidl::internal::WireEventSender<::test_anonymous::SomeProtocol>
    : public ::fidl::internal::SyncEndpointManagedVeneer<
          ::fidl::internal::WireEventSender<::test_anonymous::SomeProtocol>> {
 public:
  using SyncEndpointManagedVeneer::SyncEndpointManagedVeneer;
};

template <>
class ::fidl::internal::WireBufferEventSender<::test_anonymous::SomeProtocol>
    : public ::fidl::internal::SyncEndpointBufferVeneer<
          ::fidl::internal::WireBufferEventSender<
              ::test_anonymous::SomeProtocol>> {
 public:
  using SyncEndpointBufferVeneer::SyncEndpointBufferVeneer;
};
#endif  // __Fuchsia__
