From 204c54849f2c8aca4897b7cf6d3007f8e1991801 Mon Sep 17 00:00:00 2001 From: Apostolof Date: Thu, 26 Sep 2019 11:20:23 +0300 Subject: [PATCH] Init rewrite, Add message struct --- Makefile | 7 +- lib/circ_buff.c | 362 ----------------------------- lib/circ_buff.h | 80 ------- lib/helpers.c | 353 ---------------------------- lib/helpers.h | 65 ------ lib/message.c | 132 +++++++++++ lib/message.h | 44 ++++ lib/node.c | 124 ---------- lib/node.h | 59 ----- src/zaqar.c | 95 -------- src/zaqar.h | 28 --- test/test_circ_buff.c | 517 ------------------------------------------ test/test_message.c | 107 +++++++++ test/test_node.c | 176 -------------- 14 files changed, 288 insertions(+), 1861 deletions(-) delete mode 100644 lib/circ_buff.c delete mode 100644 lib/circ_buff.h delete mode 100644 lib/helpers.c delete mode 100644 lib/helpers.h create mode 100644 lib/message.c create mode 100644 lib/message.h delete mode 100644 lib/node.c delete mode 100644 lib/node.h delete mode 100644 src/zaqar.c delete mode 100644 src/zaqar.h delete mode 100644 test/test_circ_buff.c create mode 100644 test/test_message.c delete mode 100644 test/test_node.c diff --git a/Makefile b/Makefile index e7a3eb5..bd58346 100644 --- a/Makefile +++ b/Makefile @@ -28,7 +28,7 @@ PATHD = build/depends/ PATHO = build/objs/ PATHR = build/results/ -BUILD_PATHS = $(PATHB) $(PATHD) $(PATHO) $(PATHR) $(PATHL) +BUILD_PATHS = $(PATHB) $(PATHD) $(PATHO) $(PATHR) $(PATHL) $(PATHTR) COMPILE = gcc -c CROSSCOMPILE = arm-linux-gnueabihf-gcc -c @@ -112,7 +112,7 @@ $(PATHR)%.txt: $(PATHB)%.$(TARGET_EXTENSION) -./$< > $@ 2>&1 $(PATHB)test_%.$(TARGET_EXTENSION): $(PATHO)test_%.o $(PATHO)test_%_Runner.o $(PATHO)%.t.o $(PATHU)unity.o - $(TARLINK) -o $@ $^ + $(TARLINK) $(TARLINKFLAGS) -o $@ $^ $(PATHO)%.o: $(PATHTR)%.c $(TARCOMPILE) $(TARFLAGS) $< -o $@ @@ -153,6 +153,9 @@ $(PATHO): $(PATHR): $(MKDIR) $(PATHR) +$(PATHTR): + $(MKDIR) $(PATHTR) + clean: $(CLEANUP) $(PATHO)*.o $(CLEANUP) $(PATHB)*.$(TARGET_EXTENSION) diff --git a/lib/circ_buff.c b/lib/circ_buff.c deleted file mode 100644 index f926acf..0000000 --- a/lib/circ_buff.c +++ /dev/null @@ -1,362 +0,0 @@ -#include -#include -#include -#include -#include - -#include - -#include "circ_buff.h" - -// Defines the circular buffer structure -struct circ_buf_t { - char **buffer; - size_t head; - size_t tail; - size_t max; // of the buffer - size_t el_size; - bool full; -}; - -// Private Functions - -unit_static void advance_pointer(cbuf_handle_t cbuf) { - assert(cbuf); - - if(cbuf->full) { - cbuf->tail = (cbuf->tail + 1) % cbuf->max; - } - - cbuf->head = (cbuf->head + 1) % cbuf->max; - - // We mark full because we will advance tail on the next time around - cbuf->full = (cbuf->head == cbuf->tail); -} - -unit_static void retreat_pointer(cbuf_handle_t cbuf) { - assert(cbuf); - - cbuf->full = false; - cbuf->tail = (cbuf->tail + 1) % cbuf->max; -} - -// APIs - -cbuf_handle_t circ_buf_init(char **buffer, size_t size, size_t element_size) { - assert(buffer && size); - - cbuf_handle_t cbuf = malloc(sizeof(circ_buf_t)); - assert(cbuf); - - cbuf->buffer = buffer; - cbuf->max = size; - cbuf->el_size = element_size; - circ_buf_reset(cbuf); - - assert(circ_buf_empty(cbuf)); - - return cbuf; -} - -void circ_buf_free(cbuf_handle_t cbuf) { - assert(cbuf); - free(cbuf); -} - -void circ_buf_reset(cbuf_handle_t cbuf) { - assert(cbuf); - - cbuf->head = 0; - cbuf->tail = 0; - cbuf->full = false; -} - -size_t circ_buf_size(cbuf_handle_t cbuf) { - assert(cbuf); - - size_t size = cbuf->max; - - if(!cbuf->full) { - if(cbuf->head >= cbuf->tail) { - size = (cbuf->head - cbuf->tail); - } - else { - size = (cbuf->max + cbuf->head - cbuf->tail); - } - } - - return size; -} - -size_t circ_buf_capacity(cbuf_handle_t cbuf) { - assert(cbuf); - - return cbuf->max; -} - -void circ_buf_put(cbuf_handle_t cbuf, const char *data) { - assert(cbuf && cbuf->buffer); - - strcpy(cbuf->buffer[cbuf->head], data); - - advance_pointer(cbuf); -} - -void circ_buf_mul_add(cbuf_handle_t cbuf, char **data, uint8_t size, - int (*compar)(const void *, const void *)) { - assert(cbuf && data && cbuf->buffer); - - qsort(data, size, sizeof(char*), compar); - - char *last_element = (char*) malloc(circ_buf_element_size(cbuf) * sizeof(char)); - for (uint8_t i = 0; i < size; ++i) { - circ_buf_read(cbuf, 0, last_element); - - if (compar(&data[i], &last_element) < 0) { - continue; - } - - circ_buf_put(cbuf, data[i]); - } - - free(last_element); - - int end_buffer_size = circ_buf_size(cbuf); - char **temp_array = (char **) malloc(end_buffer_size * sizeof(char *)); - for (uint8_t buff_el = 0; buff_el < end_buffer_size; ++buff_el) { - temp_array[buff_el] = (char *) malloc(circ_buf_element_size(cbuf) * sizeof(char)); - circ_buf_get(cbuf, temp_array[buff_el]); - } - - qsort(temp_array, end_buffer_size, sizeof(char*), compar); - - for (uint8_t i = 0; i < end_buffer_size; ++i) { - circ_buf_put(cbuf, temp_array[i]); - } - - for (uint8_t buff_el = 0; buff_el < end_buffer_size; ++buff_el) { - free(temp_array[buff_el]); - } - free(temp_array); -} - -int circ_buf_get(cbuf_handle_t cbuf, char *data) { - assert(cbuf && data && cbuf->buffer); - - int r = -1; - - if(!circ_buf_empty(cbuf)) { - strcpy(data, cbuf->buffer[cbuf->tail]); - retreat_pointer(cbuf); - - r = 0; - } - - return r; -} - -int circ_buf_read(cbuf_handle_t cbuf, size_t position, char *data) { - assert(cbuf && data && cbuf->buffer && (position < circ_buf_size(cbuf))); - - int r = -1; - - if(!circ_buf_empty(cbuf)) { - strcpy(data, cbuf->buffer[(cbuf->tail + position) % cbuf->max]); - - r = 0; - } - - return r; -} - -void diff_bufs(cbuf_handle_t cbuf1, cbuf_handle_t cbuf2, - char ***add1, char ***add2) { - assert(cbuf1 && cbuf2 && - (circ_buf_element_size(cbuf1) == circ_buf_element_size(cbuf2)) && - (circ_buf_capacity(cbuf1) == circ_buf_capacity(cbuf2))); - - // Initializes the diff arrays - (*add1) = (char **) malloc(circ_buf_capacity(cbuf2) * sizeof(char *)); - (*add2) = (char **) malloc(circ_buf_capacity(cbuf1) * sizeof(char *)); - - char *curr_str1 = (char*) malloc(circ_buf_element_size(cbuf1) * sizeof(char)); - char *curr_str2 = (char*) malloc(circ_buf_element_size(cbuf2) * sizeof(char)); - /*uint8_t diff_array_index = 0; - for (uint8_t i = 0; i < circ_buf_size(cbuf1); ++i) { - // Reads current element of cbuf1 - circ_buf_read(cbuf1, i, curr_str1); - bool element_exists = false; - - for (uint8_t j = 0; j < circ_buf_size(cbuf2); ++j) { - circ_buf_read(cbuf2, j, curr_str2); - // Checks against cbuf2 elements - if (!strcmp(curr_str2, curr_str1)) { - element_exists = true; - break; - } - } - - if (!element_exists) { - (*add2)[diff_array_index] = (char*) malloc(circ_buf_element_size(cbuf1) * sizeof(char)); - strcpy((*add2)[diff_array_index], curr_str1); - ++diff_array_index; - } - } - - (*add1)[diff_array_index] = (char*) malloc(circ_buf_element_size(cbuf1) * sizeof(char)); - strcpy((*add1)[diff_array_index], EOB); - - diff_array_index = 0; - for (uint8_t i = 0; i < circ_buf_size(cbuf2); ++i) { - // Reads current element of cbuf2 - circ_buf_read(cbuf2, i, curr_str2); - bool element_exists = false; - - for (uint8_t j = 0; j < circ_buf_size(cbuf1); ++j) { - circ_buf_read(cbuf1, j, curr_str1); - // Checks against cbuf1 elements - if (!strcmp(curr_str1, curr_str2)) { - element_exists = true; - break; - } - } - - if (!element_exists) { - (*add1)[diff_array_index] = (char*) malloc(circ_buf_element_size(cbuf2) * sizeof(char)); - strcpy((*add1)[diff_array_index], curr_str2); - ++diff_array_index; - } - } - - (*add2)[diff_array_index] = (char*) malloc(circ_buf_element_size(cbuf2) * sizeof(char)); - strcpy((*add2)[diff_array_index], EOB);*/ - - - - uint8_t cbuf1_idx = 0, cbuf2_idx = 0, add1_arr_idx = 0, add2_arr_idx = 0; - while ((cbuf1_idx < circ_buf_size(cbuf1)) && - (cbuf2_idx < circ_buf_size(cbuf2))) { - circ_buf_read(cbuf1, cbuf1_idx, curr_str1); - circ_buf_read(cbuf2, cbuf2_idx, curr_str2); - - int strcmp_res = strcmp(curr_str1, curr_str2); - if (!strcmp_res) { - ++cbuf1_idx; - ++cbuf2_idx; - } else { // TODO: change the inner comparisons (strtok etc) - if (strcmp_res < 0) { - (*add2)[add2_arr_idx] = (char*) malloc(circ_buf_element_size(cbuf2) * sizeof(char)); - strcpy((*add2)[add2_arr_idx], curr_str1); - ++add2_arr_idx; - ++cbuf1_idx; - } - else if (strcmp_res > 0) { - (*add1)[add1_arr_idx] = (char*) malloc(circ_buf_element_size(cbuf1) * sizeof(char)); - strcpy((*add1)[add1_arr_idx], curr_str2); - ++add1_arr_idx; - ++cbuf2_idx; - } - } - } - - while (cbuf1_idx < circ_buf_size(cbuf1)) { - (*add2)[add2_arr_idx] = (char*) malloc(circ_buf_element_size(cbuf2) * sizeof(char)); - circ_buf_read(cbuf1, cbuf1_idx, curr_str1); - strcpy((*add2)[add2_arr_idx], curr_str1); - ++add2_arr_idx; - ++cbuf1_idx; - } - - while (cbuf2_idx < circ_buf_size(cbuf2)) { - (*add1)[add1_arr_idx] = (char*) malloc(circ_buf_element_size(cbuf1) * sizeof(char)); - circ_buf_read(cbuf2, cbuf2_idx, curr_str2); - strcpy((*add1)[add1_arr_idx], curr_str2); - ++add1_arr_idx; - ++cbuf2_idx; - } - - (*add1)[add1_arr_idx] = (char*) malloc(circ_buf_element_size(cbuf1) * sizeof(char)); - strcpy((*add1)[add1_arr_idx], EOB); - - (*add2)[add2_arr_idx] = (char*) malloc(circ_buf_element_size(cbuf2) * sizeof(char)); - strcpy((*add2)[add2_arr_idx], EOB); - - free(curr_str1); - free(curr_str2); - - /*uint8_t i = 0; - printf("add1:\n"); - while (strcmp((*add1)[i], EOB)) { - printf("%s\n", (*add1)[i]); - ++i; - } - - i = 0; - printf("add2:\n"); - while (strcmp((*add2)[i], EOB)) { - printf("%s\n", (*add2)[i]); - ++i; - }*/ -} - -int circ_buf_serialize(cbuf_handle_t cbuf, char **serialized) { - char *temp = (char*) malloc(circ_buf_element_size(cbuf) * sizeof(char)); - const char separator[2] = "\r"; - uint8_t char_sum = circ_buf_size(cbuf) - 1; - uint8_t i; - - for (i = 0; i < circ_buf_size(cbuf); ++i) { - circ_buf_read(cbuf, i, temp); - char_sum += strlen(temp); - } - - (*serialized) = (char*) malloc((char_sum + 1) * sizeof(char)); - strcpy((*serialized), ""); - - for (i = 0; i < circ_buf_size(cbuf) - 1; ++i) { - circ_buf_read(cbuf, i, temp); - strcat((*serialized), temp); - strcat((*serialized), separator); - } - - circ_buf_read(cbuf, i, temp); - strcat((*serialized), temp); - - free(temp); - - return strlen((*serialized)); -} - -int circ_buf_deserialize(cbuf_handle_t cbuf, const char *serialized) { - char *str = calloc(strlen(serialized) + 1, sizeof(char)); - strcpy(str, serialized); - const char separator[2] = "\r"; - char *token; - - token = strtok(str, separator); - - while (token != NULL) { - circ_buf_put(cbuf, token); - token = strtok(NULL, separator); - } - - return circ_buf_size(cbuf); -} - -bool circ_buf_empty(cbuf_handle_t cbuf) { - assert(cbuf); - - return (!cbuf->full && (cbuf->head == cbuf->tail)); -} - -bool circ_buf_full(cbuf_handle_t cbuf) { - assert(cbuf); - - return cbuf->full; -} - -size_t circ_buf_element_size(cbuf_handle_t cbuf) { - assert(cbuf); - - return cbuf->el_size; -} \ No newline at end of file diff --git a/lib/circ_buff.h b/lib/circ_buff.h deleted file mode 100644 index 5d2a5fd..0000000 --- a/lib/circ_buff.h +++ /dev/null @@ -1,80 +0,0 @@ -/* - * Implementation of a simple circular buffer data structure. - * Based on the example and guide found here: - * https://embeddedartistry.com/blog/2017/4/6/circular-buffers-in-cc -*/ -#ifndef CIRC_BUFF_H_ -#define CIRC_BUFF_H_ - -#include - -#define EOB "-1" - -// Circular buffer structure -typedef struct circ_buf_t circ_buf_t; -// and handle type -typedef circ_buf_t *cbuf_handle_t; - -#ifdef TEST //This is a test build -// Makes private functions reachable by the tester -#define unit_static -unit_static void advance_pointer(cbuf_handle_t cbuf); -unit_static void retreat_pointer(cbuf_handle_t cbuf); -#else -#define unit_static static -#endif - -// Initializes a circular buffer structure and returns the circular buffer handle. -// Pass in a storage buffer and size. -cbuf_handle_t circ_buf_init(char **buffer, size_t size, size_t element_size); - -// Frees a circular buffer structure. Does not free data buffer! -void circ_buf_free(cbuf_handle_t cbuf); - -// Resets the circular buffer to empty, head == tail. Data not cleared! -void circ_buf_reset(cbuf_handle_t cbuf); - -// Adds data to the end of the buffer, even if the buffer is full. Old data is overwritten. -void circ_buf_put(cbuf_handle_t cbuf, const char *data); - -// Adds multiple entries to the buffer, keeping the data in ascending order according to the -// function compar provided in the parameters. If the buffer is full, smallest data are overwritten. -// Doesn't check for duplicates! -void circ_buf_mul_add(cbuf_handle_t cbuf, char **data, uint8_t size, - int (*compar)(const void *, const void *)); - -// Retrieves a value from the buffer. -int circ_buf_get(cbuf_handle_t cbuf, char *data); - -// Reads a value from the buffer. Does NOT retrieve, size is not reduced! -int circ_buf_read(cbuf_handle_t cbuf, size_t position, char *data); - -// Compares the buffers cbuf1 and cbuf2. Elements present on cbuf1 that do not -// exist on cbuf2 are added to the array add2, elements present on cbuf2 that do -// not exist on cbuf1 are added to the array add1. -// Both buffers must be ordered on the same way! -void diff_bufs(cbuf_handle_t cbuf1, cbuf_handle_t cbuf2, - char ***add1, char ***add2); - -// Serializes the whole buffer to a single string -int circ_buf_serialize(cbuf_handle_t cbuf, char **serialized); - -// De-serializes a string to a buffer -int circ_buf_deserialize(cbuf_handle_t cbuf, const char *serialized); - -// Checks if the buffer is empty. -bool circ_buf_empty(cbuf_handle_t cbuf); - -// Checks if the buffer is full. -bool circ_buf_full(cbuf_handle_t cbuf); - -// Returns the capacity of the buffer. -size_t circ_buf_capacity(cbuf_handle_t cbuf); - -// Returns the number of elements stored in the buffer. -size_t circ_buf_size(cbuf_handle_t cbuf); - -// Returns the size of each element. -size_t circ_buf_element_size(cbuf_handle_t cbuf); - -#endif //CIRC_BUFF_H_ diff --git a/lib/helpers.c b/lib/helpers.c deleted file mode 100644 index 21f0c3d..0000000 --- a/lib/helpers.c +++ /dev/null @@ -1,353 +0,0 @@ -#include "helpers.h" - -/* - * Function based on this example: - * http://man7.org/linux/man-pages/man3/getifaddrs.3.html#EXAMPLE -*/ -int get_own_id(void) { - int id = -1; - struct ifaddrs *ifaddr, *ifa; - int family, s, n; - char host[NI_MAXHOST]; - - if (getifaddrs(&ifaddr) == -1) { - perror("Couldn't get network interfaces."); - exit(EXIT_FAILURE); - } - - // Walks through linked list, maintaining head pointer so we can free list later - for (ifa = ifaddr, n = 0; ifa != NULL; ifa = ifa->ifa_next, n++) { - if (ifa->ifa_addr == NULL) { - continue; - } - - family = ifa->ifa_addr->sa_family; - - // Gets the address of an AF_INET* interface address - if (family == AF_INET || family == AF_INET6) { - s = getnameinfo(ifa->ifa_addr, - (family == AF_INET) ? sizeof(struct sockaddr_in) : sizeof(struct sockaddr_in6), - host, NI_MAXHOST, NULL, 0, NI_NUMERICHOST); - if (s != 0) { - printf("getnameinfo() failed: %s\n", gai_strerror(s)); - exit(EXIT_FAILURE); - } - - id = extract_id_from_ip(host); - if (id < 0) { - continue; - } - - break; - } - } - - freeifaddrs(ifaddr); - - return(id); -} - -int extract_id_from_ip(const char *ip) { - const char separator[2] = "."; - int id = 0; - char *rest, *token, *ip_cp; - - ip_cp = malloc(strlen(ip) * sizeof(char)); - strcpy(ip_cp, ip); - - rest = ip_cp; - token = strtok_r(rest, separator, &rest); - if (!token || atoi(token) != 10) { - return -1; - } - - token = strtok_r(rest, separator, &rest); - if (!token || atoi(token) != 0) { - return -1; - } - - token = strtok_r(rest, separator, &rest); - if (!token) { - return -1; - } - id = atoi(token) * 100; - - token = strtok_r(rest, separator, &rest); - if (!token) { - return -1; - } - id += atoi(token); - - return id; -} - -void set_timer_and_handler(void (*handler)(int), long int timer_interval) { - struct itimerval interval_timer; - struct sigaction signal_action; - - // Installs handler as the signal handler for SIGALRM - memset(&signal_action, 0, sizeof(signal_action)); - signal_action.sa_handler = handler; - if (sigaction(SIGALRM, &signal_action, NULL)) { - perror("Couldn't install function handler for SIGALRM signals."); - exit(EXIT_FAILURE); - } - - // Sets an interval timer to deliver a SIGALRM signal every timer_interval seconds - interval_timer.it_interval.tv_usec = 0; - interval_timer.it_interval.tv_sec = timer_interval; - interval_timer.it_value.tv_usec = 0; - interval_timer.it_value.tv_sec = timer_interval; - - if (setitimer(ITIMER_REAL, &interval_timer, NULL) == -1) { - perror("Couldn't set timer."); - exit(EXIT_FAILURE); - } -} - -void enable_echo_broadcast(void) { - if (system("echo 0 > /proc/sys/net/ipv4/icmp_echo_ignore_broadcasts") < 0) { - perror("Couldn't allow echo broadcasts."); - exit(EXIT_FAILURE); - } -} - -/* - * Function based on this snippet: - * https://codereview.stackexchange.com/a/58107 -*/ -void search_for_neighbors(node_handle_t **neighbors, uint16_t *num_neighbors, uint16_t port) { - // Broadcasts ping - if (system("ping -b 10.255.255.255 -c 3 > /dev/null") < 0) { - perror("Couldn't broadcast echo."); - exit(EXIT_FAILURE); - } - - // Reads the ARP file checking for connected devices - FILE *arpCache = fopen(ARP_CACHE, "r"); - if (!arpCache) { - perror("ARP Cache: Failed to open file \"" ARP_CACHE "\""); - exit(EXIT_FAILURE); - } - - // Ignores the first line, which contains the header - char header[ARP_BUFFER_LEN]; - if (!fgets(header, sizeof(header), arpCache)) { - perror("Couldn't read ARP file header."); - exit(EXIT_FAILURE); - } - - // Extracts IP addresses found in the file - char ipAddr[ARP_BUFFER_LEN]; - char **neighbors_ips = (char **) malloc(sizeof(char *)); - if (!neighbors_ips) { - perror("Unable to allocate memory for neighbor IP."); - exit(EXIT_FAILURE); - } - - int count = 0; - while (1 == fscanf(arpCache, ARP_LINE_FORMAT, ipAddr)) { - ++count; - if (count > 1) { - char **r_neighbors_ips = realloc(neighbors_ips, count * sizeof(char *)); - if (!r_neighbors_ips) { - free(r_neighbors_ips); - perror("Unable to reallocate memory for neighbor IP."); - exit(EXIT_FAILURE); - } - - neighbors_ips = r_neighbors_ips; - } - - neighbors_ips[count - 1] = (char *) malloc(ARP_BUFFER_LEN * sizeof(char)); - strcpy(neighbors_ips[count - 1], ipAddr); - } - - // Allocates memory for the new neighbors structs - if (!(*num_neighbors)) { - // Neighbors array came empty - (*neighbors) = (node_handle_t *) malloc(count * sizeof(node_handle_t)); - if (!neighbors_ips) { - perror("Unable to allocate memory for nodes."); - exit(EXIT_FAILURE); - } - } else { - node_handle_t *r_neighbors = realloc((*neighbors), count * sizeof(node_handle_t)); - if (!r_neighbors) { - free(r_neighbors); - perror("Unable to reallocate memory for nodes."); - exit(EXIT_FAILURE); - } - - (*neighbors) = r_neighbors; - } - - // Adds new event timestamps to neighbors structs - for (uint8_t i = 0; i < count; ++i) { - bool found_flag = false; - - for (uint8_t j = 0; j < (*num_neighbors); ++j) { - if (!strcmp(inet_ntoa(node_get_addr((*neighbors)[j]).sin_addr), - neighbors_ips[i])) { - bool node_alive = check_node_alive(neighbors_ips[i]); - node_add_timestamp((*neighbors)[i], time(NULL), node_alive); - - found_flag = true; - break; - } - } - - if (!found_flag) { - // New node found! - printf("Adding %s\n", neighbors_ips[i]); - struct sockaddr_in peer_name; - init_sockaddr(&peer_name, neighbors_ips[i], port); - (*neighbors)[(*num_neighbors)++] = node_init(peer_name); - } - } - - if (!((*num_neighbors) == count)) { - (*num_neighbors) = count; - } - - fclose(arpCache); -} - -void create_message(node_handle_t *neighbors, char *new_message, int own_id, - uint8_t num_neighbors, uint16_t max_message_length) { - node_handle_t random_node = neighbors[rand() % (num_neighbors)]; - - int peer_id = extract_id_from_ip(inet_ntoa((node_get_addr(random_node)).sin_addr)); - if (peer_id < 0) { - perror("Couldn't extract own ID."); - exit(EXIT_FAILURE); - } - - snprintf(new_message, max_message_length, "%04d_%04d_%ld_%s", own_id, peer_id, time(NULL), - "It's amazing... It's fantastic!"); -} - -bool check_node_alive(const char *ipv4) { - char command[64]; - - snprintf(command, 64, "ping %s -c 1 -W 1 | grep \"1 received\" > /dev/null", ipv4); - - int call_res = system(command); - if (call_res < 0) { - perror("Couldn't ping node."); - exit(EXIT_FAILURE); - } - - return call_res == 0; -} - -/* - * Function based on this example: - * https://www.gnu.org/software/libc/manual/html_node/Inet-Example.html#Inet-Example -*/ -int create_socket_and_listen(uint16_t port, uint8_t backlog_size) { - int in_sock; - struct sockaddr_in own_name; - - // Creates the socket - in_sock = socket(PF_INET, SOCK_STREAM, 0); - if (in_sock < 0) { - perror("Couldn't create the socket."); - exit(EXIT_FAILURE); - } - - // Gives the socket a name - own_name.sin_family = AF_INET; - own_name.sin_port = htons(port); - own_name.sin_addr.s_addr = htonl(INADDR_ANY); - - // Binds own address structure to socket - if (bind(in_sock, (struct sockaddr *) &own_name, sizeof(own_name)) < 0) { - perror("Couldn't bind the address structure to the socket."); - exit(EXIT_FAILURE); - } - - if (listen(in_sock, backlog_size) < 0) { - perror("Couldn't listen for connections on the socket."); - exit(EXIT_FAILURE); - } - - return in_sock; -} - -void send_message(struct sockaddr_in peer_name, const char *message) { - int out_sock; - - // Creates the socket - out_sock = socket(PF_INET, SOCK_STREAM, 0); - if (out_sock < 0) { - perror("Couldn't create the socket."); - exit(EXIT_FAILURE); - } - - // Connects to the peer - if (connect(out_sock, (struct sockaddr *) &peer_name, sizeof(peer_name))) { - printf("Couldn't connect to the peer.\n"); - } else { - // Sends data to the peer - write_to_peer(out_sock, message); - } - - close(out_sock); -} - -void accept_connection(int sock, struct sockaddr_in *peer_name, fd_set *active_fd_set) { - size_t peer_name_size = sizeof((*peer_name)); - int comm_socket = accept(sock, (struct sockaddr *) peer_name, &peer_name_size); - if (comm_socket < 0) { - perror("Couldn't accept the connection."); - exit(EXIT_FAILURE); - } - - fprintf(stderr, "Connected to host %s, port %hd.\n", - inet_ntoa((*peer_name).sin_addr), ntohs((*peer_name).sin_port)); - FD_SET(comm_socket, active_fd_set); -} - -void write_to_peer(int file_desc, const char *message) { - int num_bytes = write(file_desc, message, strlen(message) + 1); - if (num_bytes < 0) { - perror("Couldn't write to peer."); - exit(EXIT_FAILURE); - } -} - -int read_from_peer(int file_des, uint16_t max_line) { - char buffer[max_line]; - int num_bytes; - - num_bytes = read(file_des, buffer, sizeof(buffer)); - if (num_bytes < 0) { - perror("Couldn't read from peer."); - exit(EXIT_FAILURE); - } else if (num_bytes == 0) - // End-of-file - return -1; - else { - fprintf(stderr, "Got message: `%s'\n", buffer); - return 0; - } -} - -/* - * Function based on this example: - * https://www.gnu.org/software/libc/manual/html_node/Inet-Example.html#Inet-Example -*/ -void init_sockaddr(struct sockaddr_in *peer_name, const char *ipv4, uint16_t port) { - struct hostent *hostinfo; - - peer_name->sin_family = AF_INET; - peer_name->sin_port = htons(port); - hostinfo = gethostbyname(ipv4); - if (hostinfo == NULL) { - fprintf(stderr, "Unknown host %s.\n", ipv4); - exit(EXIT_FAILURE); - } - - peer_name->sin_addr = *(struct in_addr *) hostinfo->h_addr_list[0]; -} diff --git a/lib/helpers.h b/lib/helpers.h deleted file mode 100644 index 45768fc..0000000 --- a/lib/helpers.h +++ /dev/null @@ -1,65 +0,0 @@ -#ifndef HELPERS_H_ -#define HELPERS_H_ - -#define _GNU_SOURCE - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include "node.h" - -// Macros to turn a numeric macro into a string literal -#define xstr(s) str(s) -#define str(s) #s - -// Neighbor discovery related definitions -#define ARP_CACHE "/proc/net/arp" -#define ARP_STRING_LEN 1023 -#define ARP_BUFFER_LEN (ARP_STRING_LEN + 1) -#define PING_BUFFER_LEN 1024 - -// Format for fscanf() to read the 1st field of ARP -#define ARP_LINE_FORMAT "%" xstr(ARP_STRING_LEN) "s %*s %*s %*s %*s %*s" - -int get_own_id(void); - -int extract_id_from_ip(const char *ip); - -void set_timer_and_handler(void (*handler)(int), long int timer_interval); - -void enable_echo_broadcast(void); - -void search_for_neighbors(node_handle_t **neighbors, uint16_t *num_neighbors, uint16_t port); - -void create_message(node_handle_t *neighbors, char *new_message, int own_id, - uint8_t num_neighbors, uint16_t max_message_length); - -bool check_node_alive(const char *ipv4); - -int create_socket_and_listen(uint16_t port, uint8_t backlog_size); - -void send_message(struct sockaddr_in peer_name, const char *message); - -void accept_connection(int sock, struct sockaddr_in *client_name, fd_set *active_fd_set); - -void write_to_peer(int filedes, const char *message); - -int read_from_peer(int file_des, uint16_t max_line); - -void init_sockaddr(struct sockaddr_in *name, const char *hostname, uint16_t port); - -#endif //HELPERS_H_ diff --git a/lib/message.c b/lib/message.c new file mode 100644 index 0000000..98c45e3 --- /dev/null +++ b/lib/message.c @@ -0,0 +1,132 @@ +#include +#include +#include +#include + +#include "message.h" + +/* Private functions */ + +// Defines the node structure +struct message_t { + char *message; + uint16_t received_from, *sent_to; + observer_func *observers; + int message_length, num_sent_to, num_observers; +}; + +unit_static void message_state_changed(message_handle_t message_handle) { + assert(message_handle); + + for (uint16_t i = 0; i < message_handle->num_observers; ++i) { + (message_handle->observers[i])(); + } +} + +/* API */ + +message_handle_t message_init(const char *message, int message_length, uint16_t received_from) { + //assert(addr); + assert(message_length <= MAX_MESSAGE_LENGTH); + + message_handle_t message_handle = malloc(sizeof(message_t)); + assert(message_handle); + + message_handle->message = malloc((message_length + 1) * sizeof(char)); + strcpy(message_handle->message, message); + message_handle->message_length = message_length; + + message_handle->received_from = received_from; + + message_handle->sent_to = NULL; + message_handle->num_sent_to = 0; + + message_handle->observers = NULL; + message_handle->num_observers = 0; + + return message_handle; +} + +void message_free(message_handle_t message_handle) { + assert(message_handle); + + free(message_handle->sent_to); + free(message_handle->observers); + free(message_handle->message); + free(message_handle); +} + +void message_add_sent_to(message_handle_t message_handle, uint16_t sent_to) { + assert(message_handle); + + if (message_handle->sent_to == NULL) { + message_handle->sent_to = (uint16_t *) malloc(sizeof(uint16_t)); + if (!message_handle->sent_to) { + perror("Unable to allocate memory for message receivers."); + exit(EXIT_FAILURE); + } + ++(message_handle->num_sent_to); + } else { + uint16_t *r_sent_to = realloc(message_handle->sent_to, ++(message_handle->num_sent_to) * sizeof(uint16_t)); + if (!r_sent_to) { + free(r_sent_to); + perror("Unable to reallocate memory for message receivers."); + exit(EXIT_FAILURE); + } + + message_handle->sent_to = r_sent_to; + } + + message_handle->sent_to[message_handle->num_sent_to - 1] = sent_to; + message_state_changed(message_handle); +} + +char *message_get(message_handle_t message_handle, int *message_length) { + assert(message_handle); + + char *message = (char *) malloc((message_handle->message_length + 1) * sizeof(char)); + if (!message) { + perror("Unable to allocate memory for message return."); + exit(EXIT_FAILURE); + } + + strcpy(message, message_handle->message); + (*message_length) = message_handle->message_length; + + return message; +} + +bool message_sent_to(message_handle_t message_handle, uint16_t node) { + assert(message_handle); + + for (uint16_t i = 0; i < message_handle->num_sent_to; ++i) { + if (message_handle->sent_to[i] == node) { + return true; + } + } + + return false; +} + +void message_attach_observer(message_handle_t message_handle, observer_func observer) { + assert(message_handle); + + if (message_handle->observers == NULL) { + message_handle->observers = (observer_func *) malloc(sizeof(observer_func)); + if (!message_handle->observers) { + perror("Unable to allocate memory for message observers."); + exit(EXIT_FAILURE); + } + ++(message_handle->num_observers); + } else { + uint16_t *r_observers = realloc(message_handle->observers, + ++(message_handle->num_observers) * sizeof(observer_func)); + if (!r_observers) { + free(r_observers); + perror("Unable to reallocate memory for message observers."); + exit(EXIT_FAILURE); + } + } + + message_handle->observers[message_handle->num_observers - 1] = observer; +} \ No newline at end of file diff --git a/lib/message.h b/lib/message.h new file mode 100644 index 0000000..c478b2f --- /dev/null +++ b/lib/message.h @@ -0,0 +1,44 @@ +#ifndef MESSAGE_H_ +#define MESSAGE_H_ + +#include +#include + +#define MAX_MESSAGE_LENGTH 277 + +// Message structure +typedef struct message_t message_t; +// and handle type +typedef message_t *message_handle_t; + +typedef void (*observer_func)(void); + +#ifdef TEST //This is a test build +// Makes private functions reachable by the tester +#define unit_static +// Calls all observer functions attached to this message. +unit_static void message_state_changed(message_handle_t message_handle); +#else +#define unit_static static +#endif + +// Initializes a message structure and returns the message handle. User must provide the length of +// the message without the null termination character (strlen); +message_handle_t message_init(const char *message, int message_length, uint16_t received_from); + +// Frees a message structure. +void message_free(message_handle_t message_handle); + +// Adds an new receiver to the message. +void message_add_sent_to(message_handle_t message_handle, uint16_t sent_to); + +// Returns the message. +char *message_get(message_handle_t message_handle, int *message_length); + +// Returns true if the message has been previously sent to this node, false otherwise. +bool message_sent_to(message_handle_t message_handle, uint16_t node); + +// Attaches an observer function to the message. +void message_attach_observer(message_handle_t message_handle, observer_func observer); + +#endif //MESSAGE_H_ diff --git a/lib/node.c b/lib/node.c deleted file mode 100644 index 6d9bf19..0000000 --- a/lib/node.c +++ /dev/null @@ -1,124 +0,0 @@ -#include -#include -#include -#include - -#include "node.h" - -// Defines the node structure -struct node_t { - struct sockaddr_in addr; - uint64_t **events; - uint64_t appearance_duration; - uint8_t events_size; - node_status _node_status; -}; - -node_handle_t node_init(struct sockaddr_in addr) { - //assert(addr); - - node_handle_t node = malloc(sizeof(node_t)); - assert(node); - - node->addr = addr; - node->events_size = 0; - node->events = (uint64_t **) malloc(2 * sizeof(uint64_t)); - node->events[0] = (uint64_t *) malloc(sizeof(uint64_t)); - node->events[1] = (uint64_t *) malloc(sizeof(uint64_t)); - node->events[0][0] = 0; - node->events[1][0] = 0; - node->appearance_duration = 0; - node->_node_status = NODE_INITIALIAZED; - - return node; -} - -void node_free(node_handle_t node) { - assert(node); - - free(node->events[0]); - free(node->events[1]); - free(node->events); - free(node); -} - -void node_add_timestamp(node_handle_t node, time_t timestamp, bool visible) { - assert(node && timestamp); - - if ((visible && !node->events[1][node->events_size - 1]) || - (!visible && node->events[1][node->events_size - 1])) { - return; - } - - if (visible) { - int *realloc_r = realloc(node->events[0], node->events_size + 1); - if (!realloc_r) { - node_free(node); - perror("Error trying to reallocate memory for event timestamps!"); - exit(EXIT_FAILURE); - } - realloc_r = realloc(node->events[1], node->events_size + 1); - if (!realloc_r) { - node_free(node); - perror("Error trying to reallocate memory for event timestamps!"); - exit(EXIT_FAILURE); - } - - node->events[0][node->events_size] = timestamp; - node->events[1][node->events_size] = 0; - node->_node_status = NODE_PRESENT; - ++node->events_size; - } else { - node->events[1][node->events_size - 1] = timestamp; - node->_node_status = NODE_GONE; - node->appearance_duration += node->events[1][node->events_size - 1] - - node->events[0][node->events_size - 1]; - } -} - -struct sockaddr_in node_get_addr(node_handle_t node) { - assert(node); - - return node->addr; -} - -enum node_status node_get_status(node_handle_t node) { - assert(node); - - return node->_node_status; -} - -uint8_t node_get_latest_appearance_duration(node_handle_t node) { - assert(node); - - if (node->_node_status == NODE_INITIALIAZED) { - return 0; - } else if (node->events[1][node->events_size - 1] == 0) { - return (uint64_t)time(NULL) - node->events[0][node->events_size - 1]; - } else { - return node->events[1][node->events_size - 1] - node->events[0][node->events_size - 1]; - } -} - -uint8_t node_get_total_appearance_duration(node_handle_t node) { - assert(node); - - return node->appearance_duration; -} - -uint8_t node_get_event_table(node_handle_t node, time_t ***event_table) { - assert(node && event_table); - - if (node->events_size < 1) { - return 0; - } - - (*event_table) = (time_t **) malloc(2 * sizeof(time_t *)); - (*event_table)[0] = (time_t *) malloc(node->events_size * sizeof(time_t)); - (*event_table)[1] = (time_t *) malloc(node->events_size * sizeof(time_t)); - - memcpy((*event_table)[0], node->events[0], node->events_size * sizeof(time_t)); - memcpy((*event_table)[1], node->events[1], node->events_size * sizeof(time_t)); - - return node->events_size; -} \ No newline at end of file diff --git a/lib/node.h b/lib/node.h deleted file mode 100644 index b506445..0000000 --- a/lib/node.h +++ /dev/null @@ -1,59 +0,0 @@ -#ifndef NODE_H_ -#define NODE_H_ - -#include -#include -#include - -// Node structure -typedef struct node_t node_t; -// and handle type -typedef node_t *node_handle_t; - -typedef enum node_status { NODE_INITIALIAZED, NODE_PRESENT, NODE_GONE } node_status; - -#ifdef TEST //This is a test build -// Makes private functions reachable by the tester -#define unit_static -#else -#define unit_static static -#endif - -// Initializes a node structure and returns the node handle. -node_handle_t node_init(struct sockaddr_in addr); - -// Frees a node structure. -void node_free(node_handle_t node); - -// Adds an event timestamp to the node. Either the (re)appearance or the disappearance of the node. -void node_add_timestamp(node_handle_t node, time_t timestamp, bool visible); - -// Returns the address of the node -struct sockaddr_in node_get_addr(node_handle_t node); - -node_status node_get_status(node_handle_t node); - -//uint8_t node_get_appear_count(node_handle_t node); - -//uint8_t node_get_disappear_count(node_handle_t node); - -//void node_get_latest_appear(node_handle_t node, ); - -//void node_get_latest_disappear(node_handle_t node, ); - -// Returns the duration (in seconds) of the latest stretch of time that this node has been visible. -uint8_t node_get_latest_appearance_duration(node_handle_t node); - -// Returns the total duration (in seconds) of time that this node was visible. -uint8_t node_get_total_appearance_duration(node_handle_t node); - -// Returns the event timestamps table for this node. -uint8_t node_get_event_table(node_handle_t node, time_t ***event_table); - -// Serializes the whole node to a single string -//int circ_buf_serialize(node_handle_t node, char **serialized); - -// De-serializes a string to a node -//int circ_buf_deserialize(node_handle_t node, const char *serialized); - -#endif //NODE_H_ diff --git a/src/zaqar.c b/src/zaqar.c deleted file mode 100644 index 40ea2d3..0000000 --- a/src/zaqar.c +++ /dev/null @@ -1,95 +0,0 @@ -#include "zaqar.h" - -#define MESSAGE "You got mail!!! xo xo xo" - -volatile sig_atomic_t sigalrm_flag = false; - -int main(void) { - int in_sock, own_id; - fd_set active_fd_set, read_fd_set; - struct sockaddr_in peer_name; - node_handle_t *neighbors; - uint16_t num_neighbors = 0; - - own_id = get_own_id(); - if (own_id < 0) { - perror("Couldn't extract own ID."); - exit(EXIT_FAILURE); - } - - // Enables echo broadcast pings - enable_echo_broadcast(); - - // Searches network for neighbors - search_for_neighbors(&neighbors, &num_neighbors, PORT); - - // Sets a timer and handler to produce interrupts for sending messages - set_timer_and_handler(handle_alarm, TIMER_INTERVAL); - - // Creates a socket and sets it up to accept connections - in_sock = create_socket_and_listen(PORT, BACKLOG_SIZE); - - // Initializes the set of active sockets - // Clears the descriptor set - FD_ZERO(&active_fd_set); - // Sets socket in active readset - FD_SET(in_sock, &active_fd_set); - - while (1) { - if (sigalrm_flag) { - // It's time to send a message! - char new_message[MAX_MESSAGE_LENGTH]; - - search_for_neighbors(&neighbors, &num_neighbors, PORT); - create_message(neighbors, new_message, own_id, num_neighbors, MAX_MESSAGE_LENGTH); - - for (uint8_t i = 0; i < num_neighbors; ++i) { - if (node_get_status(neighbors[i]) == NODE_PRESENT) { - send_message(node_get_addr(neighbors[i]), new_message); - } - } - - sigalrm_flag = false; - } - - // Shallow copies the readset - read_fd_set = active_fd_set; - - // Blocks until input arrives on one or more active sockets - if (select(FD_SETSIZE, &read_fd_set, NULL, NULL, NULL) < 0) { - // Handles the wake-up from alarm signal interrupts - if (sigalrm_flag) { - continue; - } - - perror("Couldn't initiate synchronous I/O multiplexing."); - exit(EXIT_FAILURE); - } - - // Services all the sockets with input pending - for (int i = 0; i < FD_SETSIZE; ++i) { - if (FD_ISSET(i, &read_fd_set)) { - if (i == in_sock) { - // Connection request on original socket - accept_connection(in_sock, &peer_name, &active_fd_set); - } else { - // Data arriving on an already-connected socket - if (read_from_peer(i, MAX_MESSAGE_LENGTH) < 0) { - close(i); - FD_CLR(i, &active_fd_set); - } - } - } - } - } - - return 0; -} - -void handle_alarm(int sig) { - if (sig != SIGALRM) { - return; - } else { - sigalrm_flag = true; - } -} \ No newline at end of file diff --git a/src/zaqar.h b/src/zaqar.h deleted file mode 100644 index 5567b77..0000000 --- a/src/zaqar.h +++ /dev/null @@ -1,28 +0,0 @@ -#ifndef ZAQAR_H_ -#define ZAQAR_H_ - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include - -#include "helpers.h" -#include "node.h" - -#define TIMER_INTERVAL 10 -#define PORT 5000 -#define MAX_MESSAGE_LENGTH 277 -#define BACKLOG_SIZE 2 - -void handle_alarm(int sig); - -#endif //ZAQAR_H_ diff --git a/test/test_circ_buff.c b/test/test_circ_buff.c deleted file mode 100644 index 41daf34..0000000 --- a/test/test_circ_buff.c +++ /dev/null @@ -1,517 +0,0 @@ -#include -#include -#include -#include - -#include "unity.h" -#include "circ_buff.h" - -#define BUFFER_SIZE 8 -#define BUFFER_ELEMENT_SIZE 278 - -int compar(const void* entry1, const void* entry2) { - char **pstr1 = (char**)entry1, **pstr2 = (char**)entry2; - char *str1 = calloc(strlen(*pstr1) + 1, sizeof(char)), - *str2 = calloc(strlen(*pstr2) + 1, sizeof(char)); - strcpy(str1, *pstr1); - strcpy(str2, *pstr2); - - const char s[2] = "_"; - strtok(str1, s); - char* rest = strtok(NULL, ""); - int num1 = atoi(rest); - - strtok(str2, s); - rest = strtok(NULL, ""); - int num2 = atoi(rest); - - free(str1); - free(str2); - - return num1 - num2; -} - -void free_buffer(char** buffer) { - for(uint8_t i = 0; i < BUFFER_SIZE; ++i) { - free(buffer[i]); - } -} - -void test_circ_buf_init(void) { - char** buffer = (char **) malloc(BUFFER_SIZE * sizeof(char *)); - for (uint8_t buff_el = 0; buff_el < BUFFER_SIZE; ++buff_el) { - buffer[buff_el] = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - } - - TEST_ASSERT_NOT_NULL(circ_buf_init(buffer, BUFFER_SIZE, BUFFER_ELEMENT_SIZE)); - - free_buffer(buffer); - free(buffer); -} - -void test_circ_buf_put(void) { - char** buffer = (char **) malloc(BUFFER_SIZE * sizeof(char *)); - for (uint8_t buff_el = 0; buff_el < BUFFER_SIZE; ++buff_el) { - buffer[buff_el] = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - } - - cbuf_handle_t circ_buf = circ_buf_init(buffer, BUFFER_SIZE, BUFFER_ELEMENT_SIZE); - char* temp = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - - for(uint8_t i = 0; i < (BUFFER_SIZE - 2); ++i) { - snprintf(temp, BUFFER_ELEMENT_SIZE, "string_%d", i); - - circ_buf_put(circ_buf, temp); - } - - TEST_ASSERT_EQUAL_STRING_LEN("string_0", buffer[0], BUFFER_ELEMENT_SIZE); - TEST_ASSERT_EQUAL_STRING_LEN("string_1", buffer[1], BUFFER_ELEMENT_SIZE); - TEST_ASSERT_EQUAL_STRING_LEN("string_2", buffer[2], BUFFER_ELEMENT_SIZE); - TEST_ASSERT_EQUAL_STRING_LEN("string_3", buffer[3], BUFFER_ELEMENT_SIZE); - TEST_ASSERT_EQUAL_STRING_LEN("string_4", buffer[4], BUFFER_ELEMENT_SIZE); - TEST_ASSERT_EQUAL_STRING_LEN("string_5", buffer[5], BUFFER_ELEMENT_SIZE); - - for(uint8_t i = 0; i < BUFFER_SIZE; ++i) { - snprintf(temp, BUFFER_ELEMENT_SIZE, "string_%d", i); - - circ_buf_put(circ_buf, temp); - } - - free(temp); - - TEST_ASSERT_EQUAL_STRING_LEN("string_2", buffer[0], BUFFER_ELEMENT_SIZE); - TEST_ASSERT_EQUAL_STRING_LEN("string_3", buffer[1], BUFFER_ELEMENT_SIZE); - TEST_ASSERT_EQUAL_STRING_LEN("string_4", buffer[2], BUFFER_ELEMENT_SIZE); - TEST_ASSERT_EQUAL_STRING_LEN("string_5", buffer[3], BUFFER_ELEMENT_SIZE); - TEST_ASSERT_EQUAL_STRING_LEN("string_6", buffer[4], BUFFER_ELEMENT_SIZE); - TEST_ASSERT_EQUAL_STRING_LEN("string_7", buffer[5], BUFFER_ELEMENT_SIZE); - TEST_ASSERT_EQUAL_STRING_LEN("string_0", buffer[6], BUFFER_ELEMENT_SIZE); - TEST_ASSERT_EQUAL_STRING_LEN("string_1", buffer[7], BUFFER_ELEMENT_SIZE); - - circ_buf_free(circ_buf); - free_buffer(buffer); - free(buffer); -} - -void test_circ_buf_mul_add(void) { - char** buffer = (char **) malloc(BUFFER_SIZE * sizeof(char *)); - for (uint8_t buff_el = 0; buff_el < BUFFER_SIZE; ++buff_el) { - buffer[buff_el] = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - } - - cbuf_handle_t circ_buf = circ_buf_init(buffer, BUFFER_SIZE, BUFFER_ELEMENT_SIZE); - char* temp = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - char** to_add = (char **) malloc(5 * sizeof(char*)); - - for(uint8_t i = 0; i < (BUFFER_SIZE - 2); ++i) { - snprintf(temp, BUFFER_ELEMENT_SIZE, "string_%d", i); - - to_add[i] = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - - if (i < 5) { - snprintf(to_add[i], BUFFER_ELEMENT_SIZE, "string_%d", i + 10); - } - - circ_buf_put(circ_buf, temp); - } - - free(temp); - - circ_buf_mul_add(circ_buf, to_add, 5, compar); - - char* actual = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - - circ_buf_get(circ_buf, actual); - TEST_ASSERT_EQUAL_STRING_LEN("string_3", actual, BUFFER_ELEMENT_SIZE); - circ_buf_get(circ_buf, actual); - TEST_ASSERT_EQUAL_STRING_LEN("string_4", actual, BUFFER_ELEMENT_SIZE); - circ_buf_get(circ_buf, actual); - TEST_ASSERT_EQUAL_STRING_LEN("string_5", actual, BUFFER_ELEMENT_SIZE); - circ_buf_get(circ_buf, actual); - TEST_ASSERT_EQUAL_STRING_LEN("string_10", actual, BUFFER_ELEMENT_SIZE); - circ_buf_get(circ_buf, actual); - TEST_ASSERT_EQUAL_STRING_LEN("string_11", actual, BUFFER_ELEMENT_SIZE); - circ_buf_get(circ_buf, actual); - TEST_ASSERT_EQUAL_STRING_LEN("string_12", actual, BUFFER_ELEMENT_SIZE); - circ_buf_get(circ_buf, actual); - TEST_ASSERT_EQUAL_STRING_LEN("string_13", actual, BUFFER_ELEMENT_SIZE); - circ_buf_get(circ_buf, actual); - TEST_ASSERT_EQUAL_STRING_LEN("string_14", actual, BUFFER_ELEMENT_SIZE); - - free(actual); - circ_buf_free(circ_buf); - free(buffer); -} - -void test_circ_buf_get(void) { - char** buffer = (char **) malloc(BUFFER_SIZE * sizeof(char *)); - for (uint8_t buff_el = 0; buff_el < BUFFER_SIZE; ++buff_el) { - buffer[buff_el] = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - } - - cbuf_handle_t circ_buf = circ_buf_init(buffer, BUFFER_SIZE, BUFFER_ELEMENT_SIZE); - char* temp = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - - for(uint8_t i = 0; i < (BUFFER_SIZE - 2); ++i) { - snprintf(temp, BUFFER_ELEMENT_SIZE, "string_%d", i); - - circ_buf_put(circ_buf, temp); - } - - free(temp); - - char* actual = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - char* expected = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - - for(uint8_t i = 0; i < (BUFFER_SIZE - 2); ++i) { - circ_buf_get(circ_buf, actual); - snprintf(expected, BUFFER_ELEMENT_SIZE, "string_%d", i); - - TEST_ASSERT_EQUAL_STRING_LEN(expected, actual, BUFFER_ELEMENT_SIZE); - } - - free(actual); - free(expected); - - circ_buf_free(circ_buf); - free_buffer(buffer); - free(buffer); -} - -void test_circ_buf_read(void) { - char** buffer = (char **) malloc(BUFFER_SIZE * sizeof(char *)); - for (uint8_t buff_el = 0; buff_el < BUFFER_SIZE; ++buff_el) { - buffer[buff_el] = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - } - - cbuf_handle_t circ_buf = circ_buf_init(buffer, BUFFER_SIZE, BUFFER_ELEMENT_SIZE); - char* temp = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - - for(uint8_t i = 0; i < (BUFFER_SIZE - 2); ++i) { - snprintf(temp, BUFFER_ELEMENT_SIZE, "string_%d", i); - - circ_buf_put(circ_buf, temp); - } - - free(temp); - - char* actual = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - char* expected = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - - for(uint8_t i = 0; i < (BUFFER_SIZE - 2); ++i) { - circ_buf_read(circ_buf, i, actual); - snprintf(expected, BUFFER_ELEMENT_SIZE, "string_%d", i); - - TEST_ASSERT_EQUAL_STRING_LEN(expected, actual, BUFFER_ELEMENT_SIZE); - TEST_ASSERT_EQUAL_INT8(BUFFER_SIZE - 2, circ_buf_size(circ_buf)); - } - - free(actual); - free(expected); - - circ_buf_free(circ_buf); - free_buffer(buffer); - free(buffer); -} - -void test_circ_buf_serialize(void) { - char** buffer = (char **) malloc(BUFFER_SIZE * sizeof(char *)); - for (uint8_t buff_el = 0; buff_el < BUFFER_SIZE; ++buff_el) { - buffer[buff_el] = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - } - - cbuf_handle_t circ_buf = circ_buf_init(buffer, BUFFER_SIZE, BUFFER_ELEMENT_SIZE); - char* temp = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - - for(uint8_t i = 0; i < (BUFFER_SIZE - 2); ++i) { - snprintf(temp, BUFFER_ELEMENT_SIZE, "string_%d", i); - - circ_buf_put(circ_buf, temp); - } - - free(temp); - - char* serialized; - uint8_t serialized_length = circ_buf_serialize(circ_buf, &serialized); - TEST_ASSERT_EQUAL_UINT8(53, serialized_length); - - char* expected = "string_0\rstring_1\rstring_2\rstring_3\rstring_4\rstring_5"; - TEST_ASSERT_EQUAL_STRING_LEN(expected, serialized, 53); - - circ_buf_free(circ_buf); - free_buffer(buffer); - free(buffer); -} - -void test_circ_buf_deserialize(void) { - char** buffer = (char **) malloc(BUFFER_SIZE * sizeof(char *)); - for (uint8_t buff_el = 0; buff_el < BUFFER_SIZE; ++buff_el) { - buffer[buff_el] = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - } - - cbuf_handle_t circ_buf = circ_buf_init(buffer, BUFFER_SIZE, BUFFER_ELEMENT_SIZE); - - char* serialized = "string_0\rstring_1\rstring_2\rstring_3\rstring_4\rstring_5"; - uint8_t deserialized_size = circ_buf_deserialize(circ_buf, serialized); - TEST_ASSERT_EQUAL_UINT8(6, deserialized_size); - - char* actual = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - char* expected = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - - for(uint8_t i = 0; i < (BUFFER_SIZE - 2); ++i) { - circ_buf_get(circ_buf, actual); - snprintf(expected, BUFFER_ELEMENT_SIZE, "string_%d", i); - - TEST_ASSERT_EQUAL_STRING_LEN(expected, actual, BUFFER_ELEMENT_SIZE); - } - - free(actual); - free(expected); - - circ_buf_free(circ_buf); - free_buffer(buffer); - free(buffer); -} - -void test_circ_buf_empty(void) { - char** buffer = (char **) malloc(BUFFER_SIZE * sizeof(char *)); - for (uint8_t buff_el = 0; buff_el < BUFFER_SIZE; ++buff_el) { - buffer[buff_el] = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - } - - cbuf_handle_t circ_buf = circ_buf_init(buffer, BUFFER_SIZE, BUFFER_ELEMENT_SIZE); - - TEST_ASSERT_TRUE(circ_buf_empty(circ_buf)); - - for(uint8_t i = 0; i < BUFFER_SIZE; ++i) { - circ_buf_put(circ_buf, "Lorem ipsum"); - } - - TEST_ASSERT_FALSE(circ_buf_empty(circ_buf)); - - char* temp = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - - for(uint8_t i = 0; i < BUFFER_SIZE; ++i) { - circ_buf_get(circ_buf, temp); - } - - free(temp); - - TEST_ASSERT_TRUE(circ_buf_empty(circ_buf)); - - circ_buf_free(circ_buf); - free_buffer(buffer); - free(buffer); -} - - -void test_circ_buf_full(void) { - char** buffer = (char **) malloc(BUFFER_SIZE * sizeof(char *)); - for (uint8_t buff_el = 0; buff_el < BUFFER_SIZE; ++buff_el) { - buffer[buff_el] = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - } - - cbuf_handle_t circ_buf = circ_buf_init(buffer, BUFFER_SIZE, BUFFER_ELEMENT_SIZE); - - for(uint8_t i = 0; i < (BUFFER_SIZE - 1); ++i) { - circ_buf_put(circ_buf, "Lorem ipsum"); - TEST_ASSERT_FALSE(circ_buf_full(circ_buf)); - } - - circ_buf_put(circ_buf, "Lorem ipsum"); - TEST_ASSERT_TRUE(circ_buf_full(circ_buf)); - - circ_buf_free(circ_buf); - free_buffer(buffer); - free(buffer); -} - - -void test_circ_buf_capacity(void) { - char** buffer = (char **) malloc(BUFFER_SIZE * sizeof(char *)); - for (uint8_t buff_el = 0; buff_el < BUFFER_SIZE; ++buff_el) { - buffer[buff_el] = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - } - - cbuf_handle_t circ_buf = circ_buf_init(buffer, BUFFER_SIZE, BUFFER_ELEMENT_SIZE); - - TEST_ASSERT_EQUAL_INT8(BUFFER_SIZE, circ_buf_capacity(circ_buf)); - - circ_buf_put(circ_buf, "Lorem ipsum"); - circ_buf_put(circ_buf, "Lorem ipsum"); - - TEST_ASSERT_EQUAL_INT8(BUFFER_SIZE, circ_buf_capacity(circ_buf)); - - char* temp = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - circ_buf_get(circ_buf, temp); - free(temp); - - TEST_ASSERT_EQUAL_INT8(BUFFER_SIZE, circ_buf_capacity(circ_buf)); - - circ_buf_free(circ_buf); - free_buffer(buffer); - free(buffer); -} - -void test_circ_buf_size(void) { - char** buffer = (char **) malloc(BUFFER_SIZE * sizeof(char *)); - for (uint8_t buff_el = 0; buff_el < BUFFER_SIZE; ++buff_el) { - buffer[buff_el] = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - } - - cbuf_handle_t circ_buf = circ_buf_init(buffer, BUFFER_SIZE, BUFFER_ELEMENT_SIZE); - - TEST_ASSERT_EQUAL_INT8(0, circ_buf_size(circ_buf)); - - for(uint8_t i = 0; i < BUFFER_SIZE; ++i) { - circ_buf_put(circ_buf, "Lorem ipsum"); - TEST_ASSERT_EQUAL_INT8(i + 1, circ_buf_size(circ_buf)); - } - - char* temp = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - - for(uint8_t i = 0; i < BUFFER_SIZE; ++i) { - circ_buf_get(circ_buf, temp); - TEST_ASSERT_EQUAL_INT8(BUFFER_SIZE - i - 1, circ_buf_size(circ_buf)); - } - - free(temp); - - circ_buf_free(circ_buf); - free_buffer(buffer); - free(buffer); -} - -void test_circ_buf_reset(void) { - char** buffer = (char **) malloc(BUFFER_SIZE * sizeof(char *)); - for (uint8_t buff_el = 0; buff_el < BUFFER_SIZE; ++buff_el) { - buffer[buff_el] = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - } - - cbuf_handle_t circ_buf = circ_buf_init(buffer, BUFFER_SIZE, BUFFER_ELEMENT_SIZE); - - for(uint8_t i = 0; i < BUFFER_SIZE - 3; ++i) { - circ_buf_put(circ_buf, "Lorem ipsum"); - } - - circ_buf_reset(circ_buf); - - TEST_ASSERT_EQUAL_INT8(0, circ_buf_size(circ_buf)); - TEST_ASSERT_EQUAL_INT8(BUFFER_SIZE, circ_buf_capacity(circ_buf)); - TEST_ASSERT_TRUE(circ_buf_empty(circ_buf)); - TEST_ASSERT_FALSE(circ_buf_full(circ_buf)); - - circ_buf_free(circ_buf); - free_buffer(buffer); - free(buffer); -} - -void test_circ_buf_element_size(void) { - char** buffer = (char **) malloc(BUFFER_SIZE * sizeof(char *)); - for (uint8_t buff_el = 0; buff_el < BUFFER_SIZE; ++buff_el) { - buffer[buff_el] = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - } - - cbuf_handle_t circ_buf = circ_buf_init(buffer, BUFFER_SIZE, BUFFER_ELEMENT_SIZE); - - TEST_ASSERT_EQUAL_INT8(BUFFER_ELEMENT_SIZE, circ_buf_element_size(circ_buf)); - - circ_buf_put(circ_buf, "Lorem ipsum"); - circ_buf_put(circ_buf, "Lorem ipsum"); - - TEST_ASSERT_EQUAL_INT8(BUFFER_ELEMENT_SIZE, circ_buf_element_size(circ_buf)); - - char* temp = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - circ_buf_get(circ_buf, temp); - free(temp); - - TEST_ASSERT_EQUAL_INT8(BUFFER_ELEMENT_SIZE, circ_buf_element_size(circ_buf)); - - circ_buf_free(circ_buf); - free_buffer(buffer); - free(buffer); -} - -void test_advance_pointer(void) { - char** buffer = (char **) malloc(BUFFER_SIZE * sizeof(char *)); - for (uint8_t buff_el = 0; buff_el < BUFFER_SIZE; ++buff_el) { - buffer[buff_el] = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - } - - cbuf_handle_t circ_buf = circ_buf_init(buffer, BUFFER_SIZE, BUFFER_ELEMENT_SIZE); - - advance_pointer(circ_buf); - TEST_ASSERT_EQUAL_INT8(1, circ_buf_size(circ_buf)); - advance_pointer(circ_buf); - TEST_ASSERT_EQUAL_INT8(2, circ_buf_size(circ_buf)); - - circ_buf_free(circ_buf); - free_buffer(buffer); - free(buffer); -} - -void test_retreat_pointer(void) { - char** buffer = (char **) malloc(BUFFER_SIZE * sizeof(char *)); - for (uint8_t buff_el = 0; buff_el < BUFFER_SIZE; ++buff_el) { - buffer[buff_el] = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - } - - cbuf_handle_t circ_buf = circ_buf_init(buffer, BUFFER_SIZE, BUFFER_ELEMENT_SIZE); - - for(uint8_t i = 0; i < BUFFER_SIZE - 3; ++i) { - circ_buf_put(circ_buf, "Lorem ipsum"); - } - - retreat_pointer(circ_buf); - TEST_ASSERT_EQUAL_INT8(BUFFER_SIZE - 4, circ_buf_size(circ_buf)); - retreat_pointer(circ_buf); - TEST_ASSERT_EQUAL_INT8(BUFFER_SIZE - 5, circ_buf_size(circ_buf)); - - circ_buf_free(circ_buf); - free_buffer(buffer); - free(buffer); -} - -void test_diff_bufs(void) { - char** buffer1 = (char **) malloc(BUFFER_SIZE * sizeof(char *)); - char** buffer2 = (char **) malloc(BUFFER_SIZE * sizeof(char *)); - for (uint8_t buff_el = 0; buff_el < BUFFER_SIZE; ++buff_el) { - buffer1[buff_el] = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - buffer2[buff_el] = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - } - - cbuf_handle_t circ_buf1 = circ_buf_init(buffer1, BUFFER_SIZE, BUFFER_ELEMENT_SIZE); - cbuf_handle_t circ_buf2 = circ_buf_init(buffer2, BUFFER_SIZE, BUFFER_ELEMENT_SIZE); - - char* temp = (char *) malloc(BUFFER_ELEMENT_SIZE * sizeof(char)); - for(uint8_t i = 0; i < (BUFFER_SIZE - 2); ++i) { - snprintf(temp, BUFFER_ELEMENT_SIZE, "string_%d", i); - circ_buf_put(circ_buf1, temp); - - snprintf(temp, BUFFER_ELEMENT_SIZE, "string_%d", i + 2); - circ_buf_put(circ_buf2, temp); - } - - free(temp); - - char** add1 = NULL; - char** add2 = NULL; - diff_bufs(circ_buf1, circ_buf2, &add1, &add2); - - TEST_ASSERT_NOT_NULL(add1[0]); - TEST_ASSERT_NOT_NULL(add2[0]); - - TEST_ASSERT_EQUAL_STRING("string_6", add1[0]); - TEST_ASSERT_EQUAL_STRING("string_7", add1[1]); - TEST_ASSERT_EQUAL_STRING(EOB, add1[2]); - TEST_ASSERT_EQUAL_STRING("string_0", add2[0]); - TEST_ASSERT_EQUAL_STRING("string_1", add2[1]); - TEST_ASSERT_EQUAL_STRING(EOB, add2[2]); - - circ_buf_free(circ_buf1); - free_buffer(buffer1); - free(buffer1); - circ_buf_free(circ_buf2); - free_buffer(buffer2); - free(buffer2); -} diff --git a/test/test_message.c b/test/test_message.c new file mode 100644 index 0000000..a9d016d --- /dev/null +++ b/test/test_message.c @@ -0,0 +1,107 @@ +#include +#include +#include +#include + +#include "unity.h" +#include "message.h" + +struct message_t { + char *message; + uint16_t received_from, *sent_to; + observer_func *observers; + int message_length, num_sent_to, num_observers; +}; + +void test_message_init(void) { + const char message[] = "testing"; + + message_handle_t message_handle = message_init(message, strlen(message), 0); + + TEST_ASSERT_NOT_NULL(message_handle); + TEST_ASSERT_EQUAL_INT(strlen(message), message_handle->message_length); + TEST_ASSERT_EQUAL_INT(0, message_handle->num_sent_to); + TEST_ASSERT_EQUAL_INT(0, message_handle->num_observers); + + message_free(message_handle); +} + +void test_message_add_sent_to(void) { + const char message[] = "testing"; + message_handle_t message_handle = message_init(message, strlen(message), 0); + + const uint16_t expected[] = {4, 345, 26463, 35, 43663, 347, 3262}; + for (int i = 0; i < 7; ++i) { + message_add_sent_to(message_handle, expected[i]); + } + + TEST_ASSERT_EQUAL_UINT16_ARRAY(expected, message_handle->sent_to, 7); + + message_free(message_handle); +} + +void test_message_get(void) { + const char expected[] = "testing"; + message_handle_t message_handle = message_init(expected, strlen(expected), 0); + + int message_length = -1; + char *actual = message_get(message_handle, &message_length); + + TEST_ASSERT_EQUAL_UINT16(strlen(expected), message_length); + TEST_ASSERT_EQUAL_STRING_LEN(expected, actual, message_length); + + free(actual); + message_free(message_handle); +} + +void test_message_sent_to(void) { + const char message[] = "testing"; + message_handle_t message_handle = message_init(message, strlen(message), 0); + + const uint16_t expected[] = {4, 345, 26463, 35, 43663, 347, 3262}; + for (int i = 0; i < 7; ++i) { + message_add_sent_to(message_handle, expected[i]); + } + + TEST_ASSERT_EQUAL_INT(7, message_handle->num_sent_to); + + TEST_ASSERT_TRUE(message_sent_to(message_handle, 345)); + TEST_ASSERT_TRUE(message_sent_to(message_handle, 43663)); + TEST_ASSERT_TRUE(message_sent_to(message_handle, 347)); + TEST_ASSERT_FALSE(message_sent_to(message_handle, 0)); + TEST_ASSERT_FALSE(message_sent_to(message_handle, -1)); + TEST_ASSERT_FALSE(message_sent_to(message_handle, 348)); + + message_free(message_handle); +} + +bool globalTestVariable = false; +void test_observer(void) { + globalTestVariable = true; +} + +void test_message_attach_observer(void) { + const char message[] = "testing"; + message_handle_t message_handle = message_init(message, strlen(message), 0); + + message_attach_observer(message_handle, test_observer); + + TEST_ASSERT_EQUAL_INT(1, message_handle->num_observers); + TEST_ASSERT_NOT_NULL(message_handle->observers); + TEST_ASSERT_EQUAL_PTR(test_observer, message_handle->observers[0]); + + message_free(message_handle); +} + +void test_message_state_changed(void) { + const char message[] = "testing"; + message_handle_t message_handle = message_init(message, strlen(message), 0); + + message_attach_observer(message_handle, &test_observer); + globalTestVariable = false; + message_state_changed(message_handle); + + TEST_ASSERT_TRUE(globalTestVariable); + + message_free(message_handle); +} diff --git a/test/test_node.c b/test/test_node.c deleted file mode 100644 index ec7e9e6..0000000 --- a/test/test_node.c +++ /dev/null @@ -1,176 +0,0 @@ -#include -#include "unity.h" - -#include "node.h" - -struct node_t { - struct sockaddr_in addr; - uint64_t** events; - uint64_t appearance_duration; - uint8_t events_size; - node_status _node_status; -}; - -void test_node_init(void) { - struct sockaddr_in myaddr; - - myaddr.sin_family = AF_INET; - myaddr.sin_port = htons(2288); - myaddr.sin_addr.s_addr = htonl(INADDR_ANY); - - node_handle_t node = node_init(myaddr); - TEST_ASSERT_NOT_NULL(node); - - node_free(node); -} - -void test_node_add_timestamp(void) { - struct sockaddr_in myaddr; - - myaddr.sin_family = AF_INET; - myaddr.sin_port = htons(2288); - myaddr.sin_addr.s_addr = htonl(INADDR_ANY); - - node_handle_t node = node_init(myaddr); - - time_t base_time = time(NULL); - - node_add_timestamp(node, base_time - 15, true); - TEST_ASSERT_EQUAL_MEMORY(base_time - 15, node->events[0][0], sizeof(time_t)); - TEST_ASSERT_EQUAL_MEMORY(0, node->events[1][0], sizeof(time_t)); - - node_add_timestamp(node, base_time - 10, false); - TEST_ASSERT_EQUAL_MEMORY(base_time - 10, node->events[1][0], sizeof(time_t)); - - node_add_timestamp(node, base_time - 5, true); - TEST_ASSERT_EQUAL_MEMORY(base_time - 5, node->events[0][1], sizeof(time_t)); - TEST_ASSERT_EQUAL_MEMORY(0, node->events[1][1], sizeof(time_t)); - - node_add_timestamp(node, base_time, false); - TEST_ASSERT_EQUAL_MEMORY(base_time, node->events[1][1], sizeof(time_t)); - - node_add_timestamp(node, base_time + 5, false); - TEST_ASSERT_EQUAL_MEMORY(base_time, node->events[1][1], sizeof(time_t)); - - node_add_timestamp(node, base_time + 10, true); - TEST_ASSERT_EQUAL_MEMORY(base_time + 10, node->events[0][2], sizeof(time_t)); - TEST_ASSERT_EQUAL_MEMORY(0, node->events[1][2], sizeof(time_t)); - - node_free(node); -} - -void test_node_get_addr(void){ - struct sockaddr_in myaddr; - - myaddr.sin_family = AF_INET; - myaddr.sin_port = htons(2288); - myaddr.sin_addr.s_addr = htonl(INADDR_ANY); - - node_handle_t node = node_init(myaddr); - - struct sockaddr_in actual = node_get_addr(node); - TEST_ASSERT_EQUAL_MEMORY(&myaddr, &actual, sizeof(myaddr)); - - node_free(node); -} - -void test_node_get_status(void){ - struct sockaddr_in myaddr; - - myaddr.sin_family = AF_INET; - myaddr.sin_port = htons(2288); - myaddr.sin_addr.s_addr = htonl(INADDR_ANY); - - node_handle_t node = node_init(myaddr); - - TEST_ASSERT_EQUAL_INT(NODE_INITIALIAZED, node_get_status(node)); - - node_add_timestamp(node, time(NULL), true); - TEST_ASSERT_EQUAL_INT(NODE_PRESENT, node_get_status(node)); - - node_add_timestamp(node, time(NULL), false); - TEST_ASSERT_EQUAL_INT(NODE_GONE, node_get_status(node)); - - node_free(node); -} - -void test_node_get_latest_appearance_duration(void){ - struct sockaddr_in myaddr; - - myaddr.sin_family = AF_INET; - myaddr.sin_port = htons(2288); - myaddr.sin_addr.s_addr = htonl(INADDR_ANY); - - node_handle_t node = node_init(myaddr); - - time_t base_time = time(NULL); - node_add_timestamp(node, base_time - 10, true); - TEST_ASSERT_UINT8_WITHIN(1, 10, node_get_latest_appearance_duration(node)); - - node_add_timestamp(node, base_time + 10, false); - TEST_ASSERT_EQUAL_UINT8(20, node_get_latest_appearance_duration(node)); - - node_free(node); -} - -void test_node_get_total_appearance_duration(void){ - struct sockaddr_in myaddr; - - myaddr.sin_family = AF_INET; - myaddr.sin_port = htons(2288); - myaddr.sin_addr.s_addr = htonl(INADDR_ANY); - - node_handle_t node = node_init(myaddr); - - time_t base_time = time(NULL); - - node_add_timestamp(node, base_time - 30, true); - node_add_timestamp(node, base_time - 25, false); - TEST_ASSERT_EQUAL_UINT8(5, node_get_total_appearance_duration(node)); - - node_add_timestamp(node, base_time - 12, true); - node_add_timestamp(node, base_time - 5, false); - TEST_ASSERT_EQUAL_UINT8(12, node_get_total_appearance_duration(node)); - - node_free(node); -} - -void test_node_get_event_table(void){ - struct sockaddr_in myaddr; - - myaddr.sin_family = AF_INET; - myaddr.sin_port = htons(2288); - myaddr.sin_addr.s_addr = htonl(INADDR_ANY); - - node_handle_t node = node_init(myaddr); - - time_t base_time = time(NULL); - - node_add_timestamp(node, base_time - 15, true); - node_add_timestamp(node, base_time - 10, false); - node_add_timestamp(node, base_time - 5, true); - node_add_timestamp(node, base_time, false); - node_add_timestamp(node, base_time + 5, false); - node_add_timestamp(node, base_time + 10, true); - - time_t** event_table; - uint8_t num_entries = node_get_event_table(node, &event_table); - TEST_ASSERT_EQUAL_UINT8(3, num_entries); - TEST_ASSERT_NOT_NULL(event_table); - - time_t** expected_table = (time_t**) malloc(2 * sizeof(time_t *)); - expected_table[0] = (time_t*) malloc(3 * sizeof(time_t)); - expected_table[1] = (time_t*) malloc(3 * sizeof(time_t)); - - expected_table[0][0] = base_time - 15; - expected_table[1][0] = base_time - 10; - expected_table[0][1] = base_time - 5; - expected_table[1][1] = base_time; - expected_table[0][2] = base_time + 10; - expected_table[1][2] = 0; - - TEST_ASSERT_EQUAL_MEMORY_ARRAY(expected_table[0], event_table[0], sizeof(time_t), 3); - TEST_ASSERT_EQUAL_MEMORY_ARRAY(expected_table[1], event_table[1], sizeof(time_t), 3); - - node_free(node); -}