Example #1
0
void
UnixSocketImpl::Accept()
{
  MOZ_ASSERT(!NS_IsMainThread());
  mTask = nullptr;

  if (!mConnector) {
    NS_WARNING("No connector object available!");
    return;
  }

  // This will set things we don't particularly care about, but it will hand
  // back the correct structure size which is what we do care about.
  if (!mConnector->CreateAddr(true, mAddrSize, mAddr, nullptr)) {
    NS_WARNING("Cannot create socket address!");
    return;
  }

  if (mFd.get() < 0)
  {
    mFd = mConnector->Create();
    if (mFd.get() < 0) {
      return;
    }

    if (!SetNonblockFlags()) {
      return;
    }

    if (bind(mFd.get(), (struct sockaddr*)&mAddr, mAddrSize)) {
#ifdef DEBUG
      LOG("...bind(%d) gave errno %d", mFd.get(), errno);
#endif
      return;
    }

    if (listen(mFd.get(), 1)) {
#ifdef DEBUG
      LOG("...listen(%d) gave errno %d", mFd.get(), errno);
#endif
      return;
    }

  }

  int client_fd;
  client_fd = accept(mFd.get(), (struct sockaddr*)&mAddr, &mAddrSize);
  if (client_fd < 0) {
    EnqueueTask(SOCKET_RETRY_TIME_MS, new SocketAcceptTask(this));
    return;
  }

  if (!mConnector->SetUp(client_fd)) {
    NS_WARNING("Could not set up socket!");
    return;
  }
  mFd.reset(client_fd);

  nsRefPtr<OnSocketEventTask> t =
    new OnSocketEventTask(this, OnSocketEventTask::CONNECT_SUCCESS);
  NS_DispatchToMainThread(t);

  SetUpIO();
}
Example #2
0
void
UnixSocketImpl::Connect()
{
  MOZ_ASSERT(!NS_IsMainThread());

  if (!mConnector) {
    NS_WARNING("No connector object available!");
    return;
  }

  if(mFd.get() < 0)
  {
    mFd = mConnector->Create();
    if (mFd.get() < 0) {
      return;
    }
  }

  int ret;

  if (!mConnector->CreateAddr(false, mAddrSize, mAddr, mAddress.get())) {
    NS_WARNING("Cannot create socket address!");
    return;
  }

  // Select non-blocking IO.
  if (!SetNonblockFlags()) {
    nsRefPtr<OnSocketEventTask> t =
      new OnSocketEventTask(this, OnSocketEventTask::CONNECT_ERROR);
    NS_DispatchToMainThread(t);
    return;
  }

  ret = connect(mFd.get(), (struct sockaddr*)&mAddr, mAddrSize);

  if (ret) {
    if (errno == EINPROGRESS) {
      // Select blocking IO again, since we've now at least queue'd the connect
      // as nonblock.
      int current_opts = fcntl(mFd.get(), F_GETFL, 0);
      if (-1 == current_opts) {
        NS_WARNING("Cannot get socket opts!");
        nsRefPtr<OnSocketEventTask> t =
          new OnSocketEventTask(this, OnSocketEventTask::CONNECT_ERROR);
        NS_DispatchToMainThread(t);
        return;
      }
      if (-1 == fcntl(mFd.get(), F_SETFL, current_opts & ~O_NONBLOCK)) {
        NS_WARNING("Cannot set socket opts to blocking!");
        nsRefPtr<OnSocketEventTask> t =
          new OnSocketEventTask(this, OnSocketEventTask::CONNECT_ERROR);
        NS_DispatchToMainThread(t);
        return;
      }

      // Set up a write watch to make sure we receive the connect signal
      MessageLoopForIO::current()->WatchFileDescriptor(
        mFd.get(),
        false,
        MessageLoopForIO::WATCH_WRITE,
        &mWriteWatcher,
        this);

#ifdef DEBUG
      LOG("UnixSocket Connection delayed!");
#endif
      return;
    }
#if DEBUG
    LOG("Socket connect errno=%d\n", errno);
#endif
    mFd.reset(-1);
    nsRefPtr<OnSocketEventTask> t =
      new OnSocketEventTask(this, OnSocketEventTask::CONNECT_ERROR);
    NS_DispatchToMainThread(t);
    return;
  }

  if (!mConnector->SetUp(mFd)) {
    NS_WARNING("Could not set up socket!");
    return;
  }

  nsRefPtr<OnSocketEventTask> t =
    new OnSocketEventTask(this, OnSocketEventTask::CONNECT_SUCCESS);
  NS_DispatchToMainThread(t);

  SetUpIO();
}
Example #3
0
void
UnixSocketImpl::Accept()
{
  socklen_t addr_sz;
  struct sockaddr addr;

  if (!mConnector) {
    NS_WARNING("No connector object available!");
    return;
  }

  // This will set things we don't particularly care about, but it will hand
  // back the correct structure size which is what we do care about.
  mConnector->CreateAddr(true, addr_sz, &addr, nullptr);

  if(mFd.get() < 0)
  {
    mFd = mConnector->Create();
    if (mFd.get() < 0) {
      return;
    }

    if (!SetNonblockFlags()) {
      return;
    }

    if (bind(mFd.get(), &addr, addr_sz)) {
#ifdef DEBUG
      LOG("...bind(%d) gave errno %d", mFd.get(), errno);
#endif
      return;
    }

    if (listen(mFd.get(), 1)) {
#ifdef DEBUG
      LOG("...listen(%d) gave errno %d", mFd.get(), errno);
#endif
      return;
    }

  }

  int client_fd;
  client_fd = accept(mFd.get(), &addr, &addr_sz);
  if (client_fd < 0) {
    EnqueueTask(SOCKET_RETRY_TIME_MS, new SocketAcceptTask(this));
    return;
  }

  if (!mConnector->SetUp(client_fd)) {
    NS_WARNING("Could not set up socket!");
    return;
  }
  mFd.reset(client_fd);

  nsRefPtr<OnSocketEventTask> t =
    new OnSocketEventTask(this, OnSocketEventTask::CONNECT_SUCCESS);
  NS_DispatchToMainThread(t);

  // Due to the fact that we've dispatched our OnConnectSuccess message before
  // starting reading, we're guaranteed that any subsequent read tasks will
  // happen after the object has been notified of a successful connect.
  XRE_GetIOMessageLoop()->PostTask(FROM_HERE,
                                   new StartImplReadingTask(this));
}