普通文本  |  655行  |  18.89 KB

// Copyright (c) 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.

#include "ppapi/cpp/extensions/dev/socket_dev.h"

#include "ppapi/cpp/completion_callback.h"
#include "ppapi/cpp/extensions/optional.h"
#include "ppapi/cpp/extensions/to_var_converter.h"
#include "ppapi/cpp/logging.h"
#include "ppapi/cpp/module_impl.h"

namespace pp {

namespace {

template <> const char* interface_name<PPB_Ext_Socket_Dev_0_2>() {
  return PPB_EXT_SOCKET_DEV_INTERFACE_0_2;
}

}  // namespace

namespace ext {
namespace socket {

const char* const SocketType_Dev::kTcp = "tcp";
const char* const SocketType_Dev::kUdp = "udp";

SocketType_Dev::SocketType_Dev() : value(NONE) {
}

SocketType_Dev::SocketType_Dev(ValueType in_value) : value(in_value) {
}

SocketType_Dev::~SocketType_Dev() {
}

bool SocketType_Dev::Populate(const PP_Var& var_value) {
  if (var_value.type != PP_VARTYPE_STRING)
    return false;

  std::string string_value = Var(var_value).AsString();
  if (string_value == kTcp) {
    value = TCP;
  } else if (string_value == kUdp) {
    value = UDP;
  } else {
    value = NONE;
    return false;
  }
  return true;
}

Var SocketType_Dev::CreateVar() const {
  switch (value) {
    case TCP:
      return Var(kTcp);
    case UDP:
      return Var(kUdp);
    default:
      PP_NOTREACHED();
      return Var(std::string());
  }
}

const char* const CreateInfo_Dev::kSocketId = "socketId";

CreateInfo_Dev::CreateInfo_Dev()
    : socket_id(kSocketId) {
}

CreateInfo_Dev::~CreateInfo_Dev() {
}

bool CreateInfo_Dev::Populate(const PP_Ext_Socket_CreateInfo_Dev& value) {
  if (value.type != PP_VARTYPE_DICTIONARY)
    return false;

  VarDictionary dict(value);
  bool result = socket_id.Populate(dict);

  return result;
}

Var CreateInfo_Dev::CreateVar() const {
  VarDictionary dict;

  bool result = socket_id.AddTo(&dict);
  // Suppress unused variable warnings.
  static_cast<void>(result);
  PP_DCHECK(result);

  return dict;
}

const char* const AcceptInfo_Dev::kResultCode = "resultCode";
const char* const AcceptInfo_Dev::kSocketId = "socketId";

AcceptInfo_Dev::AcceptInfo_Dev()
    : result_code(kResultCode),
      socket_id(kSocketId) {
}

AcceptInfo_Dev::~AcceptInfo_Dev() {
}

bool AcceptInfo_Dev::Populate(const PP_Ext_Socket_AcceptInfo_Dev& value) {
  if (value.type != PP_VARTYPE_DICTIONARY)
    return false;

  VarDictionary dict(value);
  bool result = result_code.Populate(dict);
  result = socket_id.Populate(dict) && result;

  return result;
}

Var AcceptInfo_Dev::CreateVar() const {
  VarDictionary dict;

  bool result = result_code.AddTo(&dict);
  result = socket_id.MayAddTo(&dict) && result;
  PP_DCHECK(result);

  return dict;
}

const char* const ReadInfo_Dev::kResultCode = "resultCode";
const char* const ReadInfo_Dev::kData = "data";

ReadInfo_Dev::ReadInfo_Dev()
    : result_code(kResultCode),
      data(kData) {
}

ReadInfo_Dev::~ReadInfo_Dev() {
}

bool ReadInfo_Dev::Populate(const PP_Ext_Socket_ReadInfo_Dev& value) {
  if (value.type != PP_VARTYPE_DICTIONARY)
    return false;

  VarDictionary dict(value);
  bool result = result_code.Populate(dict);
  result = data.Populate(dict) && result;

  return result;
}

Var ReadInfo_Dev::CreateVar() const {
  VarDictionary dict;

  bool result = result_code.AddTo(&dict);
  result = data.AddTo(&dict) && result;
  PP_DCHECK(result);

  return dict;
}

const char* const WriteInfo_Dev::kBytesWritten = "bytesWritten";

WriteInfo_Dev::WriteInfo_Dev()
    : bytes_written(kBytesWritten) {
}

WriteInfo_Dev::~WriteInfo_Dev() {
}

bool WriteInfo_Dev::Populate(const PP_Ext_Socket_WriteInfo_Dev& value) {
  if (value.type != PP_VARTYPE_DICTIONARY)
    return false;

  VarDictionary dict(value);
  bool result = bytes_written.Populate(dict);

  return result;
}

Var WriteInfo_Dev::CreateVar() const {
  VarDictionary dict;

  bool result = bytes_written.AddTo(&dict);
  // Suppress unused variable warnings.
  static_cast<void>(result);
  PP_DCHECK(result);

  return dict;
}

const char* const RecvFromInfo_Dev::kResultCode = "resultCode";
const char* const RecvFromInfo_Dev::kData = "data";
const char* const RecvFromInfo_Dev::kAddress = "address";
const char* const RecvFromInfo_Dev::kPort = "port";

RecvFromInfo_Dev::RecvFromInfo_Dev()
    : result_code(kResultCode),
      data(kData),
      address(kAddress),
      port(kPort) {
}

RecvFromInfo_Dev::~RecvFromInfo_Dev() {
}

bool RecvFromInfo_Dev::Populate(const PP_Ext_Socket_RecvFromInfo_Dev& value) {
  if (value.type != PP_VARTYPE_DICTIONARY)
    return false;

  VarDictionary dict(value);
  bool result = result_code.Populate(dict);
  result = data.Populate(dict) && result;
  result = address.Populate(dict) && result;
  result = port.Populate(dict) && result;

  return result;
}

Var RecvFromInfo_Dev::CreateVar() const {
  VarDictionary dict;

  bool result = result_code.AddTo(&dict);
  result = data.AddTo(&dict) && result;
  result = address.AddTo(&dict) && result;
  result = port.AddTo(&dict) && result;
  PP_DCHECK(result);

  return dict;
}

const char* const SocketInfo_Dev::kSocketType = "socketType";
const char* const SocketInfo_Dev::kConnected = "connected";
const char* const SocketInfo_Dev::kPeerAddress = "peerAddress";
const char* const SocketInfo_Dev::kPeerPort = "peerPort";
const char* const SocketInfo_Dev::kLocalAddress = "localAddress";
const char* const SocketInfo_Dev::kLocalPort = "localPort";

SocketInfo_Dev::SocketInfo_Dev()
    : socket_type(kSocketType),
      connected(kConnected),
      peer_address(kPeerAddress),
      peer_port(kPeerPort),
      local_address(kLocalAddress),
      local_port(kLocalPort) {
}

SocketInfo_Dev::~SocketInfo_Dev() {
}

bool SocketInfo_Dev::Populate(const PP_Ext_Socket_SocketInfo_Dev& value) {
  if (value.type != PP_VARTYPE_DICTIONARY)
    return false;

  VarDictionary dict(value);
  bool result = socket_type.Populate(dict);
  result = connected.Populate(dict) && result;
  result = peer_address.Populate(dict) && result;
  result = peer_port.Populate(dict) && result;
  result = local_address.Populate(dict) && result;
  result = local_port.Populate(dict) && result;

  return result;
}

Var SocketInfo_Dev::CreateVar() const {
  VarDictionary dict;

  bool result = socket_type.AddTo(&dict);
  result = connected.AddTo(&dict) && result;
  result = peer_address.MayAddTo(&dict) && result;
  result = peer_port.MayAddTo(&dict) && result;
  result = local_address.MayAddTo(&dict) && result;
  result = local_port.MayAddTo(&dict) && result;
  PP_DCHECK(result);

  return dict;
}

const char* const NetworkInterface_Dev::kName = "name";
const char* const NetworkInterface_Dev::kAddress = "address";

NetworkInterface_Dev::NetworkInterface_Dev()
    : name(kName),
      address(kAddress) {
}

NetworkInterface_Dev::~NetworkInterface_Dev() {
}

bool NetworkInterface_Dev::Populate(
    const PP_Ext_Socket_NetworkInterface_Dev& value) {
  if (value.type != PP_VARTYPE_DICTIONARY)
    return false;

  VarDictionary dict(value);
  bool result = name.Populate(dict);
  result = address.Populate(dict) && result;

  return result;
}

Var NetworkInterface_Dev::CreateVar() const {
  VarDictionary dict;

  bool result = name.AddTo(&dict);
  result = address.AddTo(&dict) && result;
  PP_DCHECK(result);

  return dict;
}

Socket_Dev::Socket_Dev(const InstanceHandle& instance) : instance_(instance) {
}

Socket_Dev::~Socket_Dev() {
}

int32_t Socket_Dev::Create(const SocketType_Dev& type,
                           const Optional<CreateOptions_Dev>& options,
                           const CreateCallback& callback) {
  if (!has_interface<PPB_Ext_Socket_Dev_0_2>())
    return callback.MayForce(PP_ERROR_NOINTERFACE);

  internal::ToVarConverter<SocketType_Dev> type_var(type);
  internal::ToVarConverter<Optional<CreateOptions_Dev> > options_var(options);

  return get_interface<PPB_Ext_Socket_Dev_0_2>()->Create(
      instance_.pp_instance(),
      type_var.pp_var(),
      options_var.pp_var(),
      callback.output(),
      callback.pp_completion_callback());
}

void Socket_Dev::Destroy(int32_t socket_id) {
  if (!has_interface<PPB_Ext_Socket_Dev_0_2>())
    return;

  internal::ToVarConverter<int32_t> socket_id_var(socket_id);

  return get_interface<PPB_Ext_Socket_Dev_0_2>()->Destroy(
      instance_.pp_instance(),
      socket_id_var.pp_var());
}

int32_t Socket_Dev::Connect(int32_t socket_id,
                            const std::string& hostname,
                            int32_t port,
                            const ConnectCallback& callback) {
  if (!has_interface<PPB_Ext_Socket_Dev_0_2>())
    return callback.MayForce(PP_ERROR_NOINTERFACE);

  internal::ToVarConverter<int32_t> socket_id_var(socket_id);
  internal::ToVarConverter<std::string> hostname_var(hostname);
  internal::ToVarConverter<int32_t> port_var(port);

  return get_interface<PPB_Ext_Socket_Dev_0_2>()->Connect(
      instance_.pp_instance(),
      socket_id_var.pp_var(),
      hostname_var.pp_var(),
      port_var.pp_var(),
      callback.output(),
      callback.pp_completion_callback());
}

int32_t Socket_Dev::Bind(int32_t socket_id,
                         const std::string& address,
                         int32_t port,
                         const BindCallback& callback) {
  if (!has_interface<PPB_Ext_Socket_Dev_0_2>())
    return callback.MayForce(PP_ERROR_NOINTERFACE);

  internal::ToVarConverter<int32_t> socket_id_var(socket_id);
  internal::ToVarConverter<std::string> address_var(address);
  internal::ToVarConverter<int32_t> port_var(port);

  return get_interface<PPB_Ext_Socket_Dev_0_2>()->Bind(
      instance_.pp_instance(),
      socket_id_var.pp_var(),
      address_var.pp_var(),
      port_var.pp_var(),
      callback.output(),
      callback.pp_completion_callback());
}

void Socket_Dev::Disconnect(int32_t socket_id) {
  if (!has_interface<PPB_Ext_Socket_Dev_0_2>())
    return;

  internal::ToVarConverter<int32_t> socket_id_var(socket_id);

  return get_interface<PPB_Ext_Socket_Dev_0_2>()->Disconnect(
      instance_.pp_instance(),
      socket_id_var.pp_var());
}

int32_t Socket_Dev::Read(int32_t socket_id,
                         const Optional<int32_t>& buffer_size,
                         const ReadCallback& callback) {
  if (!has_interface<PPB_Ext_Socket_Dev_0_2>())
    return callback.MayForce(PP_ERROR_NOINTERFACE);

  internal::ToVarConverter<int32_t> socket_id_var(socket_id);
  internal::ToVarConverter<Optional<int32_t> > buffer_size_var(buffer_size);

  return get_interface<PPB_Ext_Socket_Dev_0_2>()->Read(
      instance_.pp_instance(),
      socket_id_var.pp_var(),
      buffer_size_var.pp_var(),
      callback.output(),
      callback.pp_completion_callback());
}

int32_t Socket_Dev::Write(int32_t socket_id,
                          const VarArrayBuffer& data,
                          const WriteCallback& callback) {
  if (!has_interface<PPB_Ext_Socket_Dev_0_2>())
    return callback.MayForce(PP_ERROR_NOINTERFACE);

  internal::ToVarConverter<int32_t> socket_id_var(socket_id);
  internal::ToVarConverter<Var> data_var(data);

  return get_interface<PPB_Ext_Socket_Dev_0_2>()->Write(
      instance_.pp_instance(),
      socket_id_var.pp_var(),
      data_var.pp_var(),
      callback.output(),
      callback.pp_completion_callback());
}

int32_t Socket_Dev::RecvFrom(int32_t socket_id,
                             const Optional<int32_t>& buffer_size,
                             const RecvFromCallback& callback) {
  if (!has_interface<PPB_Ext_Socket_Dev_0_2>())
    return callback.MayForce(PP_ERROR_NOINTERFACE);

  internal::ToVarConverter<int32_t> socket_id_var(socket_id);
  internal::ToVarConverter<Optional<int32_t> > buffer_size_var(buffer_size);

  return get_interface<PPB_Ext_Socket_Dev_0_2>()->RecvFrom(
      instance_.pp_instance(),
      socket_id_var.pp_var(),
      buffer_size_var.pp_var(),
      callback.output(),
      callback.pp_completion_callback());
}

int32_t Socket_Dev::SendTo(int32_t socket_id,
                           const VarArrayBuffer& data,
                           const std::string& address,
                           int32_t port,
                           const SendToCallback& callback) {
  if (!has_interface<PPB_Ext_Socket_Dev_0_2>())
    return callback.MayForce(PP_ERROR_NOINTERFACE);

  internal::ToVarConverter<int32_t> socket_id_var(socket_id);
  internal::ToVarConverter<Var> data_var(data);
  internal::ToVarConverter<std::string> address_var(address);
  internal::ToVarConverter<int32_t> port_var(port);

  return get_interface<PPB_Ext_Socket_Dev_0_2>()->SendTo(
      instance_.pp_instance(),
      socket_id_var.pp_var(),
      data_var.pp_var(),
      address_var.pp_var(),
      port_var.pp_var(),
      callback.output(),
      callback.pp_completion_callback());
}

int32_t Socket_Dev::Listen(int32_t socket_id,
                           const std::string& address,
                           int32_t port,
                           const Optional<int32_t>& backlog,
                           const ListenCallback& callback) {
  if (!has_interface<PPB_Ext_Socket_Dev_0_2>())
    return callback.MayForce(PP_ERROR_NOINTERFACE);

  internal::ToVarConverter<int32_t> socket_id_var(socket_id);
  internal::ToVarConverter<std::string> address_var(address);
  internal::ToVarConverter<int32_t> port_var(port);
  internal::ToVarConverter<Optional<int32_t> > backlog_var(backlog);

  return get_interface<PPB_Ext_Socket_Dev_0_2>()->Listen(
      instance_.pp_instance(),
      socket_id_var.pp_var(),
      address_var.pp_var(),
      port_var.pp_var(),
      backlog_var.pp_var(),
      callback.output(),
      callback.pp_completion_callback());
}

int32_t Socket_Dev::Accept(int32_t socket_id,
                           const AcceptCallback& callback) {
  if (!has_interface<PPB_Ext_Socket_Dev_0_2>())
    return callback.MayForce(PP_ERROR_NOINTERFACE);

  internal::ToVarConverter<int32_t> socket_id_var(socket_id);

  return get_interface<PPB_Ext_Socket_Dev_0_2>()->Accept(
      instance_.pp_instance(),
      socket_id_var.pp_var(),
      callback.output(),
      callback.pp_completion_callback());
}

int32_t Socket_Dev::SetKeepAlive(int32_t socket_id,
                                 bool enable,
                                 const Optional<int32_t>& delay,
                                 const SetKeepAliveCallback& callback) {
  if (!has_interface<PPB_Ext_Socket_Dev_0_2>())
    return callback.MayForce(PP_ERROR_NOINTERFACE);

  internal::ToVarConverter<int32_t> socket_id_var(socket_id);
  internal::ToVarConverter<bool> enable_var(enable);
  internal::ToVarConverter<Optional<int32_t> > delay_var(delay);

  return get_interface<PPB_Ext_Socket_Dev_0_2>()->SetKeepAlive(
      instance_.pp_instance(),
      socket_id_var.pp_var(),
      enable_var.pp_var(),
      delay_var.pp_var(),
      callback.output(),
      callback.pp_completion_callback());
}

int32_t Socket_Dev::SetNoDelay(int32_t socket_id,
                               bool no_delay,
                               const SetNoDelayCallback& callback) {
  if (!has_interface<PPB_Ext_Socket_Dev_0_2>())
    return callback.MayForce(PP_ERROR_NOINTERFACE);

  internal::ToVarConverter<int32_t> socket_id_var(socket_id);
  internal::ToVarConverter<bool> no_delay_var(no_delay);

  return get_interface<PPB_Ext_Socket_Dev_0_2>()->SetNoDelay(
      instance_.pp_instance(),
      socket_id_var.pp_var(),
      no_delay_var.pp_var(),
      callback.output(),
      callback.pp_completion_callback());
}

int32_t Socket_Dev::GetInfo(int32_t socket_id,
                            const GetInfoCallback& callback) {
  if (!has_interface<PPB_Ext_Socket_Dev_0_2>())
    return callback.MayForce(PP_ERROR_NOINTERFACE);

  internal::ToVarConverter<int32_t> socket_id_var(socket_id);

  return get_interface<PPB_Ext_Socket_Dev_0_2>()->GetInfo(
      instance_.pp_instance(),
      socket_id_var.pp_var(),
      callback.output(),
      callback.pp_completion_callback());
}

int32_t Socket_Dev::GetNetworkList(const GetNetworkListCallback& callback) {
  if (!has_interface<PPB_Ext_Socket_Dev_0_2>())
    return callback.MayForce(PP_ERROR_NOINTERFACE);

  return get_interface<PPB_Ext_Socket_Dev_0_2>()->GetNetworkList(
      instance_.pp_instance(),
      callback.output(),
      callback.pp_completion_callback());
}

int32_t Socket_Dev::JoinGroup(int32_t socket_id,
                              const std::string& address,
                              const JoinGroupCallback& callback) {
  if (!has_interface<PPB_Ext_Socket_Dev_0_2>())
    return callback.MayForce(PP_ERROR_NOINTERFACE);

  internal::ToVarConverter<int32_t> socket_id_var(socket_id);
  internal::ToVarConverter<std::string> address_var(address);

  return get_interface<PPB_Ext_Socket_Dev_0_2>()->JoinGroup(
      instance_.pp_instance(),
      socket_id_var.pp_var(),
      address_var.pp_var(),
      callback.output(),
      callback.pp_completion_callback());
}

int32_t Socket_Dev::LeaveGroup(int32_t socket_id,
                               const std::string& address,
                               const LeaveGroupCallback& callback) {
  if (!has_interface<PPB_Ext_Socket_Dev_0_2>())
    return callback.MayForce(PP_ERROR_NOINTERFACE);

  internal::ToVarConverter<int32_t> socket_id_var(socket_id);
  internal::ToVarConverter<std::string> address_var(address);

  return get_interface<PPB_Ext_Socket_Dev_0_2>()->LeaveGroup(
      instance_.pp_instance(),
      socket_id_var.pp_var(),
      address_var.pp_var(),
      callback.output(),
      callback.pp_completion_callback());
}

int32_t Socket_Dev::SetMulticastTimeToLive(
    int32_t socket_id,
    int32_t ttl,
    const SetMulticastTimeToLiveCallback& callback) {
  if (!has_interface<PPB_Ext_Socket_Dev_0_2>())
    return callback.MayForce(PP_ERROR_NOINTERFACE);

  internal::ToVarConverter<int32_t> socket_id_var(socket_id);
  internal::ToVarConverter<int32_t> ttl_var(ttl);

  return get_interface<PPB_Ext_Socket_Dev_0_2>()->SetMulticastTimeToLive(
      instance_.pp_instance(),
      socket_id_var.pp_var(),
      ttl_var.pp_var(),
      callback.output(),
      callback.pp_completion_callback());
}

int32_t Socket_Dev::SetMulticastLoopbackMode(
    int32_t socket_id,
    bool enabled,
    const SetMulticastLoopbackModeCallback& callback) {
  if (!has_interface<PPB_Ext_Socket_Dev_0_2>())
    return callback.MayForce(PP_ERROR_NOINTERFACE);

  internal::ToVarConverter<int32_t> socket_id_var(socket_id);
  internal::ToVarConverter<bool> enabled_var(enabled);

  return get_interface<PPB_Ext_Socket_Dev_0_2>()->SetMulticastLoopbackMode(
      instance_.pp_instance(),
      socket_id_var.pp_var(),
      enabled_var.pp_var(),
      callback.output(),
      callback.pp_completion_callback());
}

int32_t Socket_Dev::GetJoinedGroups(int32_t socket_id,
                                    const GetJoinedGroupsCallback& callback) {
  if (!has_interface<PPB_Ext_Socket_Dev_0_2>())
    return callback.MayForce(PP_ERROR_NOINTERFACE);

  internal::ToVarConverter<int32_t> socket_id_var(socket_id);

  return get_interface<PPB_Ext_Socket_Dev_0_2>()->GetJoinedGroups(
      instance_.pp_instance(),
      socket_id_var.pp_var(),
      callback.output(),
      callback.pp_completion_callback());
}

}  // namespace socket
}  // namespace ext
}  // namespace pp