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

#include <fidl/test/protocolrequest/llcpp/fidl.h>

#include <memory>

namespace fidl_test_protocolrequest {
[[maybe_unused]] constexpr uint64_t kParent_GetChild_Ordinal =
    7929845654914578302lu;

extern "C" const fidl_type_t
    fidl_test_protocolrequest_ParentGetChildRequestTable;

extern "C" const fidl_type_t
    fidl_test_protocolrequest_ParentGetChildResponseTable;

[[maybe_unused]] constexpr uint64_t kParent_GetChildRequest_Ordinal =
    1819029190665166744lu;

extern "C" const fidl_type_t
    fidl_test_protocolrequest_ParentGetChildRequestRequestTable;

extern "C" const fidl_type_t
    fidl_test_protocolrequest_ParentGetChildRequestResponseTable;

[[maybe_unused]] constexpr uint64_t kParent_TakeChild_Ordinal =
    374110854839013230lu;

extern "C" const fidl_type_t
    fidl_test_protocolrequest_ParentTakeChildRequestTable;

extern "C" const fidl_type_t
    fidl_test_protocolrequest_ParentTakeChildResponseTable;

[[maybe_unused]] constexpr uint64_t kParent_TakeChildRequest_Ordinal =
    1574820689302890956lu;

extern "C" const fidl_type_t
    fidl_test_protocolrequest_ParentTakeChildRequestRequestTable;

extern "C" const fidl_type_t
    fidl_test_protocolrequest_ParentTakeChildRequestResponseTable;
#ifdef __Fuchsia__
}  // namespace fidl_test_protocolrequest
::fidl::WireResult<::fidl_test_protocolrequest::Parent::GetChild>::WireResult(
    ::fidl::UnownedClientEnd<::fidl_test_protocolrequest::Parent> _client) {
  ::fidl::OwnedEncodedMessage<
      ::fidl::WireRequest<::fidl_test_protocolrequest::Parent::GetChild>>
      _request(zx_txid_t(0));
  _request.GetOutgoingMessage()
      .Call<
          ::fidl::WireResponse<::fidl_test_protocolrequest::Parent::GetChild>>(
          _client, bytes_.data(), bytes_.size());
  status_ = _request.status();
  error_ = _request.error();
}

::fidl::WireResult<::fidl_test_protocolrequest::Parent::GetChild>::WireResult(
    ::fidl::UnownedClientEnd<::fidl_test_protocolrequest::Parent> _client,
    zx_time_t _deadline) {
  ::fidl::OwnedEncodedMessage<
      ::fidl::WireRequest<::fidl_test_protocolrequest::Parent::GetChild>>
      _request(zx_txid_t(0));
  _request.GetOutgoingMessage()
      .Call<
          ::fidl::WireResponse<::fidl_test_protocolrequest::Parent::GetChild>>(
          _client, bytes_.data(), bytes_.size(), _deadline);
  status_ = _request.status();
  error_ = _request.error();
}
namespace fidl_test_protocolrequest {
#endif  // __Fuchsia__

#ifdef __Fuchsia__
}  // namespace fidl_test_protocolrequest
::fidl::WireUnownedResult<::fidl_test_protocolrequest::Parent::GetChild>::
    WireUnownedResult(
        ::fidl::UnownedClientEnd<::fidl_test_protocolrequest::Parent> _client,
        uint8_t* _response_bytes, uint32_t _response_byte_capacity)
    : bytes_(_response_bytes) {
  ::fidl::OwnedEncodedMessage<
      ::fidl::WireRequest<::fidl_test_protocolrequest::Parent::GetChild>>
      _request(zx_txid_t(0));
  _request.GetOutgoingMessage()
      .Call<
          ::fidl::WireResponse<::fidl_test_protocolrequest::Parent::GetChild>>(
          _client, _response_bytes, _response_byte_capacity);
  status_ = _request.status();
  error_ = _request.error();
}
namespace fidl_test_protocolrequest {
#endif  // __Fuchsia__

#ifdef __Fuchsia__
}  // namespace fidl_test_protocolrequest
::fidl::WireResult<::fidl_test_protocolrequest::Parent::GetChildRequest>::
    WireResult(
        ::fidl::UnownedClientEnd<::fidl_test_protocolrequest::Parent> _client) {
  ::fidl::OwnedEncodedMessage<
      ::fidl::WireRequest<::fidl_test_protocolrequest::Parent::GetChildRequest>>
      _request(zx_txid_t(0));
  _request.GetOutgoingMessage()
      .Call<::fidl::WireResponse<
          ::fidl_test_protocolrequest::Parent::GetChildRequest>>(
          _client, bytes_.data(), bytes_.size());
  status_ = _request.status();
  error_ = _request.error();
}

::fidl::WireResult<::fidl_test_protocolrequest::Parent::GetChildRequest>::
    WireResult(
        ::fidl::UnownedClientEnd<::fidl_test_protocolrequest::Parent> _client,
        zx_time_t _deadline) {
  ::fidl::OwnedEncodedMessage<
      ::fidl::WireRequest<::fidl_test_protocolrequest::Parent::GetChildRequest>>
      _request(zx_txid_t(0));
  _request.GetOutgoingMessage()
      .Call<::fidl::WireResponse<
          ::fidl_test_protocolrequest::Parent::GetChildRequest>>(
          _client, bytes_.data(), bytes_.size(), _deadline);
  status_ = _request.status();
  error_ = _request.error();
}
namespace fidl_test_protocolrequest {
#endif  // __Fuchsia__

#ifdef __Fuchsia__
}  // namespace fidl_test_protocolrequest
::fidl::WireUnownedResult<
    ::fidl_test_protocolrequest::Parent::GetChildRequest>::
    WireUnownedResult(
        ::fidl::UnownedClientEnd<::fidl_test_protocolrequest::Parent> _client,
        uint8_t* _response_bytes, uint32_t _response_byte_capacity)
    : bytes_(_response_bytes) {
  ::fidl::OwnedEncodedMessage<
      ::fidl::WireRequest<::fidl_test_protocolrequest::Parent::GetChildRequest>>
      _request(zx_txid_t(0));
  _request.GetOutgoingMessage()
      .Call<::fidl::WireResponse<
          ::fidl_test_protocolrequest::Parent::GetChildRequest>>(
          _client, _response_bytes, _response_byte_capacity);
  status_ = _request.status();
  error_ = _request.error();
}
namespace fidl_test_protocolrequest {
#endif  // __Fuchsia__

#ifdef __Fuchsia__
}  // namespace fidl_test_protocolrequest
::fidl::WireResult<::fidl_test_protocolrequest::Parent::TakeChild>::WireResult(
    ::fidl::UnownedClientEnd<::fidl_test_protocolrequest::Parent> _client,
    ::fidl::ClientEnd<::fidl_test_protocolrequest::Child>&& c) {
  ::fidl::OwnedEncodedMessage<
      ::fidl::WireRequest<::fidl_test_protocolrequest::Parent::TakeChild>>
      _request(zx_txid_t(0), std::move(c));
  _request.GetOutgoingMessage().Write(_client);
  status_ = _request.status();
  error_ = _request.error();
}
namespace fidl_test_protocolrequest {
#endif  // __Fuchsia__

#ifdef __Fuchsia__
}  // namespace fidl_test_protocolrequest
::fidl::WireUnownedResult<::fidl_test_protocolrequest::Parent::TakeChild>::
    WireUnownedResult(
        ::fidl::UnownedClientEnd<::fidl_test_protocolrequest::Parent> _client,
        uint8_t* _request_bytes, uint32_t _request_byte_capacity,
        ::fidl::ClientEnd<::fidl_test_protocolrequest::Child>&& c) {
  ::fidl::UnownedEncodedMessage<
      ::fidl::WireRequest<::fidl_test_protocolrequest::Parent::TakeChild>>
      _request(_request_bytes, _request_byte_capacity, 0, std::move(c));
  _request.GetOutgoingMessage().Write(_client);
  status_ = _request.status();
  error_ = _request.error();
}
namespace fidl_test_protocolrequest {
#endif  // __Fuchsia__

#ifdef __Fuchsia__
}  // namespace fidl_test_protocolrequest
::fidl::WireResult<::fidl_test_protocolrequest::Parent::TakeChildRequest>::
    WireResult(
        ::fidl::UnownedClientEnd<::fidl_test_protocolrequest::Parent> _client,
        ::fidl::ServerEnd<::fidl_test_protocolrequest::Child>&& r) {
  ::fidl::OwnedEncodedMessage<::fidl::WireRequest<
      ::fidl_test_protocolrequest::Parent::TakeChildRequest>>
      _request(zx_txid_t(0), std::move(r));
  _request.GetOutgoingMessage().Write(_client);
  status_ = _request.status();
  error_ = _request.error();
}
namespace fidl_test_protocolrequest {
#endif  // __Fuchsia__

#ifdef __Fuchsia__
}  // namespace fidl_test_protocolrequest
::fidl::WireUnownedResult<
    ::fidl_test_protocolrequest::Parent::TakeChildRequest>::
    WireUnownedResult(
        ::fidl::UnownedClientEnd<::fidl_test_protocolrequest::Parent> _client,
        uint8_t* _request_bytes, uint32_t _request_byte_capacity,
        ::fidl::ServerEnd<::fidl_test_protocolrequest::Child>&& r) {
  ::fidl::UnownedEncodedMessage<::fidl::WireRequest<
      ::fidl_test_protocolrequest::Parent::TakeChildRequest>>
      _request(_request_bytes, _request_byte_capacity, 0, std::move(r));
  _request.GetOutgoingMessage().Write(_client);
  status_ = _request.status();
  error_ = _request.error();
}
namespace fidl_test_protocolrequest {
#endif  // __Fuchsia__

}  // namespace fidl_test_protocolrequest
#ifdef __Fuchsia__
::fidl::WireResult<::fidl_test_protocolrequest::Parent::GetChild>
fidl::internal::WireClientImpl<
    ::fidl_test_protocolrequest::Parent>::GetChild_Sync() {
  if (auto _channel = ::fidl::internal::ClientBase::GetChannel()) {
    return ::fidl::WireResult<::fidl_test_protocolrequest::Parent::GetChild>(
        ::fidl::UnownedClientEnd<::fidl_test_protocolrequest::Parent>(
            _channel->handle()));
  }
  return ::fidl::WireResult<::fidl_test_protocolrequest::Parent::GetChild>(
      ::fidl::Result(ZX_ERR_CANCELED, ::fidl::kErrorChannelUnbound));
}
#endif  // __Fuchsia__

#ifdef __Fuchsia__
::fidl::WireUnownedResult<::fidl_test_protocolrequest::Parent::GetChild>
fidl::internal::WireClientImpl<::fidl_test_protocolrequest::Parent>::
    GetChild_Sync(::fidl::BufferSpan _response_buffer) {
  if (auto _channel = ::fidl::internal::ClientBase::GetChannel()) {
    return ::fidl::WireUnownedResult<
        ::fidl_test_protocolrequest::Parent::GetChild>(
        ::fidl::UnownedClientEnd<::fidl_test_protocolrequest::Parent>(
            _channel->handle()),
        _response_buffer.data, _response_buffer.capacity);
  }
  return ::fidl::WireUnownedResult<
      ::fidl_test_protocolrequest::Parent::GetChild>(
      ::fidl::Result(ZX_ERR_CANCELED, ::fidl::kErrorChannelUnbound));
}
#endif  // __Fuchsia__

#ifdef __Fuchsia__

::fidl::WireResponseContext<
    ::fidl_test_protocolrequest::Parent::GetChild>::WireResponseContext()
    : ::fidl::internal::ResponseContext(
          ::fidl::WireResponse<
              ::fidl_test_protocolrequest::Parent::GetChild>::Type,
          ::fidl_test_protocolrequest::kParent_GetChild_Ordinal) {}

void ::fidl::WireResponseContext<
    ::fidl_test_protocolrequest::Parent::GetChild>::OnReply(uint8_t* reply) {
  OnReply(reinterpret_cast<
          ::fidl::WireResponse<::fidl_test_protocolrequest::Parent::GetChild>*>(
      reply));
}
#endif  // __Fuchsia__

#ifdef __Fuchsia__
::fidl::Result
fidl::internal::WireClientImpl<::fidl_test_protocolrequest::Parent>::GetChild(
    ::fit::callback<void(
        ::fidl::WireResponse<::fidl_test_protocolrequest::Parent::GetChild>*
            response)>
        _cb) {
  class ResponseContext final
      : public ::fidl::WireResponseContext<
            ::fidl_test_protocolrequest::Parent::GetChild> {
   public:
    ResponseContext(
        ::fit::callback<void(
            ::fidl::WireResponse<::fidl_test_protocolrequest::Parent::GetChild>*
                response)>
            cb)
        : cb_(std::move(cb)) {}

    void OnReply(
        ::fidl::WireResponse<::fidl_test_protocolrequest::Parent::GetChild>*
            response) override {
      cb_(response);

      response->_CloseHandles();

      delete this;
    }

    void OnError() override { delete this; }

   private:
    ::fit::callback<void(
        ::fidl::WireResponse<::fidl_test_protocolrequest::Parent::GetChild>*
            response)>
        cb_;
  };

  auto* _context = new ResponseContext(std::move(_cb));
  ::fidl::internal::ClientBase::PrepareAsyncTxn(_context);
  ::fidl::WireRequest<::fidl_test_protocolrequest::Parent::GetChild>::
      OwnedEncodedMessage _request(_context->Txid());
  return _request.GetOutgoingMessage().Write(this, _context);
}

::fidl::Result
fidl::internal::WireClientImpl<::fidl_test_protocolrequest::Parent>::GetChild(
    ::fidl::WireResponseContext<::fidl_test_protocolrequest::Parent::GetChild>*
        _context) {
  ::fidl::internal::ClientBase::PrepareAsyncTxn(_context);

  ::fidl::WireRequest<::fidl_test_protocolrequest::Parent::GetChild>::
      OwnedEncodedMessage _request(_context->Txid());
  return _request.GetOutgoingMessage().Write(this, _context);
}
#endif  // __Fuchsia__

#ifdef __Fuchsia__
::fidl::WireResult<::fidl_test_protocolrequest::Parent::GetChildRequest>
fidl::internal::WireClientImpl<
    ::fidl_test_protocolrequest::Parent>::GetChildRequest_Sync() {
  if (auto _channel = ::fidl::internal::ClientBase::GetChannel()) {
    return ::fidl::WireResult<
        ::fidl_test_protocolrequest::Parent::GetChildRequest>(
        ::fidl::UnownedClientEnd<::fidl_test_protocolrequest::Parent>(
            _channel->handle()));
  }
  return ::fidl::WireResult<
      ::fidl_test_protocolrequest::Parent::GetChildRequest>(
      ::fidl::Result(ZX_ERR_CANCELED, ::fidl::kErrorChannelUnbound));
}
#endif  // __Fuchsia__

#ifdef __Fuchsia__
::fidl::WireUnownedResult<::fidl_test_protocolrequest::Parent::GetChildRequest>
fidl::internal::WireClientImpl<::fidl_test_protocolrequest::Parent>::
    GetChildRequest_Sync(::fidl::BufferSpan _response_buffer) {
  if (auto _channel = ::fidl::internal::ClientBase::GetChannel()) {
    return ::fidl::WireUnownedResult<
        ::fidl_test_protocolrequest::Parent::GetChildRequest>(
        ::fidl::UnownedClientEnd<::fidl_test_protocolrequest::Parent>(
            _channel->handle()),
        _response_buffer.data, _response_buffer.capacity);
  }
  return ::fidl::WireUnownedResult<
      ::fidl_test_protocolrequest::Parent::GetChildRequest>(
      ::fidl::Result(ZX_ERR_CANCELED, ::fidl::kErrorChannelUnbound));
}
#endif  // __Fuchsia__

#ifdef __Fuchsia__

::fidl::WireResponseContext<
    ::fidl_test_protocolrequest::Parent::GetChildRequest>::WireResponseContext()
    : ::fidl::internal::ResponseContext(
          ::fidl::WireResponse<
              ::fidl_test_protocolrequest::Parent::GetChildRequest>::Type,
          ::fidl_test_protocolrequest::kParent_GetChildRequest_Ordinal) {}

void ::fidl::WireResponseContext<
    ::fidl_test_protocolrequest::Parent::GetChildRequest>::OnReply(uint8_t*
                                                                       reply) {
  OnReply(reinterpret_cast<::fidl::WireResponse<
              ::fidl_test_protocolrequest::Parent::GetChildRequest>*>(reply));
}
#endif  // __Fuchsia__

#ifdef __Fuchsia__
::fidl::Result fidl::internal::
    WireClientImpl<::fidl_test_protocolrequest::Parent>::GetChildRequest(
        ::fit::callback<
            void(::fidl::WireResponse<::fidl_test_protocolrequest::Parent::
                                          GetChildRequest>* response)>
            _cb) {
  class ResponseContext final
      : public ::fidl::WireResponseContext<
            ::fidl_test_protocolrequest::Parent::GetChildRequest> {
   public:
    ResponseContext(::fit::callback<
                    void(::fidl::WireResponse<
                         ::fidl_test_protocolrequest::Parent::GetChildRequest>*
                             response)>
                        cb)
        : cb_(std::move(cb)) {}

    void OnReply(::fidl::WireResponse<
                 ::fidl_test_protocolrequest::Parent::GetChildRequest>*
                     response) override {
      cb_(response);

      response->_CloseHandles();

      delete this;
    }

    void OnError() override { delete this; }

   private:
    ::fit::callback<void(
        ::fidl::WireResponse<
            ::fidl_test_protocolrequest::Parent::GetChildRequest>* response)>
        cb_;
  };

  auto* _context = new ResponseContext(std::move(_cb));
  ::fidl::internal::ClientBase::PrepareAsyncTxn(_context);
  ::fidl::WireRequest<::fidl_test_protocolrequest::Parent::GetChildRequest>::
      OwnedEncodedMessage _request(_context->Txid());
  return _request.GetOutgoingMessage().Write(this, _context);
}

::fidl::Result fidl::internal::
    WireClientImpl<::fidl_test_protocolrequest::Parent>::GetChildRequest(
        ::fidl::WireResponseContext<
            ::fidl_test_protocolrequest::Parent::GetChildRequest>* _context) {
  ::fidl::internal::ClientBase::PrepareAsyncTxn(_context);

  ::fidl::WireRequest<::fidl_test_protocolrequest::Parent::GetChildRequest>::
      OwnedEncodedMessage _request(_context->Txid());
  return _request.GetOutgoingMessage().Write(this, _context);
}
#endif  // __Fuchsia__

#ifdef __Fuchsia__
::fidl::Result
fidl::internal::WireClientImpl<::fidl_test_protocolrequest::Parent>::TakeChild(
    ::fidl::ClientEnd<::fidl_test_protocolrequest::Child>&& c) {
  if (auto _channel = ::fidl::internal::ClientBase::GetChannel()) {
    auto _res =
        ::fidl::WireResult<::fidl_test_protocolrequest::Parent::TakeChild>(
            ::fidl::UnownedClientEnd<::fidl_test_protocolrequest::Parent>(
                _channel->handle()),
            std::move(c));
    return ::fidl::Result(_res.status(), _res.error());
  }
  return ::fidl::Result(ZX_ERR_CANCELED, ::fidl::kErrorChannelUnbound);
}
#endif  // __Fuchsia__

#ifdef __Fuchsia__
::fidl::Result
fidl::internal::WireClientImpl<::fidl_test_protocolrequest::Parent>::TakeChild(
    ::fidl::BufferSpan _request_buffer,
    ::fidl::ClientEnd<::fidl_test_protocolrequest::Child>&& c) {
  if (auto _channel = ::fidl::internal::ClientBase::GetChannel()) {
    auto _res = ::fidl::WireUnownedResult<
        ::fidl_test_protocolrequest::Parent::TakeChild>(
        ::fidl::UnownedClientEnd<::fidl_test_protocolrequest::Parent>(
            _channel->handle()),
        _request_buffer.data, _request_buffer.capacity, std::move(c));
    return ::fidl::Result(_res.status(), _res.error());
  }
  return ::fidl::Result(ZX_ERR_CANCELED, ::fidl::kErrorChannelUnbound);
}
#endif  // __Fuchsia__

#ifdef __Fuchsia__
::fidl::Result fidl::internal::
    WireClientImpl<::fidl_test_protocolrequest::Parent>::TakeChildRequest(
        ::fidl::ServerEnd<::fidl_test_protocolrequest::Child>&& r) {
  if (auto _channel = ::fidl::internal::ClientBase::GetChannel()) {
    auto _res = ::fidl::WireResult<
        ::fidl_test_protocolrequest::Parent::TakeChildRequest>(
        ::fidl::UnownedClientEnd<::fidl_test_protocolrequest::Parent>(
            _channel->handle()),
        std::move(r));
    return ::fidl::Result(_res.status(), _res.error());
  }
  return ::fidl::Result(ZX_ERR_CANCELED, ::fidl::kErrorChannelUnbound);
}
#endif  // __Fuchsia__

#ifdef __Fuchsia__
::fidl::Result fidl::internal::
    WireClientImpl<::fidl_test_protocolrequest::Parent>::TakeChildRequest(
        ::fidl::BufferSpan _request_buffer,
        ::fidl::ServerEnd<::fidl_test_protocolrequest::Child>&& r) {
  if (auto _channel = ::fidl::internal::ClientBase::GetChannel()) {
    auto _res = ::fidl::WireUnownedResult<
        ::fidl_test_protocolrequest::Parent::TakeChildRequest>(
        ::fidl::UnownedClientEnd<::fidl_test_protocolrequest::Parent>(
            _channel->handle()),
        _request_buffer.data, _request_buffer.capacity, std::move(r));
    return ::fidl::Result(_res.status(), _res.error());
  }
  return ::fidl::Result(ZX_ERR_CANCELED, ::fidl::kErrorChannelUnbound);
}
#endif  // __Fuchsia__

#ifdef __Fuchsia__
std::optional<::fidl::UnbindInfo> fidl::internal::WireClientImpl<
    ::fidl_test_protocolrequest::Parent>::DispatchEvent(fidl_incoming_msg_t*
                                                            msg) {
  FidlHandleInfoCloseMany(msg->handles, msg->num_handles);
  return ::fidl::UnbindInfo{::fidl::UnbindInfo::kUnexpectedMessage,
                            ZX_ERR_NOT_SUPPORTED};
}
#endif  // __Fuchsia__

#ifdef __Fuchsia__

::fidl::DispatchResult fidl::internal::
    WireServerDispatcher<::fidl_test_protocolrequest::Parent>::TryDispatch(
        ::fidl::WireServer<::fidl_test_protocolrequest::Parent>* impl,
        fidl_incoming_msg_t* msg, ::fidl::Transaction* txn) {
  static const ::fidl::internal::MethodEntry entries[] = {
      {
          ::fidl_test_protocolrequest::kParent_GetChild_Ordinal,
          ::fidl::WireRequest<
              ::fidl_test_protocolrequest::Parent::GetChild>::Type,
          [](void* interface, void* bytes, ::fidl::Transaction* txn) {
            ::fidl::WireServer<::fidl_test_protocolrequest::Parent>::
                GetChildCompleter::Sync completer(txn);
            reinterpret_cast<
                ::fidl::WireServer<::fidl_test_protocolrequest::Parent>*>(
                interface)
                ->GetChild(
                    reinterpret_cast<::fidl::WireRequest<
                        ::fidl_test_protocolrequest::Parent::GetChild>*>(bytes),
                    completer);
          },
      },
      {
          ::fidl_test_protocolrequest::kParent_GetChildRequest_Ordinal,
          ::fidl::WireRequest<
              ::fidl_test_protocolrequest::Parent::GetChildRequest>::Type,
          [](void* interface, void* bytes, ::fidl::Transaction* txn) {
            ::fidl::WireServer<::fidl_test_protocolrequest::Parent>::
                GetChildRequestCompleter::Sync completer(txn);
            reinterpret_cast<
                ::fidl::WireServer<::fidl_test_protocolrequest::Parent>*>(
                interface)
                ->GetChildRequest(
                    reinterpret_cast<::fidl::WireRequest<
                        ::fidl_test_protocolrequest::Parent::GetChildRequest>*>(
                        bytes),
                    completer);
          },
      },
      {
          ::fidl_test_protocolrequest::kParent_TakeChild_Ordinal,
          ::fidl::WireRequest<
              ::fidl_test_protocolrequest::Parent::TakeChild>::Type,
          [](void* interface, void* bytes, ::fidl::Transaction* txn) {
            ::fidl::WireServer<::fidl_test_protocolrequest::Parent>::
                TakeChildCompleter::Sync completer(txn);
            reinterpret_cast<
                ::fidl::WireServer<::fidl_test_protocolrequest::Parent>*>(
                interface)
                ->TakeChild(
                    reinterpret_cast<::fidl::WireRequest<
                        ::fidl_test_protocolrequest::Parent::TakeChild>*>(
                        bytes),
                    completer);
          },
      },
      {
          ::fidl_test_protocolrequest::kParent_TakeChildRequest_Ordinal,
          ::fidl::WireRequest<
              ::fidl_test_protocolrequest::Parent::TakeChildRequest>::Type,
          [](void* interface, void* bytes, ::fidl::Transaction* txn) {
            ::fidl::WireServer<::fidl_test_protocolrequest::Parent>::
                TakeChildRequestCompleter::Sync completer(txn);
            reinterpret_cast<
                ::fidl::WireServer<::fidl_test_protocolrequest::Parent>*>(
                interface)
                ->TakeChildRequest(
                    reinterpret_cast<
                        ::fidl::WireRequest<::fidl_test_protocolrequest::
                                                Parent::TakeChildRequest>*>(
                        bytes),
                    completer);
          },
      },
  };
  return ::fidl::internal::TryDispatch(
      impl, msg, txn, entries,
      entries + sizeof(entries) / sizeof(::fidl::internal::MethodEntry));
}

::fidl::DispatchResult fidl::internal::
    WireServerDispatcher<::fidl_test_protocolrequest::Parent>::Dispatch(
        ::fidl::WireServer<::fidl_test_protocolrequest::Parent>* impl,
        fidl_incoming_msg_t* msg, ::fidl::Transaction* txn) {
  ::fidl::DispatchResult dispatch_result = TryDispatch(impl, msg, txn);
  if (dispatch_result == ::fidl::DispatchResult::kNotFound) {
    FidlHandleInfoCloseMany(msg->handles, msg->num_handles);
    txn->InternalError(
        {::fidl::UnbindInfo::kUnexpectedMessage, ZX_ERR_NOT_SUPPORTED});
  }
  return dispatch_result;
}
::fidl::DispatchResult
fidl::WireServer<::fidl_test_protocolrequest::Parent>::dispatch_message(
    fidl_incoming_msg_t* msg, ::fidl::Transaction* txn) {
  return ::fidl::internal::WireServerDispatcher<
      ::fidl_test_protocolrequest::Parent>::Dispatch(this, msg, txn);
}

::fidl::DispatchResult fidl::internal::
    WireDispatcher<::fidl_test_protocolrequest::Parent>::TryDispatch(
        ::fidl::WireInterface<::fidl_test_protocolrequest::Parent>* impl,
        fidl_incoming_msg_t* msg, ::fidl::Transaction* txn) {
  static const ::fidl::internal::MethodEntry entries[] = {
      {
          ::fidl_test_protocolrequest::kParent_GetChild_Ordinal,
          ::fidl::WireRequest<
              ::fidl_test_protocolrequest::Parent::GetChild>::Type,
          [](void* interface, void* bytes, ::fidl::Transaction* txn) {
            ::fidl::WireServer<::fidl_test_protocolrequest::Parent>::
                GetChildCompleter::Sync completer(txn);
            reinterpret_cast<
                ::fidl::WireInterface<::fidl_test_protocolrequest::Parent>*>(
                interface)
                ->GetChild(completer);
          },
      },
      {
          ::fidl_test_protocolrequest::kParent_GetChildRequest_Ordinal,
          ::fidl::WireRequest<
              ::fidl_test_protocolrequest::Parent::GetChildRequest>::Type,
          [](void* interface, void* bytes, ::fidl::Transaction* txn) {
            ::fidl::WireServer<::fidl_test_protocolrequest::Parent>::
                GetChildRequestCompleter::Sync completer(txn);
            reinterpret_cast<
                ::fidl::WireInterface<::fidl_test_protocolrequest::Parent>*>(
                interface)
                ->GetChildRequest(completer);
          },
      },
      {
          ::fidl_test_protocolrequest::kParent_TakeChild_Ordinal,
          ::fidl::WireRequest<
              ::fidl_test_protocolrequest::Parent::TakeChild>::Type,
          [](void* interface, void* bytes, ::fidl::Transaction* txn) {
            auto message = reinterpret_cast<::fidl::WireRequest<
                ::fidl_test_protocolrequest::Parent::TakeChild>*>(bytes);
            ::fidl::WireServer<::fidl_test_protocolrequest::Parent>::
                TakeChildCompleter::Sync completer(txn);
            reinterpret_cast<
                ::fidl::WireInterface<::fidl_test_protocolrequest::Parent>*>(
                interface)
                ->TakeChild(std::move(message->c), completer);
          },
      },
      {
          ::fidl_test_protocolrequest::kParent_TakeChildRequest_Ordinal,
          ::fidl::WireRequest<
              ::fidl_test_protocolrequest::Parent::TakeChildRequest>::Type,
          [](void* interface, void* bytes, ::fidl::Transaction* txn) {
            auto message = reinterpret_cast<::fidl::WireRequest<
                ::fidl_test_protocolrequest::Parent::TakeChildRequest>*>(bytes);
            ::fidl::WireServer<::fidl_test_protocolrequest::Parent>::
                TakeChildRequestCompleter::Sync completer(txn);
            reinterpret_cast<
                ::fidl::WireInterface<::fidl_test_protocolrequest::Parent>*>(
                interface)
                ->TakeChildRequest(std::move(message->r), completer);
          },
      },
  };
  return ::fidl::internal::TryDispatch(
      impl, msg, txn, entries,
      entries + sizeof(entries) / sizeof(::fidl::internal::MethodEntry));
}

::fidl::DispatchResult
fidl::internal::WireDispatcher<::fidl_test_protocolrequest::Parent>::Dispatch(
    ::fidl::WireInterface<::fidl_test_protocolrequest::Parent>* impl,
    fidl_incoming_msg_t* msg, ::fidl::Transaction* txn) {
  ::fidl::DispatchResult dispatch_result = TryDispatch(impl, msg, txn);
  if (dispatch_result == ::fidl::DispatchResult::kNotFound) {
    FidlHandleInfoCloseMany(msg->handles, msg->num_handles);
    txn->InternalError(
        {::fidl::UnbindInfo::kUnexpectedMessage, ZX_ERR_NOT_SUPPORTED});
  }
  return dispatch_result;
}
::fidl::DispatchResult
fidl::WireInterface<::fidl_test_protocolrequest::Parent>::dispatch_message(
    fidl_incoming_msg_t* msg, ::fidl::Transaction* txn) {
  return ::fidl::internal::WireDispatcher<
      ::fidl_test_protocolrequest::Parent>::Dispatch(this, msg, txn);
}
#endif  // __Fuchsia__

#ifdef __Fuchsia__
::fidl::Result fidl::WireServer<::fidl_test_protocolrequest::Parent>::
    GetChildCompleterBase::Reply(
        ::fidl::ClientEnd<::fidl_test_protocolrequest::Child>&& c) {
  ::fidl::OwnedEncodedMessage<
      ::fidl::WireResponse<::fidl_test_protocolrequest::Parent::GetChild>>
      _response{std::move(c)};
  return ::fidl::WireServer<::fidl_test_protocolrequest::Parent>::
      GetChildCompleterBase::SendReply(&_response.GetOutgoingMessage());
}
#endif  // __Fuchsia__

#ifdef __Fuchsia__
::fidl::Result fidl::WireServer<::fidl_test_protocolrequest::Parent>::
    GetChildCompleterBase::Reply(
        ::fidl::BufferSpan _backing_buffer,
        ::fidl::ClientEnd<::fidl_test_protocolrequest::Child>&& c) {
  ::fidl::WireResponse<::fidl_test_protocolrequest::Parent::GetChild>::
      UnownedEncodedMessage _response(_backing_buffer.data,
                                      _backing_buffer.capacity, std::move(c));
  return CompleterBase::SendReply(&_response.GetOutgoingMessage());
}
#endif  // __Fuchsia__

#ifdef __Fuchsia__
::fidl::Result fidl::WireServer<::fidl_test_protocolrequest::Parent>::
    GetChildRequestCompleterBase::Reply(
        ::fidl::ServerEnd<::fidl_test_protocolrequest::Child>&& r) {
  ::fidl::OwnedEncodedMessage<::fidl::WireResponse<
      ::fidl_test_protocolrequest::Parent::GetChildRequest>>
      _response{std::move(r)};
  return ::fidl::WireServer<::fidl_test_protocolrequest::Parent>::
      GetChildRequestCompleterBase::SendReply(&_response.GetOutgoingMessage());
}
#endif  // __Fuchsia__

#ifdef __Fuchsia__
::fidl::Result fidl::WireServer<::fidl_test_protocolrequest::Parent>::
    GetChildRequestCompleterBase::Reply(
        ::fidl::BufferSpan _backing_buffer,
        ::fidl::ServerEnd<::fidl_test_protocolrequest::Child>&& r) {
  ::fidl::WireResponse<::fidl_test_protocolrequest::Parent::GetChildRequest>::
      UnownedEncodedMessage _response(_backing_buffer.data,
                                      _backing_buffer.capacity, std::move(r));
  return CompleterBase::SendReply(&_response.GetOutgoingMessage());
}
#endif  // __Fuchsia__

void ::fidl::WireRequest<::fidl_test_protocolrequest::Parent::GetChild>::
    _InitHeader(zx_txid_t _txid) {
  fidl_init_txn_header(&_hdr, _txid,
                       ::fidl_test_protocolrequest::kParent_GetChild_Ordinal);
}

void ::fidl::WireResponse<
    ::fidl_test_protocolrequest::Parent::GetChild>::_InitHeader() {
  fidl_init_txn_header(&_hdr, 0,
                       ::fidl_test_protocolrequest::kParent_GetChild_Ordinal);
}

void ::fidl::WireResponse<
    ::fidl_test_protocolrequest::Parent::GetChild>::_CloseHandles() {
  c.reset();
}

void ::fidl::WireRequest<::fidl_test_protocolrequest::Parent::GetChildRequest>::
    _InitHeader(zx_txid_t _txid) {
  fidl_init_txn_header(
      &_hdr, _txid,
      ::fidl_test_protocolrequest::kParent_GetChildRequest_Ordinal);
}

void ::fidl::WireResponse<
    ::fidl_test_protocolrequest::Parent::GetChildRequest>::_InitHeader() {
  fidl_init_txn_header(
      &_hdr, 0, ::fidl_test_protocolrequest::kParent_GetChildRequest_Ordinal);
}

void ::fidl::WireResponse<
    ::fidl_test_protocolrequest::Parent::GetChildRequest>::_CloseHandles() {
  r.reset();
}

void ::fidl::WireRequest<::fidl_test_protocolrequest::Parent::TakeChild>::
    _InitHeader(zx_txid_t _txid) {
  fidl_init_txn_header(&_hdr, _txid,
                       ::fidl_test_protocolrequest::kParent_TakeChild_Ordinal);
}

void ::fidl::WireRequest<
    ::fidl_test_protocolrequest::Parent::TakeChild>::_CloseHandles() {
  c.reset();
}

void ::fidl::WireRequest<::fidl_test_protocolrequest::Parent::
                             TakeChildRequest>::_InitHeader(zx_txid_t _txid) {
  fidl_init_txn_header(
      &_hdr, _txid,
      ::fidl_test_protocolrequest::kParent_TakeChildRequest_Ordinal);
}

void ::fidl::WireRequest<
    ::fidl_test_protocolrequest::Parent::TakeChildRequest>::_CloseHandles() {
  r.reset();
}

#ifdef __Fuchsia__

#endif  // __Fuchsia__

#ifdef __Fuchsia__
std::optional<::fidl::UnbindInfo> fidl::internal::WireClientImpl<
    ::fidl_test_protocolrequest::Child>::DispatchEvent(fidl_incoming_msg_t*
                                                           msg) {
  FidlHandleInfoCloseMany(msg->handles, msg->num_handles);
  return ::fidl::UnbindInfo{::fidl::UnbindInfo::kUnexpectedMessage,
                            ZX_ERR_NOT_SUPPORTED};
}
#endif  // __Fuchsia__

#ifdef __Fuchsia__

::fidl::DispatchResult fidl::internal::
    WireServerDispatcher<::fidl_test_protocolrequest::Child>::TryDispatch(
        ::fidl::WireServer<::fidl_test_protocolrequest::Child>* impl,
        fidl_incoming_msg_t* msg, ::fidl::Transaction* txn) {
  return ::fidl::DispatchResult::kNotFound;
}

::fidl::DispatchResult fidl::internal::
    WireServerDispatcher<::fidl_test_protocolrequest::Child>::Dispatch(
        ::fidl::WireServer<::fidl_test_protocolrequest::Child>* impl,
        fidl_incoming_msg_t* msg, ::fidl::Transaction* txn) {
  FidlHandleInfoCloseMany(msg->handles, msg->num_handles);
  txn->InternalError(
      {::fidl::UnbindInfo::kUnexpectedMessage, ZX_ERR_NOT_SUPPORTED});
  return ::fidl::DispatchResult::kNotFound;
}
::fidl::DispatchResult
fidl::WireServer<::fidl_test_protocolrequest::Child>::dispatch_message(
    fidl_incoming_msg_t* msg, ::fidl::Transaction* txn) {
  return ::fidl::internal::WireServerDispatcher<
      ::fidl_test_protocolrequest::Child>::Dispatch(this, msg, txn);
}

::fidl::DispatchResult
fidl::internal::WireDispatcher<::fidl_test_protocolrequest::Child>::TryDispatch(
    ::fidl::WireInterface<::fidl_test_protocolrequest::Child>* impl,
    fidl_incoming_msg_t* msg, ::fidl::Transaction* txn) {
  return ::fidl::DispatchResult::kNotFound;
}

::fidl::DispatchResult
fidl::internal::WireDispatcher<::fidl_test_protocolrequest::Child>::Dispatch(
    ::fidl::WireInterface<::fidl_test_protocolrequest::Child>* impl,
    fidl_incoming_msg_t* msg, ::fidl::Transaction* txn) {
  FidlHandleInfoCloseMany(msg->handles, msg->num_handles);
  txn->InternalError(
      {::fidl::UnbindInfo::kUnexpectedMessage, ZX_ERR_NOT_SUPPORTED});
  return ::fidl::DispatchResult::kNotFound;
}
::fidl::DispatchResult
fidl::WireInterface<::fidl_test_protocolrequest::Child>::dispatch_message(
    fidl_incoming_msg_t* msg, ::fidl::Transaction* txn) {
  return ::fidl::internal::WireDispatcher<
      ::fidl_test_protocolrequest::Child>::Dispatch(this, msg, txn);
}
#endif  // __Fuchsia__

#ifdef __Fuchsia__

#endif  // __Fuchsia__
