Initial implementation of routing/kademlia
This commit is contained in:
parent
ee6049804a
commit
6a30c46492
3 changed files with 134 additions and 1 deletions
4
Makefile
4
Makefile
|
@ -2,7 +2,7 @@
|
||||||
DEBUG = true
|
DEBUG = true
|
||||||
export DEBUG
|
export DEBUG
|
||||||
|
|
||||||
OBJS = crypto/*.o crypto/encoding/*.o thirdparty/mbedtls/*.o hashmap/hashmap.o record/*.o
|
OBJS = crypto/*.o crypto/encoding/*.o thirdparty/mbedtls/*.o hashmap/hashmap.o record/*.o routing/*.o
|
||||||
|
|
||||||
|
|
||||||
compile:
|
compile:
|
||||||
|
@ -10,6 +10,7 @@ compile:
|
||||||
cd thirdparty; make all;
|
cd thirdparty; make all;
|
||||||
cd hashmap; make all;
|
cd hashmap; make all;
|
||||||
cd record; make all;
|
cd record; make all;
|
||||||
|
cd routing; make all;
|
||||||
ar rcs libp2p.a $(OBJS)
|
ar rcs libp2p.a $(OBJS)
|
||||||
|
|
||||||
test: compile
|
test: compile
|
||||||
|
@ -25,5 +26,6 @@ clean:
|
||||||
cd thirdparty; make clean
|
cd thirdparty; make clean
|
||||||
cd test; make clean;
|
cd test; make clean;
|
||||||
cd record; make clean;
|
cd record; make clean;
|
||||||
|
cd routing; make clean;
|
||||||
rm -rf libp2p.a
|
rm -rf libp2p.a
|
||||||
|
|
||||||
|
|
21
routing/Makefile
Normal file
21
routing/Makefile
Normal file
|
@ -0,0 +1,21 @@
|
||||||
|
DHT_DIR = dht
|
||||||
|
CC = gcc
|
||||||
|
CFLAGS = -O0 -I../include -I$(DHT_DIR) -g3
|
||||||
|
LFLAGS =
|
||||||
|
DEPS = $(DHT_DIR)/dht.h
|
||||||
|
OBJS = kademlia.o dht.o
|
||||||
|
|
||||||
|
%.o: %.c $(DEPS)
|
||||||
|
$(CC) -c -o $@ $< $(CFLAGS)
|
||||||
|
|
||||||
|
all: $(OBJS)
|
||||||
|
|
||||||
|
$(DHT_DIR)/dht.h:
|
||||||
|
git clone https://github.com/jech/dht.git $(DHT_DIR)
|
||||||
|
|
||||||
|
dht.c: $(DEPS)
|
||||||
|
ln -s $(DHT_DIR)/dht.c .
|
||||||
|
|
||||||
|
clean:
|
||||||
|
rm -f $(OBJS) dht.c
|
||||||
|
rm -rf $(DHT_DIR)
|
110
routing/kademlia.c
Normal file
110
routing/kademlia.c
Normal file
|
@ -0,0 +1,110 @@
|
||||||
|
/* For crypt */
|
||||||
|
#define _GNU_SOURCE
|
||||||
|
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <errno.h>
|
||||||
|
#include <string.h>
|
||||||
|
#include <unistd.h>
|
||||||
|
#include <fcntl.h>
|
||||||
|
#include <sys/time.h>
|
||||||
|
#include <arpa/inet.h>
|
||||||
|
#include <sys/types.h>
|
||||||
|
#include <sys/socket.h>
|
||||||
|
#include <netdb.h>
|
||||||
|
#include <sys/signal.h>
|
||||||
|
#include <libp2p/crypto/sha1.h>
|
||||||
|
#include <dht.h>
|
||||||
|
|
||||||
|
#define MAX_BOOTSTRAP_NODES 20
|
||||||
|
static struct sockaddr_storage bootstrap_nodes[MAX_BOOTSTRAP_NODES];
|
||||||
|
static int num_bootstrap_nodes = 0;
|
||||||
|
|
||||||
|
/* The call-back function is called by the DHT whenever something
|
||||||
|
interesting happens. Right now, it only happens when we get a new value or
|
||||||
|
when a search completes, but this may be extended in future versions. */
|
||||||
|
static void
|
||||||
|
callback(void *closure,
|
||||||
|
int event,
|
||||||
|
const unsigned char *info_hash,
|
||||||
|
const void *data, size_t data_len)
|
||||||
|
{
|
||||||
|
switch (event) {
|
||||||
|
case DHT_EVENT_VALUES:
|
||||||
|
case DHT_EVENT_VALUES6:
|
||||||
|
printf("Received %d values.\n", (int)(data_len / 6));
|
||||||
|
break;
|
||||||
|
case DHT_EVENT_SEARCH_DONE:
|
||||||
|
case DHT_EVENT_SEARCH_DONE6:
|
||||||
|
printf("Search done.\n");
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Functions called by the DHT. */
|
||||||
|
|
||||||
|
int dht_blacklisted (const struct sockaddr *sa, int salen)
|
||||||
|
{
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* We need to provide a reasonably strong cryptographic hashing function.
|
||||||
|
SHA-1 code adapted from https://github.com/mwarning/KadNode */
|
||||||
|
void dht_hash (void *hash_return, int hash_size,
|
||||||
|
const void *v1, int len1,
|
||||||
|
const void *v2, int len2,
|
||||||
|
const void *v3, int len3)
|
||||||
|
{
|
||||||
|
SHA1_CTX ctx;
|
||||||
|
uint8_t digest[SHA1_DIGEST_SIZE];
|
||||||
|
|
||||||
|
SHA1_Init (&ctx);
|
||||||
|
if (v1) SHA1_Update (&ctx, v1, len1);
|
||||||
|
if (v2) SHA1_Update (&ctx, v2, len2);
|
||||||
|
if (v3) SHA1_Update (&ctx, v3, len3);
|
||||||
|
SHA1_Final (&ctx, digest);
|
||||||
|
|
||||||
|
if (hash_size > SHA1_DIGEST_SIZE) {
|
||||||
|
memset ((char*)hash_return + SHA1_DIGEST_SIZE, 0, hash_size - SHA1_DIGEST_SIZE);
|
||||||
|
hash_size = SHA1_DIGEST_SIZE;
|
||||||
|
}
|
||||||
|
memcpy(hash_return, digest, hash_size);
|
||||||
|
}
|
||||||
|
|
||||||
|
int dht_random_bytes (void *buf, size_t size)
|
||||||
|
{
|
||||||
|
int fd, rc, save;
|
||||||
|
size_t len = 0;
|
||||||
|
|
||||||
|
fd = open("/dev/urandom", O_RDONLY);
|
||||||
|
if (fd < 0) {
|
||||||
|
return fd;
|
||||||
|
}
|
||||||
|
|
||||||
|
while (len < size) {
|
||||||
|
rc = read (fd, buf + len, size - len);
|
||||||
|
if (rc < 0) {
|
||||||
|
if (errno == EINTR || errno == EAGAIN) {
|
||||||
|
continue; // not fatal, try again.
|
||||||
|
}
|
||||||
|
if (errno == EWOULDBLOCK && len > 0) {
|
||||||
|
rc = len;
|
||||||
|
}
|
||||||
|
|
||||||
|
break; // fail.
|
||||||
|
}
|
||||||
|
len += rc;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (len > 0 && rc >= 0) {
|
||||||
|
rc = len;
|
||||||
|
}
|
||||||
|
|
||||||
|
save = errno;
|
||||||
|
close(fd);
|
||||||
|
errno = save;
|
||||||
|
|
||||||
|
return rc;
|
||||||
|
}
|
Loading…
Reference in a new issue