Git changes...

This commit is contained in:
Naim A 2012-11-27 16:01:40 +02:00
parent ce247fc7d5
commit 7266aa2f5a
6 changed files with 96 additions and 87 deletions

View file

@ -38,7 +38,7 @@ int db_add_peer (dbConnection *, uint8_t [20], db_peerEntry*);
*/ */
int db_load_peers (dbConnection *, uint8_t [20], db_peerEntry *lst, int *sZ); int db_load_peers (dbConnection *, uint8_t [20], db_peerEntry *lst, int *sZ);
int db_get_stats (dbConnection *, uint8_t [20], uint32_t *seeders, uint32_t *leechers, uint32_t *completed); int db_get_stats (dbConnection *, uint8_t [20], int32_t *seeders, int32_t *leechers, int32_t *completed);
/** /**
* Calculates Stats, Removes expired data. * Calculates Stats, Removes expired data.

View file

@ -1,5 +1,6 @@
#include "database.h" #include "database.h"
#include "../multiplatform.h" #include "../multiplatform.h"
#include "../tools.h"
#include <sqlite3.h> #include <sqlite3.h>
#include <stdlib.h> #include <stdlib.h>
#include <string.h> #include <string.h>
@ -94,7 +95,7 @@ int db_add_peer (dbConnection *db, uint8_t info_hash[20], db_peerEntry *pE)
char xHash [50]; // we just need 40 + \0 = 41. char xHash [50]; // we just need 40 + \0 = 41.
char *hash = xHash; char *hash = xHash;
_to_hex_str(info_hash, hash); to_hex_str(info_hash, hash);
_db_make_torrent_table(db->db, hash); _db_make_torrent_table(db->db, hash);
@ -137,7 +138,7 @@ int db_load_peers (dbConnection *db, uint8_t info_hash[20], db_peerEntry *lst, i
sql[0] = '\0'; sql[0] = '\0';
char hash [50]; char hash [50];
_to_hex_str(info_hash, hash); to_hex_str(info_hash, hash);
strcat(sql, "SELECT ip,port FROM 't"); strcat(sql, "SELECT ip,port FROM 't");
strcat(sql, hash); strcat(sql, hash);
@ -176,7 +177,7 @@ int db_load_peers (dbConnection *db, uint8_t info_hash[20], db_peerEntry *lst, i
return 0; return 0;
} }
int db_get_stats (dbConnection *db, uint8_t hash[20], uint32_t *seeders, uint32_t *leechers, uint32_t *completed) int db_get_stats (dbConnection *db, uint8_t hash[20], int32_t *seeders, int32_t *leechers, int32_t *completed)
{ {
*seeders = 0; *seeders = 0;
*leechers = 0; *leechers = 0;
@ -217,7 +218,7 @@ int db_cleanup (dbConnection *db)
while (sqlite3_step(stmt) == SQLITE_ROW) while (sqlite3_step(stmt) == SQLITE_ROW)
{ {
_to_hex_str(sqlite3_column_blob(stmt, 0), hash); to_hex_str(sqlite3_column_blob(stmt, 0), hash);
// drop table: // drop table:
strcpy(temp, "DROP TABLE IF EXISTS 't"); strcpy(temp, "DROP TABLE IF EXISTS 't");
@ -245,7 +246,7 @@ int db_cleanup (dbConnection *db)
while (sqlite3_step(stmt) == SQLITE_ROW) while (sqlite3_step(stmt) == SQLITE_ROW)
{ {
uint8_t *binHash = sqlite3_column_blob(stmt, 0); uint8_t *binHash = sqlite3_column_blob(stmt, 0);
_to_hex_str (binHash, hash); to_hex_str (binHash, hash);
// total users... // total users...
strcpy (temp, "SELECT COUNT(*) FROM 't"); strcpy (temp, "SELECT COUNT(*) FROM 't");

View file

@ -30,3 +30,17 @@ uint32_t m_hton32 (uint32_t n)
m_byteswap (&r, &n, 4); m_byteswap (&r, &n, 4);
return r; return r;
} }
static const char hexadecimal[] = "0123456789abcdef";
void to_hex_str (const uint8_t *hash, char *data)
{
int i;
for (i = 0;i < 20;i++)
{
data[i * 2] = hexadecimal[hash[i] / 16];
data[i * 2 + 1] = hexadecimal[hash[i] % 16];
}
data[40] = '\0';
}

View file

@ -25,4 +25,6 @@ uint32_t m_hton32 (uint32_t n);
uint64_t m_hton64 (uint64_t n); uint64_t m_hton64 (uint64_t n);
void to_hex_str (const uint8_t *hash, char *data);
#endif /* TOOLS_H_ */ #endif /* TOOLS_H_ */

View file

@ -10,6 +10,7 @@
#define FLAG_RUNNING 0x01 #define FLAG_RUNNING 0x01
#define UDP_BUFFER_SIZE 2048 #define UDP_BUFFER_SIZE 2048
#define CLEANUP_INTERVAL 20 #define CLEANUP_INTERVAL 20
#define TRACKER_INTERVAL 60 // normally 1800
#ifdef WIN32 #ifdef WIN32
static DWORD _thread_start (LPVOID arg); static DWORD _thread_start (LPVOID arg);
@ -114,7 +115,6 @@ static int _send_error (udpServerInstance *usi, SOCKADDR_IN *remote, uint32_t tr
error.transaction_id = transactionID; error.transaction_id = transactionID;
error.message = msg; error.message = msg;
int msg_sz = 4 + 4 + 1 + strlen(msg); int msg_sz = 4 + 4 + 1 + strlen(msg);
char buff [msg_sz]; char buff [msg_sz];
@ -125,7 +125,6 @@ static int _send_error (udpServerInstance *usi, SOCKADDR_IN *remote, uint32_t tr
buff[i] = msg[i - 8]; buff[i] = msg[i - 8];
} }
printf("ERROR SENT\n");
sendto(usi->sock, buff, msg_sz, 0, (SOCKADDR*)remote, sizeof(*remote)); sendto(usi->sock, buff, msg_sz, 0, (SOCKADDR*)remote, sizeof(*remote));
return 0; return 0;
@ -145,30 +144,6 @@ static int _handle_connection (udpServerInstance *usi, SOCKADDR_IN *remote, char
return 0; return 0;
} }
static int _is_good_peer (uint32_t ip, uint16_t port)
{
SOCKADDR_IN addr;
addr.sin_family = AF_INET;
#ifdef WIN32
addr.sin_addr.S_un.S_addr = htonl( ip );
#elif defined (linux)
addr.sin_addr.s_addr = htonl( ip );
#endif
addr.sin_port = htons (port);
SOCKET cli = socket (AF_INET, SOCK_STREAM, IPPROTO_TCP);
if (cli == INVALID_SOCKET)
return 1;
if (connect(cli, (SOCKADDR*)&addr, sizeof(SOCKADDR_IN)) == SOCKET_ERROR)
{
closesocket (cli);
return 1;
}
printf ("Client Verified.\n");
closesocket (cli);
return 0;
}
static int _handle_announce (udpServerInstance *usi, SOCKADDR_IN *remote, char *data) static int _handle_announce (udpServerInstance *usi, SOCKADDR_IN *remote, char *data)
{ {
AnnounceRequest *req = (AnnounceRequest*)data; AnnounceRequest *req = (AnnounceRequest*)data;
@ -186,44 +161,28 @@ static int _handle_announce (udpServerInstance *usi, SOCKADDR_IN *remote, char *
req->uploaded = m_hton64 (req->uploaded); req->uploaded = m_hton64 (req->uploaded);
req->num_want = m_hton32 (req->num_want); req->num_want = m_hton32 (req->num_want);
req->left = m_hton64 (req->left); req->left = m_hton64 (req->left);
if (req->ip_address == 0) // default
{
req->ip_address = m_hton32 (remote->sin_addr.s_addr);
}
// if (_is_good_peer(req->ip_address, req->port) != 0)
// {
// _send_error (usi, remote, req->transaction_id, "Couldn't verify your client.");
// return 0;
// }
// load peers // load peers
int q = 30; int q = 30;
if (req->num_want >= 1) if (req->num_want >= 1)
q = min (q, req->num_want); q = min (q, req->num_want);
db_peerEntry *peers = NULL; db_peerEntry *peers = malloc (sizeof(db_peerEntry) * q);
db_load_peers(usi->conn, req->info_hash, peers, &q);
// printf("%d peers found.\n", q);
int bSize = 20; // header is 20 bytes int bSize = 20; // header is 20 bytes
bSize += (6 * q); // + 6 bytes per peer.
if (req->event == 3) // stopped; they don't need anymore peers! int32_t seeders, leechers, completed;
{
q = 0; // don't need any peers!
}
else
{
peers = malloc (sizeof(db_peerEntry) * q);
db_load_peers(usi->conn, req->info_hash, peers, &q);
}
bSize += (6 * q); // + 6 bytes per peer (ip->4, port->2).
uint32_t seeders, leechers, completed;
db_get_stats (usi->conn, req->info_hash, &seeders, &leechers, &completed); db_get_stats (usi->conn, req->info_hash, &seeders, &leechers, &completed);
uint8_t buff [bSize]; uint8_t buff [bSize];
AnnounceResponse *resp = (AnnounceResponse*)buff; AnnounceResponse *resp = (AnnounceResponse*)buff;
resp->action = m_hton32(1); resp->action = m_hton32(1);
resp->interval = m_hton32 ( 1800 ); resp->interval = m_hton32 ( TRACKER_INTERVAL );
resp->leechers = m_hton32(leechers); resp->leechers = m_hton32(leechers);
resp->seeders = m_hton32 (seeders); resp->seeders = m_hton32 (seeders);
resp->transaction_id = req->transaction_id; resp->transaction_id = req->transaction_id;
@ -246,29 +205,24 @@ static int _handle_announce (udpServerInstance *usi, SOCKADDR_IN *remote, char *
// printf("%u.%u.%u.%u:%u\n", buff[20 + x], buff[21 + x], buff[22 + x], buff[23 + x], peers[i].port); // printf("%u.%u.%u.%u:%u\n", buff[20 + x], buff[21 + x], buff[22 + x], buff[23 + x], peers[i].port);
} }
free (peers);
if (peers != NULL)
free (peers);
sendto(usi->sock, (char*)buff, bSize, 0, (SOCKADDR*)remote, sizeof(SOCKADDR_IN)); sendto(usi->sock, (char*)buff, bSize, 0, (SOCKADDR*)remote, sizeof(SOCKADDR_IN));
// Add peer to list: // Add peer to list:
db_peerEntry pE; db_peerEntry pE;
pE.downloaded = req->downloaded; pE.downloaded = req->downloaded;
pE.uploaded = req->uploaded; pE.uploaded = req->uploaded;
pE.left = req->left; pE.left = req->left;
pE.peer_id = req->peer_id; pE.peer_id = req->peer_id;
pE.ip = req->ip_address; if (req->ip_address == 0) // default
pE.port = req->port;
if (req->event == 3) // stopped
{ {
// just remove client from swarm, and return empty peer list... pE.ip = m_hton32 (remote->sin_addr.s_addr);
db_remove_peer(usi->conn, req->info_hash, &pE);
return 0;
} }
else
{
pE.ip = req->ip_address;
}
pE.port = req->port;
db_add_peer(usi->conn, req->info_hash, &pE); db_add_peer(usi->conn, req->info_hash, &pE);
return 0; return 0;
@ -280,12 +234,52 @@ static int _handle_scrape (udpServerInstance *usi, SOCKADDR_IN *remote, char *da
// _send_error (usi, remote, sR->transaction_id, "Scrape wasn't implemented yet!"); // _send_error (usi, remote, sR->transaction_id, "Scrape wasn't implemented yet!");
ScrapeResponse resp; // validate request length:
resp.resp_part = NULL; int v = len - 16;
resp.action = 2; if (v < 0 || v % 20 != 0)
resp.transaction_id = sR->transaction_id; {
printf("BAD SCRAPE: len=%d\n", len);
_send_error (usi, remote, sR->transaction_id, "Bad scrape request.");
return 0;
}
sendto (usi->sock, (const char*)&resp, 8, 0, (SOCKADDR*)remote, sizeof(SOCKADDR_IN)); // get torrent count.
int c = v / 20;
uint8_t hash [20];
char xHash [50];
uint8_t buffer [8 + (12 * c)];
ScrapeResponse *resp = (ScrapeResponse*)buffer;
resp->action = m_hton32 (2);
resp->transaction_id = sR->transaction_id;
int i, j;
printf("Scrape: (%d) \n", c);
for (i = 0;i < c;i++)
{
for (j = 0; j < 20;j++)
hash[j] = data[j + (i*20)+16];
to_hex_str (hash, xHash);
printf("\t%s\n", xHash);
int32_t *seeders = (int32_t*)&buffer[i*12+8];
int32_t *completed = (int32_t*)&buffer[i*12+12];
int32_t *leechers = (int32_t*)&buffer[i*12+16];
int32_t s, c, l;
db_get_stats (usi->conn, hash, &s, &l, &c);
*seeders = m_hton32 (s);
*completed = m_hton32 (c);
*leechers = m_hton32 (l);
}
fflush (stdout);
sendto (usi->sock, buffer, sizeof(buffer), 0, (SOCKADDR*)remote, sizeof(SOCKADDR_IN));
return 0; return 0;
} }
@ -297,7 +291,7 @@ static int _resolve_request (udpServerInstance *usi, SOCKADDR_IN *remote, char *
uint32_t action = m_hton32(cR->action); uint32_t action = m_hton32(cR->action);
// printf(":: %x:%u ACTION=%d\n", remote->sin_addr.s_addr , remote->sin_port, action); printf(":: %x:%u ACTION=%d\n", remote->sin_addr.s_addr , remote->sin_port, action);
if (action == 0 && r >= 16) if (action == 0 && r >= 16)
return _handle_connection(usi, remote, data); return _handle_connection(usi, remote, data);
@ -333,7 +327,9 @@ static void* _thread_start (void *arg)
{ {
fflush(stdout); fflush(stdout);
// peek into the first 12 bytes of data; determine if connection request or announce request. // peek into the first 12 bytes of data; determine if connection request or announce request.
r = recvfrom(usi->sock, tmpBuff, UDP_BUFFER_SIZE, 0, (SOCKADDR*)&remoteAddr, &addrSz); r = recvfrom(usi->sock, tmpBuff, UDP_BUFFER_SIZE, 0, (SOCKADDR*)&remoteAddr, (unsigned*)&addrSz);
if (r <= 0)
continue; // bad request...
// printf("RECV:%d\n", r); // printf("RECV:%d\n", r);
r = _resolve_request(usi, &remoteAddr, tmpBuff, r); r = _resolve_request(usi, &remoteAddr, tmpBuff, r);
// printf("R=%d\n", r); // printf("R=%d\n", r);
@ -345,7 +341,7 @@ static void* _thread_start (void *arg)
} }
#ifdef WIN32 #ifdef WIN32
static DWORD _maintainance_start (LPVOID arg) static DWORD _maintainance_start (LPVOID arg);
#elif defined (linux) #elif defined (linux)
static void* _maintainance_start (void *arg) static void* _maintainance_start (void *arg)
#endif #endif

View file

@ -59,20 +59,16 @@ struct udp_scrape_request
uint64_t connection_id; uint64_t connection_id;
uint32_t action; uint32_t action;
uint32_t transaction_id; uint32_t transaction_id;
struct reqD {
uint8_t info_hash [20]; uint8_t *torrent_list_data;
} *req_part;
}; };
struct udp_scrape_response struct udp_scrape_response
{ {
uint32_t action; uint32_t action;
uint32_t transaction_id; uint32_t transaction_id;
struct respD {
uint32_t seeders; uint8_t *data;
uint32_t completed;
uint32_t leechers;
} *resp_part;
}; };
struct udp_error_response struct udp_error_response