More dialer code
This commit is contained in:
parent
81263fc1a2
commit
5c08094548
13 changed files with 231 additions and 33 deletions
|
@ -2,7 +2,7 @@
|
|||
|
||||
#include "libp2p/conn/connection.h"
|
||||
|
||||
struct Connection* libp2p_conn_connection_open(struct TransportDialer* transport_dialer, struct maddr* multiaddress) {
|
||||
struct Connection* libp2p_conn_connection_new(struct TransportDialer* transport_dialer, struct MultiAddress* multiaddress) {
|
||||
struct Connection* out = NULL;
|
||||
|
||||
if (transport_dialer != NULL) {
|
||||
|
@ -13,3 +13,11 @@ struct Connection* libp2p_conn_connection_open(struct TransportDialer* transport
|
|||
}
|
||||
return out;
|
||||
}
|
||||
|
||||
void libp2p_conn_connection_free(struct Connection* connection) {
|
||||
if (connection != NULL) {
|
||||
fclose(connection->socket_handle);
|
||||
free(connection);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -15,13 +15,21 @@
|
|||
struct Dialer* libp2p_conn_dialer_new(char* peer_id, struct PrivateKey* private_key) {
|
||||
struct Dialer* dialer = (struct Dialer*)malloc(sizeof(struct Dialer));
|
||||
if (dialer != NULL) {
|
||||
dialer->peer_id = peer_id;
|
||||
dialer->private_key = private_key;
|
||||
dialer->peer_id = malloc(strlen(peer_id) + 1);
|
||||
if (dialer->peer_id != NULL) {
|
||||
strcpy(dialer->peer_id, peer_id);
|
||||
dialer->private_key = (struct PrivateKey*)malloc(sizeof(struct PrivateKey));
|
||||
if (dialer->private_key != NULL) {
|
||||
libp2p_crypto_private_key_copy(private_key, dialer->private_key);
|
||||
dialer->fallback_dialer = NULL;
|
||||
dialer->transport_dialers = NULL;
|
||||
}
|
||||
return dialer;
|
||||
}
|
||||
}
|
||||
}
|
||||
libp2p_conn_dialer_free(dialer);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/**
|
||||
* free resources from the Dialer
|
||||
|
@ -49,10 +57,10 @@ void libp2p_conn_dialer_free(struct Dialer* in) {
|
|||
* @param muiltiaddress who to connect to
|
||||
* @returns a Connection, or NULL
|
||||
*/
|
||||
struct Connection* libp2p_conn_dialer_get_connection(struct Dialer* dialer, struct maddr* multiaddress) {
|
||||
struct Connection* libp2p_conn_dialer_get_connection(struct Dialer* dialer, struct MultiAddress* multiaddress) {
|
||||
struct Connection* conn = libp2p_conn_transport_dialer_get(dialer->transport_dialers, multiaddress);
|
||||
if (conn == NULL) {
|
||||
conn = libp2p_conn_connection_open(dialer->fallback_dialer, multiaddress);
|
||||
conn = libp2p_conn_connection_new(dialer->fallback_dialer, multiaddress);
|
||||
}
|
||||
return conn;
|
||||
}
|
||||
|
|
|
@ -2,17 +2,18 @@
|
|||
|
||||
#include "libp2p/conn/transport_dialer.h"
|
||||
|
||||
struct TransportDialer* libp2p_conn_transport_dialer_new(struct maddr* multiaddr) {
|
||||
struct TransportDialer* libp2p_conn_transport_dialer_new(struct MultiAddress* multiaddr) {
|
||||
struct TransportDialer* out = (struct TransportDialer*)malloc(sizeof(struct TransportDialer));
|
||||
if (out != NULL) {
|
||||
out->multiaddr = (struct maddr*)malloc(sizeof(struct maddr));
|
||||
out->multiaddr = (struct MultiAddress*)malloc(sizeof(struct MultiAddress));
|
||||
if (out->multiaddr == NULL) {
|
||||
free(out);
|
||||
libp2p_conn_transport_dialer_free(out);
|
||||
return NULL;
|
||||
}
|
||||
if (multiaddress_copy(multiaddr, out->multiaddr) == 0) {
|
||||
libp2p_conn_transport_dialer_free(out);
|
||||
return NULL;
|
||||
}
|
||||
out->multiaddr->bsize[0] = multiaddr->bsize[0];
|
||||
memcpy(out->multiaddr->bytes, multiaddr->bytes, 400);
|
||||
memcpy(out->multiaddr->string, multiaddr->string, 800);
|
||||
}
|
||||
return out;
|
||||
}
|
||||
|
@ -31,7 +32,7 @@ void libp2p_conn_transport_dialer_free(struct TransportDialer* in) {
|
|||
* @param multiaddr the address
|
||||
* @returns a connection, or NULL if no appropriate dialer was found
|
||||
*/
|
||||
struct Connection* libp2p_conn_transport_dialer_get(struct Libp2pLinkedList* transport_dialers, struct maddr* multiaddr) {
|
||||
struct Connection* libp2p_conn_transport_dialer_get(struct Libp2pLinkedList* transport_dialers, struct MultiAddress* multiaddr) {
|
||||
//TODO: implement this method
|
||||
return NULL;
|
||||
}
|
||||
|
|
|
@ -24,7 +24,7 @@ int libp2p_crypto_encoding_base64_encode(const unsigned char* input_data, size_t
|
|||
* @param output_data the buffer to store the output
|
||||
* @param max_output_length the length of the output buffer
|
||||
* @param bytes_written the number of bytes written to output_data
|
||||
* @returns a pointer to the decoded data
|
||||
* @returns true(1) on success, otherwise 0
|
||||
*/
|
||||
int libp2p_crypto_encoding_base64_decode(const unsigned char* input_data, size_t input_length, unsigned char* output_data, size_t max_output_length, size_t* bytes_written) {
|
||||
int retVal = mbedtls_base64_decode(output_data, max_output_length, bytes_written, input_data, input_length);
|
||||
|
|
18
crypto/key.c
18
crypto/key.c
|
@ -130,11 +130,25 @@ void libp2p_crypto_private_key_free(struct PrivateKey* in) {
|
|||
}
|
||||
}
|
||||
|
||||
int libp2p_crypto_private_key_protobuf_encode_size(struct PrivateKey* in) {
|
||||
int libp2p_crypto_private_key_copy(const struct PrivateKey* source, struct PrivateKey* destination) {
|
||||
if (source != NULL && destination != NULL) {
|
||||
destination->type = source->type;
|
||||
destination->data = (unsigned char*)malloc(source->data_size);
|
||||
if (destination->data != NULL) {
|
||||
memcpy(destination->data, source->data, source->data_size);
|
||||
destination->data_size = source->data_size;
|
||||
return 1;
|
||||
}
|
||||
libp2p_crypto_private_key_free(destination);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
size_t libp2p_crypto_private_key_protobuf_encode_size(const struct PrivateKey* in) {
|
||||
return 22 + in->data_size;
|
||||
}
|
||||
|
||||
int libp2p_crypto_private_key_protobuf_encode(struct PrivateKey* in, unsigned char* buffer, size_t max_buffer_length, size_t* bytes_written) {
|
||||
int libp2p_crypto_private_key_protobuf_encode(const struct PrivateKey* in, unsigned char* buffer, size_t max_buffer_length, size_t* bytes_written) {
|
||||
*bytes_written = 0;
|
||||
size_t bytes_used;
|
||||
// type (RSA vs ED25519)
|
||||
|
|
|
@ -1,3 +1,4 @@
|
|||
#pragma once
|
||||
/**
|
||||
* Implements an interface to connect and talk to different nodes.
|
||||
* A Dialer will connect, and return a Connection structure
|
||||
|
@ -7,15 +8,15 @@
|
|||
#include "multiaddr/multiaddr.h"
|
||||
|
||||
struct Connection {
|
||||
int socket_handle;
|
||||
FILE* socket_handle;
|
||||
/**
|
||||
* Read from the stream
|
||||
* @param socket_handle the socket to read from
|
||||
* @param in what was read in NOTE: this allocates memory
|
||||
* @param in_size the number of bytes read in
|
||||
* @returns 0 on success, otherwise an error code
|
||||
* @returns number of bytes written or negative number on error
|
||||
*/
|
||||
int (*read)(int socket_handle, char** in, size_t* in_size);
|
||||
int (*read)(const struct Connection* conn, char** in, size_t* in_size);
|
||||
/**
|
||||
* Write to the stream
|
||||
* @param socket_handle the socket to write to
|
||||
|
@ -23,7 +24,21 @@ struct Connection {
|
|||
* @param out_size the number of bytes to write
|
||||
* @returns 0 on success, otherwise an error code
|
||||
*/
|
||||
int (*write)(int socket_handle, char* out, size_t* out_size);
|
||||
int (*write)(const struct Connection* conn, char* out, size_t out_size);
|
||||
};
|
||||
|
||||
struct Connection* libp2p_conn_connection_open(struct TransportDialer* transport_dialer, struct maddr* multiaddress);
|
||||
/**
|
||||
* creates a new connection
|
||||
* @param transport_dialer the TransportDialer to use
|
||||
* @param multiaddress the destination
|
||||
* @returns a connection that is ready to be read from / written to
|
||||
*/
|
||||
struct Connection* libp2p_conn_connection_new(struct TransportDialer* transport_dialer, struct MultiAddress* multiaddress);
|
||||
|
||||
/***
|
||||
* close a connection and dispose of struct
|
||||
* @param connection the resource to clean up
|
||||
*/
|
||||
void libp2p_conn_connection_free(struct Connection* connection);
|
||||
|
||||
|
||||
|
|
|
@ -6,6 +6,8 @@
|
|||
|
||||
#include "libp2p/crypto/key.h"
|
||||
#include "multiaddr/multiaddr.h"
|
||||
#include "libp2p/conn/connection.h"
|
||||
#include "libp2p/conn/transport_dialer.h"
|
||||
|
||||
struct Dialer {
|
||||
/**
|
||||
|
@ -41,4 +43,4 @@ void libp2p_conn_dialer_free(struct Dialer* in);
|
|||
* @param muiltiaddress who to connect to
|
||||
* @returns a Connection, or NULL
|
||||
*/
|
||||
struct Connection* libp2p_conn_dialer_get_connection(struct Dialer* dialer, struct maddr* multiaddress);
|
||||
struct Connection* libp2p_conn_dialer_get_connection(struct Dialer* dialer, struct MultiAddress* multiaddress);
|
||||
|
|
|
@ -4,10 +4,10 @@
|
|||
#include "libp2p/utils/linked_list.h"
|
||||
|
||||
struct TransportDialer {
|
||||
struct maddr* multiaddr;
|
||||
struct MultiAddress* multiaddr;
|
||||
};
|
||||
|
||||
struct TransportDialer* libp2p_conn_transport_dialer_new(struct maddr* multiaddr);
|
||||
struct TransportDialer* libp2p_conn_transport_dialer_new(struct MultiAddress* multiaddr);
|
||||
void libp2p_conn_transport_dialer_free(struct TransportDialer* in);
|
||||
|
||||
struct Connection* libp2p_conn_transport_dialer_get(struct Libp2pLinkedList* transport_dialers, struct maddr* multiaddr);
|
||||
struct Connection* libp2p_conn_transport_dialer_get(struct Libp2pLinkedList* transport_dialers, struct MultiAddress* multiaddr);
|
||||
|
|
|
@ -23,6 +23,7 @@ void libp2p_crypto_public_key_free(struct PublicKey* in);
|
|||
|
||||
struct PrivateKey* libp2p_crypto_private_key_new();
|
||||
void libp2p_crypto_private_key_free(struct PrivateKey* in);
|
||||
int libp2p_crypto_private_key_copy(const struct PrivateKey* source, struct PrivateKey* destination);
|
||||
|
||||
/**
|
||||
* Unmarshal a public key from a protobuf
|
||||
|
@ -30,7 +31,10 @@ void libp2p_crypto_private_key_free(struct PrivateKey* in);
|
|||
int libp2p_crypto_public_key_protobuf_decode(unsigned char* buffer, size_t buffer_length, struct PublicKey** out);
|
||||
size_t libp2p_crypto_public_key_protobuf_encode_size(const struct PublicKey* in);
|
||||
int libp2p_crypto_public_key_protobuf_encode(const struct PublicKey* in, unsigned char* buffer, size_t max_buffer_length, size_t* bytes_written);
|
||||
// private key
|
||||
int libp2p_crypto_private_key_protobuf_decode(unsigned char* buffer, size_t buffer_length, struct PrivateKey** out);
|
||||
size_t libp2p_crypto_private_key_protobuf_encode_size(const struct PrivateKey* in);
|
||||
int libp2p_crypto_private_key_protobuf_encode(const struct PrivateKey* in, unsigned char* buffer, size_t max_buffer_length, size_t* bytes_written);
|
||||
|
||||
/**
|
||||
* convert a public key into a peer id
|
||||
|
|
|
@ -5,7 +5,7 @@ ifdef DEBUG
|
|||
CFLAGS += -g3
|
||||
endif
|
||||
|
||||
LFLAGS = -L../ -L../../c-multihash
|
||||
LFLAGS = -L../ -L../../c-multihash -L../../c-multiaddr
|
||||
DEPS = crypto/test_base58.h crypto/test_rsa.h test_mbedtls.h
|
||||
OBJS = testit.o ../../c-protobuf/protobuf.o ../../c-protobuf/varint.o ../libp2p.a
|
||||
|
||||
|
@ -13,7 +13,7 @@ OBJS = testit.o ../../c-protobuf/protobuf.o ../../c-protobuf/varint.o ../libp2p.
|
|||
$(CC) -c -o $@ $< $(CFLAGS)
|
||||
|
||||
testit_libp2p: $(OBJS) $(DEPS)
|
||||
$(CC) -o $@ $(OBJS) $(LFLAGS) -lp2p -lm -lmultihash
|
||||
$(CC) -o $@ $(OBJS) $(LFLAGS) -lp2p -lm -lmultihash -lmultiaddr
|
||||
|
||||
all_others:
|
||||
cd ../crypto; make all;
|
||||
|
|
|
@ -1,12 +1,64 @@
|
|||
#include <stdlib.h>
|
||||
|
||||
#include "libp2p/conn/dialer.h"
|
||||
#include "test_helper.h"
|
||||
|
||||
int test_dialer_new() {
|
||||
struct PrivateKey* private_key = NULL;
|
||||
struct Dialer* dialer = libp2p_conn_dialer_new("ABC", private_key);
|
||||
char* peer_id = "QmQSDGgxSVTkHmtT25rTzQtc5C1Yg8SpGK3BTws8YsJ4x3";
|
||||
struct PrivateKey* private_key = libp2p_crypto_private_key_new();
|
||||
struct Dialer* dialer = libp2p_conn_dialer_new(peer_id, private_key);
|
||||
if (dialer == NULL)
|
||||
return 0;
|
||||
libp2p_conn_dialer_free(dialer);
|
||||
return 1;
|
||||
}
|
||||
|
||||
int test_dialer_dial() {
|
||||
int retVal = 0;
|
||||
char* config_dir = "/home/parallels/.ipfs/config";
|
||||
char* destination_string = "/ip/192.210.179.217/tcp/4001";
|
||||
char* peer_id = NULL;
|
||||
struct PrivateKey* private_key = NULL;
|
||||
struct Dialer* dialer = NULL;
|
||||
struct MultiAddress* destination_address = NULL;
|
||||
struct Connection* conn = NULL;
|
||||
char* result = NULL;
|
||||
size_t result_size = 0;
|
||||
|
||||
test_helper_get_id_from_config(config_dir, &private_key, &peer_id);
|
||||
if (private_key == NULL)
|
||||
goto exit;
|
||||
|
||||
dialer = libp2p_conn_dialer_new(peer_id, private_key);
|
||||
if (dialer == NULL)
|
||||
goto exit;
|
||||
|
||||
destination_address = multiaddress_new_from_string(destination_string);
|
||||
if (destination_address == NULL)
|
||||
goto exit;
|
||||
|
||||
// now try to dial
|
||||
conn = libp2p_conn_dialer_get_connection(dialer, destination_address);
|
||||
if (conn == NULL)
|
||||
goto exit;
|
||||
|
||||
if (conn->write(conn, "ping", 4) == 0)
|
||||
goto exit;
|
||||
|
||||
if (conn->read(conn, &result, &result_size) == 0)
|
||||
goto exit;
|
||||
|
||||
if (result_size < 4 || strncmp(result, "pong", 4) != 0)
|
||||
goto exit;
|
||||
|
||||
// clean up resources
|
||||
retVal = 1;
|
||||
exit:
|
||||
if (result != NULL)
|
||||
free(result);
|
||||
multiaddress_free(destination_address);
|
||||
libp2p_conn_dialer_free(dialer);
|
||||
libp2p_crypto_private_key_free(private_key);
|
||||
libp2p_conn_connection_free(conn);
|
||||
return retVal;
|
||||
}
|
||||
|
|
92
test/test_helper.h
Normal file
92
test/test_helper.h
Normal file
|
@ -0,0 +1,92 @@
|
|||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
|
||||
#include "libp2p/crypto/key.h"
|
||||
|
||||
void read_file(char* path, char** contents) {
|
||||
FILE* fd = fopen(path, "r");
|
||||
fseek(fd, 0L, SEEK_END);
|
||||
size_t num_bytes = ftell(fd);
|
||||
rewind(fd);
|
||||
*contents = malloc(num_bytes);
|
||||
fread(*contents, 1, num_bytes, fd);
|
||||
fclose(fd);
|
||||
return;
|
||||
}
|
||||
|
||||
struct PrivateKey* base64ToPrivateKey(char* base64) {
|
||||
int retVal = 0;
|
||||
size_t decode_base64_size = 0;
|
||||
unsigned char* decode_base64 = NULL;
|
||||
struct PrivateKey* out = NULL;
|
||||
|
||||
// 1) take the private key and turn it back into bytes (decode base 64)
|
||||
decode_base64_size = libp2p_crypto_encoding_base64_decode_size(strlen(base64));
|
||||
decode_base64 = (unsigned char*)malloc(decode_base64_size);
|
||||
if (decode_base64 == NULL)
|
||||
goto exit;
|
||||
memset(decode_base64, 0, decode_base64_size);
|
||||
|
||||
if (!libp2p_crypto_encoding_base64_decode((unsigned char*)base64, strlen(base64), &decode_base64[0], decode_base64_size, &decode_base64_size))
|
||||
goto exit;
|
||||
|
||||
if (!libp2p_crypto_private_key_protobuf_decode(decode_base64, decode_base64_size, &out))
|
||||
goto exit;
|
||||
|
||||
retVal = 1;
|
||||
exit:
|
||||
if (retVal != 1) {
|
||||
libp2p_crypto_private_key_free(out);
|
||||
out = NULL;
|
||||
}
|
||||
return out;
|
||||
}
|
||||
|
||||
int test_helper_get_id_from_config(char* path, struct PrivateKey** private_ptr, char** peer_ptr) {
|
||||
int retVal = 0;
|
||||
char* contents = NULL;
|
||||
char* ptr = NULL;
|
||||
char* end = NULL;
|
||||
int length = 0;
|
||||
read_file(path, &contents);
|
||||
if (contents == NULL)
|
||||
goto exit;
|
||||
|
||||
// peer id
|
||||
ptr = strstr(contents, "PeerID");
|
||||
if (ptr == NULL)
|
||||
goto exit;
|
||||
|
||||
ptr = strstr(ptr, "Qm");
|
||||
if (ptr == NULL)
|
||||
goto exit;
|
||||
|
||||
end = strstr(ptr, "\"");
|
||||
|
||||
length = end - ptr;
|
||||
*peer_ptr = malloc(length + 1);
|
||||
if (*peer_ptr == NULL)
|
||||
goto exit;
|
||||
memcpy(*peer_ptr, ptr, length);
|
||||
(*peer_ptr)[length] = 0;
|
||||
|
||||
// private key
|
||||
ptr = strstr(contents, "PrivKey\":");
|
||||
if (ptr == NULL)
|
||||
goto exit;
|
||||
ptr += 9;
|
||||
ptr = strstr(ptr, "\"");
|
||||
ptr++;
|
||||
|
||||
end = strstr(ptr, "\"");
|
||||
end[0] = 0;
|
||||
|
||||
// turn the encoded private key into a struct
|
||||
*private_ptr = base64ToPrivateKey(ptr);
|
||||
|
||||
retVal = 1;
|
||||
exit:
|
||||
if (contents != NULL)
|
||||
free(contents);
|
||||
return retVal;
|
||||
}
|
|
@ -36,7 +36,8 @@ const char* names[] = {
|
|||
"test_multistream_connect",
|
||||
"test_multistream_get_list",
|
||||
"test_ephemeral_key_generate",
|
||||
"test_dialer_new"
|
||||
"test_dialer_new",
|
||||
"test_dialer_dial"
|
||||
};
|
||||
|
||||
int (*funcs[])(void) = {
|
||||
|
@ -65,7 +66,8 @@ int (*funcs[])(void) = {
|
|||
test_multistream_connect,
|
||||
test_multistream_get_list,
|
||||
test_ephemeral_key_generate,
|
||||
test_dialer_new
|
||||
test_dialer_new,
|
||||
test_dialer_dial
|
||||
};
|
||||
|
||||
int testit(const char* name, int (*func)(void)) {
|
||||
|
|
Loading…
Reference in a new issue