@ -12,12 +12,16 @@
# include <fcntl.h>
# include <fcntl.h>
# include <sys/stat.h>
# include <sys/stat.h>
# define HEXKEY_LEN 64 // 32 bytes * 2 hex chars
# define PRIV_HEXKEY_LEN 65 // 32 bytes * 2 hex chars + null
# define HEXNODEID_LEN 16 // 8 bytes * 2 hex chars
# define PUB_HEXKEY_LEN 129 // 64 bytes * 2 hex chars + null
# define HEXNODEID_LEN 17 // 8 bytes * 2 hex chars + null
# define MAX_LINE_LEN 1024
# define MAX_LINE_LEN 1024
void bytes_to_hex ( const uint8_t * bytes , size_t len , char * hex_str , size_t hex_len ) {
void bytes_to_hex ( const uint8_t * bytes , size_t len , char * hex_str , size_t hex_len ) {
if ( ! bytes | | ! hex_str | | hex_len < len * 2 + 1 ) return ;
if ( ! bytes | | ! hex_str | | hex_len < len * 2 + 1 ) {
if ( hex_str & & hex_len > 0 ) hex_str [ 0 ] = ' \0 ' ;
return ;
}
for ( size_t i = 0 ; i < len ; i + + ) {
for ( size_t i = 0 ; i < len ; i + + ) {
snprintf ( hex_str + i * 2 , hex_len - i * 2 , " %02x " , bytes [ i ] ) ;
snprintf ( hex_str + i * 2 , hex_len - i * 2 , " %02x " , bytes [ i ] ) ;
}
}
@ -25,9 +29,17 @@ void bytes_to_hex(const uint8_t *bytes, size_t len, char *hex_str, size_t hex_le
}
}
static int is_valid_hex_key ( const char * key ) {
static int is_valid_priv_key ( const char * key ) {
if ( ! key | | strlen ( key ) ! = HEXKEY_LEN ) return 0 ;
if ( ! key | | strlen ( key ) ! = 64 ) return 0 ;
for ( int i = 0 ; i < HEXKEY_LEN ; i + + ) {
for ( int i = 0 ; i < 64 ; i + + ) {
if ( ! isxdigit ( ( unsigned char ) key [ i ] ) ) return 0 ;
}
return 1 ;
}
static int is_valid_pub_key ( const char * key ) {
if ( ! key | | strlen ( key ) ! = 128 ) return 0 ;
for ( int i = 0 ; i < 128 ; i + + ) {
if ( ! isxdigit ( ( unsigned char ) key [ i ] ) ) return 0 ;
if ( ! isxdigit ( ( unsigned char ) key [ i ] ) ) return 0 ;
}
}
return 1 ;
return 1 ;
@ -204,8 +216,8 @@ int config_ensure_keys_and_node_id(const char *filename) {
struct global_config * global = & config - > global ;
struct global_config * global = & config - > global ;
// Check if we need to generate anything
// Check if we need to generate anything
int need_priv_key = ! is_valid_hex _key ( global - > my_private_key_hex ) ;
int need_priv_key = ! is_valid_priv _key ( global - > my_private_key_hex ) ;
int need_pub_key = ! is_valid_hex _key ( global - > my_public_key_hex ) ;
int need_pub_key = ! is_valid_pub _key ( global - > my_public_key_hex ) ;
int need_node_id = ! is_valid_node_id ( global - > my_node_id ) ;
int need_node_id = ! is_valid_node_id ( global - > my_node_id ) ;
if ( ! need_priv_key & & ! need_pub_key & & ! need_node_id ) {
if ( ! need_priv_key & & ! need_pub_key & & ! need_node_id ) {
@ -214,11 +226,12 @@ int config_ensure_keys_and_node_id(const char *filename) {
}
}
// Generate keys if needed
// Generate keys if needed
char new_priv_key [ HEXKEY_LEN + 1 ] = { 0 } ;
char new_priv_key [ PRIV_ HEXKEY_LEN] = { 0 } ;
char new_pub_key [ HEXKEY_LEN + 1 ] = { 0 } ;
char new_pub_key [ PUB_ HEXKEY_LEN] = { 0 } ;
uint64_t new_node_id = 0 ;
uint64_t new_node_id = 0 ;
if ( need_priv_key | | need_pub_key ) {
if ( need_priv_key ) {
// Generate new keypair if private key is invalid
struct SC_MYKEYS mykeys ;
struct SC_MYKEYS mykeys ;
if ( sc_generate_keypair ( & mykeys ) ! = SC_OK ) {
if ( sc_generate_keypair ( & mykeys ) ! = SC_OK ) {
DEBUG_ERROR ( DEBUG_CATEGORY_CONFIG , " Failed to generate keypair " ) ;
DEBUG_ERROR ( DEBUG_CATEGORY_CONFIG , " Failed to generate keypair " ) ;
@ -227,6 +240,32 @@ int config_ensure_keys_and_node_id(const char *filename) {
}
}
bytes_to_hex ( mykeys . private_key , SC_PRIVKEY_SIZE , new_priv_key , sizeof ( new_priv_key ) ) ;
bytes_to_hex ( mykeys . private_key , SC_PRIVKEY_SIZE , new_priv_key , sizeof ( new_priv_key ) ) ;
bytes_to_hex ( mykeys . public_key , SC_PUBKEY_SIZE , new_pub_key , sizeof ( new_pub_key ) ) ;
bytes_to_hex ( mykeys . public_key , SC_PUBKEY_SIZE , new_pub_key , sizeof ( new_pub_key ) ) ;
} else if ( need_pub_key ) {
// Compute public key from existing private key
uint8_t priv_bin [ SC_PRIVKEY_SIZE ] ;
uint8_t pub_bin [ SC_PUBKEY_SIZE ] ;
// Convert private key from hex to binary
for ( int i = 0 ; i < SC_PRIVKEY_SIZE ; i + + ) {
unsigned int byte ;
if ( sscanf ( global - > my_private_key_hex + i * 2 , " %2x " , & byte ) ! = 1 ) {
DEBUG_ERROR ( DEBUG_CATEGORY_CONFIG , " Invalid private key hex format " ) ;
free_config ( config ) ;
return - 1 ;
}
priv_bin [ i ] = ( uint8_t ) byte ;
}
// Compute public key
if ( sc_compute_public_key_from_private ( priv_bin , pub_bin ) ! = SC_OK ) {
DEBUG_ERROR ( DEBUG_CATEGORY_CONFIG , " Failed to compute public key from private key " ) ;
free_config ( config ) ;
return - 1 ;
}
// Convert to hex
bytes_to_hex ( priv_bin , SC_PRIVKEY_SIZE , new_priv_key , sizeof ( new_priv_key ) ) ;
bytes_to_hex ( pub_bin , SC_PUBKEY_SIZE , new_pub_key , sizeof ( new_pub_key ) ) ;
}
}
if ( need_node_id ) {
if ( need_node_id ) {
@ -268,7 +307,7 @@ int config_ensure_keys_and_node_id(const char *filename) {
int ret = 0 ;
int ret = 0 ;
if ( need_priv_key ) {
if ( need_node_id ) {
char node_id_hex [ HEXNODEID_LEN + 1 ] ;
char node_id_hex [ HEXNODEID_LEN + 1 ] ;
snprintf ( node_id_hex , sizeof ( node_id_hex ) , " %llx " , ( unsigned long long ) new_node_id ) ;
snprintf ( node_id_hex , sizeof ( node_id_hex ) , " %llx " , ( unsigned long long ) new_node_id ) ;
if ( insert_or_replace_option ( & work_buf , & work_len , & buf_capacity , " my_node_id " , node_id_hex ) < 0 ) {
if ( insert_or_replace_option ( & work_buf , & work_len , & buf_capacity , " my_node_id " , node_id_hex ) < 0 ) {