Changeset 8482
- Timestamp:
- May 22, 2009, 4:45:41 PM (14 years ago)
- Location:
- trunk/third-party/dht
- Files:
-
- 3 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/third-party/dht/CHANGES
r8440 r8482 1 22 May 2009: dht-0.6 2 3 * Fixed a buffer overflow (when reading) in parse_message. 4 * Fixed slightly inacurrate metric computation when searching. 5 * Removed a slightly inaccurate shortcut when responding to find_nodes. 6 * Relaxed the rate-limiting parameters to 4 requests per second. 7 1 8 19 May 2009: dht-0.5 2 9 -
trunk/third-party/dht/dht-example.c
r8440 r8482 156 156 157 157 i++; 158 if(i >= argc) 159 goto usage; 158 160 159 161 infop = info; … … 173 175 } 174 176 175 if(i < argc)176 goto usage;177 178 177 /* If you set dht_debug to a stream, every action taken by the DHT will 179 178 be logged. */ -
trunk/third-party/dht/dht.c
r8478 r8482 110 110 111 111 /* When performing a search, we search for up to SEARCH_NODES closest nodes 112 to the destinati n, and use the additional ones to backtrack if any of112 to the destination, and use the additional ones to backtrack if any of 113 113 the target 8 turn out to be dead. */ 114 114 #define SEARCH_NODES 14 … … 154 154 const unsigned char *nodes, int nodes_len, 155 155 const unsigned char *token, int token_len); 156 static int send_ bucket_nodes(int s, struct sockaddr *sa, int salen,157 const unsigned char *tid, int tid_len,158 struct bucket *b,159 const unsigned char *token, int token_len);156 static int send_closest_nodes(int s, struct sockaddr *sa, int salen, 157 const unsigned char *tid, int tid_len, 158 const unsigned char *id, 159 const unsigned char *token, int token_len); 160 160 static int send_get_peers(int s, struct sockaddr *sa, int salen, 161 161 unsigned char *tid, int tid_len, … … 318 318 319 319 return 8 * i + j; 320 } 321 322 /* Determine whether id1 or id2 is closer to ref */ 323 int 324 xorcmp(const unsigned char *id1, const unsigned char *id2, 325 const unsigned char *ref) 326 { 327 int i; 328 for(i = 0; i < 20; i++) { 329 unsigned char xor1, xor2; 330 if(id1[i] == id2[i]) 331 continue; 332 xor1 = id1[i] ^ ref[i]; 333 xor2 = id2[i] ^ ref[i]; 334 if(xor1 < xor2) 335 return -1; 336 else 337 return 1; 338 } 339 return 0; 320 340 } 321 341 … … 584 604 n = b->nodes; 585 605 while(n) { 586 if(n->pinged >= 3 ) {606 if(n->pinged >= 3 && n->pinged_time < now.tv_sec - 15) { 587 607 memcpy(n->id, id, 20); 588 608 n->sin = *sin; … … 605 625 /* Pick the first dubious node that we haven't pinged in the 606 626 last 15 seconds. This gives nodes the time to reply, but 607 tends to concentrate on the same nodes. */ 627 tends to concentrate on the same nodes, so that we get rid 628 of bad nodes fast. */ 608 629 if(!node_good(n)) { 609 630 dubious = 1; … … 720 741 unsigned char *token, int token_len) 721 742 { 722 int bits = common_bits(id, sr->id);723 743 struct search_node *n; 724 744 int i, j; … … 729 749 goto found; 730 750 } 731 if( common_bits(sr->id, sr->nodes[i].id) < bits)751 if(xorcmp(id, sr->nodes[i].id, sr->id) < 0) 732 752 break; 733 753 } … … 1558 1578 debugf("Find node!\n"); 1559 1579 new_node(s, id, &source, 1); 1560 { 1561 struct bucket *b = find_bucket(target); 1562 if(b) { 1563 debugf("Sending nodes from bucket.\n"); 1564 send_bucket_nodes(s, 1565 (struct sockaddr*)&source, 1566 sizeof(source), 1567 tid, tid_len, b, NULL, 0); 1568 } 1569 } 1580 debugf("Sending closest nodes.\n"); 1581 send_closest_nodes(s, (struct sockaddr*)&source, sizeof(source), 1582 tid, tid_len, target, NULL, 0); 1570 1583 break; 1571 1584 case GET_PEERS: … … 1597 1610 1598 1611 } else { 1599 struct bucket *b = find_bucket(info_hash); 1600 if(b) { 1601 unsigned char token[TOKEN_SIZE]; 1602 make_token((unsigned char*)&source.sin_addr, 1603 ntohs(source.sin_port), 1604 0, token); 1605 debugf("Sending nodes for get_peers.\n"); 1606 send_bucket_nodes(s, (struct sockaddr*)&source, 1607 sizeof(source), 1608 tid, tid_len, b, 1609 token, TOKEN_SIZE); 1610 } 1612 unsigned char token[TOKEN_SIZE]; 1613 make_token((unsigned char*)&source.sin_addr, 1614 ntohs(source.sin_port), 1615 0, token); 1616 debugf("Sending nodes for get_peers.\n"); 1617 send_closest_nodes(s, (struct sockaddr*)&source, 1618 sizeof(source), 1619 tid, tid_len, info_hash, 1620 token, TOKEN_SIZE); 1611 1621 } 1612 1622 } … … 1952 1962 1953 1963 static int 1954 buffer_bucket(unsigned char *buf, int bufsize, struct bucket *b) 1955 { 1956 int i = 0; 1964 insert_closest_node(unsigned char *nodes, int numnodes, 1965 const unsigned char *id, struct node *n) 1966 { 1967 int i; 1968 for(i = 0; i< numnodes; i++) { 1969 if(id_cmp(nodes + 26 * i, id) == 0) 1970 return numnodes; 1971 if(xorcmp(n->id, nodes + 26 * i, id) < 0) 1972 break; 1973 } 1974 1975 if(i == 8) 1976 return numnodes; 1977 1978 if(numnodes < 8) 1979 numnodes++; 1980 1981 if(i < numnodes - 1) 1982 memmove(nodes + 26 * (i + 1), nodes + 26 * i, 26 * (numnodes - i - 1)); 1983 1984 memcpy(nodes + 26 * i, n->id, 20); 1985 memcpy(nodes + 26 * i + 20, &n->sin.sin_addr, 4); 1986 memcpy(nodes + 26 * i + 24, &n->sin.sin_port, 2); 1987 1988 return numnodes; 1989 } 1990 1991 static int 1992 buffer_closest_nodes(unsigned char *nodes, int numnodes, 1993 const unsigned char *id, struct bucket *b) 1994 { 1957 1995 struct node *n = b->nodes; 1958 while(n && i < bufsize - 26) { 1959 if(node_good(n)) { 1960 memcpy(buf + i, n->id, 20); 1961 memcpy(buf + i + 20, &n->sin.sin_addr, 4); 1962 memcpy(buf + i + 24, &n->sin.sin_port, 2); 1963 i += 26; 1964 } 1996 while(n) { 1997 if(node_good(n)) 1998 numnodes = insert_closest_node(nodes, numnodes, id, n); 1965 1999 n = n->next; 1966 2000 } 1967 return i;2001 return numnodes; 1968 2002 } 1969 2003 1970 2004 int 1971 send_ bucket_nodes(int s, struct sockaddr *sa, int salen,1972 const unsigned char *tid, int tid_len,1973 struct bucket *b,1974 const unsigned char *token, int token_len)2005 send_closest_nodes(int s, struct sockaddr *sa, int salen, 2006 const unsigned char *tid, int tid_len, 2007 const unsigned char *id, 2008 const unsigned char *token, int token_len) 1975 2009 { 1976 2010 unsigned char nodes[8 * 26]; 1977 int nodeslen = 0; 1978 1979 nodeslen = buffer_bucket(nodes, 8 * 26, b); 2011 int numnodes = 0; 2012 struct bucket *b; 2013 2014 b = find_bucket(id); 2015 numnodes = buffer_closest_nodes(nodes, numnodes, id, b); 2016 if(b->next) 2017 numnodes = buffer_closest_nodes(nodes, numnodes, id, b->next); 2018 b = previous_bucket(b); 2019 if(b) 2020 numnodes = buffer_closest_nodes(nodes, numnodes, id, b); 2021 1980 2022 return send_found_nodes(s, sa, salen, tid, tid_len, 1981 nodes, n odeslen,2023 nodes, numnodes * 26, 1982 2024 token, token_len); 1983 2025 } … … 2111 2153 size_t i; 2112 2154 2155 /* size_t is unsigned */ 2113 2156 if(needlelen > haystacklen) 2114 2157 return NULL;
Note: See TracChangeset
for help on using the changeset viewer.