Added session key to ServerConnection

This commit is contained in:
Timerix 2025-10-25 10:47:08 +05:00
parent b1ca05759e
commit 60bc501227
6 changed files with 29 additions and 15 deletions

View File

@ -32,14 +32,14 @@ Result(ClientCredential*) ClientCredential_create(str username, str password){
StringBuilder_append_str(&sb, password); StringBuilder_append_str(&sb, password);
StringBuilder_append_str(&sb, username); StringBuilder_append_str(&sb, username);
Array(u8) password_and_username = str_castTo_Array(StringBuilder_getStr(&sb)); Array(u8) password_and_username = str_castTo_Array(StringBuilder_getStr(&sb));
cred->aes_key = Array_alloc(u8, password_hash_size); cred->aes_key = Array_alloc(u8, PASSWORD_HASH_SIZE);
Defer( Defer(
if(!success){ if(!success){
free(cred->aes_key.data); free(cred->aes_key.data);
} }
); );
// lvl 1 hash - is used as AES key for user data // lvl 1 hash - is used as AES key for user data
hash_password(password_and_username, cred->aes_key.data, __passhash_lvl_iter); hash_password(password_and_username, cred->aes_key.data, __PASSWORD_HASH_LVL_ITERATIONS);
DecryptorAES_construct(&cred->user_data_aes_dec, cred->aes_key); DecryptorAES_construct(&cred->user_data_aes_dec, cred->aes_key);
EncryptorAES_construct(&cred->user_data_aes_enc, cred->aes_key); EncryptorAES_construct(&cred->user_data_aes_enc, cred->aes_key);

View File

@ -6,6 +6,7 @@ void ServerConnection_close(ServerConnection* conn){
socket_close(conn->system_socket); socket_close(conn->system_socket);
socket_close(conn->content_socket); socket_close(conn->content_socket);
RSA_destroyPublicKey(&conn->server_pk); RSA_destroyPublicKey(&conn->server_pk);
free(conn->session_key.data);
free(conn); free(conn);
} }
@ -51,15 +52,22 @@ Result(ServerConnection*) ServerConnection_open(ClientCredential* client_credent
ServerConnection_close(conn); ServerConnection_close(conn);
); );
try_void(ServerLink_parse(server_link_cstr, &conn->server_end, &conn->server_pk));
conn->session_key = Array_alloc_size(__AES_SESSION_KEY_SIZE);
br_hmac_drbg_context key_rng = { .vtable = &br_hmac_drbg_vtable };
rng_init_sha256_seedFromTime(&key_rng.vtable);
br_hmac_drbg_generate(&key_rng, conn->session_key.data, conn->session_key.size);
// TODO: add more entropy to the key to prevent easy key cracking when attacker knows the time when connection request was sent to a server
printf("connecting to server %s\n", server_link_cstr); printf("connecting to server %s\n", server_link_cstr);
try(conn->system_socket, i, socket_open_TCP()); try(conn->system_socket, i, socket_open_TCP());
try_void(socket_connect(conn->system_socket, conn->server_end)); try_void(socket_connect(conn->system_socket, conn->server_end));
// send client public key to server // send session key to server
// request server info // request server info
// show server info // show server info
// save server info to user's db // save server info to user's db
// hash password more times
// request log in // request log in
// if not registered, request registration and then log in // if not registered, request registration and then log in

View File

@ -20,7 +20,8 @@ static const str farewell_art = STR(
"\\(_,J J L l`,)/\n" "\\(_,J J L l`,)/\n"
); );
static ClientCredential* client_credential = NULL; static ClientCredential* _client_credential = NULL;
static ServerConnection* _server_connection = NULL;
static Result(void) commandExec(str command, bool* stop); static Result(void) commandExec(str command, bool* stop);
@ -48,7 +49,7 @@ Result(void) client_run() {
using_history(); using_history();
fputs(greeting_art.data, stdout); fputs(greeting_art.data, stdout);
try_void(askUserNameAndPassword(&client_credential)); try_void(askUserNameAndPassword(&_client_credential));
char* command_input_prev = NULL; char* command_input_prev = NULL;
char* command_input_raw = NULL; char* command_input_raw = NULL;
@ -73,7 +74,8 @@ Result(void) client_run() {
} }
} }
ClientCredential_free(client_credential); ClientCredential_free(_client_credential);
ServerConnection_close(_server_connection);
Return RESULT_VOID; Return RESULT_VOID;
} }
@ -104,8 +106,8 @@ static Result(void) commandExec(str command, bool* stop){
fgets(answer_buf, answer_buf_size, stdin); fgets(answer_buf, answer_buf_size, stdin);
str new_server_link = str_from_cstr(answer_buf); str new_server_link = str_from_cstr(answer_buf);
str_trim(&new_server_link, true); str_trim(&new_server_link, true);
try(ServerConnection* conn, p, ServerConnection_open(client_credential, new_server_link.data)); ServerConnection_close(_server_connection);
// TODO: store server connection somewhere try(_server_connection, p, ServerConnection_open(_client_credential, new_server_link.data));
} }
else if(is_alias("c") || is_alias("connect")){ else if(is_alias("c") || is_alias("connect")){
// TODO: read saved servers from database // TODO: read saved servers from database

View File

@ -20,6 +20,7 @@ typedef struct ServerConnection {
Socket content_socket; Socket content_socket;
br_rsa_public_key server_pk; br_rsa_public_key server_pk;
EncryptorRSA rsa_enc; EncryptorRSA rsa_enc;
Array(u8) session_key;
EncryptorAES session_aes_enc; EncryptorAES session_aes_enc;
DecryptorAES session_aes_dec; DecryptorAES session_aes_dec;
} ServerConnection; } ServerConnection;

View File

@ -13,12 +13,12 @@
/// @brief hashes password multiple times using its own hash as salt /// @brief hashes password multiple times using its own hash as salt
/// @param password some byte array /// @param password some byte array
/// @param out_buffer u8[password_hash_size] /// @param out_buffer u8[PASSWORD_HASH_SIZE]
/// @param iterations number of iterations /// @param iterations number of iterations
void hash_password(Array(u8) password, u8* out_buffer, i32 iterations); void hash_password(Array(u8) password, u8* out_buffer, i32 iterations);
#define password_hash_size 32 #define PASSWORD_HASH_SIZE 32
#define __passhash_lvl_iter 1e5 #define __PASSWORD_HASH_LVL_ITERATIONS 1e5
////////////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////////////
// rng.c // // rng.c //
@ -38,6 +38,9 @@ void rng_init_sha256_seedFromTime(const br_prng_class** rng_vtable_ptr);
// AES.c // // AES.c //
////////////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////////////
#define __AES_SESSION_KEY_SIZE 32
#define __AES_DB_KEY_SIZE 32
typedef struct EncryptedBlockInfo { typedef struct EncryptedBlockInfo {
u8 padding_size; u8 padding_size;
u32 _reserved; u32 _reserved;
@ -87,7 +90,7 @@ void DecryptorAES_decrypt(DecryptorAES* ptr, Array(u8) src, Array(u8) dst, u32*
// RSA.c // // RSA.c //
////////////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////////////
#define __rsa_key_size_default 3072 #define __RSA_DEFAULT_KEY_SIZE 3072
/// @brief generate random key pair based on system time /// @brief generate random key pair based on system time
/// @param key_size size of public key in bits (2048/3072/4096) /// @param key_size size of public key in bits (2048/3072/4096)

View File

@ -3,7 +3,7 @@
#include "assert.h" #include "assert.h"
void hash_password(Array(u8) password, u8* out_buffer, i32 iterations){ void hash_password(Array(u8) password, u8* out_buffer, i32 iterations){
assert(password_hash_size == br_sha256_SIZE);; assert(PASSWORD_HASH_SIZE == br_sha256_SIZE);;
memset(out_buffer, 0, br_sha256_SIZE); memset(out_buffer, 0, br_sha256_SIZE);
br_sha256_context sha256_ctx; br_sha256_context sha256_ctx;
br_sha256_init(&sha256_ctx); br_sha256_init(&sha256_ctx);
@ -11,7 +11,7 @@ void hash_password(Array(u8) password, u8* out_buffer, i32 iterations){
for(i32 i = 0; i < iterations; i++){ for(i32 i = 0; i < iterations; i++){
br_sha256_update(&sha256_ctx, password.data, password.size); br_sha256_update(&sha256_ctx, password.data, password.size);
br_sha256_out(&sha256_ctx, out_buffer); br_sha256_out(&sha256_ctx, out_buffer);
br_sha256_update(&sha256_ctx, out_buffer, password_hash_size); br_sha256_update(&sha256_ctx, out_buffer, PASSWORD_HASH_SIZE);
} }
br_sha256_out(&sha256_ctx, out_buffer); br_sha256_out(&sha256_ctx, out_buffer);
} }