示例#1
0
int SocketConnector::connect( const std::string& address, int port, bool noDelay,
                              int sendBufSize, int rcvBufSize , int mode)
{

  int socket = socket_createConnector(mode);

  if ( socket != -1 )
  {
    if( noDelay )
      socket_setsockopt( socket, TCP_NODELAY );
    if( sendBufSize )
      socket_setsockopt( socket, SO_SNDBUF, sendBufSize );
    if( rcvBufSize )
      socket_setsockopt( socket, SO_RCVBUF, rcvBufSize );

    if( socket_connect( socket, address.c_str(), port ) < 0 )
    {
      DWORD code = GetLastError();
      socket_close( socket );
      SetLastError(code);
      socket = -1;
    }
    else
    {
      m_monitor.addConnect( socket );
    }
  }
  return socket;

  
}
THREAD_PROC ThreadedSocketAcceptor::socketAcceptorThread( void* p )
{
  AcceptorThreadInfo * info = reinterpret_cast < AcceptorThreadInfo* > ( p );

  ThreadedSocketAcceptor* pAcceptor = info->m_pAcceptor;
  int s = info->m_socket;
  int port = info->m_port;
  delete info;

  int noDelay = 0;
  int sendBufSize = 0;
  int rcvBufSize = 0;
  socket_getsockopt( s, TCP_NODELAY, noDelay );
  socket_getsockopt( s, SO_SNDBUF, sendBufSize );
  socket_getsockopt( s, SO_RCVBUF, rcvBufSize );

  int socket = 0;
  while ( ( !pAcceptor->isStopped() && ( socket = socket_accept( s ) ) >= 0 ) )
  {
    if( noDelay )
      socket_setsockopt( socket, TCP_NODELAY );
    if( sendBufSize )
      socket_setsockopt( socket, SO_SNDBUF, sendBufSize );
    if( rcvBufSize )
      socket_setsockopt( socket, SO_RCVBUF, rcvBufSize );

    Sessions sessions = pAcceptor->m_portToSessions[port];

    ThreadedSocketConnection * pConnection =
      new ThreadedSocketConnection
        ( socket, sessions, pAcceptor->getLog() );

    ConnectionThreadInfo* info = new ConnectionThreadInfo( pAcceptor, pConnection );

    {
      Locker l( pAcceptor->m_mutex );

      std::stringstream stream;
      stream << "Accepted connection from " << socket_peername( socket ) << " on port " << port;

      if( pAcceptor->getLog() )
        pAcceptor->getLog()->onEvent( stream.str() );

      thread_id thread;
      if ( !thread_spawn( &socketConnectionThread, info, thread ) )
      {
        delete info;
        delete pConnection;
      }
      else
        pAcceptor->addThread( socket, thread );
    }
  }

  if( !pAcceptor->isStopped() )
    pAcceptor->removeThread( s );

  return 0;
}
status_t
socket_control(net_socket* socket, int32 op, void* data, size_t length)
{
	switch (op) {
		case FIONBIO:
		{
			if (data == NULL)
				return B_BAD_VALUE;

			int value;
			if (is_syscall()) {
				if (!IS_USER_ADDRESS(data)
					|| user_memcpy(&value, data, sizeof(int)) != B_OK) {
					return B_BAD_ADDRESS;
				}
			} else
				value = *(int*)data;

			return socket_setsockopt(socket, SOL_SOCKET, SO_NONBLOCK, &value,
				sizeof(int));
		}

		case FIONREAD:
		{
			if (data == NULL)
				return B_BAD_VALUE;

			ssize_t available = socket_read_avail(socket);
			if (available < B_OK)
				return available;

			if (is_syscall()) {
				if (!IS_USER_ADDRESS(data)
					|| user_memcpy(data, &available, sizeof(ssize_t)) != B_OK) {
					return B_BAD_ADDRESS;
				}
			} else
				*(ssize_t *)data = available;

			return B_OK;
		}

		case B_SET_BLOCKING_IO:
		case B_SET_NONBLOCKING_IO:
		{
			int value = op == B_SET_NONBLOCKING_IO;
			return socket_setsockopt(socket, SOL_SOCKET, SO_NONBLOCK, &value,
				sizeof(int));
		}
	}

	return socket->first_info->control(socket->first_protocol,
		LEVEL_DRIVER_IOCTL, op, data, &length);
}
void ThreadedSocketAcceptor::onInitialize( const SessionSettings& s )
throw ( RuntimeError )
{
  short port = 0;
  std::set<int> ports;

  std::set<SessionID> sessions = s.getSessions();
  std::set<SessionID>::iterator i = sessions.begin();
  for( ; i != sessions.end(); ++i )
  {
    const Dictionary& settings = s.get( *i );
    port = (short)settings.getInt( SOCKET_ACCEPT_PORT );

    m_portToSessions[port].insert( *i );

    if( ports.find(port) != ports.end() )
      continue;
    ports.insert( port );

    const bool reuseAddress = settings.has( SOCKET_REUSE_ADDRESS ) ? 
      settings.getBool( SOCKET_REUSE_ADDRESS ) : true;

    const bool noDelay = settings.has( SOCKET_NODELAY ) ? 
      settings.getBool( SOCKET_NODELAY ) : false;

    const int sendBufSize = settings.has( SOCKET_SEND_BUFFER_SIZE ) ?
      settings.getInt( SOCKET_SEND_BUFFER_SIZE ) : 0;

    const int rcvBufSize = settings.has( SOCKET_RECEIVE_BUFFER_SIZE ) ?
      settings.getInt( SOCKET_RECEIVE_BUFFER_SIZE ) : 0;

    int socket = socket_createAcceptor( port, reuseAddress );
    if( socket < 0 )
    {
      SocketException e;
      socket_close( socket );
      throw RuntimeError( "Unable to create, bind, or listen to port " 
                         + IntConvertor::convert( (unsigned short)port ) + " (" + e.what() + ")" );
    }
    if( noDelay )
      socket_setsockopt( socket, TCP_NODELAY );
    if( sendBufSize )
      socket_setsockopt( socket, SO_SNDBUF, sendBufSize );
    if( rcvBufSize )
      socket_setsockopt( socket, SO_RCVBUF, rcvBufSize );

    m_socketToPort[socket] = port;
    m_sockets.insert( socket );
  }    
}
void ThreadedSocketInitiator::doConnect( const SessionID& s, const Dictionary& d )
{
  try
  {
    Session* session = Session::lookupSession( s );
    if( !session->isSessionTime(UtcTimeStamp()) ) return;

    Log* log = session->getLog();

    std::string address;
    short port = 0;
    std::string sourceAddress;
    short sourcePort = 0;
    getHost( s, d, address, port, sourceAddress, sourcePort );

    socket_handle socket = socket_createConnector();
    if( m_noDelay )
      socket_setsockopt( socket, TCP_NODELAY );
    if( m_sendBufSize )
      socket_setsockopt( socket, SO_SNDBUF, m_sendBufSize );
    if( m_rcvBufSize )
      socket_setsockopt( socket, SO_RCVBUF, m_rcvBufSize );

    setPending( s );
    log->onEvent( "Connecting to " + address + " on port " + IntConvertor::convert((unsigned short)port) + " (Source " + sourceAddress + ":" + IntConvertor::convert((unsigned short)sourcePort) + ")");

    ThreadedSocketConnection* pConnection =
      new ThreadedSocketConnection( s, socket, address, port, getLog(), sourceAddress, sourcePort );

    ThreadPair* pair = new ThreadPair( this, pConnection );

    {
      Locker l( m_mutex );
      thread_id thread;
      if ( thread_spawn( &socketThread, pair, thread ) )
      {
        addThread( socket, thread );
      }
      else
      {
        delete pair;
        pConnection->disconnect();
        delete pConnection;
        setDisconnected( s );
      }
    }
  }
  catch ( std::exception& ) {}
}
示例#6
0
int SocketServer::accept( int socket )
{
  SocketInfo info = m_socketToInfo[socket];

  int result = socket_accept( socket );
  if( info.m_noDelay )
    socket_setsockopt( result, TCP_NODELAY );
  if( info.m_sendBufSize )
    socket_setsockopt( result, SO_SNDBUF, info.m_sendBufSize );
  if( info.m_rcvBufSize )
    socket_setsockopt( result, SO_RCVBUF, info.m_rcvBufSize );
  if ( result >= 0 )
    m_monitor.addConnect( result );
  return result;
}
示例#7
0
int SocketServer::add( int port, bool reuse, bool noDelay, 
                       int sendBufSize, int rcvBufSize )
  throw( SocketException& )
{
  if( m_portToInfo.find(port) != m_portToInfo.end() )
    return m_portToInfo[port].m_socket;

  int socket = socket_createAcceptor( port, reuse );
  if( socket < 0 )
    throw SocketException();
  if( noDelay )
    socket_setsockopt( socket, TCP_NODELAY );
  if( sendBufSize )
    socket_setsockopt( socket, SO_SNDBUF, sendBufSize );
  if( rcvBufSize )
    socket_setsockopt( socket, SO_RCVBUF, rcvBufSize );
  m_monitor.addRead( socket );

  SocketInfo info( socket, port, noDelay, sendBufSize, rcvBufSize );
  m_socketToInfo[socket] = info;
  m_portToInfo[port] = info;
  return socket;
}
示例#8
0
int
ksocket_setsockopt(ksocket_t ks, int level, int optname, const void *optval,
    int optlen, struct cred *cr)
{
	struct sonode *so;

	/* All Solaris components should pass a cred for this operation. */
	ASSERT(cr != NULL);

	if (!KSOCKET_VALID(ks))
		return (ENOTSOCK);

	so = KSTOSO(ks);

	if (optval == NULL)
		optlen = 0;

	return (socket_setsockopt(so, level, optname, optval,
	    (t_uscalar_t)optlen, cr));
}
示例#9
0
bool NanostackSocket::open(void)
{
    nanostack_assert_locked();
    MBED_ASSERT(SOCKET_MODE_UNOPENED == mode);

    int temp_socket = socket_open(proto, 0, socket_callback);

    if (temp_socket < 0) {
        tr_error("NanostackSocket::open() failed");
        return false;
    }

    if (proto == SOCKET_TCP) {
        /* Receive and send buffers enabled by default */
        mode = SOCKET_MODE_OPENED;
    } else {
        static const int32_t rcvbuf_size = 2048;
        socket_setsockopt(temp_socket, SOCKET_SOL_SOCKET, SOCKET_SO_RCVBUF, &rcvbuf_size, sizeof rcvbuf_size);
        mode = SOCKET_MODE_DATAGRAM;
    }

    return attach(temp_socket);
}
void ThreadedSSLSocketInitiator::doConnect(const SessionID &s,
                                           const Dictionary &d)
{
  try
  {
    Session *session = Session::lookupSession(s);
    if (!session->isSessionTime(UtcTimeStamp()))
      return;

    Log *log = session->getLog();

    std::string address;
    short port = 0;
    getHost(s, d, address, port);

    int socket = socket_createConnector();
    if (m_noDelay)
      socket_setsockopt(socket, TCP_NODELAY);
    if (m_sendBufSize)
      socket_setsockopt(socket, SO_SNDBUF, m_sendBufSize);
    if (m_rcvBufSize)
      socket_setsockopt(socket, SO_RCVBUF, m_rcvBufSize);

    setPending(s);
    log->onEvent("Connecting to " + address + " on port " +
                 IntConvertor::convert((unsigned short)port));

    SSL *ssl = SSL_new(m_ctx);
    if (ssl == 0)
    {
      log->onEvent("Failed to create ssl object");
      return;
    }
    SSL_clear(ssl);
    BIO *sbio = BIO_new_socket(socket, BIO_CLOSE);
    SSL_set_bio(ssl, sbio, sbio);

    ThreadedSSLSocketConnection *pConnection = new ThreadedSSLSocketConnection(
        s, socket, ssl, address, port, getLog());

    ThreadPair *pair = new ThreadPair(this, pConnection);

    {
      Locker l(m_mutex);
      thread_id thread;
      if (thread_spawn(&socketThread, pair, thread))
      {
        addThread(SocketKey(socket, ssl), thread);
      }
      else
      {
        delete pair;
        pConnection->disconnect();
        delete pConnection;
        SSL_free(ssl);
        setDisconnected(s);
      }
    }
  }
  catch (std::exception &)
  {
  }
}