Changeset 12586


Ignore:
Timestamp:
Jul 25, 2011, 9:30:43 PM (10 years ago)
Author:
jch
Message:

Import dht-0.21. This has blacklisting support.

Location:
trunk/third-party/dht
Files:
5 edited

Legend:

Unmodified
Added
Removed
  • trunk/third-party/dht/CHANGES

    r12537 r12586  
     125 July 2011: dht-0.21
     2
     3  * Blacklisting support.
     4
    157 July 2011: dht-0.20
    26
  • trunk/third-party/dht/README

    r11663 r12586  
    158158format -- 6 or 18 bytes per node.  Its length in bytes is in data_len.
    159159
     160* dht_blacklisted
     161
     162This is a function that takes an IP address and returns true if this
     163address should be silently ignored.  Do not use this feature unless you
     164really must -- Kademlia supposes transitive reachability.
     165
    160166* dht_hash
    161167
  • trunk/third-party/dht/dht-example.c

    r11663 r12586  
    410410}
    411411
     412/* Functions called by the DHT. */
     413
     414int
     415dht_blacklisted(const struct sockaddr *sa, int salen)
     416{
     417    return 0;
     418}
     419
    412420/* We need to provide a reasonably strong cryptographic hashing function.
    413421   Here's how we'd do it if we had RSA's MD5 code. */
  • trunk/third-party/dht/dht.c

    r12537 r12586  
    212212    struct storage *next;
    213213};
     214
     215static void flush_search_node(struct search_node *n, struct search *sr);
    214216
    215217static int send_ping(const struct sockaddr *sa, int salen,
     
    637639}
    638640
     641/* Called whenever we send a request to a node, increases the ping count
     642   and, if that reaches 3, sends a ping to a new candidate. */
     643static void
     644pinged(struct node *n, struct bucket *b)
     645{
     646    n->pinged++;
     647    n->pinged_time = now.tv_sec;
     648    if(n->pinged >= 3)
     649        send_cached_ping(b ? b : find_bucket(n->id, n->ss.ss_family));
     650}
     651
     652/* The internal blacklist is an LRU cache of nodes that have sent
     653   incorrect messages. */
     654static void
     655blacklist_node(const unsigned char *id, const struct sockaddr *sa, int salen)
     656{
     657    int i;
     658
     659    debugf("Blacklisting broken node.\n");
     660
     661    if(id) {
     662        struct node *n;
     663        struct search *sr;
     664        /* Make the node easy to discard. */
     665        n = find_node(id, sa->sa_family);
     666        if(n) {
     667            n->pinged = 3;
     668            pinged(n, NULL);
     669        }
     670        /* Discard it from any searches in progress. */
     671        sr = searches;
     672        while(sr) {
     673            for(i = 0; i < sr->numnodes; i++)
     674                if(id_cmp(sr->nodes[i].id, id) == 0)
     675                    flush_search_node(&sr->nodes[i], sr);
     676            sr = sr->next;
     677        }
     678    }
     679    /* And make sure we don't hear from it again. */
     680    memcpy(&blacklist[next_blacklisted], sa, salen);
     681    next_blacklisted = (next_blacklisted + 1) % DHT_MAX_BLACKLISTED;
     682}
     683
     684static int
     685node_blacklisted(const struct sockaddr *sa, int salen)
     686{
     687    int i;
     688
     689    if(salen > sizeof(struct sockaddr_storage))
     690        abort();
     691
     692    if(dht_blacklisted(sa, salen))
     693        return 1;
     694
     695    for(i = 0; i < DHT_MAX_BLACKLISTED; i++) {
     696        if(memcmp(&blacklist[i], sa, salen) == 0)
     697            return 1;
     698    }
     699
     700    return 0;
     701}
     702
    639703/* Split a bucket into two equal parts. */
    640704static struct bucket *
     
    675739}
    676740
    677 /* Called whenever we send a request to a node. */
    678 static void
    679 pinged(struct node *n, struct bucket *b)
    680 {
    681     n->pinged++;
    682     n->pinged_time = now.tv_sec;
    683     if(n->pinged >= 3)
    684         send_cached_ping(b ? b : find_bucket(n->id, n->ss.ss_family));
    685 }
    686 
    687741/* We just learnt about a node, not necessarily a new one.  Confirm is 1 if
    688742   the node sent a message, 2 if it sent us a reply. */
     
    701755        return NULL;
    702756
    703     if(is_martian(sa))
     757    if(is_martian(sa) || node_blacklisted(sa, salen))
    704758        return NULL;
    705759
     
    13291383}
    13301384
    1331 /* We've just found out that a node is buggy. */
    1332 static void
    1333 broken_node(const unsigned char *id, const struct sockaddr *sa, int salen)
    1334 {
    1335     int i;
    1336 
    1337     debugf("Blacklisting broken node.\n");
    1338 
    1339     if(id) {
    1340         struct node *n;
    1341         struct search *sr;
    1342         /* Make the node easy to discard. */
    1343         n = find_node(id, sa->sa_family);
    1344         if(n) {
    1345             n->pinged = 3;
    1346             pinged(n, NULL);
    1347         }
    1348         /* Discard it from any searches in progress. */
    1349         sr = searches;
    1350         while(sr) {
    1351             for(i = 0; i < sr->numnodes; i++)
    1352                 if(id_cmp(sr->nodes[i].id, id) == 0)
    1353                     flush_search_node(&sr->nodes[i], sr);
    1354             sr = sr->next;
    1355         }
    1356     }
    1357     /* And make sure we don't hear from it again. */
    1358     memcpy(&blacklist[next_blacklisted], sa, salen);
    1359     next_blacklisted = (next_blacklisted + 1) % DHT_MAX_BLACKLISTED;
    1360 }
    1361 
    13621385static int
    13631386rotate_secrets(void)
     
    18471870             dht_callback *callback, void *closure)
    18481871{
    1849     int i;
    1850 
    18511872    gettimeofday(&now, NULL);
    18521873
     
    18661887            goto dontread;
    18671888
    1868         for(i = 0; i < DHT_MAX_BLACKLISTED; i++) {
    1869             if(memcmp(&blacklist[i], from, fromlen) == 0) {
    1870                 debugf("Received packet from blacklisted node.\n");
    1871                 goto dontread;
    1872             }
    1873         }
    1874 
    1875         /* See parse_message. */
     1889        if(node_blacklisted(from, fromlen)) {
     1890            debugf("Received packet from blacklisted node.\n");
     1891            goto dontread;
     1892        }
    18761893
    18771894        if(((char*)buf)[buflen] != '\0') {
     
    19161933                   time-out all our searches that go through this node.
    19171934                   Kill it. */
    1918                 broken_node(id, from, fromlen);
     1935                blacklist_node(id, from, fromlen);
    19191936                goto dontread;
    19201937            }
     
    19341951                if(nodes_len % 26 != 0 || nodes6_len % 38 != 0) {
    19351952                    debugf("Unexpected length for node info!\n");
    1936                     broken_node(id, from, fromlen);
     1953                    blacklist_node(id, from, fromlen);
    19371954                } else if(gp && sr == NULL) {
    19381955                    debugf("Unknown search!\n");
     
    23012318        abort();
    23022319
     2320    if(node_blacklisted(sa, salen)) {
     2321        debugf("Attempting to send to blacklisted node.\n");
     2322        errno = EPERM;
     2323        return -1;
     2324    }
     2325
    23032326    if(sa->sa_family == AF_INET)
    23042327        s = dht_socket;
  • trunk/third-party/dht/dht.h

    r11663 r12586  
    5151
    5252/* This must be provided by the user. */
     53int dht_blacklisted(const struct sockaddr *sa, int salen);
    5354void dht_hash(void *hash_return, int hash_size,
    5455              const void *v1, int len1,
Note: See TracChangeset for help on using the changeset viewer.