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

#pragma once

#include "lib/fidl/cpp/internal/header.h"

//
// Domain objects declarations (i.e. "natural types" in unified bindings).
//
namespace fidl {
namespace test {
namespace bindingsdenylist {
#ifdef __Fuchsia__

class OnlyLibfuzzerAndDeps;
using OnlyLibfuzzerAndDepsHandle =
    ::fidl::InterfaceHandle<OnlyLibfuzzerAndDeps>;
#endif  // __Fuchsia__

#ifdef __Fuchsia__
class OnlyHlcpp;
#endif  // __Fuchsia__

#ifdef __Fuchsia__

class OnlyCppAndDeps;
using OnlyCppAndDepsHandle = ::fidl::InterfaceHandle<OnlyCppAndDeps>;
#endif  // __Fuchsia__

#ifdef __Fuchsia__

namespace _internal {
extern "C" const fidl_type_t
    fidl_test_bindingsdenylist_OnlyLibfuzzerAndDepsLibfuzzerNeedsNonemptyProtocolRequestTable;

}  // namespace _internal
class OnlyLibfuzzerAndDeps_RequestEncoder {
 public:
  static ::fidl::HLCPPOutgoingMessage LibfuzzerNeedsNonemptyProtocol(
      ::fidl::Encoder* _encoder) {
    fidl_trace(WillHLCPPEncode);
    _encoder->Alloc(16 - sizeof(fidl_message_header_t));

    fidl_trace(
        DidHLCPPEncode,
        &::fidl::test::bindingsdenylist::_internal::
            fidl_test_bindingsdenylist_OnlyLibfuzzerAndDepsLibfuzzerNeedsNonemptyProtocolRequestTable,
        _encoder->GetPtr<const char>(0), _encoder->CurrentLength(),
        _encoder->CurrentHandleCount());

    return _encoder->GetMessage();
  }
};
namespace _internal {
extern "C" const fidl_type_t
    fidl_test_bindingsdenylist_OnlyLibfuzzerAndDepsLibfuzzerNeedsNonemptyProtocolResponseTable;

}  // namespace _internal
class OnlyLibfuzzerAndDeps_ResponseEncoder {
 public:
  static ::fidl::HLCPPOutgoingMessage LibfuzzerNeedsNonemptyProtocol(
      ::fidl::Encoder* _encoder) {
    fidl_trace(WillHLCPPEncode);
    _encoder->Alloc(16 - sizeof(fidl_message_header_t));

    fidl_trace(
        DidHLCPPEncode,
        &::fidl::test::bindingsdenylist::_internal::
            fidl_test_bindingsdenylist_OnlyLibfuzzerAndDepsLibfuzzerNeedsNonemptyProtocolResponseTable,
        _encoder->GetPtr<const char>(0), _encoder->CurrentLength(),
        _encoder->CurrentHandleCount());
    return _encoder->GetMessage();
  }
};
#endif  // __Fuchsia__

#ifdef __Fuchsia__

class OnlyCppAndDeps_RequestEncoder {
 public:
};

class OnlyCppAndDeps_ResponseEncoder {
 public:
};
#endif  // __Fuchsia__

constexpr uint32_t AllBindings = 0u;

}  // namespace bindingsdenylist
}  // namespace test

//
// Proxies and stubs declarations
//
namespace test {
namespace bindingsdenylist {
#ifdef __Fuchsia__

using OnlyLibfuzzerAndDepsPtr = ::fidl::InterfacePtr<OnlyLibfuzzerAndDeps>;
class OnlyLibfuzzerAndDeps_Proxy;
class OnlyLibfuzzerAndDeps_Stub;
class OnlyLibfuzzerAndDeps_EventSender;
class OnlyLibfuzzerAndDeps_Sync;
using OnlyLibfuzzerAndDepsSyncPtr =
    ::fidl::SynchronousInterfacePtr<OnlyLibfuzzerAndDeps>;
class OnlyLibfuzzerAndDeps_SyncProxy;

namespace internal {
constexpr uint64_t
    kOnlyLibfuzzerAndDeps_LibfuzzerNeedsNonemptyProtocol_Ordinal =
        0x1c84a24d8d4e3d28lu;
}  // namespace internal
#endif  // __Fuchsia__

#ifdef __Fuchsia__
class OnlyHlcpp;
#endif  // __Fuchsia__

#ifdef __Fuchsia__

using OnlyCppAndDepsPtr = ::fidl::InterfacePtr<OnlyCppAndDeps>;
class OnlyCppAndDeps_Proxy;
class OnlyCppAndDeps_Stub;
class OnlyCppAndDeps_EventSender;
class OnlyCppAndDeps_Sync;
using OnlyCppAndDepsSyncPtr = ::fidl::SynchronousInterfacePtr<OnlyCppAndDeps>;
class OnlyCppAndDeps_SyncProxy;

#endif  // __Fuchsia__

#ifdef __Fuchsia__

class OnlyLibfuzzerAndDeps {
 public:
  using Proxy_ = ::fidl::test::bindingsdenylist::OnlyLibfuzzerAndDeps_Proxy;
  using Stub_ = ::fidl::test::bindingsdenylist::OnlyLibfuzzerAndDeps_Stub;
  using EventSender_ =
      ::fidl::test::bindingsdenylist::OnlyLibfuzzerAndDeps_EventSender;
  using Sync_ = ::fidl::test::bindingsdenylist::OnlyLibfuzzerAndDeps_Sync;
  virtual ~OnlyLibfuzzerAndDeps();
  using LibfuzzerNeedsNonemptyProtocolCallback = fit::function<void()>;

  virtual void LibfuzzerNeedsNonemptyProtocol(
      LibfuzzerNeedsNonemptyProtocolCallback callback) = 0;
};

class OnlyLibfuzzerAndDeps_RequestDecoder {
 public:
  OnlyLibfuzzerAndDeps_RequestDecoder() = default;
  virtual ~OnlyLibfuzzerAndDeps_RequestDecoder() = default;
  static const fidl_type_t* GetType(uint64_t ordinal, bool* out_needs_response);
  virtual void LibfuzzerNeedsNonemptyProtocol() = 0;
};

class OnlyLibfuzzerAndDeps_ResponseDecoder {
 public:
  OnlyLibfuzzerAndDeps_ResponseDecoder() = default;
  virtual ~OnlyLibfuzzerAndDeps_ResponseDecoder() = default;
  static const fidl_type_t* GetType(uint64_t ordinal);
  virtual void LibfuzzerNeedsNonemptyProtocol() = 0;
};

class OnlyLibfuzzerAndDeps_EventSender {
 public:
  virtual ~OnlyLibfuzzerAndDeps_EventSender();
};

class OnlyLibfuzzerAndDeps_Sync {
 public:
  using Proxy_ = ::fidl::test::bindingsdenylist::OnlyLibfuzzerAndDeps_SyncProxy;
  virtual ~OnlyLibfuzzerAndDeps_Sync();
  virtual zx_status_t LibfuzzerNeedsNonemptyProtocol() = 0;
};

class OnlyLibfuzzerAndDeps_Proxy final : public ::fidl::internal::Proxy,
                                         public OnlyLibfuzzerAndDeps {
 public:
  explicit OnlyLibfuzzerAndDeps_Proxy(
      ::fidl::internal::ProxyController* controller);
  ~OnlyLibfuzzerAndDeps_Proxy() override;

  zx_status_t Dispatch_(::fidl::HLCPPIncomingMessage message) override;
  void LibfuzzerNeedsNonemptyProtocol(
      LibfuzzerNeedsNonemptyProtocolCallback callback) override;

 private:
  OnlyLibfuzzerAndDeps_Proxy(
      const ::fidl::test::bindingsdenylist::OnlyLibfuzzerAndDeps_Proxy&) =
      delete;
  OnlyLibfuzzerAndDeps_Proxy& operator=(
      const ::fidl::test::bindingsdenylist::OnlyLibfuzzerAndDeps_Proxy&) =
      delete;

  ::fidl::internal::ProxyController* controller_;
};

class OnlyLibfuzzerAndDeps_Stub final
    : public ::fidl::internal::Stub,
      public ::fidl::test::bindingsdenylist::OnlyLibfuzzerAndDeps_EventSender {
 public:
  typedef class ::fidl::test::bindingsdenylist::OnlyLibfuzzerAndDeps
      OnlyLibfuzzerAndDeps_clazz;
  explicit OnlyLibfuzzerAndDeps_Stub(
      ::fidl::test::bindingsdenylist::OnlyLibfuzzerAndDeps_Stub::
          OnlyLibfuzzerAndDeps_clazz* impl);
  ~OnlyLibfuzzerAndDeps_Stub() override;

  zx_status_t Dispatch_(::fidl::HLCPPIncomingMessage message,
                        ::fidl::internal::PendingResponse response) override;

 private:
  ::fidl::test::bindingsdenylist::OnlyLibfuzzerAndDeps_Stub::
      OnlyLibfuzzerAndDeps_clazz* impl_;
};

class OnlyLibfuzzerAndDeps_SyncProxy
    : public ::fidl::test::bindingsdenylist::OnlyLibfuzzerAndDeps_Sync {
 public:
  explicit OnlyLibfuzzerAndDeps_SyncProxy(::zx::channel channel);
  ~OnlyLibfuzzerAndDeps_SyncProxy() override;
  zx_status_t LibfuzzerNeedsNonemptyProtocol() override;

 private:
  ::fidl::internal::SynchronousProxy proxy_;
  friend class ::fidl::SynchronousInterfacePtr<OnlyLibfuzzerAndDeps>;
};
#endif  // __Fuchsia__

#ifdef __Fuchsia__

class OnlyHlcpp final {
 public:
  class Handler;

  static constexpr char Name[] = "fidl.test.bindingsdenylist.OnlyHlcpp";

  explicit OnlyHlcpp(std::unique_ptr<::fidl::ServiceConnector> service)
      : service_(std::move(service)) {}

  explicit operator bool() const { return !!service_; }

 private:
  std::unique_ptr<::fidl::ServiceConnector> service_;
};

/// Facilitates member protocol registration for servers.
class OnlyHlcpp::Handler final {
 public:
  /// Constructs a new |Handler|. Does not take ownership of |service|.
  explicit Handler(::fidl::ServiceHandlerBase* service) { (void)service; }

 private:
};
#endif  // __Fuchsia__

#ifdef __Fuchsia__

class OnlyCppAndDeps {
 public:
  using Proxy_ = ::fidl::test::bindingsdenylist::OnlyCppAndDeps_Proxy;
  using Stub_ = ::fidl::test::bindingsdenylist::OnlyCppAndDeps_Stub;
  using EventSender_ =
      ::fidl::test::bindingsdenylist::OnlyCppAndDeps_EventSender;
  using Sync_ = ::fidl::test::bindingsdenylist::OnlyCppAndDeps_Sync;
  virtual ~OnlyCppAndDeps();
};

class OnlyCppAndDeps_RequestDecoder {
 public:
  OnlyCppAndDeps_RequestDecoder() = default;
  virtual ~OnlyCppAndDeps_RequestDecoder() = default;
  static const fidl_type_t* GetType(uint64_t ordinal, bool* out_needs_response);
};

class OnlyCppAndDeps_ResponseDecoder {
 public:
  OnlyCppAndDeps_ResponseDecoder() = default;
  virtual ~OnlyCppAndDeps_ResponseDecoder() = default;
  static const fidl_type_t* GetType(uint64_t ordinal);
};

class OnlyCppAndDeps_EventSender {
 public:
  virtual ~OnlyCppAndDeps_EventSender();
};

class OnlyCppAndDeps_Sync {
 public:
  using Proxy_ = ::fidl::test::bindingsdenylist::OnlyCppAndDeps_SyncProxy;
  virtual ~OnlyCppAndDeps_Sync();
};

class OnlyCppAndDeps_Proxy final : public ::fidl::internal::Proxy,
                                   public OnlyCppAndDeps {
 public:
  explicit OnlyCppAndDeps_Proxy(::fidl::internal::ProxyController* controller);
  ~OnlyCppAndDeps_Proxy() override;

  zx_status_t Dispatch_(::fidl::HLCPPIncomingMessage message) override;

 private:
  OnlyCppAndDeps_Proxy(
      const ::fidl::test::bindingsdenylist::OnlyCppAndDeps_Proxy&) = delete;
  OnlyCppAndDeps_Proxy& operator=(
      const ::fidl::test::bindingsdenylist::OnlyCppAndDeps_Proxy&) = delete;

  ::fidl::internal::ProxyController* controller_;
};

class OnlyCppAndDeps_Stub final
    : public ::fidl::internal::Stub,
      public ::fidl::test::bindingsdenylist::OnlyCppAndDeps_EventSender {
 public:
  typedef class ::fidl::test::bindingsdenylist::OnlyCppAndDeps
      OnlyCppAndDeps_clazz;
  explicit OnlyCppAndDeps_Stub(
      ::fidl::test::bindingsdenylist::OnlyCppAndDeps_Stub::OnlyCppAndDeps_clazz*
          impl);
  ~OnlyCppAndDeps_Stub() override;

  zx_status_t Dispatch_(::fidl::HLCPPIncomingMessage message,
                        ::fidl::internal::PendingResponse response) override;

 private:
  ::fidl::test::bindingsdenylist::OnlyCppAndDeps_Stub::OnlyCppAndDeps_clazz*
      impl_;
};

class OnlyCppAndDeps_SyncProxy
    : public ::fidl::test::bindingsdenylist::OnlyCppAndDeps_Sync {
 public:
  explicit OnlyCppAndDeps_SyncProxy(::zx::channel channel);
  ~OnlyCppAndDeps_SyncProxy() override;

 private:
  ::fidl::internal::SynchronousProxy proxy_;
  friend class ::fidl::SynchronousInterfacePtr<OnlyCppAndDeps>;
};
#endif  // __Fuchsia__

}  // namespace bindingsdenylist
}  // namespace test
}  // namespace fidl
