moved request handlers to separate files
This commit is contained in:
parent
ea4a649e00
commit
96a117bc50
@ -1,8 +1,8 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
|
|
||||||
#define log(context, severity, format, ...) printf("[%s][" severity "]: " format "\n", context ,##__VA_ARGS__)
|
#define log(context, severity, format, ...) printf("[%s/" severity "]: " format "\n", context ,##__VA_ARGS__)
|
||||||
#define logDebug(context, format, ...) log(context, "DEBUG", format ,##__VA_ARGS__)
|
#define logDebug(context, format, ...) log(context, "DEBUG", format ,##__VA_ARGS__)
|
||||||
#define logInfo(context, format, ...) log(context, "INFO", format ,##__VA_ARGS__)
|
#define logInfo(context, format, ...) log(context, "INFO", format ,##__VA_ARGS__)
|
||||||
#define logWarning(context, format, ...) log(context, "WARNING", format ,##__VA_ARGS__)
|
#define logWarn(context, format, ...) log(context, "WARN", format ,##__VA_ARGS__)
|
||||||
#define logError(context, format, ...) log(context, "ERROR", format ,##__VA_ARGS__)
|
#define logError(context, format, ...) log(context, "ERROR", format ,##__VA_ARGS__)
|
||||||
|
|||||||
@ -10,7 +10,7 @@ void ClientConnection_close(ClientConnection* conn){
|
|||||||
}
|
}
|
||||||
|
|
||||||
Result(ClientConnection*) ClientConnection_accept(ServerCredentials* server_credentials,
|
Result(ClientConnection*) ClientConnection_accept(ServerCredentials* server_credentials,
|
||||||
Socket sock_tcp, EndpointIPv4 client_end, u64 session_id)
|
ConnectionHandlerArgs* args)
|
||||||
{
|
{
|
||||||
Deferral(32);
|
Deferral(32);
|
||||||
|
|
||||||
@ -22,13 +22,14 @@ Result(ClientConnection*) ClientConnection_accept(ServerCredentials* server_cred
|
|||||||
ClientConnection_close(conn);
|
ClientConnection_close(conn);
|
||||||
);
|
);
|
||||||
|
|
||||||
conn->client_end = client_end;
|
conn->client_end = args->client_end;
|
||||||
conn->session_id = session_id;
|
conn->session_id = args->session_id;
|
||||||
|
conn->authorized = false;
|
||||||
conn->session_key = Array_alloc_size(AES_SESSION_KEY_SIZE);
|
conn->session_key = Array_alloc_size(AES_SESSION_KEY_SIZE);
|
||||||
// correct session key will be received from client later
|
// correct session key will be received from client later
|
||||||
Array_memset(conn->session_key, 0);
|
Array_memset(conn->session_key, 0);
|
||||||
EncryptedSocketTCP_construct(&conn->sock, sock_tcp, NETWORK_BUFFER_SIZE, conn->session_key);
|
EncryptedSocketTCP_construct(&conn->sock, args->accepted_socket, NETWORK_BUFFER_SIZE, conn->session_key);
|
||||||
try_void(socket_TCP_enableAliveChecks_default(sock_tcp));
|
try_void(socket_TCP_enableAliveChecks_default(args->accepted_socket));
|
||||||
|
|
||||||
// decrypt the rsa messages using server private key
|
// decrypt the rsa messages using server private key
|
||||||
RSADecryptor rsa_dec;
|
RSADecryptor rsa_dec;
|
||||||
@ -52,7 +53,7 @@ Result(ClientConnection*) ClientConnection_accept(ServerCredentials* server_cred
|
|||||||
// send PacketHeader and ServerHandshake over encrypted TCP socket
|
// send PacketHeader and ServerHandshake over encrypted TCP socket
|
||||||
ServerHandshake server_handshake = {0};
|
ServerHandshake server_handshake = {0};
|
||||||
ServerHandshake_construct(&server_handshake, &packet_header,
|
ServerHandshake_construct(&server_handshake, &packet_header,
|
||||||
session_id);
|
conn->session_id);
|
||||||
try_void(EncryptedSocketTCP_sendStruct(&conn->sock, &packet_header));
|
try_void(EncryptedSocketTCP_sendStruct(&conn->sock, &packet_header));
|
||||||
try_void(EncryptedSocketTCP_sendStruct(&conn->sock, &server_handshake));
|
try_void(EncryptedSocketTCP_sendStruct(&conn->sock, &server_handshake));
|
||||||
|
|
||||||
|
|||||||
25
src/server/request_handlers/Login.c
Normal file
25
src/server/request_handlers/Login.c
Normal file
@ -0,0 +1,25 @@
|
|||||||
|
#include "request_handlers.h"
|
||||||
|
|
||||||
|
|
||||||
|
declare_RequestHandler(Login)
|
||||||
|
{
|
||||||
|
Deferral(4);
|
||||||
|
logDebug(log_ctx, "requested %s", req_type_name);
|
||||||
|
|
||||||
|
LoginRequest req = {0};
|
||||||
|
try_void(PacketHeader_validateContentSize(req_head, sizeof(req)));
|
||||||
|
try_void(EncryptedSocketTCP_recvStruct(&conn->sock, &req));
|
||||||
|
|
||||||
|
//TODO: try authorize client
|
||||||
|
u64 user_id;
|
||||||
|
u64 landing_channel_id;
|
||||||
|
|
||||||
|
LoginResponse res = {0};
|
||||||
|
LoginResponse_construct(&res, res_head, user_id, landing_channel_id);
|
||||||
|
try_void(EncryptedSocketTCP_sendStruct(&conn->sock, res_head));
|
||||||
|
try_void(EncryptedSocketTCP_sendStruct(&conn->sock, &res));
|
||||||
|
conn->authorized = true;
|
||||||
|
logInfo(log_ctx, "client authorized");
|
||||||
|
|
||||||
|
Return RESULT_VOID;
|
||||||
|
}
|
||||||
21
src/server/request_handlers/Register.c
Normal file
21
src/server/request_handlers/Register.c
Normal file
@ -0,0 +1,21 @@
|
|||||||
|
#include "request_handlers.h"
|
||||||
|
|
||||||
|
declare_RequestHandler(Register)
|
||||||
|
{
|
||||||
|
Deferral(4);
|
||||||
|
logDebug(log_ctx, "requested %s", req_type_name);
|
||||||
|
|
||||||
|
RegisterRequest req = {0};
|
||||||
|
try_void(PacketHeader_validateContentSize(req_head, sizeof(req)));
|
||||||
|
try_void(EncryptedSocketTCP_recvStruct(&conn->sock, &req));
|
||||||
|
|
||||||
|
//TODO: try register client
|
||||||
|
u64 user_id;
|
||||||
|
|
||||||
|
RegisterResponse res = {0};
|
||||||
|
RegisterResponse_construct(&res, res_head, user_id);
|
||||||
|
try_void(EncryptedSocketTCP_sendStruct(&conn->sock, res_head));
|
||||||
|
try_void(EncryptedSocketTCP_sendStruct(&conn->sock, &res));
|
||||||
|
|
||||||
|
Return RESULT_VOID;
|
||||||
|
}
|
||||||
21
src/server/request_handlers/ServerPublicInfo.c
Normal file
21
src/server/request_handlers/ServerPublicInfo.c
Normal file
@ -0,0 +1,21 @@
|
|||||||
|
#include "request_handlers.h"
|
||||||
|
|
||||||
|
declare_RequestHandler(ServerPublicInfo)
|
||||||
|
{
|
||||||
|
Deferral(4);
|
||||||
|
logDebug(log_ctx, "requested %s", req_type_name);
|
||||||
|
|
||||||
|
ServerPublicInfoRequest req = {0};
|
||||||
|
try_void(PacketHeader_validateContentSize(req_head, sizeof(req)));
|
||||||
|
try_void(EncryptedSocketTCP_recvStruct(&conn->sock, &req));
|
||||||
|
|
||||||
|
//TODO: try find requested info
|
||||||
|
Array(u8) content;
|
||||||
|
|
||||||
|
PacketHeader_construct(res_head,
|
||||||
|
PROTOCOL_VERSION, PacketType_ServerPublicInfoResponse, content.size);
|
||||||
|
try_void(EncryptedSocketTCP_sendStruct(&conn->sock, res_head));
|
||||||
|
try_void(EncryptedSocketTCP_send(&conn->sock, content));
|
||||||
|
|
||||||
|
Return RESULT_VOID;
|
||||||
|
}
|
||||||
27
src/server/request_handlers/request_handlers.h
Normal file
27
src/server/request_handlers/request_handlers.h
Normal file
@ -0,0 +1,27 @@
|
|||||||
|
#pragma once
|
||||||
|
#include "network/tcp-chat-protocol/v1.h"
|
||||||
|
#include "server/server.h"
|
||||||
|
#include "log.h"
|
||||||
|
|
||||||
|
|
||||||
|
Result(char*) __sendErrorMessage(ClientConnection* conn, PacketHeader* req_head, PacketHeader* res_head,
|
||||||
|
u32 msg_buf_size, cstr format, va_list argv);
|
||||||
|
Result(char*) sendErrorMessage(ClientConnection* conn, PacketHeader* req_head, PacketHeader* res_head,
|
||||||
|
u32 msg_buf_size, cstr format, ...) ATTRIBUTE_CHECK_FORMAT_PRINTF(5, 6);
|
||||||
|
|
||||||
|
|
||||||
|
#define declare_RequestHandler(TYPE) \
|
||||||
|
Result(void) handleRequest_##TYPE( \
|
||||||
|
cstr log_ctx, cstr req_type_name, \
|
||||||
|
ClientConnection* conn, PacketHeader* req_head, PacketHeader* res_head)
|
||||||
|
|
||||||
|
#define case_handleRequest(TYPE) \
|
||||||
|
case PacketType_##TYPE##Request:\
|
||||||
|
try_void(handleRequest_##TYPE(log_ctx, #TYPE, conn, &req_head, &res_head));\
|
||||||
|
break;
|
||||||
|
|
||||||
|
declare_RequestHandler(ServerPublicInfo);
|
||||||
|
declare_RequestHandler(Login);
|
||||||
|
declare_RequestHandler(Register);
|
||||||
|
|
||||||
|
|
||||||
31
src/server/request_handlers/send_error.c
Normal file
31
src/server/request_handlers/send_error.c
Normal file
@ -0,0 +1,31 @@
|
|||||||
|
#include "request_handlers.h"
|
||||||
|
|
||||||
|
Result(char*) __sendErrorMessage(ClientConnection* conn, PacketHeader* req_head, PacketHeader* res_head,
|
||||||
|
u32 msg_buf_size, cstr format, va_list argv)
|
||||||
|
{
|
||||||
|
Deferral(4);
|
||||||
|
//TODO: limit ErrorMessage size to fit into EncryptedSocketTCP.internal_buffer_size
|
||||||
|
Array(u8) err_buf = Array_alloc(u8, msg_buf_size);
|
||||||
|
bool err_complete = false;
|
||||||
|
Defer(if(!err_complete) free(err_buf.data));
|
||||||
|
vsprintf(err_buf.data, format, argv);
|
||||||
|
err_buf.size = strlen(err_buf.data);
|
||||||
|
|
||||||
|
PacketHeader_construct(res_head,
|
||||||
|
PROTOCOL_VERSION, PacketType_ErrorMessage, err_buf.size);
|
||||||
|
try_void(EncryptedSocketTCP_sendStruct(&conn->sock, res_head));
|
||||||
|
try_void(EncryptedSocketTCP_send(&conn->sock, err_buf));
|
||||||
|
|
||||||
|
err_complete = true;
|
||||||
|
Return RESULT_VALUE(p, err_buf.data);
|
||||||
|
}
|
||||||
|
|
||||||
|
Result(char*) sendErrorMessage(ClientConnection* conn, PacketHeader* req_head, PacketHeader* res_head,
|
||||||
|
u32 msg_buf_size, cstr format, ...)
|
||||||
|
{
|
||||||
|
va_list argv;
|
||||||
|
va_start(argv, format);
|
||||||
|
ResultVar(char*) err_msg = __sendErrorMessage(conn, req_head, res_head, msg_buf_size, format, argv);
|
||||||
|
va_end(argv);
|
||||||
|
return err_msg;
|
||||||
|
}
|
||||||
9
src/server/request_handlers/template
Normal file
9
src/server/request_handlers/template
Normal file
@ -0,0 +1,9 @@
|
|||||||
|
#include "request_handlers.h"
|
||||||
|
|
||||||
|
declare_RequestHandler(T)
|
||||||
|
{
|
||||||
|
Deferral(4);
|
||||||
|
logDebug(log_ctx, "requested %s", req_type_name);
|
||||||
|
|
||||||
|
Return RESULT_VOID;
|
||||||
|
}
|
||||||
@ -6,12 +6,7 @@
|
|||||||
#include "config.h"
|
#include "config.h"
|
||||||
#include "log.h"
|
#include "log.h"
|
||||||
#include "network/tcp-chat-protocol/v1.h"
|
#include "network/tcp-chat-protocol/v1.h"
|
||||||
|
#include "server/request_handlers/request_handlers.h"
|
||||||
typedef struct ConnectionHandlerArgs {
|
|
||||||
Socket accepted_socket;
|
|
||||||
EndpointIPv4 client_end;
|
|
||||||
u64 session_id;
|
|
||||||
} ConnectionHandlerArgs;
|
|
||||||
|
|
||||||
static void* handle_connection(void* _args);
|
static void* handle_connection(void* _args);
|
||||||
static Result(void) try_handle_connection(ConnectionHandlerArgs* args, cstr log_ctx);
|
static Result(void) try_handle_connection(ConnectionHandlerArgs* args, cstr log_ctx);
|
||||||
@ -50,7 +45,7 @@ static Result(void) parseConfig(cstr config_path){
|
|||||||
|
|
||||||
Result(void) server_run(cstr server_endpoint_cstr, cstr config_path){
|
Result(void) server_run(cstr server_endpoint_cstr, cstr config_path){
|
||||||
Deferral(32);
|
Deferral(32);
|
||||||
cstr log_ctx = "Server/MainThread";
|
cstr log_ctx = "MainThread";
|
||||||
logInfo(log_ctx, "starting server");
|
logInfo(log_ctx, "starting server");
|
||||||
logDebug(log_ctx, "parsing config");
|
logDebug(log_ctx, "parsing config");
|
||||||
try_void(parseConfig(config_path));
|
try_void(parseConfig(config_path));
|
||||||
@ -104,100 +99,39 @@ static Result(void) try_handle_connection(ConnectionHandlerArgs* args, cstr log_
|
|||||||
logInfo(log_ctx, "session closed");
|
logInfo(log_ctx, "session closed");
|
||||||
);
|
);
|
||||||
// establish encrypted connection
|
// establish encrypted connection
|
||||||
try(conn, p,
|
try(conn, p, ClientConnection_accept(_server_credentials, args));
|
||||||
ClientConnection_accept(
|
|
||||||
_server_credentials,
|
|
||||||
args->accepted_socket,
|
|
||||||
args->client_end,
|
|
||||||
args->session_id
|
|
||||||
)
|
|
||||||
);
|
|
||||||
logInfo(log_ctx, "session accepted");
|
logInfo(log_ctx, "session accepted");
|
||||||
|
|
||||||
// handle unauthorized requests
|
// handle requests
|
||||||
bool ahtorized = false;
|
PacketHeader req_head = {0};
|
||||||
PacketHeader req_header = {0};
|
PacketHeader res_head = {0};
|
||||||
PacketHeader res_header = {0};
|
while(true){
|
||||||
while(!ahtorized){
|
sleepMsec(20);
|
||||||
sleepMsec(50);
|
|
||||||
//TODO: implement some additional check if socket is dead or not
|
//TODO: implement some additional check if socket is dead or not
|
||||||
|
|
||||||
try_void(EncryptedSocketTCP_recvStruct(&conn->sock, &req_header));
|
try_void(EncryptedSocketTCP_recvStruct(&conn->sock, &req_head));
|
||||||
try_void(PacketHeader_validateMagic(&req_header));
|
try_void(PacketHeader_validateMagic(&req_head));
|
||||||
//TODO: move request handlers to separate functions
|
|
||||||
switch(req_header.type){
|
switch(req_head.type){
|
||||||
default:{
|
// send error message and close connection
|
||||||
Array(u8) err_buf = Array_alloc(u8, 128);
|
default:
|
||||||
bool err_complete = false;
|
try(char* err_msg, p,
|
||||||
Defer(if(!err_complete) free(err_buf.data));
|
sendErrorMessage(
|
||||||
sprintf(err_buf.data, "Received unexpected packet of type %u",
|
conn, &req_head, &res_head,
|
||||||
req_header.type);
|
128, "Received unexpected packet of type %u",
|
||||||
err_buf.size = strlen(err_buf.data);
|
req_head.type
|
||||||
|
)
|
||||||
PacketHeader_construct(&res_header,
|
);
|
||||||
PROTOCOL_VERSION, PacketType_ErrorMessage, err_buf.size);
|
logWarn(log_ctx, "%s", err_msg);
|
||||||
try_void(EncryptedSocketTCP_sendStruct(&conn->sock, &res_header));
|
Return RESULT_VOID;
|
||||||
//TODO: limit ErrorMessage size to fit into EncryptedSocketTCP.internal_buffer_size
|
|
||||||
try_void(EncryptedSocketTCP_send(&conn->sock, err_buf));
|
// unauthorized requests
|
||||||
|
case_handleRequest(ServerPublicInfo);
|
||||||
err_complete = true;
|
case_handleRequest(Login);
|
||||||
Return RESULT_ERROR(err_buf.data, true);
|
case_handleRequest(Register);
|
||||||
}
|
// authorized requests
|
||||||
|
|
||||||
case PacketType_ServerPublicInfoRequest:{
|
|
||||||
ServerPublicInfoRequest req = {0};
|
|
||||||
try_void(PacketHeader_validateContentSize(&req_header, sizeof(req)));
|
|
||||||
try_void(EncryptedSocketTCP_recvStruct(&conn->sock, &req));
|
|
||||||
|
|
||||||
//TODO: try find requested info
|
|
||||||
Array(u8) content;
|
|
||||||
|
|
||||||
PacketHeader_construct(&res_header,
|
|
||||||
PROTOCOL_VERSION, PacketType_ServerPublicInfoResponse, content.size);
|
|
||||||
try_void(EncryptedSocketTCP_sendStruct(&conn->sock, &res_header));
|
|
||||||
try_void(EncryptedSocketTCP_send(&conn->sock, content));
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
case PacketType_LoginRequest:{
|
|
||||||
LoginRequest req = {0};
|
|
||||||
try_void(PacketHeader_validateContentSize(&req_header, sizeof(req)));
|
|
||||||
try_void(EncryptedSocketTCP_recvStruct(&conn->sock, &req));
|
|
||||||
|
|
||||||
//TODO: try authorize client
|
|
||||||
u64 user_id;
|
|
||||||
u64 landing_channel_id;
|
|
||||||
|
|
||||||
LoginResponse res = {0};
|
|
||||||
LoginResponse_construct(&res, &res_header, user_id, landing_channel_id);
|
|
||||||
try_void(EncryptedSocketTCP_sendStruct(&conn->sock, &res_header));
|
|
||||||
try_void(EncryptedSocketTCP_sendStruct(&conn->sock, &res));
|
|
||||||
ahtorized = true;
|
|
||||||
logInfo(log_ctx, "client authorized");
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
case PacketType_RegisterRequest:{
|
|
||||||
RegisterRequest req = {0};
|
|
||||||
try_void(PacketHeader_validateContentSize(&req_header, sizeof(req)));
|
|
||||||
try_void(EncryptedSocketTCP_recvStruct(&conn->sock, &req));
|
|
||||||
|
|
||||||
//TODO: try register client
|
|
||||||
u64 user_id;
|
|
||||||
|
|
||||||
RegisterResponse res = {0};
|
|
||||||
RegisterResponse_construct(&res, &res_header, user_id);
|
|
||||||
try_void(EncryptedSocketTCP_sendStruct(&conn->sock, &res_header));
|
|
||||||
try_void(EncryptedSocketTCP_sendStruct(&conn->sock, &res));
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// handle authorized requests
|
|
||||||
while(true){
|
|
||||||
sleepMsec(50);
|
|
||||||
}
|
|
||||||
|
|
||||||
Return RESULT_VOID;
|
Return RESULT_VOID;
|
||||||
}
|
}
|
||||||
|
|||||||
@ -16,10 +16,10 @@ Result(ServerCredentials*) ServerCredentials_create(cstr rsa_sk_base64, cstr rsa
|
|||||||
void ServerCredentials_free(ServerCredentials* cred);
|
void ServerCredentials_free(ServerCredentials* cred);
|
||||||
|
|
||||||
|
|
||||||
typedef struct ServerMetadata {
|
typedef struct ServerInfo {
|
||||||
str name;
|
str name;
|
||||||
str description;
|
str description;
|
||||||
} ServerMetadata;
|
} ServerInfo;
|
||||||
|
|
||||||
|
|
||||||
typedef struct ClientConnection {
|
typedef struct ClientConnection {
|
||||||
@ -27,9 +27,17 @@ typedef struct ClientConnection {
|
|||||||
EndpointIPv4 client_end;
|
EndpointIPv4 client_end;
|
||||||
Array(u8) session_key;
|
Array(u8) session_key;
|
||||||
EncryptedSocketTCP sock;
|
EncryptedSocketTCP sock;
|
||||||
|
bool authorized;
|
||||||
} ClientConnection;
|
} ClientConnection;
|
||||||
|
|
||||||
Result(ClientConnection*) ClientConnection_accept(ServerCredentials* server_credentials,
|
|
||||||
Socket sock, EndpointIPv4 client_end, u64 session_id);
|
typedef struct ConnectionHandlerArgs {
|
||||||
|
Socket accepted_socket;
|
||||||
|
EndpointIPv4 client_end;
|
||||||
|
u64 session_id;
|
||||||
|
} ConnectionHandlerArgs;
|
||||||
|
|
||||||
|
Result(ClientConnection*) ClientConnection_accept(ServerCredentials* server_credentials,
|
||||||
|
ConnectionHandlerArgs* args);
|
||||||
|
|
||||||
void ClientConnection_close(ClientConnection* conn);
|
void ClientConnection_close(ClientConnection* conn);
|
||||||
Loading…
Reference in New Issue
Block a user