diff options
Diffstat (limited to 'extern/verse/dist/v_connection.c')
-rw-r--r-- | extern/verse/dist/v_connection.c | 490 |
1 files changed, 0 insertions, 490 deletions
diff --git a/extern/verse/dist/v_connection.c b/extern/verse/dist/v_connection.c deleted file mode 100644 index 3bfafad5660..00000000000 --- a/extern/verse/dist/v_connection.c +++ /dev/null @@ -1,490 +0,0 @@ -/* -** -*/ - -#include <stdio.h> -#include <stdlib.h> -#include <string.h> - -#include "v_cmd_buf.h" -#include "v_network_in_que.h" -#include "v_network_out_que.h" -#include "v_cmd_gen.h" -#include "v_connection.h" -#include "v_encryption.h" -#include "v_util.h" - -#if !defined(V_GENERATE_FUNC_MODE) -#include "verse.h" - -#define CONNECTION_CHUNK_SIZE 16 -#define V_MAX_CONNECT_PACKET_SIZE 1500 -#define V_CON_MAX_MICROSECOND_BETWEEN_SENDS 100 -#define V_RE_CONNECTON_TIME_OUT 4 -#define V_CONNECTON_TIME_OUT 30 - -typedef struct { - VNetOutQueue *out_queue; - VNetInQueue in_queue; - VNetworkAddress network_address; - boolean connected; - unsigned int avatar; -/* unsigned int packet_id;*/ - int32 timedelta_s; - uint32 timedelta_f; - boolean destroy_flag; - void *ordered_storage; - char name[V_ENCRYPTION_LOGIN_KEY_SIZE / 2]; - char pass[V_ENCRYPTION_LOGIN_KEY_SIZE / 2]; - VConnectStage connect_stage; - unsigned int stage_atempts; - uint8 key_my[V_ENCRYPTION_LOGIN_KEY_FULL_SIZE]; - uint8 key_other[V_ENCRYPTION_LOGIN_KEY_FULL_SIZE]; - uint8 key_data[V_ENCRYPTION_DATA_KEY_SIZE]; - uint8 *expected_key; -} VConnection; - -static struct { - VConnection *con; - unsigned int con_count; - unsigned int current_connection; - VNetworkAddress *connect_address; - void *unified_func_storage; - uint16 connect_port; - unsigned int pending_packets; - uint8 host_id[V_ENCRYPTION_LOGIN_KEY_FULL_SIZE]; -} VConData; - -extern void cmd_buf_init(void); - -void v_con_init(void) /* since verse doesnt have an init function this function is runned over an ove ard starts whit a check it it has run before */ -{ - static boolean v_con_initialized = FALSE; - - if(v_con_initialized) - return; - cmd_buf_init(); - v_con_initialized = TRUE; - VConData.con = malloc(CONNECTION_CHUNK_SIZE * sizeof *VConData.con); - memset(VConData.con, 0, CONNECTION_CHUNK_SIZE * sizeof *VConData.con); /* Clear the memory. */ - VConData.con_count = 0; - VConData.pending_packets = 0; -/* v_e_connect_create_key(&VConData.host_id[V_ENCRYPTION_LOGIN_PRIVATE_START], - &VConData.host_id[V_ENCRYPTION_LOGIN_PUBLIC_START], - &VConData.host_id[V_ENCRYPTION_LOGIN_N_START]);*/ /* default host id if none is set by user */ -} - -void verse_set_port(uint16 port) -{ - v_n_set_port(port); -} - -void verse_host_id_create(uint8 *id) -{ - v_e_connect_create_key(&id[V_ENCRYPTION_LOGIN_PRIVATE_START], - &id[V_ENCRYPTION_LOGIN_PUBLIC_START], &id[V_ENCRYPTION_LOGIN_N_START]); -} - -void verse_host_id_set(uint8 *id) -{ - memcpy(VConData.host_id, id, V_ENCRYPTION_LOGIN_KEY_FULL_SIZE); -} - -extern void *v_fs_create_func_storage(void); -extern void *v_create_ordered_storage(void); -extern void v_destroy_ordered_storage(void *data); - -void *v_con_connect(uint32 ip, uint16 port, VConnectStage stage) /* creates a new connection slot */ -{ - v_con_init(); /* init connections, if not done yet */ - if((VConData.con_count - 1) % CONNECTION_CHUNK_SIZE == 0) /* do we need more slots for connections, then reallocate more space */ - VConData.con = realloc(VConData.con, (sizeof *VConData.con) * (VConData.con_count + CONNECTION_CHUNK_SIZE)); - VConData.con[VConData.con_count].out_queue = v_noq_create_network_queue(); /* create a out queue fo all out going commands */ - v_niq_clear(&VConData.con[VConData.con_count].in_queue); /* clear and init the que of incomming packets.*/ - VConData.con[VConData.con_count].connected = FALSE; /* not yet propperly connected and should not accept commands yet */ - VConData.con[VConData.con_count].network_address.ip = ip; /* ip address of other side */ - VConData.con[VConData.con_count].network_address.port = port; /* port used by other side */ - VConData.con[VConData.con_count].avatar = 0; /* no avatar set yet*/ -/* VConData.con[VConData.con_count].packet_id = 2;*/ - VConData.con[VConData.con_count].destroy_flag = FALSE; /* this is a flag that is set once the connection is about to be destroyed.*/ - VConData.con[VConData.con_count].ordered_storage = v_create_ordered_storage(); - VConData.con[VConData.con_count].name[0] = 0; /* nouser name set yet */ - VConData.con[VConData.con_count].pass[0] = 0; /* no password set yet */ - VConData.con[VConData.con_count].connect_stage = stage; /* this is the stage of the connection, it show if the connection is ready, the init state depends if this is a client or host */ - VConData.con[VConData.con_count].stage_atempts = 0; /* each stage in the connection prosess is atempted multiple times to avoid failiure if packets get lost*/ - VConData.con[VConData.con_count].timedelta_s = 0; /* number of seconds since last incomming packet to the connection*/ - VConData.con[VConData.con_count].timedelta_f = 0; /* number of fractions of a second since last incomming packet to the connection*/ - VConData.con[VConData.con_count].expected_key = NULL; /* expected hist id if this is a client */ - VConData.current_connection = VConData.con_count; /* set the new connection to the current*/ - ++VConData.con_count; /* add one to the number of connections*/ - return VConData.con[VConData.current_connection].out_queue; -} - -void verse_session_destroy(VSession session) /* a session can not be destroyed right away, because this function might be called inside a call back from the session it tryes tpo destroy, therfor it only markes it*/ -{ - unsigned int i; - for(i = 0; i < VConData.con_count && VConData.con[i].out_queue != session; i++); - if(i < VConData.con_count) - { - VConData.con[i].destroy_flag = TRUE; - } -} - -void verse_session_set(VSession session) /* find a session and make it the current*/ -{ - unsigned int i; - for(i = 0; i < VConData.con_count && session != VConData.con[i].out_queue; i++); - if(i < VConData.con_count) - VConData.current_connection = i; -} - -VSession verse_session_get(void) -{ - if(VConData.current_connection < VConData.con_count) - return VConData.con[VConData.current_connection].out_queue; - return NULL; -} - -uint32 v_co_find_connection(uint32 ip, uint16 port) /* if a packet comes form a ip address what connection does it belong to? */ -{ - unsigned int i; - - for(i = 0; i < VConData.con_count; i++) - { - if(ip == VConData.con[i].network_address.ip && - port == VConData.con[i].network_address.port && - VConData.con[i].destroy_flag == 0) - { - return i; - } - } - return -1; -} - -boolean v_co_switch_connection(uint32 ip, uint16 port) /* switches to the current connection to one ip address if it exists */ -{ - unsigned int i; - for(i = 0; i < VConData.con_count; i++) - { - if(ip == VConData.con[i].network_address.ip && port == VConData.con[i].network_address.port) - { - VConData.current_connection = i; - return TRUE; - } - } - return FALSE; -} - -void v_con_inqueue_timer_update(void) -{ - if(VConData.current_connection < VConData.con_count) - { - v_niq_timer_update(&VConData.con[VConData.current_connection].in_queue); - } -} - -/* -extern void v_fs_buf_unpack(const uint8 *data, unsigned int length); -extern void v_fs_buf_store_pack(uint8 *data, unsigned int length); -extern boolean v_fs_buf_unpack_stored(void); -*/ -extern void v_unpack_connection(const char *buf, unsigned int buffer_length); - -extern void verse_send_packet_nak(uint32 packet_id); -extern void v_callback_connect_terminate(const char *bye); -extern boolean v_connect_unpack_ping(const char *buf, size_t buffer_length, uint32 ip, uint16 port); -extern void v_ping_update(void); -void v_fs_unpack_beginning(uint8 *data, unsigned int length); - -/* Main function that receives and distributes all incoming packets. */ -boolean v_con_network_listen(void) -{ - VNetworkAddress address; - uint8 buf[V_MAX_CONNECT_PACKET_SIZE], *store; - int size = 0; - unsigned int connection; - uint32 packet_id; - boolean ret = FALSE; - - v_con_init(); /* Init if needed. */ - connection = VConData.current_connection; /* Store current connection in a local variable so that we can restore it later. */ - size = v_n_receive_data(&address, buf, sizeof buf); /* Ask for incoming data from the network. */ - while(size != -1 && size != 0) /* Did we get any data? */ - { - VConData.current_connection = v_co_find_connection(address.ip, address.port); /* Is there a connection matching the IP and port? */ - vnp_raw_unpack_uint32(buf, &packet_id); /* Unpack the ID of the packet. */ -/* printf("got packet ID %u, %d bytes, connection %u\n", packet_id, size, VConData.current_connection);*/ - if(VConData.current_connection < VConData.con_count && - !(VConData.con[VConData.current_connection].connect_stage == V_CS_CONNECTED && packet_id == 0)) /* If this isn't a packet from an existing connection, disregard it. */ - { - if(VConData.con[VConData.current_connection].connect_stage == V_CS_CONNECTED) /* Is this connection initialized? */ - { - store = v_niq_store(&VConData.con[VConData.current_connection].in_queue, size, packet_id); /* Store the packet. */ - if(store != NULL) - { - VConData.pending_packets++; /* We now have one more packet pending unpack. */ - v_e_data_decrypt_packet(store, buf, size, VConData.con[VConData.current_connection].key_data); /* Decrypt the packet. */ - v_fs_unpack_beginning(store, size); - } - } - else - { - v_unpack_connection(buf, size); /* This is an ongoing connecton-attempt. */ - v_niq_timer_update(&VConData.con[VConData.current_connection].in_queue); - } - } - else if(v_connect_unpack_ping(buf, size, address.ip, address.port)) /* Ping handled. */ - ; - else if(v_fs_func_accept_connections()) /* Do we accept connection-attempts? */ - { - if(VConData.current_connection >= VConData.con_count || - V_RE_CONNECTON_TIME_OUT < v_niq_time_out(&VConData.con[VConData.current_connection].in_queue)) /* Is it a new client, or an old client that we haven't heard form in some time? */ - { - if(VConData.current_connection < VConData.con_count) - { - VConData.con[VConData.current_connection].network_address.ip = 0; - VConData.con[VConData.current_connection].destroy_flag = TRUE; /* Destroy old connection if there is one. */ - } - v_con_connect(address.ip, address.port, V_CS_IDLE); /* Create a new connection. */ - v_unpack_connection(buf, size); /* Unpack the connection-attempt. */ - } - } - else - { - fprintf(stderr, __FILE__ ": Unhandled packet--dropping\n"); - if(VConData.con_count > 0) - { - fprintf(stderr, __FILE__ ": State: connections=%u, current=%u (stage %u), packet_id=%u\n", - VConData.con_count, - VConData.current_connection, - (VConData.current_connection < VConData.con_count) ? VConData.con[VConData.current_connection].connect_stage : 0, - packet_id); - } - } - size = v_n_receive_data(&address, buf, sizeof buf); /* See if there are more incoming packets. */ - ret = TRUE; - } - VConData.current_connection = connection; /* Reset the current connection. */ - - return ret; -} - -extern void v_update_connection_pending(boolean resend); - -boolean v_con_callback_update(void) -{ - static unsigned int seconds; - boolean output = FALSE; - size_t size; - unsigned int connection, s; - VNetInPacked *p; - - v_n_get_current_time(&s, NULL); - connection = VConData.current_connection; - for(VConData.current_connection = 0; VConData.current_connection < VConData.con_count; VConData.current_connection++) - if(VConData.con[VConData.current_connection].connect_stage != V_CS_CONNECTED) - v_update_connection_pending(s != seconds); - seconds = s; - VConData.current_connection = connection; - if(VConData.pending_packets == 0) - return FALSE; - if(VConData.con[VConData.current_connection].connect_stage == V_CS_CONNECTED) - { - while((p = v_niq_get(&VConData.con[VConData.current_connection].in_queue, &size)) != NULL) - { - VConData.pending_packets--; - v_fs_unpack(p->data, size); - v_niq_release(&VConData.con[VConData.current_connection].in_queue, p); - output = TRUE; - } - v_con_network_listen(); - } - return output; -} - -void verse_callback_update(unsigned int microseconds) -{ - unsigned int connection, passed; - - v_ping_update(); /* Deliver any pending pings. */ - connection = VConData.current_connection; - for(VConData.current_connection = 0; VConData.current_connection < VConData.con_count; VConData.current_connection++) - { - if(VConData.con[VConData.current_connection].connect_stage == V_CS_CONNECTED) - v_noq_send_queue(VConData.con[VConData.current_connection].out_queue, &VConData.con[VConData.current_connection].network_address); - if(VConData.con[VConData.current_connection].destroy_flag == TRUE) - { - v_noq_destroy_network_queue(VConData.con[VConData.current_connection].out_queue); - VConData.pending_packets -= v_niq_free(&VConData.con[VConData.current_connection].in_queue); - v_destroy_ordered_storage(VConData.con[VConData.current_connection].ordered_storage); - if(VConData.con[VConData.current_connection].expected_key != NULL) - free(VConData.con[VConData.current_connection].expected_key); - if(VConData.con_count - 1 != VConData.current_connection) - VConData.con[VConData.current_connection] = VConData.con[VConData.con_count - 1]; - VConData.con_count--; - if(connection >= VConData.con_count) - VConData.current_connection = 0; - return; - } - } - VConData.current_connection = connection; - - if(VConData.con_count > 0) - { -/* printf("checking timeout of stage %d connection %u\n", - VConData.con[VConData.current_connection].connect_stage, VConData.current_connection); -*/ if(V_CONNECTON_TIME_OUT < v_niq_time_out(&VConData.con[VConData.current_connection].in_queue)) - { - if(VConData.con[VConData.current_connection].connect_stage != V_CS_CONNECTED) - { - VConData.con[VConData.current_connection].destroy_flag = TRUE; - } - else - v_callback_connect_terminate("connection timed out"); - } - } - - v_con_network_listen(); - if(VConData.con_count > 0) - if(v_con_callback_update()) - return; - for(passed = 0; passed < microseconds && VConData.pending_packets == 0;) - { - boolean update; - if(microseconds - passed > V_CON_MAX_MICROSECOND_BETWEEN_SENDS) /* Still a long way to go? */ - passed += v_n_wait_for_incoming(V_CON_MAX_MICROSECOND_BETWEEN_SENDS); - else - passed += v_n_wait_for_incoming(microseconds - passed); - do - { - update = v_con_network_listen(); - connection = VConData.current_connection; - for(VConData.current_connection = 0; VConData.current_connection < VConData.con_count; VConData.current_connection++) - { - if(VConData.con[VConData.current_connection].connect_stage == V_CS_CONNECTED) - { - if(v_noq_send_queue(VConData.con[VConData.current_connection].out_queue, &VConData.con[VConData.current_connection].network_address)) - update = TRUE; - } - } - VConData.current_connection = connection; - } while(update); - } - if(VConData.con_count > 0) - v_con_callback_update(); -} - -void v_con_set_name_pass(const char *name, const char *pass) -{ - v_strlcpy(VConData.con[VConData.current_connection].name, name, sizeof VConData.con[VConData.current_connection].name); - v_strlcpy(VConData.con[VConData.current_connection].pass, pass, sizeof VConData.con[VConData.current_connection].pass); -} - -const char * v_con_get_name(void) -{ - return VConData.con[VConData.current_connection].name; -} - -const char * v_con_get_pass(void) -{ - return VConData.con[VConData.current_connection].pass; -} - -void v_con_set_connect_stage(VConnectStage stage) -{ - VConData.con[VConData.current_connection].connect_stage = stage; - VConData.con[VConData.current_connection].stage_atempts = 0; -} - -VConnectStage v_con_get_connect_stage(void) -{ - return VConData.con[VConData.current_connection].connect_stage; -} - -uint8 *v_con_get_my_key(void) -{ - return VConData.con[VConData.current_connection].key_my; -} - -uint8 *v_con_get_other_key(void) -{ - return VConData.con[VConData.current_connection].key_other; -} - -uint8 **v_con_get_expected_key(void) -{ - return &VConData.con[VConData.current_connection].expected_key; -} - -uint8 * v_con_get_host_id(void) -{ - return VConData.host_id; -} - -void v_con_set_data_key(const uint8 *key) -{ - memcpy(VConData.con[VConData.current_connection].key_data, key, V_ENCRYPTION_DATA_KEY_SIZE); -} - -const uint8 * v_con_get_data_key(void) -{ - return VConData.con[VConData.current_connection].key_data; -} - -void * v_con_get_network_queue(void) -{ - return VConData.con[VConData.current_connection].out_queue; -} - -VNetworkAddress * v_con_get_network_address(void) -{ - return &VConData.con[VConData.current_connection].network_address; -} - -void * v_con_get_ordered_storage(void) -{ - return VConData.con[VConData.current_connection].ordered_storage; -} - -void v_con_set_avatar(uint32 avatar) -{ - VConData.con[VConData.current_connection].avatar = avatar; -} - -uint32 verse_session_get_avatar(void) -{ - return VConData.con[VConData.current_connection].avatar; -} - -void verse_session_get_time(uint32 *seconds, uint32 *fractions) -{ - uint32 s, f; - v_n_get_current_time(&s, &f); - if((uint32)~0 - f < VConData.con[VConData.current_connection].timedelta_f) - s++; - if(seconds != NULL) - { - if(VConData.con[VConData.current_connection].timedelta_s < 0) - *seconds = s - (uint32)(-VConData.con[VConData.current_connection].timedelta_s); - else - *seconds = s + VConData.con[VConData.current_connection].timedelta_s; - } - if(fractions != NULL) - *fractions = f + VConData.con[VConData.current_connection].timedelta_f; -} - -void v_con_set_time(uint32 seconds, uint32 fractions) -{ - uint32 s, f; - v_n_get_current_time(&s, &f); - - if(f < fractions) - s--; - if (s < seconds) - VConData.con[VConData.current_connection].timedelta_s = -(int)(seconds - s); - else - VConData.con[VConData.current_connection].timedelta_s = (int)(s - seconds); - VConData.con[VConData.current_connection].timedelta_f = f - fractions; -} - -#endif |