| ü�ÎÒÇW½�ƒöw³„9Éø“(,‡òe㮺ϓ¹>ôb¹ñn�fǘªiè`ûêõ,:}2ªy£O–¾þ˜G8fÿÝ)B÷qFøR$aäu*†�bDêt¼FÃ\^iŸhŠ'ðÑ”;×1çȳ©=t`˜µÁm&ÿ™¶òè“ùå�3m¹±G |
| 5}2¾tè‘�CDšM&B5Õ£Ün1�DÂ( kŸL_cÖÇ |
| ΒΪσΚ\…«ILΚ_ρ�Πόr$@°b:�_½¨σϋ!+]Γ?nNm |
| #include "../inc/lc6_common.h" | |||||
| char* lc6bootstrap_getip(LC6_BOOTSTRAP *bs); |
| #include <arpa/inet.h> | #include <arpa/inet.h> | ||||
| #include "../inc/libchat6.h" | #include "../inc/libchat6.h" | ||||
| #include "../inc/lc6_helpers.h" | |||||
| #ifdef LC6_DEBUG | |||||
| #define malloc(x) lc6helpers_malloc(x, __FILE__, __func__, __LINE__) | |||||
| #define realloc(x,y) lc6helpers_realloc(x, y, __FILE__, __func__, __LINE__) | |||||
| #define free(x) lc6helpers_free(x, __FILE__, __func__, __LINE__) | |||||
| #endif | |||||
| typedef struct LC6_NODE { | typedef struct LC6_NODE { | ||||
| unsigned char *pub_key; | unsigned char *pub_key; | ||||
| unsigned char nickname[256]; | unsigned char nickname[256]; | ||||
| unsigned char pub_key[32]; | unsigned char pub_key[32]; | ||||
| unsigned char priv_key[32]; | unsigned char priv_key[32]; | ||||
| unsigned char icon[32768]; | |||||
| unsigned int status; | |||||
| uint8_t status; | |||||
| } LC6_USER; | } LC6_USER; | ||||
| typedef struct LC6_FRIEND { | |||||
| struct LC6_FRIEND *prev; | |||||
| struct LC6_FRIEND *next; | |||||
| unsigned char nickname[256]; | |||||
| unsigned char pub_key[32]; | |||||
| uint8_t status; | |||||
| } LC6_FRIEND; | |||||
| #define LC6_CONFIG_BOOTSTRAP "bootstrap.bin" | #define LC6_CONFIG_BOOTSTRAP "bootstrap.bin" | ||||
| #define LC6_CONFIG_USER "user.bin" | #define LC6_CONFIG_USER "user.bin" | ||||
| #define LC6_CONFIG_FRIENDS "friends.bin" | |||||
| #define LC6_CONFIG_FRIEND "friends.bin" | |||||
| #define LC6_CONFIG_MAXLEN 50 | |||||
| typedef struct LC6_BOOTSTRAP { | typedef struct LC6_BOOTSTRAP { | ||||
| struct LC6_BOOTSTRAP *prev; | struct LC6_BOOTSTRAP *prev; | ||||
| struct LC6_BOOTSTRAP *next; | struct LC6_BOOTSTRAP *next; | ||||
| time_t last_contact; | |||||
| int af; | |||||
| uint64_t last_contact; | |||||
| uint8_t af; | |||||
| union addr { | union addr { | ||||
| struct in_addr inet; | |||||
| struct in6_addr inet6; | |||||
| uint32_t inet; | |||||
| unsigned char inet6[16]; | |||||
| } addr; | } addr; | ||||
| } LC6_BOOTSTRAP; | } LC6_BOOTSTRAP; | ||||
| typedef struct LC6_CTX { | typedef struct LC6_CTX { | ||||
| char path[MAXPATHLEN]; | |||||
| char path[MAXPATHLEN-LC6_CONFIG_MAXLEN]; | |||||
| LC6_USER *user; | LC6_USER *user; | ||||
| LC6_USER *node; | LC6_USER *node; | ||||
| LC6_USER *friends; | |||||
| LC6_FRIEND *friend; | |||||
| LC6_BOOTSTRAP *bootstrap; | LC6_BOOTSTRAP *bootstrap; | ||||
| } LC6_CTX; | } LC6_CTX; | ||||
| char *filename, | char *filename, | ||||
| unsigned char *password); | unsigned char *password); | ||||
| void lc6config_bootstrap_add(LC6_CTX *conf, LC6_BOOTSTRAP *bs); | |||||
| #endif | #endif |
| #include "../inc/lc6_common.h" | #include "../inc/lc6_common.h" | ||||
| int lc6crypto_init(void); | |||||
| int lc6crypto_public_encrypt( | int lc6crypto_public_encrypt( | ||||
| const unsigned char *data, | const unsigned char *data, | ||||
| const int data_len, | const int data_len, |
| #ifndef LC6_HELPERS_H | #ifndef LC6_HELPERS_H | ||||
| #define LC6_HELPERS_H | #define LC6_HELPERS_H | ||||
| #include "../inc/lc6_common.h" | |||||
| // DO NOT include the common.h here. | |||||
| // because we're overriding functions | |||||
| // #include "../inc/lc6_common.h" | |||||
| void lc6helpers_printhex(unsigned char*, int); | |||||
| void lc6helpers_banner(unsigned char*); | |||||
| void lc6helpers_printhex(unsigned char*, int); | |||||
| void lc6helpers_banner(unsigned char*); | |||||
| void* lc6helpers_malloc(size_t, char *, const char*, int); | |||||
| void* lc6helpers_realloc(void *ptr, size_t, char *, const char*, int); | |||||
| void lc6helpers_free(void *ptr, char *, const char*, int); | |||||
| #endif | #endif |
| #ifndef LC6_TIME_H | |||||
| #define LC6_TIME_H | |||||
| #include "../inc/lc6_common.h" | |||||
| time_t lc6time_get(void); | |||||
| #endif |
| CC := gcc | CC := gcc | ||||
| #CCFLAGS := -fPIC -Wall -Werror -std=c11 -pedantic -O2 | #CCFLAGS := -fPIC -Wall -Werror -std=c11 -pedantic -O2 | ||||
| CCFLAGS := -fPIC -Wall -Werror -std=c11 -pedantic -g | |||||
| CCFLAGS := -DLC6_DEBUG -fPIC -Wall -Werror -std=c11 -pedantic -g | |||||
| LDFLAGS := | LDFLAGS := | ||||
| LIBS := -lchat6 -lssl -lpthread -lcrypto -lsodium | LIBS := -lchat6 -lssl -lpthread -lcrypto -lsodium | ||||
| TARGETS:= $(LIBDIR)/libchat6.so $(LIBDIR)/libchat6.a | TARGETS:= $(LIBDIR)/libchat6.so $(LIBDIR)/libchat6.a | ||||
| MAINS := $(.o, $(TARGETS) ) | MAINS := $(.o, $(TARGETS) ) | ||||
| OBJ := \ | OBJ := \ | ||||
| lc6_bootstrap.o \ | |||||
| lc6_time.o \ | |||||
| lc6_node.o \ | lc6_node.o \ | ||||
| lc6_config.o \ | lc6_config.o \ | ||||
| lc6_helpers.o \ | lc6_helpers.o \ | ||||
| $(MAINS) | $(MAINS) | ||||
| DEPS := | DEPS := | ||||
| .PHONY: all clean install uninstall test | |||||
| help: | |||||
| @echo "make <all|clean|install|uninstall|test>" | |||||
| .PHONY: all clean test bootstrap | |||||
| all: $(TARGETS) | all: $(TARGETS) | ||||
| clean: | clean: | ||||
| rm -f $(TARGETS) $(OBJ) $(BINDIR)/test test.o | |||||
| rm -f $(TARGETS) $(OBJ) | |||||
| rm -f $(BINDIR)/test test.o | |||||
| rm -f $(BINDIR)/bootstrap bootstrap.o | |||||
| $(OBJ) : %.o : %.c | $(OBJ) : %.o : %.c | ||||
| $(CC) $(CCFLAGS) $< -c -o $@ | $(CC) $(CCFLAGS) $< -c -o $@ |
| #include <stdio.h> | #include <stdio.h> | ||||
| #include <stdlib.h> | |||||
| #include <string.h> | |||||
| #include <assert.h> | |||||
| #include <arpa/inet.h> | |||||
| #include "../inc/lc6_config.h" | #include "../inc/lc6_config.h" | ||||
| #include "../inc/lc6_time.h" | |||||
| #include "../inc/lc6_bootstrap.h" | |||||
| const char bootlist[4][50] = { | |||||
| "127.0.0.1", | |||||
| "2001:1a8f:ffff::abcd", | |||||
| "blah blah blah lol", | |||||
| "yep: not working ;-)" | |||||
| }; | |||||
| int main(int argc, char **argv) { | int main(int argc, char **argv) { | ||||
| LC6_CTX *conf = NULL; | LC6_CTX *conf = NULL; | ||||
| if ( argc == 2 ) { | if ( argc == 2 ) { | ||||
| int i = 0;; | |||||
| printf("Loading configuration files...\n"); | |||||
| conf = lc6config_load(argv[1], ""); | conf = lc6config_load(argv[1], ""); | ||||
| for(i=0; i<sizeof(bootlist)/sizeof(bootlist[0]); i++) { | |||||
| char *str = NULL; | |||||
| struct in_addr addr; | |||||
| struct in6_addr addr6; | |||||
| LC6_BOOTSTRAP *bs = malloc(sizeof(LC6_BOOTSTRAP)); | |||||
| assert(bs); | |||||
| memset(bs, '\0', sizeof(LC6_BOOTSTRAP)); | |||||
| printf("Parsing potential IP address '%s'\n", bootlist[i]); | |||||
| bs->prev = NULL; | |||||
| bs->next = NULL; | |||||
| bs->last_contact = lc6time_get(); | |||||
| printf("Decoding... "); | |||||
| if ( inet_pton(AF_INET, bootlist[i], &addr) == 1 ) { | |||||
| printf("IPv4\n"); | |||||
| bs->af = 4; | |||||
| bs->addr.inet = addr.s_addr; | |||||
| } | |||||
| else if ( inet_pton(AF_INET6, bootlist[i], &addr6) == 1) { | |||||
| printf("IPv6\n"); | |||||
| bs->af = 6; | |||||
| memcpy(bs->addr.inet6, &addr6, sizeof(bs->addr.inet6)); | |||||
| } | |||||
| else { | |||||
| printf("Failed\n"); | |||||
| free(bs); | |||||
| bs = NULL; | |||||
| } | |||||
| str = lc6bootstrap_getip(bs); | |||||
| printf("The result is : %s\n", str ? str : "NULL"); | |||||
| if ( str ) | |||||
| free(str); | |||||
| if ( bs ) | |||||
| lc6config_bootstrap_add(conf, bs); | |||||
| } | |||||
| lc6config_save(conf, ""); | lc6config_save(conf, ""); | ||||
| lc6config_free(conf); | |||||
| } | } | ||||
| else { | else { | ||||
| fprintf(stderr,"\ | |||||
| This is a helper programm for libchat6.\n\ | |||||
| It will initialise a bootstrap.bin configuration file\n\ | |||||
| containing a list of bootstrap clients hardcoded at the top of\n\ | |||||
| bootstrap.c. The default password for the bootstrap.bin file\n\ | |||||
| is an empty string.\n\n"); | |||||
| fprintf(stderr,"Usage: %s <path to config dir>\n", argv[0]); | fprintf(stderr,"Usage: %s <path to config dir>\n", argv[0]); | ||||
| return -1; | return -1; | ||||
| } | } |
| #include <stdio.h> | |||||
| #include <stdlib.h> | |||||
| #include <arpa/inet.h> | |||||
| #include <assert.h> | |||||
| #include <string.h> | |||||
| #include "../inc/lc6_bootstrap.h" | |||||
| char* lc6bootstrap_getip(LC6_BOOTSTRAP *bs) { | |||||
| char *str = NULL; | |||||
| if ( !bs ) | |||||
| return NULL; | |||||
| if ( bs->af == 4 ) { | |||||
| str = malloc(INET_ADDRSTRLEN); | |||||
| assert(str); | |||||
| memset(str, 0, INET_ADDRSTRLEN); | |||||
| inet_ntop(AF_INET, &bs->addr.inet, str, INET_ADDRSTRLEN); | |||||
| } | |||||
| else if ( bs->af == 6 ) { | |||||
| str = malloc(INET6_ADDRSTRLEN); | |||||
| assert(str); | |||||
| memset(str, 0, INET6_ADDRSTRLEN); | |||||
| inet_ntop(AF_INET6, &bs->addr.inet6, str, INET6_ADDRSTRLEN); | |||||
| } | |||||
| return str; | |||||
| } |
| lc6config_load_file(conf, path, LC6_CONFIG_BOOTSTRAP, password); | lc6config_load_file(conf, path, LC6_CONFIG_BOOTSTRAP, password); | ||||
| lc6config_load_file(conf, path, LC6_CONFIG_USER, password); | lc6config_load_file(conf, path, LC6_CONFIG_USER, password); | ||||
| lc6config_load_file(conf, path, LC6_CONFIG_FRIENDS, password); | |||||
| lc6config_load_file(conf, path, LC6_CONFIG_FRIEND, password); | |||||
| // complete defaults | // complete defaults | ||||
| // conf->user may stay NULL | // conf->user may stay NULL | ||||
| // conf->friends maybe you're all alone, that's ok tho. | |||||
| // conf->friend maybe you're all alone, that's ok tho. | |||||
| // conf->bootstrap | // conf->bootstrap | ||||
| // this is a major issue if we can't bootstrap | |||||
| if ( !conf->bootstrap ) | |||||
| return NULL; | |||||
| // if we can't bootstrap, we can't connect to the network | |||||
| // if ( !conf->bootstrap ) | |||||
| // return NULL; | |||||
| return conf; | return conf; | ||||
| } | } | ||||
| } | } | ||||
| } | } | ||||
| else if ( strcmp(filename, LC6_CONFIG_USER) == 0 ) { | else if ( strcmp(filename, LC6_CONFIG_USER) == 0 ) { | ||||
| conf->user = (LC6_USER*)data; | |||||
| LC6_USER *user = malloc(sizeof(LC6_USER)); | |||||
| assert(user); | |||||
| memcpy(user, data, sizeof(LC6_USER)); | |||||
| conf->user = user; | |||||
| } | } | ||||
| else if ( strcmp(filename, LC6_CONFIG_FRIENDS) == 0 ) { | |||||
| LC6_USER *prev = NULL; | |||||
| LC6_USER *chain = (LC6_USER*)data; | |||||
| else if ( strcmp(filename, LC6_CONFIG_FRIEND) == 0 ) { | |||||
| LC6_FRIEND *prev = NULL; | |||||
| LC6_FRIEND *chain = (LC6_FRIEND*)data; | |||||
| int offset = 0; | int offset = 0; | ||||
| while(offset<data_len/sizeof(LC6_USER)) { | |||||
| LC6_USER *node = malloc(sizeof(LC6_USER)); | |||||
| while(offset<data_len/sizeof(LC6_FRIEND)) { | |||||
| LC6_FRIEND *node = malloc(sizeof(LC6_FRIEND)); | |||||
| assert(node); | assert(node); | ||||
| memset(node, '\0', sizeof(LC6_USER)); | |||||
| memcpy(node, chain+offset, sizeof(LC6_USER)); | |||||
| memset(node, '\0', sizeof(LC6_FRIEND)); | |||||
| memcpy(node, chain+offset, sizeof(LC6_FRIEND)); | |||||
| if ( ! prev ) | if ( ! prev ) | ||||
| conf->user = node; | |||||
| conf->friend = node; | |||||
| else | else | ||||
| prev->next = node; | prev->next = node; | ||||
| offset++; | offset++; | ||||
| } | } | ||||
| } | } | ||||
| free(data); | |||||
| } | |||||
| void lc6config_bootstrap_add(LC6_CTX *conf, LC6_BOOTSTRAP *bs) { | |||||
| assert(conf); | |||||
| assert(bs); | |||||
| if ( conf->bootstrap ) | |||||
| conf->bootstrap->prev = bs; | |||||
| bs->prev = NULL; | |||||
| bs->next = conf->bootstrap; | |||||
| conf->bootstrap = bs; | |||||
| } | } | ||||
| void lc6config_free(LC6_CTX *conf) { | void lc6config_free(LC6_CTX *conf) { | ||||
| LC6_BOOTSTRAP *bnode = conf->bootstrap; | |||||
| LC6_USER *unode = conf->user; | |||||
| LC6_FRIEND *fnode = conf->friend; | |||||
| while(bnode) { | |||||
| LC6_BOOTSTRAP *next = bnode->next; | |||||
| free(bnode); | |||||
| bnode=next; | |||||
| } | |||||
| while(unode) { | |||||
| LC6_USER *next = unode->next; | |||||
| free(unode); | |||||
| unode=next; | |||||
| } | |||||
| while(fnode) { | |||||
| LC6_FRIEND *next = fnode->next; | |||||
| free(fnode); | |||||
| fnode=next; | |||||
| } | |||||
| if ( conf->node ) | |||||
| free(conf->node); | |||||
| free(conf); | |||||
| } | } | ||||
| int lc6config_save(LC6_CTX *conf, unsigned char *password) { | int lc6config_save(LC6_CTX *conf, unsigned char *password) { | ||||
| LC6_BOOTSTRAP *bootstrap_save = NULL; | |||||
| LC6_BOOTSTRAP *bootstrap_node = conf->bootstrap; | |||||
| int bootstrap_len = 0; | |||||
| LC6_USER *user_save = NULL; | |||||
| LC6_USER *user_node = conf->user; | |||||
| int user_len = 0; | |||||
| LC6_FRIEND *friend_save = NULL; | |||||
| LC6_FRIEND *friend_node = conf->friend; | |||||
| int friend_len = 0; | |||||
| int i; | |||||
| char file[MAXPATHLEN]; | |||||
| while(bootstrap_node) { | |||||
| bootstrap_len++; | |||||
| bootstrap_node = bootstrap_node->next; | |||||
| } | |||||
| bootstrap_node = conf->bootstrap; | |||||
| bootstrap_save = malloc(sizeof(LC6_BOOTSTRAP)*bootstrap_len); | |||||
| assert(bootstrap_save); | |||||
| memset(bootstrap_save, '\0', sizeof(LC6_BOOTSTRAP)*bootstrap_len); | |||||
| for(i=0; i<bootstrap_len; i++) { | |||||
| memcpy(bootstrap_save + i, bootstrap_node, sizeof(LC6_BOOTSTRAP)); | |||||
| (bootstrap_save+i)->prev = NULL; | |||||
| (bootstrap_save+i)->next = NULL; | |||||
| bootstrap_node = bootstrap_node->next; | |||||
| } | |||||
| snprintf(file, sizeof(file), "%s/%s", conf->path, LC6_CONFIG_BOOTSTRAP); | |||||
| lc6crypto_writefile(file, password, (unsigned char*)bootstrap_save, bootstrap_len * sizeof(LC6_BOOTSTRAP)); | |||||
| free(bootstrap_save); | |||||
| while(user_node) { | |||||
| user_len++; | |||||
| user_node = user_node->next; | |||||
| } | |||||
| user_save = malloc(sizeof(LC6_USER)*user_len); | |||||
| assert(user_save); | |||||
| memset(user_save, 0, sizeof(LC6_USER)*user_len); | |||||
| for(i=0; i<user_len; i++) { | |||||
| LC6_USER *node = conf->user + i; | |||||
| memcpy(user_save + i, node, sizeof(LC6_USER)); | |||||
| (user_save+i)->prev = NULL; | |||||
| (user_save+i)->next = NULL; | |||||
| } | |||||
| snprintf(file, sizeof(file), "%s/%s", conf->path, LC6_CONFIG_USER); | |||||
| lc6crypto_writefile(file, password, (unsigned char*)user_save, user_len * sizeof(LC6_USER)); | |||||
| free(user_save); | |||||
| while(friend_node) { | |||||
| friend_len++; | |||||
| friend_node = friend_node->next; | |||||
| } | |||||
| friend_save = malloc(sizeof(LC6_FRIEND)*friend_len); | |||||
| assert(friend_save); | |||||
| memset(friend_save, 0, sizeof(LC6_FRIEND)*friend_len); | |||||
| for(i=0; i<friend_len; i++) { | |||||
| LC6_FRIEND *node = conf->friend + i; | |||||
| memcpy(friend_save + i, node, sizeof(LC6_FRIEND)); | |||||
| (friend_save+i)->prev = NULL; | |||||
| (friend_save+i)->next = NULL; | |||||
| } | |||||
| snprintf(file, sizeof(file), "%s/%s", conf->path, LC6_CONFIG_FRIEND); | |||||
| lc6crypto_writefile(file, password, (unsigned char*)friend_save, friend_len * sizeof(LC6_FRIEND)); | |||||
| free(friend_save); | |||||
| return 1; | return 1; | ||||
| } | } |
| #include <assert.h> | #include <assert.h> | ||||
| #include "../inc/lc6_crypto.h" | #include "../inc/lc6_crypto.h" | ||||
| #include "../inc/lc6_helpers.h" | |||||
| int lc6crypto_seeded = 0; | int lc6crypto_seeded = 0; | ||||
| int lc6crypto_init(void) { | |||||
| return sodium_init(); | |||||
| } | |||||
| LC6_USER* lc6crypto_genuserkey(LC6_USER *user) { | LC6_USER* lc6crypto_genuserkey(LC6_USER *user) { | ||||
| assert(user); | assert(user); | ||||
| crypto_box_keypair(user->pub_key, user->priv_key); | crypto_box_keypair(user->pub_key, user->priv_key); | ||||
| int *data_len) | int *data_len) | ||||
| { | { | ||||
| FILE *fh; | FILE *fh; | ||||
| unsigned char hash[crypto_generichash_BYTES]; | |||||
| unsigned char *encrypted; | |||||
| unsigned char key[crypto_secretbox_KEYBYTES]; | |||||
| unsigned char *encrypted = NULL; | |||||
| size_t total = 0; | size_t total = 0; | ||||
| crypto_generichash(hash, sizeof hash, password, strlen((char*)password), NULL, 0); | |||||
| crypto_generichash(key, sizeof(key), password, strlen((char*)password), NULL, 0); | |||||
| if ( ( fh = fopen(file, "r") ) == NULL ) | if ( ( fh = fopen(file, "r") ) == NULL ) | ||||
| return -1; | return -1; | ||||
| while(1) { | while(1) { | ||||
| unsigned char buf[4096]; | unsigned char buf[4096]; | ||||
| size_t len; | |||||
| len = fread(buf, sizeof(buf), 1, fh); | |||||
| size_t len = 0; | |||||
| len = fread(buf, 1, sizeof(buf), fh); | |||||
| if ( len == 0 && !feof(fh) ) { | |||||
| if ( len == 0 && feof(fh) ) { | |||||
| fclose(fh); | fclose(fh); | ||||
| if ( encrypted ) | if ( encrypted ) | ||||
| free(encrypted); | free(encrypted); | ||||
| assert(*data); | assert(*data); | ||||
| memset(*data, '\0', total - crypto_secretbox_NONCEBYTES); | memset(*data, '\0', total - crypto_secretbox_NONCEBYTES); | ||||
| if (crypto_secretbox_open_easy(*data, encrypted + crypto_secretbox_NONCEBYTES, *data_len, encrypted, hash) != 0) { | |||||
| if (crypto_secretbox_open_easy(*data, encrypted + crypto_secretbox_NONCEBYTES, *data_len, encrypted, key) != 0) { | |||||
| free(encrypted); | free(encrypted); | ||||
| free(*data); | free(*data); | ||||
| return -1; | return -1; | ||||
| const unsigned char *data, | const unsigned char *data, | ||||
| const int data_len) | const int data_len) | ||||
| { | { | ||||
| FILE *fh; | |||||
| unsigned char hash[crypto_generichash_BYTES]; | |||||
| unsigned char nonce[crypto_secretbox_NONCEBYTES]; | |||||
| unsigned char *encrypted; | |||||
| int offset = 0; | |||||
| crypto_generichash(hash, sizeof hash, password, strlen((char*)password), NULL, 0); | |||||
| encrypted = malloc(data_len + crypto_secretbox_NONCEBYTES); | |||||
| FILE *fh = NULL; | |||||
| unsigned char key[crypto_secretbox_KEYBYTES] = {0}; | |||||
| unsigned char nonce[crypto_secretbox_NONCEBYTES] = {0}; | |||||
| unsigned char *encrypted = NULL; | |||||
| int total_len = data_len + crypto_secretbox_NONCEBYTES + crypto_secretbox_MACBYTES; | |||||
| crypto_generichash(key, sizeof(key), password, strlen((char*)password), NULL, 0); | |||||
| randombytes_buf(nonce, sizeof(nonce)); | |||||
| encrypted = malloc(total_len); | |||||
| assert(encrypted); | |||||
| memset(encrypted, '\0', total_len); | |||||
| memcpy(encrypted, nonce, crypto_secretbox_NONCEBYTES); | memcpy(encrypted, nonce, crypto_secretbox_NONCEBYTES); | ||||
| crypto_secretbox_easy(encrypted + crypto_secretbox_NONCEBYTES, data, data_len, nonce, hash); | |||||
| crypto_secretbox_easy(encrypted + crypto_secretbox_NONCEBYTES, data, data_len, nonce, key); | |||||
| if ( ( fh = fopen(file, "w") ) == NULL ) | if ( ( fh = fopen(file, "w") ) == NULL ) | ||||
| return -1; | return -1; | ||||
| if ( fwrite(encrypted + crypto_secretbox_NONCEBYTES + offset, data_len + crypto_secretbox_NONCEBYTES, 1, fh) != 1 ) { | |||||
| if ( fwrite(encrypted, total_len, 1, fh) != 1 ) { | |||||
| free(encrypted); | free(encrypted); | ||||
| fclose(fh); | |||||
| return -1; | return -1; | ||||
| } | } | ||||
| fclose(fh); | fclose(fh); | ||||
| free(encrypted); | free(encrypted); | ||||
| return 0; | return 0; | ||||
| } | } | ||||
| #include <stdio.h> | #include <stdio.h> | ||||
| #include <stdlib.h> | |||||
| #include "../inc/lc6_helpers.h" | |||||
| void lc6helpers_printhex(unsigned char *data, int data_len) { | void lc6helpers_printhex(unsigned char *data, int data_len) { | ||||
| printf("################################################\n"); | printf("################################################\n"); | ||||
| printf("\n"); | printf("\n"); | ||||
| } | } | ||||
| #ifdef LC6_DEBUG | |||||
| void* lc6helpers_malloc(size_t size, char *file, const char *func, int line) { | |||||
| printf("[%s:%d] %s called malloc(%lu)\n", file, line, func, size); | |||||
| return malloc(size); | |||||
| } | |||||
| void* lc6helpers_realloc(void *ptr, size_t size, char *file, const char *func, int line) { | |||||
| printf("[%s:%d] %s called realloc(%p, %lu)\n", file, line, func, ptr, size); | |||||
| return realloc(ptr, size); | |||||
| } | |||||
| void lc6helpers_free(void *ptr, char *file, const char *func, int line) { | |||||
| printf("[%s:%d] %s called free(%p)\n", file, line, func, ptr); | |||||
| free(ptr); | |||||
| } | |||||
| #endif |
| #include <time.h> | |||||
| #include "../inc/lc6_time.h" | |||||
| time_t lc6time_get(void) { | |||||
| return time(NULL); | |||||
| } |
| #include <stdio.h> | #include <stdio.h> | ||||
| #include <stdlib.h> | #include <stdlib.h> | ||||
| #include <assert.h> | |||||
| #include "../inc/lc6_crypto.h" | #include "../inc/lc6_crypto.h" | ||||
| #include "../inc/lc6_user.h" | #include "../inc/lc6_user.h" | ||||
| } | } | ||||
| void lc6user_free(LC6_CTX *conf, LC6_USER *user) { | void lc6user_free(LC6_CTX *conf, LC6_USER *user) { | ||||
| assert(conf); | |||||
| if ( !user ) | if ( !user ) | ||||
| return; | return; | ||||
| if ( conf->user == user ) | if ( conf->user == user ) | ||||
| conf->user = user->next; | conf->user = user->next; | ||||
| if ( conf->friends == user ) | |||||
| conf->friends = user->next; | |||||
| free(user); | free(user); | ||||
| } | } |
| #include "../inc/lc6_config.h" | #include "../inc/lc6_config.h" | ||||
| #include "../inc/lc6_user.h" | #include "../inc/lc6_user.h" | ||||
| #include "../inc/lc6_crypto.h" | |||||
| LIBCHAT* libchat_init(char *path, unsigned char *password) { | LIBCHAT* libchat_init(char *path, unsigned char *password) { | ||||
| LC6_CTX *conf; | |||||
| LC6_CTX *conf = lc6config_load(path, password); | |||||
| lc6crypto_init(); | |||||
| conf = lc6config_load(path, password); | |||||
| if ( !conf ) | if ( !conf ) | ||||
| return NULL; | return NULL; |