示例#1
0
void Tracker::event_sock_ready2read(network::Socket sock)
{
	if (m_state == TRACKER_STATE_RELEASING)
		return;
	try
	{
		bool closed;
		size_t received = m_nm->Socket_recv(sock, m_buf + m_buflen, BUFFER_SIZE - m_buflen, closed);
		m_buflen += received;
		process_response();
		if (closed)
		{
			delete_socket();
			if (m_status == TRACKER_STATUS_UPDATING)
				m_status = TRACKER_STATUS_ERROR;
			return;
		}
	}
	catch (Exception & e)
	{
		delete_socket();
		m_status = TRACKER_STATUS_ERROR;
		logger::LOGGER() << "Tracker ready to read event failure";
	}
}
示例#2
0
void Tracker::forced_releasing()
{
	if (m_state == TRACKER_STATE_FAILURE)
		return;
	m_ready2release = true;
	delete_socket();
}
示例#3
0
void Tracker::event_sock_error(network::Socket sock, int errno_)
{
	delete_socket();
	if (m_status == TRACKER_STATUS_UPDATING)
		m_status = TRACKER_STATUS_ERROR;
	m_ready2release = (m_state == TRACKER_STATE_RELEASING);
}
示例#4
0
void Gobby::GSelector::set(const net6::socket& sock, net6::io_condition cond)
{
	// Lock mutex - required for connection establishment which happens
	// in a different thread for the GUI to remain responsive.

	// After the connection to Glib::signal_io() the main thread may be
	// woken up immediately by incoming data and call GSelector::set to
	// send out some data even before the assignment to the
	// sigc::connection in the connecting thread has been finished!
	Glib::RecMutex::Lock lock(*m_mutex);

	map_type::iterator iter = m_map.find(&sock);

	if(cond != net6::IO_NONE)
	{
		if(iter == m_map.end() )
			add_socket(sock, cond);
		else
			modify_socket(iter, cond);
	}
	else if(iter != m_map.end() )
	{
		delete_socket(iter);
	}
}
示例#5
0
void Tracker::event_sock_unresolved(network::Socket sock)
{
	if (m_state == TRACKER_STATE_FAILURE)
		return;
	m_status = TRACKER_STATUS_UNRESOLVED;
	delete_socket();
	m_ready2release = (m_state == TRACKER_STATE_RELEASING);
}
示例#6
0
void Tracker::event_sock_timeout(network::Socket sock)
{
#ifdef BITTORRENT_DEBUG
	logger::LOGGER() << "Tracker " << m_announce.c_str() << " timeout";
#endif
	if (m_state == TRACKER_STATE_FAILURE)
		return;
	m_status = TRACKER_STATUS_TIMEOUT;
	delete_socket();
	m_ready2release = (m_state == TRACKER_STATE_RELEASING);
}
示例#7
0
Tracker::~Tracker()
{
#ifdef BITTORRENT_DEBUG
	logger::LOGGER() << "Tracker " << m_announce.c_str() << " destructor";
#endif
	if (m_addr != NULL)
		delete m_addr;
	delete_socket();
#ifdef BITTORRENT_DEBUG
	logger::LOGGER() << "Tracker " << m_announce.c_str() << " destroyed";
#endif
}
示例#8
0
void Tracker::event_sock_connected(network::Socket sock)
{
	try
	{
		if (m_addr == NULL)
			m_addr = new sockaddr_in;
		m_nm->Socket_get_addr(sock, *m_addr);
		send_request(m_event_after_connect);
	}
	catch (Exception & e)
	{
		logger::LOGGER() << "Tracker " << m_announce.c_str() << "  error while sending request";
		delete_socket();
		m_status = TRACKER_STATUS_ERROR;
		m_ready2release = (m_state == TRACKER_STATE_RELEASING);
	}
}
示例#9
0
socket_t *find_socket( uint16 src_port, uint16 dest_port, int proto )
{
	socket_t *result = 0;
	EnterCriticalSection( &router_section );
	int i = get_socket_index( src_port, dest_port, proto );
	if( i >= 0 ) {
		result = all_sockets[i];
	} else {
		i = get_socket_index( src_port, proto );
		if( i >= 0 ) {
			delete_socket( all_sockets[i] );
		}
	}
	LeaveCriticalSection( &router_section );

  D(bug("find_socket(%d,%d): %s\r\n", src_port, dest_port, result ? "found" : "not found"));

	return result;
}
示例#10
0
void Tracker::prepare2release()
{
#ifdef BITTORRENT_DEBUG
	logger::LOGGER() << "Tracker " << m_announce.c_str() << " prepare2release";
#endif
	if (m_state == TRACKER_STATE_FAILURE)
	{
		#ifdef BITTORRENT_DEBUG
			logger::LOGGER() << "Tracker is fail " << m_announce.c_str() << " prepare2release";
		#endif
		m_ready2release = true;
		return;
	}
	if (send_stopped() != ERR_NO_ERROR)
	{
		delete_socket();
		m_ready2release = true;
	}
	m_state = TRACKER_STATE_RELEASING;
}
示例#11
0
int Tracker::process_response()
{
	char * rnrn = strchr(m_buf,'\r');
	char * data = NULL;
	ssize_t len = 0;
	while (rnrn != NULL)
	{
		if (strncmp(rnrn, "\r\n\r\n", 4) == 0)
		{
			data = rnrn + 4;
			break;
		}
		rnrn = strchr(rnrn + 4,'\r');
	}
	if (data == NULL)
	{
		m_status = TRACKER_STATUS_ERROR;
		logger::LOGGER() << "Tracker invalid response(data == null)";
		return ERR_INTERNAL;
	}
	len = m_buflen - (data - m_buf);


	bencode::be_node * response = bencode::decode(data, len, false);
	if (response == NULL)
	{
		m_status = TRACKER_STATUS_ERROR;
		logger::LOGGER() << "Tracker invalid response(not bencode)";
		return ERR_INTERNAL;
	}
	//bencode::dump(response);
	bencode::be_str * b_str = NULL;
	char * c_str = NULL;
	m_status = TRACKER_STATUS_OK;
	m_tracker_failure = "";
	if (bencode::get_str(response, "warning message", &b_str) == 0)
	{
		c_str = bencode::str2c_str(b_str);
		m_status = TRACKER_STATUS_SEE_FAILURE_MESSAGE;
		m_tracker_failure = c_str;
		delete[] c_str;
	}
	if (bencode::get_str(response, "failure reason", &b_str) == 0)
	{
		c_str = bencode::str2c_str(b_str);
		m_status = TRACKER_STATUS_SEE_FAILURE_MESSAGE;
		m_tracker_failure = c_str;
		delete[] c_str;
	}
	bencode::get_int(response,"interval",&m_interval);
	bencode::get_int(response,"min interval",&m_min_interval);
	if (bencode::get_str(response,"tracker id",&b_str) == 0)
	{
		c_str = bencode::str2c_str(b_str);
		m_tracker_id = c_str;
		delete[] c_str;
	}
	bencode::get_int(response,"complete",&m_seeders);
	bencode::get_int(response,"incomplete",&m_leechers);
	if (bencode::get_str(response,"peers",&b_str) == 0)
	{
		int len = b_str->len;
		char * t_str = b_str->ptr;
		if (len % 6 != 0)
		{
			bencode::_free(response);
			m_status = TRACKER_STATUS_ERROR;
			logger::LOGGER() << "Tracker invalid response(invalid peer list)";
			return ERR_INTERNAL;
		}
		int peers_count = len / 6;
		m_peers.clear();
		FILE * f = fopen("peers", "wb");
		for(int i = 0; i < peers_count; i++)
		{
			sockaddr_in addr;
			memcpy((void*)&addr.sin_addr, (void*)&t_str[i * 6], 4);
			memcpy(&addr.sin_port, &t_str[i * 6 + 4], 2);
			addr.sin_family = AF_INET;
			m_peers.push_back(addr);
			fwrite((void*)&addr, 1, sizeof(sockaddr_in), f);
		}
		fclose(f);
	}

	bencode::_free(response);
	m_buflen = 0;
	m_torrent->add_seeders(m_peers);
	delete_socket();
	return 0;
}