// services/service_manager/public/mojom/service_manager.mojom.cc is auto generated by mojom_bindings_generator.py, do not edit

// Copyright 2013 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#if defined(__clang__)
#pragma clang diagnostic push
#pragma clang diagnostic ignored "-Wunused-private-field"
#endif

#include "services/service_manager/public/mojom/service_manager.mojom.h"

#include <math.h>
#include <stdint.h>
#include <utility>

#include "base/debug/alias.h"
#include "base/hash/md5_constexpr.h"
#include "base/run_loop.h"
#include "base/strings/string_number_conversions.h"
#include "base/trace_event/trace_event.h"
#include "base/trace_event/typed_macros.h"
#include "mojo/public/cpp/bindings/lib/generated_code_util.h"
#include "mojo/public/cpp/bindings/lib/message_internal.h"
#include "mojo/public/cpp/bindings/lib/send_message_helper.h"
#include "mojo/public/cpp/bindings/lib/proxy_to_responder.h"
#include "mojo/public/cpp/bindings/lib/serialization_util.h"
#include "mojo/public/cpp/bindings/lib/unserialized_message_context.h"
#include "mojo/public/cpp/bindings/lib/validate_params.h"
#include "mojo/public/cpp/bindings/lib/validation_errors.h"
#include "mojo/public/cpp/bindings/mojo_buildflags.h"
#include "mojo/public/interfaces/bindings/interface_control_messages.mojom.h"
#include "third_party/perfetto/include/perfetto/tracing/traced_value.h"

#include "services/service_manager/public/mojom/service_manager.mojom-params-data.h"
#include "services/service_manager/public/mojom/service_manager.mojom-shared-message-ids.h"

#include "services/service_manager/public/mojom/service_manager.mojom-import-headers.h"
#include "services/service_manager/public/mojom/service_manager.mojom-test-utils.h"


#ifndef SERVICES_SERVICE_MANAGER_PUBLIC_MOJOM_SERVICE_MANAGER_MOJOM_JUMBO_H_
#define SERVICES_SERVICE_MANAGER_PUBLIC_MOJOM_SERVICE_MANAGER_MOJOM_JUMBO_H_
#endif



namespace service_manager {
namespace mojom {
RunningServiceInfo::RunningServiceInfo()
    : identity(),
      pid(),
      state() {}

RunningServiceInfo::RunningServiceInfo(
    const ::service_manager::Identity& identity_in,
    uint32_t pid_in,
    InstanceState state_in)
    : identity(std::move(identity_in)),
      pid(std::move(pid_in)),
      state(std::move(state_in)) {}

RunningServiceInfo::~RunningServiceInfo() = default;

void RunningServiceInfo::WriteIntoTrace(
    perfetto::TracedValue traced_context) const {
  [[maybe_unused]] auto dict = std::move(traced_context).WriteDictionary();
  perfetto::WriteIntoTracedValueWithFallback(
    dict.AddItem(
      "identity"), this->identity,
#if BUILDFLAG(MOJO_TRACE_ENABLED)
      "<value of type const ::service_manager::Identity&>"
#else
      "<value>"
#endif  // BUILDFLAG(MOJO_TRACE_ENABLED)
    );
  perfetto::WriteIntoTracedValueWithFallback(
    dict.AddItem(
      "pid"), this->pid,
#if BUILDFLAG(MOJO_TRACE_ENABLED)
      "<value of type uint32_t>"
#else
      "<value>"
#endif  // BUILDFLAG(MOJO_TRACE_ENABLED)
    );
  perfetto::WriteIntoTracedValueWithFallback(
    dict.AddItem(
      "state"), this->state,
#if BUILDFLAG(MOJO_TRACE_ENABLED)
      "<value of type InstanceState>"
#else
      "<value>"
#endif  // BUILDFLAG(MOJO_TRACE_ENABLED)
    );
}

bool RunningServiceInfo::Validate(
    const void* data,
    mojo::internal::ValidationContext* validation_context) {
  return Data_::Validate(data, validation_context);
}
const char ServiceManagerListener::Name_[] = "service_manager.mojom.ServiceManagerListener";

std::pair<uint32_t, const void*> ServiceManagerListener::MessageToMethodInfo_(mojo::Message& message) {
  switch (message.name()) {
    case internal::kServiceManagerListener_OnInit_Name: {
      constexpr uint32_t value = base::MD5Hash32Constexpr(
              "(Impl)service_manager::mojom::ServiceManagerListener::OnInit");
#if BUILDFLAG(IS_FUCHSIA)
        return std::make_pair(value, nullptr);
#else
        return std::make_pair(value, reinterpret_cast<const void*>(&ServiceManagerListener::OnInit_Sym::IPCSymbol));
#endif // BUILDFLAG(IS_FUCHSIA)
    }
    case internal::kServiceManagerListener_OnServiceCreated_Name: {
      constexpr uint32_t value = base::MD5Hash32Constexpr(
              "(Impl)service_manager::mojom::ServiceManagerListener::OnServiceCreated");
#if BUILDFLAG(IS_FUCHSIA)
        return std::make_pair(value, nullptr);
#else
        return std::make_pair(value, reinterpret_cast<const void*>(&ServiceManagerListener::OnServiceCreated_Sym::IPCSymbol));
#endif // BUILDFLAG(IS_FUCHSIA)
    }
    case internal::kServiceManagerListener_OnServiceStarted_Name: {
      constexpr uint32_t value = base::MD5Hash32Constexpr(
              "(Impl)service_manager::mojom::ServiceManagerListener::OnServiceStarted");
#if BUILDFLAG(IS_FUCHSIA)
        return std::make_pair(value, nullptr);
#else
        return std::make_pair(value, reinterpret_cast<const void*>(&ServiceManagerListener::OnServiceStarted_Sym::IPCSymbol));
#endif // BUILDFLAG(IS_FUCHSIA)
    }
    case internal::kServiceManagerListener_OnServicePIDReceived_Name: {
      constexpr uint32_t value = base::MD5Hash32Constexpr(
              "(Impl)service_manager::mojom::ServiceManagerListener::OnServicePIDReceived");
#if BUILDFLAG(IS_FUCHSIA)
        return std::make_pair(value, nullptr);
#else
        return std::make_pair(value, reinterpret_cast<const void*>(&ServiceManagerListener::OnServicePIDReceived_Sym::IPCSymbol));
#endif // BUILDFLAG(IS_FUCHSIA)
    }
    case internal::kServiceManagerListener_OnServiceFailedToStart_Name: {
      constexpr uint32_t value = base::MD5Hash32Constexpr(
              "(Impl)service_manager::mojom::ServiceManagerListener::OnServiceFailedToStart");
#if BUILDFLAG(IS_FUCHSIA)
        return std::make_pair(value, nullptr);
#else
        return std::make_pair(value, reinterpret_cast<const void*>(&ServiceManagerListener::OnServiceFailedToStart_Sym::IPCSymbol));
#endif // BUILDFLAG(IS_FUCHSIA)
    }
    case internal::kServiceManagerListener_OnServiceStopped_Name: {
      constexpr uint32_t value = base::MD5Hash32Constexpr(
              "(Impl)service_manager::mojom::ServiceManagerListener::OnServiceStopped");
#if BUILDFLAG(IS_FUCHSIA)
        return std::make_pair(value, nullptr);
#else
        return std::make_pair(value, reinterpret_cast<const void*>(&ServiceManagerListener::OnServiceStopped_Sym::IPCSymbol));
#endif // BUILDFLAG(IS_FUCHSIA)
    }
  }
  return std::make_pair(0, nullptr);
}


const char* ServiceManagerListener::MessageToMethodName_(mojo::Message& message) {
#if BUILDFLAG(MOJO_TRACE_ENABLED)
  bool is_response = message.has_flag(mojo::Message::kFlagIsResponse);
  if (!is_response) {
    switch (message.name()) {
      case internal::kServiceManagerListener_OnInit_Name:
            return "Receive service_manager::mojom::ServiceManagerListener::OnInit";
      case internal::kServiceManagerListener_OnServiceCreated_Name:
            return "Receive service_manager::mojom::ServiceManagerListener::OnServiceCreated";
      case internal::kServiceManagerListener_OnServiceStarted_Name:
            return "Receive service_manager::mojom::ServiceManagerListener::OnServiceStarted";
      case internal::kServiceManagerListener_OnServicePIDReceived_Name:
            return "Receive service_manager::mojom::ServiceManagerListener::OnServicePIDReceived";
      case internal::kServiceManagerListener_OnServiceFailedToStart_Name:
            return "Receive service_manager::mojom::ServiceManagerListener::OnServiceFailedToStart";
      case internal::kServiceManagerListener_OnServiceStopped_Name:
            return "Receive service_manager::mojom::ServiceManagerListener::OnServiceStopped";
    }
  } else {
    switch (message.name()) {
      case internal::kServiceManagerListener_OnInit_Name:
            return "Receive reply service_manager::mojom::ServiceManagerListener::OnInit";
      case internal::kServiceManagerListener_OnServiceCreated_Name:
            return "Receive reply service_manager::mojom::ServiceManagerListener::OnServiceCreated";
      case internal::kServiceManagerListener_OnServiceStarted_Name:
            return "Receive reply service_manager::mojom::ServiceManagerListener::OnServiceStarted";
      case internal::kServiceManagerListener_OnServicePIDReceived_Name:
            return "Receive reply service_manager::mojom::ServiceManagerListener::OnServicePIDReceived";
      case internal::kServiceManagerListener_OnServiceFailedToStart_Name:
            return "Receive reply service_manager::mojom::ServiceManagerListener::OnServiceFailedToStart";
      case internal::kServiceManagerListener_OnServiceStopped_Name:
            return "Receive reply service_manager::mojom::ServiceManagerListener::OnServiceStopped";
    }
  }
  return "Receive unknown mojo message";
#else
  bool is_response = message.has_flag(mojo::Message::kFlagIsResponse);
  if (is_response) {
    return "Receive mojo reply";
  } else {
    return "Receive mojo message";
  }
#endif // BUILDFLAG(MOJO_TRACE_ENABLED)
}

#if !BUILDFLAG(IS_FUCHSIA)
void ServiceManagerListener::OnInit_Sym::IPCSymbol() {
  // This method's address is used for indetifiying the mojo method name after
  // symblozation. So each IPCSymbol should have a unique address.
  NO_CODE_FOLDING();
}
void ServiceManagerListener::OnServiceCreated_Sym::IPCSymbol() {
  // This method's address is used for indetifiying the mojo method name after
  // symblozation. So each IPCSymbol should have a unique address.
  NO_CODE_FOLDING();
}
void ServiceManagerListener::OnServiceStarted_Sym::IPCSymbol() {
  // This method's address is used for indetifiying the mojo method name after
  // symblozation. So each IPCSymbol should have a unique address.
  NO_CODE_FOLDING();
}
void ServiceManagerListener::OnServicePIDReceived_Sym::IPCSymbol() {
  // This method's address is used for indetifiying the mojo method name after
  // symblozation. So each IPCSymbol should have a unique address.
  NO_CODE_FOLDING();
}
void ServiceManagerListener::OnServiceFailedToStart_Sym::IPCSymbol() {
  // This method's address is used for indetifiying the mojo method name after
  // symblozation. So each IPCSymbol should have a unique address.
  NO_CODE_FOLDING();
}
void ServiceManagerListener::OnServiceStopped_Sym::IPCSymbol() {
  // This method's address is used for indetifiying the mojo method name after
  // symblozation. So each IPCSymbol should have a unique address.
  NO_CODE_FOLDING();
}
# endif // !BUILDFLAG(IS_FUCHSIA)

ServiceManagerListenerProxy::ServiceManagerListenerProxy(mojo::MessageReceiverWithResponder* receiver)
    : receiver_(receiver) {
}

void ServiceManagerListenerProxy::OnInit(
    std::vector<RunningServiceInfoPtr> in_running_services) {
#if BUILDFLAG(MOJO_TRACE_ENABLED)
  TRACE_EVENT1(
    "mojom", "Send service_manager::mojom::ServiceManagerListener::OnInit", "input_parameters",
    [&](perfetto::TracedValue context){
      auto dict = std::move(context).WriteDictionary();
      perfetto::WriteIntoTracedValueWithFallback(
           dict.AddItem("running_services"), in_running_services,
                        "<value of type std::vector<RunningServiceInfoPtr>>");
   });
#endif
  const bool kExpectsResponse = false;
  const bool kIsSync = false;
  const bool kAllowInterrupt = true;
  
  const uint32_t kFlags =
      ((kExpectsResponse) ? mojo::Message::kFlagExpectsResponse : 0) |
      ((kIsSync) ? mojo::Message::kFlagIsSync : 0) |
      ((kAllowInterrupt) ? 0 : mojo::Message::kFlagNoInterrupt);
  
  mojo::Message message(
      internal::kServiceManagerListener_OnInit_Name, kFlags, 0, 0, nullptr);
  mojo::internal::MessageFragment<
      ::service_manager::mojom::internal::ServiceManagerListener_OnInit_Params_Data> params(
          message);
  params.Allocate();
  mojo::internal::MessageFragment<
      typename decltype(params->running_services)::BaseType>
      running_services_fragment(params.message());
  const mojo::internal::ContainerValidateParams running_services_validate_params(
      0, false, nullptr);
  mojo::internal::Serialize<mojo::ArrayDataView<::service_manager::mojom::RunningServiceInfoDataView>>(
      in_running_services, running_services_fragment, &running_services_validate_params);
  params->running_services.Set(
      running_services_fragment.is_null() ? nullptr : running_services_fragment.data());
  MOJO_INTERNAL_DLOG_SERIALIZATION_WARNING(
      params->running_services.is_null(),
      mojo::internal::VALIDATION_ERROR_UNEXPECTED_NULL_POINTER,
      "null running_services in ServiceManagerListener.OnInit request");

#if defined(ENABLE_IPC_FUZZER)
  message.set_interface_name(ServiceManagerListener::Name_);
  message.set_method_name("OnInit");
#endif
  // This return value may be ignored as false implies the Connector has
  // encountered an error, which will be visible through other means.
  ::mojo::internal::SendMessage(*receiver_, message);
}

void ServiceManagerListenerProxy::OnServiceCreated(
    RunningServiceInfoPtr in_service) {
#if BUILDFLAG(MOJO_TRACE_ENABLED)
  TRACE_EVENT1(
    "mojom", "Send service_manager::mojom::ServiceManagerListener::OnServiceCreated", "input_parameters",
    [&](perfetto::TracedValue context){
      auto dict = std::move(context).WriteDictionary();
      perfetto::WriteIntoTracedValueWithFallback(
           dict.AddItem("service"), in_service,
                        "<value of type RunningServiceInfoPtr>");
   });
#endif
  const bool kExpectsResponse = false;
  const bool kIsSync = false;
  const bool kAllowInterrupt = true;
  
  const uint32_t kFlags =
      ((kExpectsResponse) ? mojo::Message::kFlagExpectsResponse : 0) |
      ((kIsSync) ? mojo::Message::kFlagIsSync : 0) |
      ((kAllowInterrupt) ? 0 : mojo::Message::kFlagNoInterrupt);
  
  mojo::Message message(
      internal::kServiceManagerListener_OnServiceCreated_Name, kFlags, 0, 0, nullptr);
  mojo::internal::MessageFragment<
      ::service_manager::mojom::internal::ServiceManagerListener_OnServiceCreated_Params_Data> params(
          message);
  params.Allocate();
  mojo::internal::MessageFragment<
      typename decltype(params->service)::BaseType> service_fragment(
          params.message());
  mojo::internal::Serialize<::service_manager::mojom::RunningServiceInfoDataView>(
      in_service, service_fragment);
  params->service.Set(
      service_fragment.is_null() ? nullptr : service_fragment.data());
  MOJO_INTERNAL_DLOG_SERIALIZATION_WARNING(
      params->service.is_null(),
      mojo::internal::VALIDATION_ERROR_UNEXPECTED_NULL_POINTER,
      "null service in ServiceManagerListener.OnServiceCreated request");

#if defined(ENABLE_IPC_FUZZER)
  message.set_interface_name(ServiceManagerListener::Name_);
  message.set_method_name("OnServiceCreated");
#endif
  // This return value may be ignored as false implies the Connector has
  // encountered an error, which will be visible through other means.
  ::mojo::internal::SendMessage(*receiver_, message);
}

void ServiceManagerListenerProxy::OnServiceStarted(
    const ::service_manager::Identity& in_identity, uint32_t in_pid_deprecated) {
#if BUILDFLAG(MOJO_TRACE_ENABLED)
  TRACE_EVENT1(
    "mojom", "Send service_manager::mojom::ServiceManagerListener::OnServiceStarted", "input_parameters",
    [&](perfetto::TracedValue context){
      auto dict = std::move(context).WriteDictionary();
      perfetto::WriteIntoTracedValueWithFallback(
           dict.AddItem("identity"), in_identity,
                        "<value of type const ::service_manager::Identity&>");
      perfetto::WriteIntoTracedValueWithFallback(
           dict.AddItem("pid_deprecated"), in_pid_deprecated,
                        "<value of type uint32_t>");
   });
#endif
  const bool kExpectsResponse = false;
  const bool kIsSync = false;
  const bool kAllowInterrupt = true;
  
  const uint32_t kFlags =
      ((kExpectsResponse) ? mojo::Message::kFlagExpectsResponse : 0) |
      ((kIsSync) ? mojo::Message::kFlagIsSync : 0) |
      ((kAllowInterrupt) ? 0 : mojo::Message::kFlagNoInterrupt);
  
  mojo::Message message(
      internal::kServiceManagerListener_OnServiceStarted_Name, kFlags, 0, 0, nullptr);
  mojo::internal::MessageFragment<
      ::service_manager::mojom::internal::ServiceManagerListener_OnServiceStarted_Params_Data> params(
          message);
  params.Allocate();
  mojo::internal::MessageFragment<
      typename decltype(params->identity)::BaseType> identity_fragment(
          params.message());
  mojo::internal::Serialize<::service_manager::mojom::IdentityDataView>(
      in_identity, identity_fragment);
  params->identity.Set(
      identity_fragment.is_null() ? nullptr : identity_fragment.data());
  MOJO_INTERNAL_DLOG_SERIALIZATION_WARNING(
      params->identity.is_null(),
      mojo::internal::VALIDATION_ERROR_UNEXPECTED_NULL_POINTER,
      "null identity in ServiceManagerListener.OnServiceStarted request");
  params->pid_deprecated = in_pid_deprecated;

#if defined(ENABLE_IPC_FUZZER)
  message.set_interface_name(ServiceManagerListener::Name_);
  message.set_method_name("OnServiceStarted");
#endif
  // This return value may be ignored as false implies the Connector has
  // encountered an error, which will be visible through other means.
  ::mojo::internal::SendMessage(*receiver_, message);
}

void ServiceManagerListenerProxy::OnServicePIDReceived(
    const ::service_manager::Identity& in_identity, uint32_t in_pid) {
#if BUILDFLAG(MOJO_TRACE_ENABLED)
  TRACE_EVENT1(
    "mojom", "Send service_manager::mojom::ServiceManagerListener::OnServicePIDReceived", "input_parameters",
    [&](perfetto::TracedValue context){
      auto dict = std::move(context).WriteDictionary();
      perfetto::WriteIntoTracedValueWithFallback(
           dict.AddItem("identity"), in_identity,
                        "<value of type const ::service_manager::Identity&>");
      perfetto::WriteIntoTracedValueWithFallback(
           dict.AddItem("pid"), in_pid,
                        "<value of type uint32_t>");
   });
#endif
  const bool kExpectsResponse = false;
  const bool kIsSync = false;
  const bool kAllowInterrupt = true;
  
  const uint32_t kFlags =
      ((kExpectsResponse) ? mojo::Message::kFlagExpectsResponse : 0) |
      ((kIsSync) ? mojo::Message::kFlagIsSync : 0) |
      ((kAllowInterrupt) ? 0 : mojo::Message::kFlagNoInterrupt);
  
  mojo::Message message(
      internal::kServiceManagerListener_OnServicePIDReceived_Name, kFlags, 0, 0, nullptr);
  mojo::internal::MessageFragment<
      ::service_manager::mojom::internal::ServiceManagerListener_OnServicePIDReceived_Params_Data> params(
          message);
  params.Allocate();
  mojo::internal::MessageFragment<
      typename decltype(params->identity)::BaseType> identity_fragment(
          params.message());
  mojo::internal::Serialize<::service_manager::mojom::IdentityDataView>(
      in_identity, identity_fragment);
  params->identity.Set(
      identity_fragment.is_null() ? nullptr : identity_fragment.data());
  MOJO_INTERNAL_DLOG_SERIALIZATION_WARNING(
      params->identity.is_null(),
      mojo::internal::VALIDATION_ERROR_UNEXPECTED_NULL_POINTER,
      "null identity in ServiceManagerListener.OnServicePIDReceived request");
  params->pid = in_pid;

#if defined(ENABLE_IPC_FUZZER)
  message.set_interface_name(ServiceManagerListener::Name_);
  message.set_method_name("OnServicePIDReceived");
#endif
  // This return value may be ignored as false implies the Connector has
  // encountered an error, which will be visible through other means.
  ::mojo::internal::SendMessage(*receiver_, message);
}

void ServiceManagerListenerProxy::OnServiceFailedToStart(
    const ::service_manager::Identity& in_identity) {
#if BUILDFLAG(MOJO_TRACE_ENABLED)
  TRACE_EVENT1(
    "mojom", "Send service_manager::mojom::ServiceManagerListener::OnServiceFailedToStart", "input_parameters",
    [&](perfetto::TracedValue context){
      auto dict = std::move(context).WriteDictionary();
      perfetto::WriteIntoTracedValueWithFallback(
           dict.AddItem("identity"), in_identity,
                        "<value of type const ::service_manager::Identity&>");
   });
#endif
  const bool kExpectsResponse = false;
  const bool kIsSync = false;
  const bool kAllowInterrupt = true;
  
  const uint32_t kFlags =
      ((kExpectsResponse) ? mojo::Message::kFlagExpectsResponse : 0) |
      ((kIsSync) ? mojo::Message::kFlagIsSync : 0) |
      ((kAllowInterrupt) ? 0 : mojo::Message::kFlagNoInterrupt);
  
  mojo::Message message(
      internal::kServiceManagerListener_OnServiceFailedToStart_Name, kFlags, 0, 0, nullptr);
  mojo::internal::MessageFragment<
      ::service_manager::mojom::internal::ServiceManagerListener_OnServiceFailedToStart_Params_Data> params(
          message);
  params.Allocate();
  mojo::internal::MessageFragment<
      typename decltype(params->identity)::BaseType> identity_fragment(
          params.message());
  mojo::internal::Serialize<::service_manager::mojom::IdentityDataView>(
      in_identity, identity_fragment);
  params->identity.Set(
      identity_fragment.is_null() ? nullptr : identity_fragment.data());
  MOJO_INTERNAL_DLOG_SERIALIZATION_WARNING(
      params->identity.is_null(),
      mojo::internal::VALIDATION_ERROR_UNEXPECTED_NULL_POINTER,
      "null identity in ServiceManagerListener.OnServiceFailedToStart request");

#if defined(ENABLE_IPC_FUZZER)
  message.set_interface_name(ServiceManagerListener::Name_);
  message.set_method_name("OnServiceFailedToStart");
#endif
  // This return value may be ignored as false implies the Connector has
  // encountered an error, which will be visible through other means.
  ::mojo::internal::SendMessage(*receiver_, message);
}

void ServiceManagerListenerProxy::OnServiceStopped(
    const ::service_manager::Identity& in_identity) {
#if BUILDFLAG(MOJO_TRACE_ENABLED)
  TRACE_EVENT1(
    "mojom", "Send service_manager::mojom::ServiceManagerListener::OnServiceStopped", "input_parameters",
    [&](perfetto::TracedValue context){
      auto dict = std::move(context).WriteDictionary();
      perfetto::WriteIntoTracedValueWithFallback(
           dict.AddItem("identity"), in_identity,
                        "<value of type const ::service_manager::Identity&>");
   });
#endif
  const bool kExpectsResponse = false;
  const bool kIsSync = false;
  const bool kAllowInterrupt = true;
  
  const uint32_t kFlags =
      ((kExpectsResponse) ? mojo::Message::kFlagExpectsResponse : 0) |
      ((kIsSync) ? mojo::Message::kFlagIsSync : 0) |
      ((kAllowInterrupt) ? 0 : mojo::Message::kFlagNoInterrupt);
  
  mojo::Message message(
      internal::kServiceManagerListener_OnServiceStopped_Name, kFlags, 0, 0, nullptr);
  mojo::internal::MessageFragment<
      ::service_manager::mojom::internal::ServiceManagerListener_OnServiceStopped_Params_Data> params(
          message);
  params.Allocate();
  mojo::internal::MessageFragment<
      typename decltype(params->identity)::BaseType> identity_fragment(
          params.message());
  mojo::internal::Serialize<::service_manager::mojom::IdentityDataView>(
      in_identity, identity_fragment);
  params->identity.Set(
      identity_fragment.is_null() ? nullptr : identity_fragment.data());
  MOJO_INTERNAL_DLOG_SERIALIZATION_WARNING(
      params->identity.is_null(),
      mojo::internal::VALIDATION_ERROR_UNEXPECTED_NULL_POINTER,
      "null identity in ServiceManagerListener.OnServiceStopped request");

#if defined(ENABLE_IPC_FUZZER)
  message.set_interface_name(ServiceManagerListener::Name_);
  message.set_method_name("OnServiceStopped");
#endif
  // This return value may be ignored as false implies the Connector has
  // encountered an error, which will be visible through other means.
  ::mojo::internal::SendMessage(*receiver_, message);
}

// static
bool ServiceManagerListenerStubDispatch::Accept(
    ServiceManagerListener* impl,
    mojo::Message* message) {
  switch (message->header()->name) {
    case internal::kServiceManagerListener_OnInit_Name: {

      DCHECK(message->is_serialized());
      internal::ServiceManagerListener_OnInit_Params_Data* params =
          reinterpret_cast<internal::ServiceManagerListener_OnInit_Params_Data*>(
              message->mutable_payload());
      
      bool success = true;
      std::vector<RunningServiceInfoPtr> p_running_services{};
      ServiceManagerListener_OnInit_ParamsDataView input_data_view(params, message);
      
      if (success && !input_data_view.ReadRunningServices(&p_running_services))
        success = false;
      if (!success) {
        ReportValidationErrorForMessage(
            message,
            mojo::internal::VALIDATION_ERROR_DESERIALIZATION_FAILED,
            ServiceManagerListener::Name_, 0, false);
        return false;
      }
      // A null |impl| means no implementation was bound.
      DCHECK(impl);
      impl->OnInit(
std::move(p_running_services));
      return true;
    }
    case internal::kServiceManagerListener_OnServiceCreated_Name: {

      DCHECK(message->is_serialized());
      internal::ServiceManagerListener_OnServiceCreated_Params_Data* params =
          reinterpret_cast<internal::ServiceManagerListener_OnServiceCreated_Params_Data*>(
              message->mutable_payload());
      
      bool success = true;
      RunningServiceInfoPtr p_service{};
      ServiceManagerListener_OnServiceCreated_ParamsDataView input_data_view(params, message);
      
      if (success && !input_data_view.ReadService(&p_service))
        success = false;
      if (!success) {
        ReportValidationErrorForMessage(
            message,
            mojo::internal::VALIDATION_ERROR_DESERIALIZATION_FAILED,
            ServiceManagerListener::Name_, 1, false);
        return false;
      }
      // A null |impl| means no implementation was bound.
      DCHECK(impl);
      impl->OnServiceCreated(
std::move(p_service));
      return true;
    }
    case internal::kServiceManagerListener_OnServiceStarted_Name: {

      DCHECK(message->is_serialized());
      internal::ServiceManagerListener_OnServiceStarted_Params_Data* params =
          reinterpret_cast<internal::ServiceManagerListener_OnServiceStarted_Params_Data*>(
              message->mutable_payload());
      
      bool success = true;
      ::service_manager::Identity p_identity{};
      uint32_t p_pid_deprecated{};
      ServiceManagerListener_OnServiceStarted_ParamsDataView input_data_view(params, message);
      
      if (success && !input_data_view.ReadIdentity(&p_identity))
        success = false;
      if (success)
        p_pid_deprecated = input_data_view.pid_deprecated();
      if (!success) {
        ReportValidationErrorForMessage(
            message,
            mojo::internal::VALIDATION_ERROR_DESERIALIZATION_FAILED,
            ServiceManagerListener::Name_, 2, false);
        return false;
      }
      // A null |impl| means no implementation was bound.
      DCHECK(impl);
      impl->OnServiceStarted(
std::move(p_identity), 
std::move(p_pid_deprecated));
      return true;
    }
    case internal::kServiceManagerListener_OnServicePIDReceived_Name: {

      DCHECK(message->is_serialized());
      internal::ServiceManagerListener_OnServicePIDReceived_Params_Data* params =
          reinterpret_cast<internal::ServiceManagerListener_OnServicePIDReceived_Params_Data*>(
              message->mutable_payload());
      
      bool success = true;
      ::service_manager::Identity p_identity{};
      uint32_t p_pid{};
      ServiceManagerListener_OnServicePIDReceived_ParamsDataView input_data_view(params, message);
      
      if (success && !input_data_view.ReadIdentity(&p_identity))
        success = false;
      if (success)
        p_pid = input_data_view.pid();
      if (!success) {
        ReportValidationErrorForMessage(
            message,
            mojo::internal::VALIDATION_ERROR_DESERIALIZATION_FAILED,
            ServiceManagerListener::Name_, 3, false);
        return false;
      }
      // A null |impl| means no implementation was bound.
      DCHECK(impl);
      impl->OnServicePIDReceived(
std::move(p_identity), 
std::move(p_pid));
      return true;
    }
    case internal::kServiceManagerListener_OnServiceFailedToStart_Name: {

      DCHECK(message->is_serialized());
      internal::ServiceManagerListener_OnServiceFailedToStart_Params_Data* params =
          reinterpret_cast<internal::ServiceManagerListener_OnServiceFailedToStart_Params_Data*>(
              message->mutable_payload());
      
      bool success = true;
      ::service_manager::Identity p_identity{};
      ServiceManagerListener_OnServiceFailedToStart_ParamsDataView input_data_view(params, message);
      
      if (success && !input_data_view.ReadIdentity(&p_identity))
        success = false;
      if (!success) {
        ReportValidationErrorForMessage(
            message,
            mojo::internal::VALIDATION_ERROR_DESERIALIZATION_FAILED,
            ServiceManagerListener::Name_, 4, false);
        return false;
      }
      // A null |impl| means no implementation was bound.
      DCHECK(impl);
      impl->OnServiceFailedToStart(
std::move(p_identity));
      return true;
    }
    case internal::kServiceManagerListener_OnServiceStopped_Name: {

      DCHECK(message->is_serialized());
      internal::ServiceManagerListener_OnServiceStopped_Params_Data* params =
          reinterpret_cast<internal::ServiceManagerListener_OnServiceStopped_Params_Data*>(
              message->mutable_payload());
      
      bool success = true;
      ::service_manager::Identity p_identity{};
      ServiceManagerListener_OnServiceStopped_ParamsDataView input_data_view(params, message);
      
      if (success && !input_data_view.ReadIdentity(&p_identity))
        success = false;
      if (!success) {
        ReportValidationErrorForMessage(
            message,
            mojo::internal::VALIDATION_ERROR_DESERIALIZATION_FAILED,
            ServiceManagerListener::Name_, 5, false);
        return false;
      }
      // A null |impl| means no implementation was bound.
      DCHECK(impl);
      impl->OnServiceStopped(
std::move(p_identity));
      return true;
    }
  }
  return false;
}

// static
bool ServiceManagerListenerStubDispatch::AcceptWithResponder(
    ServiceManagerListener* impl,
    mojo::Message* message,
    std::unique_ptr<mojo::MessageReceiverWithStatus> responder) {
  [[maybe_unused]] const bool message_is_sync =
      message->has_flag(mojo::Message::kFlagIsSync);
  [[maybe_unused]] const uint64_t request_id = message->request_id();
  switch (message->header()->name) {
    case internal::kServiceManagerListener_OnInit_Name: {
      break;
    }
    case internal::kServiceManagerListener_OnServiceCreated_Name: {
      break;
    }
    case internal::kServiceManagerListener_OnServiceStarted_Name: {
      break;
    }
    case internal::kServiceManagerListener_OnServicePIDReceived_Name: {
      break;
    }
    case internal::kServiceManagerListener_OnServiceFailedToStart_Name: {
      break;
    }
    case internal::kServiceManagerListener_OnServiceStopped_Name: {
      break;
    }
  }
  return false;
}


static const mojo::internal::GenericValidationInfo kServiceManagerListenerValidationInfo[] = {
    {&internal::ServiceManagerListener_OnInit_Params_Data::Validate,
     nullptr /* no response */},
    {&internal::ServiceManagerListener_OnServiceCreated_Params_Data::Validate,
     nullptr /* no response */},
    {&internal::ServiceManagerListener_OnServiceStarted_Params_Data::Validate,
     nullptr /* no response */},
    {&internal::ServiceManagerListener_OnServicePIDReceived_Params_Data::Validate,
     nullptr /* no response */},
    {&internal::ServiceManagerListener_OnServiceFailedToStart_Params_Data::Validate,
     nullptr /* no response */},
    {&internal::ServiceManagerListener_OnServiceStopped_Params_Data::Validate,
     nullptr /* no response */},
};

bool ServiceManagerListenerRequestValidator::Accept(mojo::Message* message) {
  const char* name = ::service_manager::mojom::ServiceManagerListener::Name_;
  return mojo::internal::ValidateRequestGenericPacked(message, name, kServiceManagerListenerValidationInfo);
}

const char ServiceManager::Name_[] = "service_manager.mojom.ServiceManager";

std::pair<uint32_t, const void*> ServiceManager::MessageToMethodInfo_(mojo::Message& message) {
  switch (message.name()) {
    case internal::kServiceManager_AddListener_Name: {
      constexpr uint32_t value = base::MD5Hash32Constexpr(
              "(Impl)service_manager::mojom::ServiceManager::AddListener");
#if BUILDFLAG(IS_FUCHSIA)
        return std::make_pair(value, nullptr);
#else
        return std::make_pair(value, reinterpret_cast<const void*>(&ServiceManager::AddListener_Sym::IPCSymbol));
#endif // BUILDFLAG(IS_FUCHSIA)
    }
  }
  return std::make_pair(0, nullptr);
}


const char* ServiceManager::MessageToMethodName_(mojo::Message& message) {
#if BUILDFLAG(MOJO_TRACE_ENABLED)
  bool is_response = message.has_flag(mojo::Message::kFlagIsResponse);
  if (!is_response) {
    switch (message.name()) {
      case internal::kServiceManager_AddListener_Name:
            return "Receive service_manager::mojom::ServiceManager::AddListener";
    }
  } else {
    switch (message.name()) {
      case internal::kServiceManager_AddListener_Name:
            return "Receive reply service_manager::mojom::ServiceManager::AddListener";
    }
  }
  return "Receive unknown mojo message";
#else
  bool is_response = message.has_flag(mojo::Message::kFlagIsResponse);
  if (is_response) {
    return "Receive mojo reply";
  } else {
    return "Receive mojo message";
  }
#endif // BUILDFLAG(MOJO_TRACE_ENABLED)
}

#if !BUILDFLAG(IS_FUCHSIA)
void ServiceManager::AddListener_Sym::IPCSymbol() {
  // This method's address is used for indetifiying the mojo method name after
  // symblozation. So each IPCSymbol should have a unique address.
  NO_CODE_FOLDING();
}
# endif // !BUILDFLAG(IS_FUCHSIA)

ServiceManagerProxy::ServiceManagerProxy(mojo::MessageReceiverWithResponder* receiver)
    : receiver_(receiver) {
}

void ServiceManagerProxy::AddListener(
    ::mojo::PendingRemote<ServiceManagerListener> in_listener) {
#if BUILDFLAG(MOJO_TRACE_ENABLED)
  TRACE_EVENT1(
    "mojom", "Send service_manager::mojom::ServiceManager::AddListener", "input_parameters",
    [&](perfetto::TracedValue context){
      auto dict = std::move(context).WriteDictionary();
      perfetto::WriteIntoTracedValueWithFallback(
           dict.AddItem("listener"), in_listener,
                        "<value of type ::mojo::PendingRemote<ServiceManagerListener>>");
   });
#endif
  const bool kExpectsResponse = false;
  const bool kIsSync = false;
  const bool kAllowInterrupt = true;
  
  const uint32_t kFlags =
      ((kExpectsResponse) ? mojo::Message::kFlagExpectsResponse : 0) |
      ((kIsSync) ? mojo::Message::kFlagIsSync : 0) |
      ((kAllowInterrupt) ? 0 : mojo::Message::kFlagNoInterrupt);
  
  mojo::Message message(
      internal::kServiceManager_AddListener_Name, kFlags, 0, 0, nullptr);
  mojo::internal::MessageFragment<
      ::service_manager::mojom::internal::ServiceManager_AddListener_Params_Data> params(
          message);
  params.Allocate();
  mojo::internal::Serialize<mojo::InterfacePtrDataView<::service_manager::mojom::ServiceManagerListenerInterfaceBase>>(
      in_listener, &params->listener, &params.message());
  MOJO_INTERNAL_DLOG_SERIALIZATION_WARNING(
      !mojo::internal::IsHandleOrInterfaceValid(params->listener),
      mojo::internal::VALIDATION_ERROR_UNEXPECTED_INVALID_HANDLE,
      "invalid listener in ServiceManager.AddListener request");

#if defined(ENABLE_IPC_FUZZER)
  message.set_interface_name(ServiceManager::Name_);
  message.set_method_name("AddListener");
#endif
  // This return value may be ignored as false implies the Connector has
  // encountered an error, which will be visible through other means.
  ::mojo::internal::SendMessage(*receiver_, message);
}

// static
bool ServiceManagerStubDispatch::Accept(
    ServiceManager* impl,
    mojo::Message* message) {
  switch (message->header()->name) {
    case internal::kServiceManager_AddListener_Name: {

      DCHECK(message->is_serialized());
      internal::ServiceManager_AddListener_Params_Data* params =
          reinterpret_cast<internal::ServiceManager_AddListener_Params_Data*>(
              message->mutable_payload());
      
      bool success = true;
      ::mojo::PendingRemote<ServiceManagerListener> p_listener{};
      ServiceManager_AddListener_ParamsDataView input_data_view(params, message);
      
      if (success) {
        p_listener =
            input_data_view.TakeListener<decltype(p_listener)>();
      }
      if (!success) {
        ReportValidationErrorForMessage(
            message,
            mojo::internal::VALIDATION_ERROR_DESERIALIZATION_FAILED,
            ServiceManager::Name_, 0, false);
        return false;
      }
      // A null |impl| means no implementation was bound.
      DCHECK(impl);
      impl->AddListener(
std::move(p_listener));
      return true;
    }
  }
  return false;
}

// static
bool ServiceManagerStubDispatch::AcceptWithResponder(
    ServiceManager* impl,
    mojo::Message* message,
    std::unique_ptr<mojo::MessageReceiverWithStatus> responder) {
  [[maybe_unused]] const bool message_is_sync =
      message->has_flag(mojo::Message::kFlagIsSync);
  [[maybe_unused]] const uint64_t request_id = message->request_id();
  switch (message->header()->name) {
    case internal::kServiceManager_AddListener_Name: {
      break;
    }
  }
  return false;
}


static const mojo::internal::GenericValidationInfo kServiceManagerValidationInfo[] = {
    {&internal::ServiceManager_AddListener_Params_Data::Validate,
     nullptr /* no response */},
};

bool ServiceManagerRequestValidator::Accept(mojo::Message* message) {
  const char* name = ::service_manager::mojom::ServiceManager::Name_;
  return mojo::internal::ValidateRequestGenericPacked(message, name, kServiceManagerValidationInfo);
}



}  // namespace mojom
}  // namespace service_manager


namespace mojo {


// static
bool StructTraits<::service_manager::mojom::RunningServiceInfo::DataView, ::service_manager::mojom::RunningServiceInfoPtr>::Read(
    ::service_manager::mojom::RunningServiceInfo::DataView input,
    ::service_manager::mojom::RunningServiceInfoPtr* output) {
  bool success = true;
  ::service_manager::mojom::RunningServiceInfoPtr result(::service_manager::mojom::RunningServiceInfo::New());
  
      if (success && !input.ReadIdentity(&result->identity))
        success = false;
      if (success)
        result->pid = input.pid();
      if (success && !input.ReadState(&result->state))
        success = false;
  *output = std::move(result);
  return success;
}

}  // namespace mojo


// Symbols declared in the -test-utils.h header are defined here instead of a
// separate .cc file to save compile time.


namespace service_manager {
namespace mojom {


void ServiceManagerListenerInterceptorForTesting::OnInit(std::vector<RunningServiceInfoPtr> running_services) {
  GetForwardingInterface()->OnInit(std::move(running_services));
}
void ServiceManagerListenerInterceptorForTesting::OnServiceCreated(RunningServiceInfoPtr service) {
  GetForwardingInterface()->OnServiceCreated(std::move(service));
}
void ServiceManagerListenerInterceptorForTesting::OnServiceStarted(const ::service_manager::Identity& identity, uint32_t pid_deprecated) {
  GetForwardingInterface()->OnServiceStarted(std::move(identity), std::move(pid_deprecated));
}
void ServiceManagerListenerInterceptorForTesting::OnServicePIDReceived(const ::service_manager::Identity& identity, uint32_t pid) {
  GetForwardingInterface()->OnServicePIDReceived(std::move(identity), std::move(pid));
}
void ServiceManagerListenerInterceptorForTesting::OnServiceFailedToStart(const ::service_manager::Identity& identity) {
  GetForwardingInterface()->OnServiceFailedToStart(std::move(identity));
}
void ServiceManagerListenerInterceptorForTesting::OnServiceStopped(const ::service_manager::Identity& identity) {
  GetForwardingInterface()->OnServiceStopped(std::move(identity));
}
ServiceManagerListenerAsyncWaiter::ServiceManagerListenerAsyncWaiter(
    ServiceManagerListener* proxy) : proxy_(proxy) {}

ServiceManagerListenerAsyncWaiter::~ServiceManagerListenerAsyncWaiter() = default;




void ServiceManagerInterceptorForTesting::AddListener(::mojo::PendingRemote<ServiceManagerListener> listener) {
  GetForwardingInterface()->AddListener(std::move(listener));
}
ServiceManagerAsyncWaiter::ServiceManagerAsyncWaiter(
    ServiceManager* proxy) : proxy_(proxy) {}

ServiceManagerAsyncWaiter::~ServiceManagerAsyncWaiter() = default;






}  // namespace mojom
}  // namespace service_manager


#if defined(__clang__)
#pragma clang diagnostic pop
#endif