void SocksConnection::WriteSocksReply(SocksReplyCode reason, 
      const QHostAddress &addr, quint16 port) 
  {
    QHostAddress a = (addr.isNull() || addr.protocol() != QAbstractSocket::IPv4Protocol) 
      ? QHostAddress("8.8.8.8") : addr;

    QByteArray reply(4, 0);
    reply[0] = (uchar)SocksVersion_5; // Protocol version
    reply[1] = reason;  // Reply
    reply[2] = 0x00; // Reserved 
    reply[3] = SocksAddress_IPv4;     // Address type
    // reply[4] IP Octet 1
    // reply[5] IP Octet 2
    // reply[6] IP Octet 3
    // reply[7] IP Octet 3
    // reply[8] Port Octet 1
    // reply[9] Port Octet 1

    QDataStream stream(&reply, QIODevice::Append);
    stream.setByteOrder(QDataStream::BigEndian);

    stream << a.toIPv4Address();
    stream << port;

    for(int i=0;i<reply.count();i++) {
      qDebug() << "SOCKS reply" << i << "|" << (unsigned char)reply[i];
    }

    TryWrite(reply);
  }
Exemple #2
0
int FifoPush(Fifo *fifo, void *data, int size) {
	struct FifoElem *cur;

	int rv = FifoFlush(fifo);
	if (rv == -1) {
		return -1;
	}

	if (EMPTY(fifo)) {
		int newSize = TryWrite(fifo->fd, data, size);
		if (newSize == -1) {
			return -1;
		} else if (newSize == size) {
			return 1;
		} else {
			data += newSize;
			size -= newSize;
		}
	} else if (FULL(fifo)) {
		return 0;
	}

	void *dataCopy = malloc(size);
	memcpy(dataCopy, data, size);

	fifo->Tail = (fifo->Tail+1)%(FIFO_ELEMS*2);
	cur = &TAIL_ELEM(fifo);
	cur->DataCur = cur->DataStart = dataCopy;
	cur->Remaining = size;

	return 1;
}
  void SocksConnection::SendMethodsReply() 
  {
    // Reply is two bytes:
    //  byte[0] = version (0x05)
    //  byte[1] = method (0x00 is no auth)

    QByteArray reply(2, 0);
    reply[0] = (uchar) SocksVersion_5;

    for(int i=0; i<_methods_buf.count(); i++) {
      qDebug() << "METHODS[]" << i << "=" << (int)((uchar)_methods_buf[i]);
    }

    bool close = false;

    // If the SOCKS proto version is wrong, or if the 
    // authentication method is unacceptable
    if((_version != (uchar)SocksVersion_5) || !_methods_buf.contains(SocksAuth_NoAuth)) {
      qDebug() << "Sending invalid reply header for protocol " << (int)_version;
      reply[1] = ((uchar)SocksAuth_NoneAcceptable);
      close = true;
    } else {
      qDebug() << "Sending OK method reply";
      reply[1] = (uchar)SocksAuth_NoAuth;
      _state = ConnState_WaitingForRequestHeader;
    }
 
    TryWrite(reply);

    if(close) Close();
  }
 void SocksConnection::HandleTcpResponse(QSharedPointer<Packet> pp) 
 {
   TcpResponsePacket *rp = dynamic_cast<TcpResponsePacket*>(pp.data());
   if(!rp) {
     qWarning() << "SOCKS Could not cast TcpResponsePacket";
     return;
   }
   qDebug() << "SOCKS response : " << rp->GetResponseData().count();
   TryWrite(rp->GetResponseData());
 }
Exemple #5
0
//----------------------------------------------------------------------------------------------
void CRingBuffer::Write(unsigned char* pData, unsigned int Size)
{
	Assert(Size < m_Size / 2); // writes greater than half buffer size can cause a lock condition
	bool Res = false;
	while(!Res)
	{
		Res = TryWrite(pData, Size);
		if(!Res)
		{
			Sleep(0);
		}
	}
}
void NetworkManager::OnConnect()
{
	// accept client
	// register new client socket to epoll instance
	int clientFd;
	sockaddr_in clientAddr;
	socklen_t addrLen = 0;
	// #4. accept
	if((clientFd = accept(m_serverFd, (struct sockaddr*)&clientAddr, &addrLen)) < 0)
	{
		fprintf(stderr, "[ERROR] : ACCEPT ERROR\n");
		exit(-1);
	}
	// make socket non-blocking
	int flags = fcntl(clientFd, F_GETFL, 0);
	if(flags < 0)
	{
		fprintf(stderr, "[ERROR] : MAKE SOCKET NONBLOCKING ERROR\n");
		exit(-1);
	}
	flags = fcntl(clientFd, F_SETFL, flags | O_NONBLOCK);

	Session* pSession = new Session(clientFd, clientAddr);
	pSession->state = SS_CONNECTED;
	m_pSessionMap.insert(std::pair<int, Session*>(clientFd, pSession));

	struct epoll_event epollEvent;

	epollEvent.events = EPOLLIN | EPOLLERR; //| EPOLLOUT | EPOLLERR;
	epollEvent.data.fd = clientFd;

	// register server fd to epoll
	if(epoll_ctl(m_epollFdList[clientFd%NETWORK_THREAD_NUM], EPOLL_CTL_ADD, clientFd, &epollEvent) < 0)
	{
		fprintf(stderr, "[ERROR] : EPOLL CTL ERROR\n");
		exit(-1);
	}

	// give session to user
	Packet writePacket;
	S_PT_SESSION_U data;
	data.sessionId = clientFd;
	MAKE_PT_SESSION_U(writePacket.buffer, writePacket.size, data);

	TryWrite(clientFd, writePacket);

	printf("%d session connected\n", clientFd);

}
Exemple #7
0
void CDatagrams::OnRun()
{
	if ( ! IsValid() ) return;

	DHT.OnRun();

	TryWrite();
	ManageOutput();

	do
	{
		ManagePartials();
	}
	while ( TryRead() );

	Measure();
}
Exemple #8
0
static int FifoFlushOnce(Fifo *fifo) {
	int rv;
	if (EMPTY(fifo)) return 0;
	do {
		struct FifoElem *cur = &HEAD_ELEM(fifo);
		int written = TryWrite(fifo->fd, cur->DataCur, cur->Remaining);
		if (written == -1) {
			return -1;
		}
		rv += written;
		
		if (written == cur->Remaining) {
			FifoPop(fifo);
			continue;
		} else {
			cur->DataCur += written;
			cur->Remaining -= written;
		}
	} while (0);
	return rv;
}
Exemple #9
0
BOOL CDatagrams::Send(const SOCKADDR_IN* pHost, CPacket* pPacket, BOOL bRelease, LPVOID pToken, BOOL bAck)
{
	ASSERT( pHost != NULL && pPacket != NULL );

	if ( ! IsValid() || Security.IsDenied( &pHost->sin_addr ) )
	{
		if ( bRelease ) pPacket->Release();
		return FALSE;
	}

	if ( pPacket->m_nProtocol != PROTOCOL_G2 )
	{
		CBuffer pBuffer;
		pPacket->ToBuffer( &pBuffer, false );

		m_nOutPackets++;
		switch ( pPacket->m_nProtocol )
		{
		case PROTOCOL_G1:
			Statistics.Current.Gnutella1.Outgoing++;
			break;
		case PROTOCOL_ED2K:
			Statistics.Current.eDonkey.Outgoing++;
			break;
		case PROTOCOL_DC:
			Statistics.Current.DC.Outgoing++;
			break;
		case PROTOCOL_BT:
			Statistics.Current.BitTorrent.Outgoing++;
			break;
		//default:
		//	;	// Other?
		}

		pPacket->SmartDump( pHost, TRUE, TRUE );
		if ( bRelease ) pPacket->Release();

		CNetwork::SendTo( m_hSocket, (LPSTR)pBuffer.m_pBuffer, pBuffer.m_nLength, pHost );

		return TRUE;
	}

	// Gnutella2 uses SGP-powered datagrams

	if ( m_pOutputFree == NULL || m_pBufferFree == NULL )
	{
		if ( m_pOutputLast == NULL )
		{
			if ( bRelease ) pPacket->Release();
			theApp.Message( MSG_DEBUG, _T("CDatagrams output frames exhausted.") );
			return FALSE;
		}
		Remove( m_pOutputLast );
	}

	if ( m_pBufferFree == NULL )
	{
		if ( bRelease ) pPacket->Release();
		theApp.Message( MSG_DEBUG, _T("CDatagrams output frames really exhausted.") );
		return FALSE;
	}

	CDatagramOut* pDG = m_pOutputFree;
	m_pOutputFree = m_pOutputFree->m_pNextHash;

	if ( m_nInFrags < 1 )
		bAck = FALSE;

	pDG->Create( pHost, (CG2Packet*)pPacket, m_nSequence++, m_pBufferFree, bAck );

	m_pBufferFree = m_pBufferFree->m_pNext;
	m_nBufferFree--;

	pDG->m_pToken		= pToken;
	pDG->m_pNextTime	= NULL;
	pDG->m_pPrevTime	= m_pOutputFirst;

	if ( m_pOutputFirst )
		m_pOutputFirst->m_pNextTime = pDG;
	else
		m_pOutputLast = pDG;

	m_pOutputFirst = pDG;

	BYTE nHash	= BYTE( ( pHost->sin_addr.S_un.S_un_b.s_b1
				+ pHost->sin_addr.S_un.S_un_b.s_b2
				+ pHost->sin_addr.S_un.S_un_b.s_b3
				+ pHost->sin_addr.S_un.S_un_b.s_b4
				+ pHost->sin_port
				+ pDG->m_nSequence ) & 0xff );

	CDatagramOut** pHash = m_pOutputHash + ( nHash & HASH_MASK );

	if ( *pHash ) (*pHash)->m_pPrevHash = &pDG->m_pNextHash;
	pDG->m_pNextHash = *pHash;
	pDG->m_pPrevHash = pHash;
	*pHash = pDG;

	m_nOutPackets++;
	Statistics.Current.Gnutella2.Outgoing++;

#ifdef DEBUG_UDP
	theApp.Message( MSG_DEBUG, _T("UDP: Queued SGP (#%i) x%i for %s:%lu"),
		pDG->m_nSequence, pDG->m_nCount, (LPCTSTR)CString( inet_ntoa( pDG->m_pHost.sin_addr ) ), htons( pDG->m_pHost.sin_port ) );
#endif

	pPacket->SmartDump( pHost, TRUE, TRUE );
	if ( bRelease ) pPacket->Release();

	TryWrite();

	return TRUE;
}