From 9c8ece1538d31dba9a416c9f29f88e18510f4c75 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ram=C5=ABnas=20Ma=C5=BEeikis?= Date: Sat, 18 May 2019 16:32:20 +0300 Subject: Whole-project: partial implementation of protocol. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This commit is part of ticket #31. Branch is not in a compiling state. Work is being done on utility functions and protocol implementation. To be completed later. Signed-off-by: Ramūnas Mažeikis --- src/common/protocol.c | 169 ++++++++++++++++++++++++++++++++++++++++++ src/common/protocol_private.h | 66 +++++++++++++++++ src/common/utils.c | 22 ++++++ 3 files changed, 257 insertions(+) create mode 100644 src/common/protocol.c create mode 100644 src/common/protocol_private.h create mode 100644 src/common/utils.c (limited to 'src/common') diff --git a/src/common/protocol.c b/src/common/protocol.c new file mode 100644 index 0000000..8243c8a --- /dev/null +++ b/src/common/protocol.c @@ -0,0 +1,169 @@ +/* + * Usurpataion --- clinet-server protocol implementation. + * + * Copyright (C) 2019 Ramūnas Mažeikis + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; version 2.1 + * of the License. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA + */ + +#include "protocol.h" +#include "protocol_private.h" +#include "net.h" +#include +#include + +#define READ_INT(x) (*((int*)(x))) +#define READ_TLV_TYPE(x) (*((int*))(x)) +#define READ_SIZE_T(x) (*((size_t)(x))) +#define READ_AS(from, type) (*(type*)(from)) + +#define GET_MSG_CHAR(i) (msg_buf[(i) % MSG_BUF_SIZE]) +#define SET_MSG_CHAR(i, ch) msg_buf[(i) % MSG_BUF_SIZE] = (ch) + +/* Increment message cursor */ +#define IMC(x) ((msg_cursor + (x)) % MSG_BUF_SIZE) + +/* Begins at 2 because this way we'll have two null's at the beggining + * indicating that going back is not possible. + * */ +static const int msg_cursor = 2; +/* Two consecutive null's indicate that going back is not possible. + * */ +static char msg_buf[MSG_BUF_SIZE] = {0}; + +static int tlv_cursor = 0; +static struct tlv tlv_buf[TLV_BUF_SIZE] = {0}; + +static size_t packet_cursor = 0; +/* Outgoing packet. + * */ +static char packet_buf[PACKET_MAX_SIZE] = {0}; + +static void push_bytes(const void * const data, const size_t size) +{ + memcpy(packet_buf + packet_cursor, data, size); + packet_cursor += size; +} + +void clear_data(void) +{ + packet_cursor = 0; +} + +void push_data(char *data, enum tlv_type type) +{ + switch (type) { + case TEXT: + case FPI1: + case TIMESTAMP: + case REQUEST: + case REPLY: + case UUID: + } +} + +void push_string(char *str) +{ + size_t size = strlen(str); + + *((enum tlv_type*)packet_buf) = TEXT; + packet_cursor += sizeof(enum tlv_type); + *((size_t*)packet_buf) = strlen(str); + packet_cursor += sizeof(size_t); + push_bytes(); +} + +void push_fpi1(fpi1_t num); + +void push_timestamp(char *data); + +void push_request(char *data); + +void push_reply(char *data); + +void push_uuid(char *data); + +void get_last_data() +{ + msg_cursor = 2; + msg_buf[0] = '\0'; + msg_buf[1] = '\0'; + tlv_cursor = 0; + /* Get packet here. Somehow. TODO */ + get_tlvs(packet_buf, tlv_buf, TLV_BUF_SIZE); +} + +struct tlv * get_tlv(void) +{ + if (tlv_buf[tlv_cursor] != NULL) { + struct tlv *ret = tlv_buf[tlv_cursor++]; + } else { + ret = NULL; + } + return ret; +} + +int tlv_count(const struct packet_data * const packet) +{ + size_t cursor = 0; + size_t length = 0; + size_t ret = 0; + + while (cursor < packet->packet_size) { + cursor += sizeof(enum tlv_type); + length = READ_SIZE_T(packet->data + cursor); + cursor += sizeof(size_t) + length; + ret++; + } + if (cursor != packet->packet_size) { + errno = TLV_OVERFLOW; + } + return ret; +} + +size_t get_tlvs( const struct packet_data * const data, + const struct tlv *buf, + size_t buf_size) +{ + size_t tlvs_read = 0; + size_t cursor = 0; + + while (cursor < data->packet_size && tlvs_read <= buf_size) { + cursor += parse_tlv(data->data, cursor, buf + tlvs_read); + tlvs_read++; + } + + if (cursor > data->packet_length) { + errno = TLV_OVERFLOW; + } + + return tlvs_read; +} + +/* Returns how many bytes were consumed by parser. + * */ +size_t parse_tlv(char *data, size_t cursor, struct tlv *t) +{ + char *begin = data + cursor; + + t->type = READ_TLV_TYPE(data + cursor); + cursor += sizeof(enum tlv_type); + t->length += READ_SIZE_T(data + cursor); + data += sizeof(size_t); + t->data = data + cursor; + + return data + cursor - begin + 1UL; +} + diff --git a/src/common/protocol_private.h b/src/common/protocol_private.h new file mode 100644 index 0000000..3a4b1b2 --- /dev/null +++ b/src/common/protocol_private.h @@ -0,0 +1,66 @@ +/* + * Usurpataion --- server-client protocol private interface. + * + * Copyright (C) 2019 Ramūnas Mažeikis + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; version 2.1 + * of the License. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA + */ + +#ifdef PROTOCOL_H_PRIVATE +#define PROTOCOL_H_PRIVATE + +#define TLV_ARR_SIZE (16) + +/* Pease don't rape the buffer with long messages, daemon-kun. */ +#define MSG_BUF_SIZE (257) + +/* UDP can carry bigger packets but memory is hard to come by and more won't be + * needed anyway. + * */ +#define PACKET_MAX_SIZE (512) + +/* Returns the amount of tlv's int a packet. + * + * If a tlv reports length that goes beyond the end of a packet, errno is set + * to TLV_OVERFLOW. To check this, set errno to 0 first. + * */ +size_t tlv_count(const struct packet_data * const packet); + +/* Parses a data packet, fills buffer of tlv's of size `buf_size` and returns + * the number of tlv's actually parsed. + * + * To check for errors, set errno to 0 and check after calling. + * */ +size_t get_tlvs( const struct packet_data * const data, + const struct tlv *buf, + size_t buf_size); + +/* Takes a null-terminated string and appends it to the next outgoing packet. + * */ +void push_string(char *str); + +void push_fpi1(fpi1_t num); + +void push_timestamp(char *data); + +void push_request(char *data); + +void push_reply(char *data); + +void push_uuid(char *data); + + + +#endif /* PROTOCOL_H_PRIVATE */ diff --git a/src/common/utils.c b/src/common/utils.c new file mode 100644 index 0000000..7bcf767 --- /dev/null +++ b/src/common/utils.c @@ -0,0 +1,22 @@ +#include "utils.h" + +fpi1_t add(fpi1_t a, fpi1_t b) +{ + return a + b; +} + +fpi1_t sub(fpi1_t a, fpi1_t b) +{ + return a - b; +} + +fpi1_t mul(fpi1_t a, fpi1_t b) +{ + return (fpi1_t)(((long)a * (long)b) / 100); +} + +fpi1_t div(fpi1_t a, fpi1_t b) +{ + return (fpi1_t)(((long)a * 10) / ((long)b * 10)); +} + -- cgit v1.2.3 From b4165ee0b257aaa9064c5ac82200ff2569a02955 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ram=C5=ABnas=20Ma=C5=BEeikis?= Date: Sun, 19 May 2019 13:52:43 +0300 Subject: Protocol: more work on protocol implementation. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Additional functions implemented for protocol and basic functions to work with uuid. Source is buildable but actual build files are not edited to accomodate the changes. Signed-off-by: Ramūnas Mažeikis --- src/common/protocol.c | 73 +++++++++++++++++++++++++++++++------------ src/common/protocol_private.h | 40 ++++++++++++++++++++---- src/common/utils.c | 17 ++++++++++ 3 files changed, 104 insertions(+), 26 deletions(-) (limited to 'src/common') diff --git a/src/common/protocol.c b/src/common/protocol.c index 8243c8a..270fa81 100644 --- a/src/common/protocol.c +++ b/src/common/protocol.c @@ -23,10 +23,8 @@ #include "net.h" #include #include +#include -#define READ_INT(x) (*((int*)(x))) -#define READ_TLV_TYPE(x) (*((int*))(x)) -#define READ_SIZE_T(x) (*((size_t)(x))) #define READ_AS(from, type) (*(type*)(from)) #define GET_MSG_CHAR(i) (msg_buf[(i) % MSG_BUF_SIZE]) @@ -38,7 +36,7 @@ /* Begins at 2 because this way we'll have two null's at the beggining * indicating that going back is not possible. * */ -static const int msg_cursor = 2; +static int msg_cursor = 2; /* Two consecutive null's indicate that going back is not possible. * */ static char msg_buf[MSG_BUF_SIZE] = {0}; @@ -78,22 +76,45 @@ void push_string(char *str) { size_t size = strlen(str); - *((enum tlv_type*)packet_buf) = TEXT; - packet_cursor += sizeof(enum tlv_type); - *((size_t*)packet_buf) = strlen(str); - packet_cursor += sizeof(size_t); - push_bytes(); + push_tlv_header(TEXT, size); + push_bytes(str, size); } -void push_fpi1(fpi1_t num); +void push_fpi1(char *num) +{ + push_tlv_header(FPI1, sizeof(fpi1_t)); + push_bytes(num, sizeof(fpi1_t)); +} -void push_timestamp(char *data); +void push_timestamp(char *data) +{ + push_tlv_header(TIMESTAMP, sizeof(time_t)); + push_bytes(data, sizeof(time_t)); +} -void push_request(char *data); +void push_request(char *data) +{ + (void)data; +} -void push_reply(char *data); +void push_reply(char *data) +{ + (void)data; +} -void push_uuid(char *data); +void push_uuid(char *data) +{ + push_tlv_header(UUID, sizeof(uuid_t)); + push_bytes(data, sizeof(uuid_t)); +} + +void push_tlv_header(enum tlv_type type, size_t size) +{ + READ_AS(packet_buf, enum tlv_type) = type; + packet_cursor += sizeof(type); + READ_AS(packet_buf, size_t) = size; + packet_cursor += sizeof(size); +} void get_last_data() { @@ -107,15 +128,16 @@ void get_last_data() struct tlv * get_tlv(void) { - if (tlv_buf[tlv_cursor] != NULL) { - struct tlv *ret = tlv_buf[tlv_cursor++]; + struct tlv *ret; + if (tlv_buf + tlv_cursor != NULL) { + struct tlv *ret = &tlv_buf[tlv_cursor++]; } else { ret = NULL; } return ret; } -int tlv_count(const struct packet_data * const packet) +size_t tlv_count(const struct packet_data * const packet) { size_t cursor = 0; size_t length = 0; @@ -123,7 +145,7 @@ int tlv_count(const struct packet_data * const packet) while (cursor < packet->packet_size) { cursor += sizeof(enum tlv_type); - length = READ_SIZE_T(packet->data + cursor); + length = READ_AS(packet->data + cursor, enum tlv_type); cursor += sizeof(size_t) + length; ret++; } @@ -133,6 +155,18 @@ int tlv_count(const struct packet_data * const packet) return ret; } +/** + * Parses tlv's from packet data and writes them to a buffer of given size. + * + * Returns how many tlv's were actually parsed. + * + * Not yet implemented. + * + * @param data + * + * @return Number of tlv's actually parsed. Greter than or equal to buffer + * size, if an error occurs. + */ size_t get_tlvs( const struct packet_data * const data, const struct tlv *buf, size_t buf_size) @@ -145,7 +179,7 @@ size_t get_tlvs( const struct packet_data * const data, tlvs_read++; } - if (cursor > data->packet_length) { + if (cursor > data->packet_size) { errno = TLV_OVERFLOW; } @@ -166,4 +200,3 @@ size_t parse_tlv(char *data, size_t cursor, struct tlv *t) return data + cursor - begin + 1UL; } - diff --git a/src/common/protocol_private.h b/src/common/protocol_private.h index 3a4b1b2..653d19c 100644 --- a/src/common/protocol_private.h +++ b/src/common/protocol_private.h @@ -18,10 +18,12 @@ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA */ -#ifdef PROTOCOL_H_PRIVATE +#ifndef PROTOCOL_H_PRIVATE #define PROTOCOL_H_PRIVATE -#define TLV_ARR_SIZE (16) +#include "utils.h" + +#define TLV_BUF_SIZE (16) /* Pease don't rape the buffer with long messages, daemon-kun. */ #define MSG_BUF_SIZE (257) @@ -38,10 +40,22 @@ * */ size_t tlv_count(const struct packet_data * const packet); -/* Parses a data packet, fills buffer of tlv's of size `buf_size` and returns - * the number of tlv's actually parsed. + +/** + * Parses tlv's from packet data and writes them to a buffer of given size. + * + * Returns how many tlv's were actually parsed. * * To check for errors, set errno to 0 and check after calling. + * + * Not yet implemented. + * + * @param data Data from network packet + * @param buf Buffer to store parsed tlv's + * @param buf_size Size of buffer used to store tlv's + * + * @return Number of tlv's actually parsed. Greter than or equal to buffer + * size, if an error occurs. * */ size_t get_tlvs( const struct packet_data * const data, const struct tlv *buf, @@ -51,16 +65,30 @@ size_t get_tlvs( const struct packet_data * const data, * */ void push_string(char *str); -void push_fpi1(fpi1_t num); +/* Reinterprets char * as fpi1_t * and appends it to the outgoing packet as a + * tlv. + */ +void push_fpi1(char *num); +/* Reinterprets char * as time_t * and appends it to the outgoing packet as a + * tlv. + */ void push_timestamp(char *data); +/* Not implemented yet. */ void push_request(char *data); +/* Not implemented yet. */ void push_reply(char *data); +/* Reinterprets char * as uuid_t * and appends it to the outgoing packet as a + * tlv. + */ void push_uuid(char *data); - +/* Appends tlv_type and size of data to a packet effectively creating a tlv + * header. + */ +void push_tlv_header(enum tlv_type type, size_t size); #endif /* PROTOCOL_H_PRIVATE */ diff --git a/src/common/utils.c b/src/common/utils.c index 7bcf767..7e4caa5 100644 --- a/src/common/utils.c +++ b/src/common/utils.c @@ -1,5 +1,22 @@ #include "utils.h" +int cmp_uuid(uuid_t *first, uuid_t *second) +{ + if (first->hi == second->hi) { + if (first->low == second->low) { + return 0; + } else if (first->low < second->low) { + return -1; + } else { + return 1; + } + } else if (first->hi < second->hi) { + return -1; + } else { + return 1; + } +} + fpi1_t add(fpi1_t a, fpi1_t b) { return a + b; -- cgit v1.2.3 From 031caaf9b7745bfc552cc86fb475de1f18d0fd6d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ram=C5=ABnas=20Ma=C5=BEeikis?= Date: Sun, 19 May 2019 17:50:53 +0300 Subject: Protocol: Implemented protocol error reporting. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Now public functions of the protocol can return an error code. More work is done on actual logic. Protocol code has bare-bones doxygen documentation. Signed-off-by: Ramūnas Mažeikis --- src/common/protocol.c | 73 +++++++++++++++++++++++++------------------ src/common/protocol_private.h | 44 ++++++++++++++++---------- src/common/utils.c | 16 ++-------- 3 files changed, 71 insertions(+), 62 deletions(-) (limited to 'src/common') diff --git a/src/common/protocol.c b/src/common/protocol.c index 270fa81..2ac8280 100644 --- a/src/common/protocol.c +++ b/src/common/protocol.c @@ -49,10 +49,14 @@ static size_t packet_cursor = 0; * */ static char packet_buf[PACKET_MAX_SIZE] = {0}; -static void push_bytes(const void * const data, const size_t size) +static int push_bytes(const void * const data, const size_t size) { + if (packet_cursor + size >= PACKET_MAX_SIZE) { + return E_PACKET_OVERFLOW; + } memcpy(packet_buf + packet_cursor, data, size); packet_cursor += size; + return 0; } void clear_data(void) @@ -60,60 +64,81 @@ void clear_data(void) packet_cursor = 0; } -void push_data(char *data, enum tlv_type type) +int push_data(const char *data, enum tlv_type type) { + int ret = E_UNKNOWN_TYPE; switch (type) { case TEXT: + ret = push_string(data); + break; case FPI1: + ret = push_fpi1(data); + break; case TIMESTAMP: + ret = push_timestamp(data); + break; case REQUEST: + ret = push_request(data); + break; case REPLY: + ret = push_reply(data); + break; case UUID: + ret = push_uuid(data); + break; } + return ret; } -void push_string(char *str) +static int push_string(char *str) { size_t size = strlen(str); push_tlv_header(TEXT, size); push_bytes(str, size); + return 0; } -void push_fpi1(char *num) +static int push_fpi1(char *num) { - push_tlv_header(FPI1, sizeof(fpi1_t)); - push_bytes(num, sizeof(fpi1_t)); + return push_tlv_header(FPI1, sizeof(fpi1_t)) + | push_bytes(num, sizeof(fpi1_t)); } -void push_timestamp(char *data) +static int push_timestamp(char *data) { - push_tlv_header(TIMESTAMP, sizeof(time_t)); - push_bytes(data, sizeof(time_t)); + return push_tlv_header(TIMESTAMP, sizeof(time_t)) + | push_bytes(data, sizeof(time_t)); } -void push_request(char *data) +static int push_request(char *data) { (void)data; + return 0; } -void push_reply(char *data) +static int push_reply(char *data) { (void)data; + return 0; } -void push_uuid(char *data) +static int push_uuid(char *data) { - push_tlv_header(UUID, sizeof(uuid_t)); - push_bytes(data, sizeof(uuid_t)); + return push_tlv_header(UUID, sizeof(uuid_t)) + | push_bytes(data, sizeof(uuid_t)); } -void push_tlv_header(enum tlv_type type, size_t size) +int push_tlv_header(enum tlv_type type, size_t size) { + if (size + sizeof(type) + packet_cursor >= PACKET_MAX_SIZE) { + return E_PACKET_OVERFLOW; + } READ_AS(packet_buf, enum tlv_type) = type; packet_cursor += sizeof(type); READ_AS(packet_buf, size_t) = size; packet_cursor += sizeof(size); + return 0; } void get_last_data() @@ -150,23 +175,11 @@ size_t tlv_count(const struct packet_data * const packet) ret++; } if (cursor != packet->packet_size) { - errno = TLV_OVERFLOW; + errno = E_TLV_OVERFLOW; } return ret; } -/** - * Parses tlv's from packet data and writes them to a buffer of given size. - * - * Returns how many tlv's were actually parsed. - * - * Not yet implemented. - * - * @param data - * - * @return Number of tlv's actually parsed. Greter than or equal to buffer - * size, if an error occurs. - */ size_t get_tlvs( const struct packet_data * const data, const struct tlv *buf, size_t buf_size) @@ -180,14 +193,12 @@ size_t get_tlvs( const struct packet_data * const data, } if (cursor > data->packet_size) { - errno = TLV_OVERFLOW; + errno = E_TLV_OVERFLOW; } return tlvs_read; } -/* Returns how many bytes were consumed by parser. - * */ size_t parse_tlv(char *data, size_t cursor, struct tlv *t) { char *begin = data + cursor; diff --git a/src/common/protocol_private.h b/src/common/protocol_private.h index 653d19c..0c0b7f9 100644 --- a/src/common/protocol_private.h +++ b/src/common/protocol_private.h @@ -23,37 +23,44 @@ #include "utils.h" +#define E_PACKET_OVERFLOW (1 << 0) + +/** Read as "A maximum of 16 tlv's per packet". */ #define TLV_BUF_SIZE (16) /* Pease don't rape the buffer with long messages, daemon-kun. */ #define MSG_BUF_SIZE (257) -/* UDP can carry bigger packets but memory is hard to come by and more won't be - * needed anyway. +/* Maximum size of packet that can fit into the packet buffer. UDP can carry + * bigger packets but memory is hard to come by and more won't be needed + * anyway. * */ #define PACKET_MAX_SIZE (512) -/* Returns the amount of tlv's int a packet. +/** Returns the amount of tlv's int a packet. * * If a tlv reports length that goes beyond the end of a packet, errno is set * to TLV_OVERFLOW. To check this, set errno to 0 first. + * + * @param packet data parsed from a packet. Function cannot use raw packets. + * + * @return Amount of tlv's in a packet. * */ -size_t tlv_count(const struct packet_data * const packet); - +size_t tlv_count(const struct packet_data * const packet_data); /** * Parses tlv's from packet data and writes them to a buffer of given size. - * + * * Returns how many tlv's were actually parsed. * * To check for errors, set errno to 0 and check after calling. - * + * * Not yet implemented. - * + * * @param data Data from network packet * @param buf Buffer to store parsed tlv's * @param buf_size Size of buffer used to store tlv's - * + * * @return Number of tlv's actually parsed. Greter than or equal to buffer * size, if an error occurs. * */ @@ -61,34 +68,37 @@ size_t get_tlvs( const struct packet_data * const data, const struct tlv *buf, size_t buf_size); -/* Takes a null-terminated string and appends it to the next outgoing packet. +/** Takes a null-terminated string and appends it to the next outgoing packet. + * + * @return Returns 0 on success. Otherwise: E_PACKET_OVERFLOW. + * * */ -void push_string(char *str); +int push_string(char *str); /* Reinterprets char * as fpi1_t * and appends it to the outgoing packet as a * tlv. */ -void push_fpi1(char *num); +int push_fpi1(char *num); /* Reinterprets char * as time_t * and appends it to the outgoing packet as a * tlv. */ -void push_timestamp(char *data); +int push_timestamp(char *data); /* Not implemented yet. */ -void push_request(char *data); +int push_request(char *data); /* Not implemented yet. */ -void push_reply(char *data); +int push_reply(char *data); /* Reinterprets char * as uuid_t * and appends it to the outgoing packet as a * tlv. */ -void push_uuid(char *data); +int push_uuid(char *data); /* Appends tlv_type and size of data to a packet effectively creating a tlv * header. */ -void push_tlv_header(enum tlv_type type, size_t size); +int push_tlv_header(enum tlv_type type, size_t size); #endif /* PROTOCOL_H_PRIVATE */ diff --git a/src/common/utils.c b/src/common/utils.c index 7e4caa5..956ef1b 100644 --- a/src/common/utils.c +++ b/src/common/utils.c @@ -1,20 +1,9 @@ #include "utils.h" +#include "string.h" int cmp_uuid(uuid_t *first, uuid_t *second) { - if (first->hi == second->hi) { - if (first->low == second->low) { - return 0; - } else if (first->low < second->low) { - return -1; - } else { - return 1; - } - } else if (first->hi < second->hi) { - return -1; - } else { - return 1; - } + return memcmp(first, second, sizeof(*first)); } fpi1_t add(fpi1_t a, fpi1_t b) @@ -36,4 +25,3 @@ fpi1_t div(fpi1_t a, fpi1_t b) { return (fpi1_t)(((long)a * 10) / ((long)b * 10)); } - -- cgit v1.2.3 From bb70fccb66f55e9cc2b9ed0bf366479828f41346 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ram=C5=ABnas=20Ma=C5=BEeikis?= Date: Mon, 20 May 2019 21:50:19 +0300 Subject: Protocol: implemented request and reply pushing to packet. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit First implementation of complete protocol interface. While the first implementation does compile, the interface might change due to demands from other parts of the project. For now reqest is a tlv that is an unsigned int which represents what message to repeat from daemon. A reply is also a tlv made of two parts --- message sequence number of type msg_ixd_t and the actual null terminated string. All of the above is subject to change. More docs. Doxygen is on the way. Signed-off-by: Ramūnas Mažeikis --- src/common/protocol.c | 14 ++++++++------ src/common/protocol_private.h | 26 +++++++++++++++++++++----- 2 files changed, 29 insertions(+), 11 deletions(-) (limited to 'src/common') diff --git a/src/common/protocol.c b/src/common/protocol.c index 2ac8280..2243dad 100644 --- a/src/common/protocol.c +++ b/src/common/protocol.c @@ -113,14 +113,17 @@ static int push_timestamp(char *data) static int push_request(char *data) { - (void)data; - return 0; + return push_tlv_header(REQUEST, sizeof(msg_idx_t)) + | push_bytes(data, sizeof(msg_idx_t)); } static int push_reply(char *data) { - (void)data; - return 0; + int ret = 0; + size_t msglen = strlen(data + sizeof(msg_idx_t)); + ret |= push_tlv_header(REPLY, msglen + sizeof(msg_idx_t)); + ret |= push_bytes(data, msglen); + return ret; } static int push_uuid(char *data) @@ -129,7 +132,7 @@ static int push_uuid(char *data) | push_bytes(data, sizeof(uuid_t)); } -int push_tlv_header(enum tlv_type type, size_t size) +static int push_tlv_header(enum tlv_type type, size_t size) { if (size + sizeof(type) + packet_cursor >= PACKET_MAX_SIZE) { return E_PACKET_OVERFLOW; @@ -147,7 +150,6 @@ void get_last_data() msg_buf[0] = '\0'; msg_buf[1] = '\0'; tlv_cursor = 0; - /* Get packet here. Somehow. TODO */ get_tlvs(packet_buf, tlv_buf, TLV_BUF_SIZE); } diff --git a/src/common/protocol_private.h b/src/common/protocol_private.h index 0c0b7f9..b74c0eb 100644 --- a/src/common/protocol_private.h +++ b/src/common/protocol_private.h @@ -75,23 +75,39 @@ size_t get_tlvs( const struct packet_data * const data, * */ int push_string(char *str); -/* Reinterprets char * as fpi1_t * and appends it to the outgoing packet as a +/** Reinterprets char * as fpi1_t * and appends it to the outgoing packet as a * tlv. */ int push_fpi1(char *num); -/* Reinterprets char * as time_t * and appends it to the outgoing packet as a +/** Reinterprets char * as time_t * and appends it to the outgoing packet as a * tlv. */ int push_timestamp(char *data); -/* Not implemented yet. */ +/** + * Pushes a request for daemon to repeat a message identified by a msg_index_t. + * + * @param data Pointer to a msg_index_t. + * + * @return 0 on success or E_PACKET_OVERFLOW, if not enough space is available + * to push all the data. + */ int push_request(char *data); -/* Not implemented yet. */ +/** + * Pushes a message to the outgoing packet buffer as a reply. A reply is just + * a null terminated string. + * + * @param data msg_idx_t representing sequence number since beggining of + * connection and a null-terminated string. + * + * @return On success --- 0 or E_PACKET_OVERFLOW, if not enough buffer is + * available. + */ int push_reply(char *data); -/* Reinterprets char * as uuid_t * and appends it to the outgoing packet as a +/** Reinterprets char * as uuid_t * and appends it to the outgoing packet as a * tlv. */ int push_uuid(char *data); -- cgit v1.2.3 From cabb90c1240015ee5cd17d91573588527bcc2482 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ram=C5=ABnas=20Ma=C5=BEeikis?= Date: Tue, 21 May 2019 17:41:21 +0300 Subject: Protocol: changes to interface and some re-implementation. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Most functions exposed in protocol.h take a connection descriptor (cd_t) as first argument. This allows for multiple connections. Device gets only one connection which means that cd_t is effectively 0 all the time. Additionaly, any function that actually does anything with a connection descriptor instead of just passing it to another function must be implemented separately in device and daemon. Signed-off-by: Ramūnas Mažeikis --- src/common/protocol.c | 109 +++++++++++++++++------------------------- src/common/protocol_private.h | 17 +++---- src/common/utils.c | 8 ++-- 3 files changed, 57 insertions(+), 77 deletions(-) (limited to 'src/common') diff --git a/src/common/protocol.c b/src/common/protocol.c index 2243dad..3d63771 100644 --- a/src/common/protocol.c +++ b/src/common/protocol.c @@ -18,6 +18,12 @@ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA */ +/** + * Common parts of protocol implementation. Handling of anything that actually + * deals with connection descriptor has to be implemented by device and daemon + * separately. + */ + #include "protocol.h" #include "protocol_private.h" #include "net.h" @@ -37,7 +43,11 @@ * indicating that going back is not possible. * */ static int msg_cursor = 2; -/* Two consecutive null's indicate that going back is not possible. + +/** + * Message buffer. + * + * Two consecutive null's indicate that going back is not possible. * */ static char msg_buf[MSG_BUF_SIZE] = {0}; @@ -49,7 +59,7 @@ static size_t packet_cursor = 0; * */ static char packet_buf[PACKET_MAX_SIZE] = {0}; -static int push_bytes(const void * const data, const size_t size) +static int push_bytes(cd_t connection, const void * const data, const size_t size) { if (packet_cursor + size >= PACKET_MAX_SIZE) { return E_PACKET_OVERFLOW; @@ -59,109 +69,78 @@ static int push_bytes(const void * const data, const size_t size) return 0; } -void clear_data(void) +void clear_data(cd_t connection) { packet_cursor = 0; } -int push_data(const char *data, enum tlv_type type) +int push_data(cd_t connection, const char *data, enum tlv_type type) { int ret = E_UNKNOWN_TYPE; switch (type) { case TEXT: - ret = push_string(data); + ret = push_string(connection, data); break; case FPI1: - ret = push_fpi1(data); + ret = push_fpi1(connection, data); break; case TIMESTAMP: - ret = push_timestamp(data); + ret = push_timestamp(connection, data); break; case REQUEST: - ret = push_request(data); + ret = push_request(connection, data); break; case REPLY: - ret = push_reply(data); + ret = push_reply(connection, data); break; case UUID: - ret = push_uuid(data); + ret = push_uuid(connection, data); break; } return ret; } -static int push_string(char *str) +static int push_string(cd_t connection, char *str) { + int ret = 0; size_t size = strlen(str); - push_tlv_header(TEXT, size); - push_bytes(str, size); - return 0; -} - -static int push_fpi1(char *num) -{ - return push_tlv_header(FPI1, sizeof(fpi1_t)) - | push_bytes(num, sizeof(fpi1_t)); -} - -static int push_timestamp(char *data) -{ - return push_tlv_header(TIMESTAMP, sizeof(time_t)) - | push_bytes(data, sizeof(time_t)); -} - -static int push_request(char *data) -{ - return push_tlv_header(REQUEST, sizeof(msg_idx_t)) - | push_bytes(data, sizeof(msg_idx_t)); + ret |= push_tlv_header(connection, TEXT, size); + ret |= push_bytes(connection, str, size); + return ret; } -static int push_reply(char *data) +static int push_fpi1(cd_t connection, char *num) { - int ret = 0; - size_t msglen = strlen(data + sizeof(msg_idx_t)); - ret |= push_tlv_header(REPLY, msglen + sizeof(msg_idx_t)); - ret |= push_bytes(data, msglen); - return ret; + return push_tlv_header(connection, FPI1, sizeof(fpi1_t)) + | push_bytes(connection, num, sizeof(fpi1_t)); } -static int push_uuid(char *data) +static int push_timestamp(cd_t connection, char *data) { - return push_tlv_header(UUID, sizeof(uuid_t)) - | push_bytes(data, sizeof(uuid_t)); + return push_tlv_header(connection, TIMESTAMP, sizeof(time_t)) + | push_bytes(connection, data, sizeof(time_t)); } -static int push_tlv_header(enum tlv_type type, size_t size) +static int push_request(cd_t connection, char *data) { - if (size + sizeof(type) + packet_cursor >= PACKET_MAX_SIZE) { - return E_PACKET_OVERFLOW; - } - READ_AS(packet_buf, enum tlv_type) = type; - packet_cursor += sizeof(type); - READ_AS(packet_buf, size_t) = size; - packet_cursor += sizeof(size); - return 0; + return push_tlv_header(connection, REQUEST, sizeof(msg_idx_t)) + | push_bytes(connection, data, sizeof(msg_idx_t)); } -void get_last_data() +static int push_reply(cd_t connection, char *data) { - msg_cursor = 2; - msg_buf[0] = '\0'; - msg_buf[1] = '\0'; - tlv_cursor = 0; - get_tlvs(packet_buf, tlv_buf, TLV_BUF_SIZE); + int ret = 0; + size_t msglen = strlen(data + sizeof(msg_idx_t)); + ret |= push_tlv_header(connection, REPLY, msglen + sizeof(msg_idx_t)); + ret |= push_bytes(connection, data, msglen); + return ret; } -struct tlv * get_tlv(void) +static int push_uuid(cd_t connection, char *data) { - struct tlv *ret; - if (tlv_buf + tlv_cursor != NULL) { - struct tlv *ret = &tlv_buf[tlv_cursor++]; - } else { - ret = NULL; - } - return ret; + return push_tlv_header(connection, UUID, sizeof(uuid_t)) + | push_bytes(connection, data, sizeof(uuid_t)); } size_t tlv_count(const struct packet_data * const packet) @@ -182,7 +161,7 @@ size_t tlv_count(const struct packet_data * const packet) return ret; } -size_t get_tlvs( const struct packet_data * const data, +size_t get_tlvs( const struct packet_data * const data, const struct tlv *buf, size_t buf_size) { diff --git a/src/common/protocol_private.h b/src/common/protocol_private.h index b74c0eb..eecbc15 100644 --- a/src/common/protocol_private.h +++ b/src/common/protocol_private.h @@ -37,7 +37,8 @@ * */ #define PACKET_MAX_SIZE (512) -/** Returns the amount of tlv's int a packet. +/** + * Returns the amount of tlv's int a packet. * * If a tlv reports length that goes beyond the end of a packet, errno is set * to TLV_OVERFLOW. To check this, set errno to 0 first. @@ -73,17 +74,17 @@ size_t get_tlvs( const struct packet_data * const data, * @return Returns 0 on success. Otherwise: E_PACKET_OVERFLOW. * * */ -int push_string(char *str); +int push_string(cd_t connection, char *str); /** Reinterprets char * as fpi1_t * and appends it to the outgoing packet as a * tlv. */ -int push_fpi1(char *num); +int push_fpi1(cd_t connection, char *num); /** Reinterprets char * as time_t * and appends it to the outgoing packet as a * tlv. */ -int push_timestamp(char *data); +int push_timestamp(cd_t connection, char *data); /** * Pushes a request for daemon to repeat a message identified by a msg_index_t. @@ -93,7 +94,7 @@ int push_timestamp(char *data); * @return 0 on success or E_PACKET_OVERFLOW, if not enough space is available * to push all the data. */ -int push_request(char *data); +int push_request(cd_t connection, char *data); /** * Pushes a message to the outgoing packet buffer as a reply. A reply is just @@ -105,16 +106,16 @@ int push_request(char *data); * @return On success --- 0 or E_PACKET_OVERFLOW, if not enough buffer is * available. */ -int push_reply(char *data); +int push_reply(cd_t connection, char *data); /** Reinterprets char * as uuid_t * and appends it to the outgoing packet as a * tlv. */ -int push_uuid(char *data); +int push_uuid(cd_t connection, char *data); /* Appends tlv_type and size of data to a packet effectively creating a tlv * header. */ -int push_tlv_header(enum tlv_type type, size_t size); +int push_tlv_header(cd_t connection, enum tlv_type type, size_t size); #endif /* PROTOCOL_H_PRIVATE */ diff --git a/src/common/utils.c b/src/common/utils.c index 956ef1b..0619517 100644 --- a/src/common/utils.c +++ b/src/common/utils.c @@ -6,22 +6,22 @@ int cmp_uuid(uuid_t *first, uuid_t *second) return memcmp(first, second, sizeof(*first)); } -fpi1_t add(fpi1_t a, fpi1_t b) +fpi1_t fpi1_add(fpi1_t a, fpi1_t b) { return a + b; } -fpi1_t sub(fpi1_t a, fpi1_t b) +fpi1_t fpi1_sub(fpi1_t a, fpi1_t b) { return a - b; } -fpi1_t mul(fpi1_t a, fpi1_t b) +fpi1_t fpi1_mul(fpi1_t a, fpi1_t b) { return (fpi1_t)(((long)a * (long)b) / 100); } -fpi1_t div(fpi1_t a, fpi1_t b) +fpi1_t fpi1_div(fpi1_t a, fpi1_t b) { return (fpi1_t)(((long)a * 10) / ((long)b * 10)); } -- cgit v1.2.3 From 5ca7e24e58f6bd657787b9235247149ffff420ae Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ram=C5=ABnas=20Ma=C5=BEeikis?= Date: Tue, 21 May 2019 19:28:23 +0300 Subject: Protocol: common no longer has device-specific implementations. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Forgot to remove device-specific code from common protocol code. Signed-off-by: Ramūnas Mažeikis --- src/common/protocol.c | 41 ----------------------------------------- src/common/protocol_private.h | 14 -------------- 2 files changed, 55 deletions(-) (limited to 'src/common') diff --git a/src/common/protocol.c b/src/common/protocol.c index 3d63771..dc0f532 100644 --- a/src/common/protocol.c +++ b/src/common/protocol.c @@ -33,47 +33,6 @@ #define READ_AS(from, type) (*(type*)(from)) -#define GET_MSG_CHAR(i) (msg_buf[(i) % MSG_BUF_SIZE]) -#define SET_MSG_CHAR(i, ch) msg_buf[(i) % MSG_BUF_SIZE] = (ch) - -/* Increment message cursor */ -#define IMC(x) ((msg_cursor + (x)) % MSG_BUF_SIZE) - -/* Begins at 2 because this way we'll have two null's at the beggining - * indicating that going back is not possible. - * */ -static int msg_cursor = 2; - -/** - * Message buffer. - * - * Two consecutive null's indicate that going back is not possible. - * */ -static char msg_buf[MSG_BUF_SIZE] = {0}; - -static int tlv_cursor = 0; -static struct tlv tlv_buf[TLV_BUF_SIZE] = {0}; - -static size_t packet_cursor = 0; -/* Outgoing packet. - * */ -static char packet_buf[PACKET_MAX_SIZE] = {0}; - -static int push_bytes(cd_t connection, const void * const data, const size_t size) -{ - if (packet_cursor + size >= PACKET_MAX_SIZE) { - return E_PACKET_OVERFLOW; - } - memcpy(packet_buf + packet_cursor, data, size); - packet_cursor += size; - return 0; -} - -void clear_data(cd_t connection) -{ - packet_cursor = 0; -} - int push_data(cd_t connection, const char *data, enum tlv_type type) { int ret = E_UNKNOWN_TYPE; diff --git a/src/common/protocol_private.h b/src/common/protocol_private.h index eecbc15..7433ff0 100644 --- a/src/common/protocol_private.h +++ b/src/common/protocol_private.h @@ -23,20 +23,6 @@ #include "utils.h" -#define E_PACKET_OVERFLOW (1 << 0) - -/** Read as "A maximum of 16 tlv's per packet". */ -#define TLV_BUF_SIZE (16) - -/* Pease don't rape the buffer with long messages, daemon-kun. */ -#define MSG_BUF_SIZE (257) - -/* Maximum size of packet that can fit into the packet buffer. UDP can carry - * bigger packets but memory is hard to come by and more won't be needed - * anyway. - * */ -#define PACKET_MAX_SIZE (512) - /** * Returns the amount of tlv's int a packet. * -- cgit v1.2.3 From 13015f9a8d2b6b982d7d84e62943fbba15aee05a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ram=C5=ABnas=20Ma=C5=BEeikis?= Date: Wed, 22 May 2019 10:49:08 +0300 Subject: Protocol: switched files to C++ and did minor fixes. The code has a chance to compile now. No changes to actual build files yet. --- src/common/protocol.c | 153 ------------------------------------------------ src/common/protocol.cpp | 153 ++++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 153 insertions(+), 153 deletions(-) delete mode 100644 src/common/protocol.c create mode 100644 src/common/protocol.cpp (limited to 'src/common') diff --git a/src/common/protocol.c b/src/common/protocol.c deleted file mode 100644 index dc0f532..0000000 --- a/src/common/protocol.c +++ /dev/null @@ -1,153 +0,0 @@ -/* - * Usurpataion --- clinet-server protocol implementation. - * - * Copyright (C) 2019 Ramūnas Mažeikis - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation; version 2.1 - * of the License. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public - * License along with this program; if not, write to the Free Software - * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA - */ - -/** - * Common parts of protocol implementation. Handling of anything that actually - * deals with connection descriptor has to be implemented by device and daemon - * separately. - */ - -#include "protocol.h" -#include "protocol_private.h" -#include "net.h" -#include -#include -#include - -#define READ_AS(from, type) (*(type*)(from)) - -int push_data(cd_t connection, const char *data, enum tlv_type type) -{ - int ret = E_UNKNOWN_TYPE; - switch (type) { - case TEXT: - ret = push_string(connection, data); - break; - case FPI1: - ret = push_fpi1(connection, data); - break; - case TIMESTAMP: - ret = push_timestamp(connection, data); - break; - case REQUEST: - ret = push_request(connection, data); - break; - case REPLY: - ret = push_reply(connection, data); - break; - case UUID: - ret = push_uuid(connection, data); - break; - } - return ret; -} - -static int push_string(cd_t connection, char *str) -{ - int ret = 0; - size_t size = strlen(str); - - ret |= push_tlv_header(connection, TEXT, size); - ret |= push_bytes(connection, str, size); - return ret; -} - -static int push_fpi1(cd_t connection, char *num) -{ - return push_tlv_header(connection, FPI1, sizeof(fpi1_t)) - | push_bytes(connection, num, sizeof(fpi1_t)); -} - -static int push_timestamp(cd_t connection, char *data) -{ - return push_tlv_header(connection, TIMESTAMP, sizeof(time_t)) - | push_bytes(connection, data, sizeof(time_t)); -} - -static int push_request(cd_t connection, char *data) -{ - return push_tlv_header(connection, REQUEST, sizeof(msg_idx_t)) - | push_bytes(connection, data, sizeof(msg_idx_t)); -} - -static int push_reply(cd_t connection, char *data) -{ - int ret = 0; - size_t msglen = strlen(data + sizeof(msg_idx_t)); - ret |= push_tlv_header(connection, REPLY, msglen + sizeof(msg_idx_t)); - ret |= push_bytes(connection, data, msglen); - return ret; -} - -static int push_uuid(cd_t connection, char *data) -{ - return push_tlv_header(connection, UUID, sizeof(uuid_t)) - | push_bytes(connection, data, sizeof(uuid_t)); -} - -size_t tlv_count(const struct packet_data * const packet) -{ - size_t cursor = 0; - size_t length = 0; - size_t ret = 0; - - while (cursor < packet->packet_size) { - cursor += sizeof(enum tlv_type); - length = READ_AS(packet->data + cursor, enum tlv_type); - cursor += sizeof(size_t) + length; - ret++; - } - if (cursor != packet->packet_size) { - errno = E_TLV_OVERFLOW; - } - return ret; -} - -size_t get_tlvs( const struct packet_data * const data, - const struct tlv *buf, - size_t buf_size) -{ - size_t tlvs_read = 0; - size_t cursor = 0; - - while (cursor < data->packet_size && tlvs_read <= buf_size) { - cursor += parse_tlv(data->data, cursor, buf + tlvs_read); - tlvs_read++; - } - - if (cursor > data->packet_size) { - errno = E_TLV_OVERFLOW; - } - - return tlvs_read; -} - -size_t parse_tlv(char *data, size_t cursor, struct tlv *t) -{ - char *begin = data + cursor; - - t->type = READ_TLV_TYPE(data + cursor); - cursor += sizeof(enum tlv_type); - t->length += READ_SIZE_T(data + cursor); - data += sizeof(size_t); - t->data = data + cursor; - - return data + cursor - begin + 1UL; -} diff --git a/src/common/protocol.cpp b/src/common/protocol.cpp new file mode 100644 index 0000000..dc0f532 --- /dev/null +++ b/src/common/protocol.cpp @@ -0,0 +1,153 @@ +/* + * Usurpataion --- clinet-server protocol implementation. + * + * Copyright (C) 2019 Ramūnas Mažeikis + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; version 2.1 + * of the License. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA + */ + +/** + * Common parts of protocol implementation. Handling of anything that actually + * deals with connection descriptor has to be implemented by device and daemon + * separately. + */ + +#include "protocol.h" +#include "protocol_private.h" +#include "net.h" +#include +#include +#include + +#define READ_AS(from, type) (*(type*)(from)) + +int push_data(cd_t connection, const char *data, enum tlv_type type) +{ + int ret = E_UNKNOWN_TYPE; + switch (type) { + case TEXT: + ret = push_string(connection, data); + break; + case FPI1: + ret = push_fpi1(connection, data); + break; + case TIMESTAMP: + ret = push_timestamp(connection, data); + break; + case REQUEST: + ret = push_request(connection, data); + break; + case REPLY: + ret = push_reply(connection, data); + break; + case UUID: + ret = push_uuid(connection, data); + break; + } + return ret; +} + +static int push_string(cd_t connection, char *str) +{ + int ret = 0; + size_t size = strlen(str); + + ret |= push_tlv_header(connection, TEXT, size); + ret |= push_bytes(connection, str, size); + return ret; +} + +static int push_fpi1(cd_t connection, char *num) +{ + return push_tlv_header(connection, FPI1, sizeof(fpi1_t)) + | push_bytes(connection, num, sizeof(fpi1_t)); +} + +static int push_timestamp(cd_t connection, char *data) +{ + return push_tlv_header(connection, TIMESTAMP, sizeof(time_t)) + | push_bytes(connection, data, sizeof(time_t)); +} + +static int push_request(cd_t connection, char *data) +{ + return push_tlv_header(connection, REQUEST, sizeof(msg_idx_t)) + | push_bytes(connection, data, sizeof(msg_idx_t)); +} + +static int push_reply(cd_t connection, char *data) +{ + int ret = 0; + size_t msglen = strlen(data + sizeof(msg_idx_t)); + ret |= push_tlv_header(connection, REPLY, msglen + sizeof(msg_idx_t)); + ret |= push_bytes(connection, data, msglen); + return ret; +} + +static int push_uuid(cd_t connection, char *data) +{ + return push_tlv_header(connection, UUID, sizeof(uuid_t)) + | push_bytes(connection, data, sizeof(uuid_t)); +} + +size_t tlv_count(const struct packet_data * const packet) +{ + size_t cursor = 0; + size_t length = 0; + size_t ret = 0; + + while (cursor < packet->packet_size) { + cursor += sizeof(enum tlv_type); + length = READ_AS(packet->data + cursor, enum tlv_type); + cursor += sizeof(size_t) + length; + ret++; + } + if (cursor != packet->packet_size) { + errno = E_TLV_OVERFLOW; + } + return ret; +} + +size_t get_tlvs( const struct packet_data * const data, + const struct tlv *buf, + size_t buf_size) +{ + size_t tlvs_read = 0; + size_t cursor = 0; + + while (cursor < data->packet_size && tlvs_read <= buf_size) { + cursor += parse_tlv(data->data, cursor, buf + tlvs_read); + tlvs_read++; + } + + if (cursor > data->packet_size) { + errno = E_TLV_OVERFLOW; + } + + return tlvs_read; +} + +size_t parse_tlv(char *data, size_t cursor, struct tlv *t) +{ + char *begin = data + cursor; + + t->type = READ_TLV_TYPE(data + cursor); + cursor += sizeof(enum tlv_type); + t->length += READ_SIZE_T(data + cursor); + data += sizeof(size_t); + t->data = data + cursor; + + return data + cursor - begin + 1UL; +} -- cgit v1.2.3 From 3fa7dd642af57b8b138e9a0d674c2d9960ebedf4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ram=C5=ABnas=20Ma=C5=BEeikis?= Date: Wed, 22 May 2019 11:33:51 +0300 Subject: Protocol: fixed type errors. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Added const where appropriate to satisfy stricter type checking of C++. Signed-off-by: Ramūnas Mažeikis --- src/common/protocol.cpp | 28 ++++++++++++++-------------- src/common/protocol_private.h | 8 ++++++++ 2 files changed, 22 insertions(+), 14 deletions(-) (limited to 'src/common') diff --git a/src/common/protocol.cpp b/src/common/protocol.cpp index dc0f532..135be37 100644 --- a/src/common/protocol.cpp +++ b/src/common/protocol.cpp @@ -31,7 +31,7 @@ #include #include -#define READ_AS(from, type) (*(type*)(from)) +#define READ_AS(type, from) (*((type*)(from))) int push_data(cd_t connection, const char *data, enum tlv_type type) { @@ -59,7 +59,7 @@ int push_data(cd_t connection, const char *data, enum tlv_type type) return ret; } -static int push_string(cd_t connection, char *str) +static int push_string(cd_t connection, const char *str) { int ret = 0; size_t size = strlen(str); @@ -69,25 +69,25 @@ static int push_string(cd_t connection, char *str) return ret; } -static int push_fpi1(cd_t connection, char *num) +static int push_fpi1(cd_t connection, const char *num) { return push_tlv_header(connection, FPI1, sizeof(fpi1_t)) | push_bytes(connection, num, sizeof(fpi1_t)); } -static int push_timestamp(cd_t connection, char *data) +static int push_timestamp(cd_t connection, const char *data) { return push_tlv_header(connection, TIMESTAMP, sizeof(time_t)) | push_bytes(connection, data, sizeof(time_t)); } -static int push_request(cd_t connection, char *data) +static int push_request(cd_t connection, const char *data) { return push_tlv_header(connection, REQUEST, sizeof(msg_idx_t)) | push_bytes(connection, data, sizeof(msg_idx_t)); } -static int push_reply(cd_t connection, char *data) +static int push_reply(cd_t connection, const char *data) { int ret = 0; size_t msglen = strlen(data + sizeof(msg_idx_t)); @@ -96,7 +96,7 @@ static int push_reply(cd_t connection, char *data) return ret; } -static int push_uuid(cd_t connection, char *data) +static int push_uuid(cd_t connection, const char *data) { return push_tlv_header(connection, UUID, sizeof(uuid_t)) | push_bytes(connection, data, sizeof(uuid_t)); @@ -110,7 +110,7 @@ size_t tlv_count(const struct packet_data * const packet) while (cursor < packet->packet_size) { cursor += sizeof(enum tlv_type); - length = READ_AS(packet->data + cursor, enum tlv_type); + length = READ_AS(enum tlv_type, packet->data + cursor); cursor += sizeof(size_t) + length; ret++; } @@ -121,7 +121,7 @@ size_t tlv_count(const struct packet_data * const packet) } size_t get_tlvs( const struct packet_data * const data, - const struct tlv *buf, + struct tlv *buf, size_t buf_size) { size_t tlvs_read = 0; @@ -139,15 +139,15 @@ size_t get_tlvs( const struct packet_data * const data, return tlvs_read; } -size_t parse_tlv(char *data, size_t cursor, struct tlv *t) +size_t parse_tlv(const char *data, size_t cursor, struct tlv *t) { - char *begin = data + cursor; + const char *begin = data + cursor; - t->type = READ_TLV_TYPE(data + cursor); + t->type = READ_AS(enum tlv_type, data + cursor); cursor += sizeof(enum tlv_type); - t->length += READ_SIZE_T(data + cursor); + t->length += READ_AS(enum tlv_type ,data + cursor); data += sizeof(size_t); - t->data = data + cursor; + t->data = (void*)data + cursor; return data + cursor - begin + 1UL; } diff --git a/src/common/protocol_private.h b/src/common/protocol_private.h index 7433ff0..d50a314 100644 --- a/src/common/protocol_private.h +++ b/src/common/protocol_private.h @@ -35,6 +35,14 @@ * */ size_t tlv_count(const struct packet_data * const packet_data); +/** + * Pushes bytes to outgoing packet and adjusts the offset accordingly. + * + * Returns E_PACKET_OVERFLOW, if no more bytes can fit into the packet. + */ + +int push_bytes(cd_t cd, const char *data, size_t size); + /** * Parses tlv's from packet data and writes them to a buffer of given size. * -- cgit v1.2.3 From 3703a6f28d48ac3f2c28d07405fab17a2a402df4 Mon Sep 17 00:00:00 2001 From: Gediminas Jakutis Date: Wed, 22 May 2019 14:44:00 +0300 Subject: device: actually make it all build and such. Signed-off-by: Gediminas Jakutis --- src/common/meson.build | 4 ++++ src/common/protocol.c | 6 +++--- 2 files changed, 7 insertions(+), 3 deletions(-) create mode 100644 src/common/meson.build (limited to 'src/common') diff --git a/src/common/meson.build b/src/common/meson.build new file mode 100644 index 0000000..b0f0c82 --- /dev/null +++ b/src/common/meson.build @@ -0,0 +1,4 @@ +common_filenames = [ +] + +common_sources = files(common_filenames) diff --git a/src/common/protocol.c b/src/common/protocol.c index dc0f532..0ffaede 100644 --- a/src/common/protocol.c +++ b/src/common/protocol.c @@ -24,12 +24,12 @@ * separately. */ -#include "protocol.h" -#include "protocol_private.h" -#include "net.h" #include #include #include +#include "protocol.h" +#include "protocol_private.h" +#include "net.h" #define READ_AS(from, type) (*(type*)(from)) -- cgit v1.2.3 From 27992079c057ea068a355e01365800d77b7ace13 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ram=C5=ABnas=20Ma=C5=BEeikis?= Date: Wed, 22 May 2019 14:56:59 +0300 Subject: Protocol: attempted to fix stupids. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Ramūnas Mažeikis --- src/common/protocol.c | 153 ++++++++++++++++++++++++++++++++++++++++++++++++ src/common/protocol.cpp | 153 ------------------------------------------------ 2 files changed, 153 insertions(+), 153 deletions(-) create mode 100644 src/common/protocol.c delete mode 100644 src/common/protocol.cpp (limited to 'src/common') diff --git a/src/common/protocol.c b/src/common/protocol.c new file mode 100644 index 0000000..43ff6a5 --- /dev/null +++ b/src/common/protocol.c @@ -0,0 +1,153 @@ +/* + * Usurpataion --- clinet-server protocol implementation. + * + * Copyright (C) 2019 Ramūnas Mažeikis + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; version 2.1 + * of the License. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA + */ + +/** + * Common parts of protocol implementation. Handling of anything that actually + * deals with connection descriptor has to be implemented by device and daemon + * separately. + */ + +#include "protocol.h" +#include "protocol_private.h" +#include "net.h" +#include +#include +#include + +#define READ_AS(type, from) (*((type*)(from))) + +int push_data(cd_t connection, const char *data, enum tlv_type type) +{ + int ret = E_UNKNOWN_TYPE; + switch (type) { + case TEXT: + ret = push_string(connection, data); + break; + case FPI1: + ret = push_fpi1(connection, data); + break; + case TIMESTAMP: + ret = push_timestamp(connection, data); + break; + case REQUEST: + ret = push_request(connection, data); + break; + case REPLY: + ret = push_reply(connection, data); + break; + case UUID: + ret = push_uuid(connection, data); + break; + } + return ret; +} + +static int push_string(cd_t connection, const char *str) +{ + int ret = 0; + size_t size = strlen(str); + + ret |= push_tlv_header(connection, TEXT, size); + ret |= push_bytes(connection, str, size); + return ret; +} + +static int push_fpi1(cd_t connection, const char *num) +{ + return push_tlv_header(connection, FPI1, sizeof(fpi1_t)) + | push_bytes(connection, num, sizeof(fpi1_t)); +} + +static int push_timestamp(cd_t connection, const char *data) +{ + return push_tlv_header(connection, TIMESTAMP, sizeof(time_t)) + | push_bytes(connection, data, sizeof(time_t)); +} + +static int push_request(cd_t connection, const char *data) +{ + return push_tlv_header(connection, REQUEST, sizeof(msg_idx_t)) + | push_bytes(connection, data, sizeof(msg_idx_t)); +} + +static int push_reply(cd_t connection, const char *data) +{ + int ret = 0; + size_t msglen = strlen(data + sizeof(msg_idx_t)); + ret |= push_tlv_header(connection, REPLY, msglen + sizeof(msg_idx_t)); + ret |= push_bytes(connection, data, msglen); + return ret; +} + +static int push_uuid(cd_t connection, const char *data) +{ + return push_tlv_header(connection, UUID, sizeof(uuid_t)) + | push_bytes(connection, data, sizeof(uuid_t)); +} + +size_t tlv_count(const struct packet_data * const packet) +{ + size_t cursor = 0; + size_t length = 0; + size_t ret = 0; + + while (cursor < packet->packet_size) { + cursor += sizeof(enum tlv_type); + length = READ_AS(enum tlv_type, packet->data + cursor); + cursor += sizeof(size_t) + length; + ret++; + } + if (cursor != packet->packet_size) { + errno = E_TLV_OVERFLOW; + } + return ret; +} + +size_t get_tlvs( const struct packet_data * const data, + struct tlv *buf, + size_t buf_size) +{ + size_t tlvs_read = 0; + size_t cursor = 0; + + while (cursor < data->packet_size && tlvs_read <= buf_size) { + cursor += parse_tlv(data->data, cursor, buf + tlvs_read); + tlvs_read++; + } + + if (cursor > data->packet_size) { + errno = E_TLV_OVERFLOW; + } + + return tlvs_read; +} + +size_t parse_tlv(const char *data, size_t cursor, struct tlv *t) +{ + const char *begin = data + cursor; + + t->type = READ_AS(enum tlv_type, data + cursor); + cursor += sizeof(enum tlv_type); + t->length += READ_AS(enum tlv_type ,data + cursor); + data += sizeof(size_t); + t->data = data + cursor; + + return data + cursor - begin + 1UL; +} diff --git a/src/common/protocol.cpp b/src/common/protocol.cpp deleted file mode 100644 index 135be37..0000000 --- a/src/common/protocol.cpp +++ /dev/null @@ -1,153 +0,0 @@ -/* - * Usurpataion --- clinet-server protocol implementation. - * - * Copyright (C) 2019 Ramūnas Mažeikis - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation; version 2.1 - * of the License. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public - * License along with this program; if not, write to the Free Software - * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA - */ - -/** - * Common parts of protocol implementation. Handling of anything that actually - * deals with connection descriptor has to be implemented by device and daemon - * separately. - */ - -#include "protocol.h" -#include "protocol_private.h" -#include "net.h" -#include -#include -#include - -#define READ_AS(type, from) (*((type*)(from))) - -int push_data(cd_t connection, const char *data, enum tlv_type type) -{ - int ret = E_UNKNOWN_TYPE; - switch (type) { - case TEXT: - ret = push_string(connection, data); - break; - case FPI1: - ret = push_fpi1(connection, data); - break; - case TIMESTAMP: - ret = push_timestamp(connection, data); - break; - case REQUEST: - ret = push_request(connection, data); - break; - case REPLY: - ret = push_reply(connection, data); - break; - case UUID: - ret = push_uuid(connection, data); - break; - } - return ret; -} - -static int push_string(cd_t connection, const char *str) -{ - int ret = 0; - size_t size = strlen(str); - - ret |= push_tlv_header(connection, TEXT, size); - ret |= push_bytes(connection, str, size); - return ret; -} - -static int push_fpi1(cd_t connection, const char *num) -{ - return push_tlv_header(connection, FPI1, sizeof(fpi1_t)) - | push_bytes(connection, num, sizeof(fpi1_t)); -} - -static int push_timestamp(cd_t connection, const char *data) -{ - return push_tlv_header(connection, TIMESTAMP, sizeof(time_t)) - | push_bytes(connection, data, sizeof(time_t)); -} - -static int push_request(cd_t connection, const char *data) -{ - return push_tlv_header(connection, REQUEST, sizeof(msg_idx_t)) - | push_bytes(connection, data, sizeof(msg_idx_t)); -} - -static int push_reply(cd_t connection, const char *data) -{ - int ret = 0; - size_t msglen = strlen(data + sizeof(msg_idx_t)); - ret |= push_tlv_header(connection, REPLY, msglen + sizeof(msg_idx_t)); - ret |= push_bytes(connection, data, msglen); - return ret; -} - -static int push_uuid(cd_t connection, const char *data) -{ - return push_tlv_header(connection, UUID, sizeof(uuid_t)) - | push_bytes(connection, data, sizeof(uuid_t)); -} - -size_t tlv_count(const struct packet_data * const packet) -{ - size_t cursor = 0; - size_t length = 0; - size_t ret = 0; - - while (cursor < packet->packet_size) { - cursor += sizeof(enum tlv_type); - length = READ_AS(enum tlv_type, packet->data + cursor); - cursor += sizeof(size_t) + length; - ret++; - } - if (cursor != packet->packet_size) { - errno = E_TLV_OVERFLOW; - } - return ret; -} - -size_t get_tlvs( const struct packet_data * const data, - struct tlv *buf, - size_t buf_size) -{ - size_t tlvs_read = 0; - size_t cursor = 0; - - while (cursor < data->packet_size && tlvs_read <= buf_size) { - cursor += parse_tlv(data->data, cursor, buf + tlvs_read); - tlvs_read++; - } - - if (cursor > data->packet_size) { - errno = E_TLV_OVERFLOW; - } - - return tlvs_read; -} - -size_t parse_tlv(const char *data, size_t cursor, struct tlv *t) -{ - const char *begin = data + cursor; - - t->type = READ_AS(enum tlv_type, data + cursor); - cursor += sizeof(enum tlv_type); - t->length += READ_AS(enum tlv_type ,data + cursor); - data += sizeof(size_t); - t->data = (void*)data + cursor; - - return data + cursor - begin + 1UL; -} -- cgit v1.2.3 From 28b26ca86cf18947d6d9543ad753ef112ff4da89 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ram=C5=ABnas=20Ma=C5=BEeikis?= Date: Wed, 22 May 2019 20:33:08 +0300 Subject: Protocol: interface redesign. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Every function is a stub now. Reimplementaion coming up. Signed-off-by: Ramūnas Mažeikis --- src/common/protocol.c | 102 ++++++++++++----------------------- src/common/protocol_private.h | 122 ++++-------------------------------------- 2 files changed, 42 insertions(+), 182 deletions(-) (limited to 'src/common') diff --git a/src/common/protocol.c b/src/common/protocol.c index 54d51f6..58a70f6 100644 --- a/src/common/protocol.c +++ b/src/common/protocol.c @@ -33,121 +33,85 @@ #define READ_AS(type, from) (*((type*)(from))) -int push_data(cd_t connection, const char *data, enum tlv_type type) +int push_data(enum tlv_type type) { - int ret = E_UNKNOWN_TYPE; + int ret = 0; switch (type) { case TEXT: - ret = push_string(connection, data); break; case FPI1: - ret = push_fpi1(connection, data); break; case TIMESTAMP: - ret = push_timestamp(connection, data); break; case REQUEST: - ret = push_request(connection, data); break; case REPLY: - ret = push_reply(connection, data); break; case UUID: - ret = push_uuid(connection, data); break; + default: + ret = E_UNKNOWN_TYPE; } return ret; } -static int push_string(cd_t connection, const char *str) +static int push_string(const char *str) { - int ret = 0; - size_t size = strlen(str); - - ret |= push_tlv_header(connection, TEXT, size); - ret |= push_bytes(connection, str, size); - return ret; + return 0; } -static int push_fpi1(cd_t connection, const char *num) +static int push_fpi1(const char *num) { - return push_tlv_header(connection, FPI1, sizeof(fpi1_t)) - | push_bytes(connection, num, sizeof(fpi1_t)); + return 0; } -static int push_timestamp(cd_t connection, const char *data) +static int push_timestamp(const char *data) { - return push_tlv_header(connection, TIMESTAMP, sizeof(time_t)) - | push_bytes(connection, data, sizeof(time_t)); + return 0; } -static int push_request(cd_t connection, const char *data) +static int push_request(const char *data) { - return push_tlv_header(connection, REQUEST, sizeof(msg_idx_t)) - | push_bytes(connection, data, sizeof(msg_idx_t)); + return 0; } -static int push_reply(cd_t connection, const char *data) +static int push_reply(const char *data) { - int ret = 0; - size_t msglen = strlen(data + sizeof(msg_idx_t)); - ret |= push_tlv_header(connection, REPLY, msglen + sizeof(msg_idx_t)); - ret |= push_bytes(connection, data, msglen); - return ret; + return 0; } -static int push_uuid(cd_t connection, const char *data) +static int push_uuid(const char *data) { - return push_tlv_header(connection, UUID, sizeof(uuid_t)) - | push_bytes(connection, data, sizeof(uuid_t)); + return 0; } size_t tlv_count(const struct packet_data * const packet) { - size_t cursor = 0; - size_t length = 0; - size_t ret = 0; - - while (cursor < packet->packet_size) { - cursor += sizeof(enum tlv_type); - length = READ_AS(enum tlv_type, packet->data + cursor); - cursor += sizeof(size_t) + length; - ret++; - } - if (cursor != packet->packet_size) { - errno = E_TLV_OVERFLOW; - } - return ret; + return 0; } -size_t get_tlvs( const struct packet_data * const data, - struct tlv *buf, - size_t buf_size) +size_t parse_tlv(const char *data, size_t cursor, struct tlv *t) { - size_t tlvs_read = 0; - size_t cursor = 0; + return 0; +} - while (cursor < data->packet_size && tlvs_read <= buf_size) { - cursor += parse_tlv(data->data, cursor, buf + tlvs_read); - tlvs_read++; - } - if (cursor > data->packet_size) { - errno = E_TLV_OVERFLOW; - } - - return tlvs_read; +int clear_data() +{ + return 0; } -size_t parse_tlv(const char *data, size_t cursor, struct tlv *t) +static int push_bytes(const char *data, size_t size) { - const char *begin = data + cursor; + return 0; +} - t->type = READ_AS(enum tlv_type, data + cursor); - cursor += sizeof(enum tlv_type); - t->length += READ_AS(enum tlv_type ,data + cursor); - data += sizeof(size_t); - t->data = data + cursor; +static int push_tlv_header(enum tlv_type type, size_t size) +{ + return 0; +} - return data + cursor - begin + 1UL; +int get_tlv(struct tlv_parser *parser, struct tlv *ret) +{ + return 0; } diff --git a/src/common/protocol_private.h b/src/common/protocol_private.h index d50a314..5228afd 100644 --- a/src/common/protocol_private.h +++ b/src/common/protocol_private.h @@ -1,115 +1,11 @@ -/* - * Usurpataion --- server-client protocol private interface. - * - * Copyright (C) 2019 Ramūnas Mažeikis - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation; version 2.1 - * of the License. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public - * License along with this program; if not, write to the Free Software - * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA - */ +#ifndef PROTOCOL_PRIVATE_H +#define PROTOCOL_PRIVATE_H -#ifndef PROTOCOL_H_PRIVATE -#define PROTOCOL_H_PRIVATE +static int push_string(const char *str); +static int push_fpi1(const char *num); +static int push_timestamp(const char *data); +static int push_request(const char *data); +static int push_reply(const char *data); +static int push_uuid(const char *data); -#include "utils.h" - -/** - * Returns the amount of tlv's int a packet. - * - * If a tlv reports length that goes beyond the end of a packet, errno is set - * to TLV_OVERFLOW. To check this, set errno to 0 first. - * - * @param packet data parsed from a packet. Function cannot use raw packets. - * - * @return Amount of tlv's in a packet. - * */ -size_t tlv_count(const struct packet_data * const packet_data); - -/** - * Pushes bytes to outgoing packet and adjusts the offset accordingly. - * - * Returns E_PACKET_OVERFLOW, if no more bytes can fit into the packet. - */ - -int push_bytes(cd_t cd, const char *data, size_t size); - -/** - * Parses tlv's from packet data and writes them to a buffer of given size. - * - * Returns how many tlv's were actually parsed. - * - * To check for errors, set errno to 0 and check after calling. - * - * Not yet implemented. - * - * @param data Data from network packet - * @param buf Buffer to store parsed tlv's - * @param buf_size Size of buffer used to store tlv's - * - * @return Number of tlv's actually parsed. Greter than or equal to buffer - * size, if an error occurs. - * */ -size_t get_tlvs( const struct packet_data * const data, - const struct tlv *buf, - size_t buf_size); - -/** Takes a null-terminated string and appends it to the next outgoing packet. - * - * @return Returns 0 on success. Otherwise: E_PACKET_OVERFLOW. - * - * */ -int push_string(cd_t connection, char *str); - -/** Reinterprets char * as fpi1_t * and appends it to the outgoing packet as a - * tlv. - */ -int push_fpi1(cd_t connection, char *num); - -/** Reinterprets char * as time_t * and appends it to the outgoing packet as a - * tlv. - */ -int push_timestamp(cd_t connection, char *data); - -/** - * Pushes a request for daemon to repeat a message identified by a msg_index_t. - * - * @param data Pointer to a msg_index_t. - * - * @return 0 on success or E_PACKET_OVERFLOW, if not enough space is available - * to push all the data. - */ -int push_request(cd_t connection, char *data); - -/** - * Pushes a message to the outgoing packet buffer as a reply. A reply is just - * a null terminated string. - * - * @param data msg_idx_t representing sequence number since beggining of - * connection and a null-terminated string. - * - * @return On success --- 0 or E_PACKET_OVERFLOW, if not enough buffer is - * available. - */ -int push_reply(cd_t connection, char *data); - -/** Reinterprets char * as uuid_t * and appends it to the outgoing packet as a - * tlv. - */ -int push_uuid(cd_t connection, char *data); - -/* Appends tlv_type and size of data to a packet effectively creating a tlv - * header. - */ -int push_tlv_header(cd_t connection, enum tlv_type type, size_t size); - -#endif /* PROTOCOL_H_PRIVATE */ +#endif /* PROTOCOL_PRIVATE_H */ \ No newline at end of file -- cgit v1.2.3 From ca9e0b1cc8084b66311705b0c79da16821eb275d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ram=C5=ABnas=20Ma=C5=BEeikis?= Date: Wed, 22 May 2019 20:38:29 +0300 Subject: Protocol: amendments to interface functions. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Ramūnas Mažeikis --- src/common/protocol.c | 22 ++++++++-------------- src/common/protocol_private.h | 16 ++++++++++------ 2 files changed, 18 insertions(+), 20 deletions(-) (limited to 'src/common') diff --git a/src/common/protocol.c b/src/common/protocol.c index 58a70f6..a7cb84f 100644 --- a/src/common/protocol.c +++ b/src/common/protocol.c @@ -55,37 +55,32 @@ int push_data(enum tlv_type type) return ret; } -static int push_string(const char *str) +static int push_string(struct tlv_packet *packet, const char *str) { return 0; } -static int push_fpi1(const char *num) +static int push_fpi1(struct tlv_packet *packet, const char *num) { return 0; } -static int push_timestamp(const char *data) +static int push_timestamp(struct tlv_packet *packet, const char *data) { return 0; } -static int push_request(const char *data) +static int push_request(struct tlv_packet *packet, const char *data) { return 0; } -static int push_reply(const char *data) +static int push_reply(struct tlv_packet *packet, const char *data) { return 0; } -static int push_uuid(const char *data) -{ - return 0; -} - -size_t tlv_count(const struct packet_data * const packet) +static int push_uuid(struct tlv_packet *packet, const char *data) { return 0; } @@ -95,18 +90,17 @@ size_t parse_tlv(const char *data, size_t cursor, struct tlv *t) return 0; } - int clear_data() { return 0; } -static int push_bytes(const char *data, size_t size) +static int push_bytes(struct tlv_packet *packet, size_t size) { return 0; } -static int push_tlv_header(enum tlv_type type, size_t size) +static int push_tlv_header(struct tlv_packet *packet, enum tlv_type type, size_t size) { return 0; } diff --git a/src/common/protocol_private.h b/src/common/protocol_private.h index 5228afd..a31103a 100644 --- a/src/common/protocol_private.h +++ b/src/common/protocol_private.h @@ -1,11 +1,15 @@ #ifndef PROTOCOL_PRIVATE_H #define PROTOCOL_PRIVATE_H -static int push_string(const char *str); -static int push_fpi1(const char *num); -static int push_timestamp(const char *data); -static int push_request(const char *data); -static int push_reply(const char *data); -static int push_uuid(const char *data); +#include "protocol_private.h" + +int push_string(struct tlv_packet *packet, const char *str); +int push_fpi1(struct tlv_packet *packet, const char *num); +int push_timestamp(struct tlv_packet *packet, const char *data); +int push_request(struct tlv_packet *packet, const char *data); +int push_reply(struct tlv_packet *packet, const char *data); +int push_uuid(struct tlv_packet *packet, const char *data); +int push_bytes(struct tlv_packet *packet, size_t size); +int push_tlv_header(struct tlv_packet *packet, enum tlv_type type, size_t size); #endif /* PROTOCOL_PRIVATE_H */ \ No newline at end of file -- cgit v1.2.3 From dd7556097b373bc62f646016a9b368899043dcc9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ram=C5=ABnas=20Ma=C5=BEeikis?= Date: Wed, 22 May 2019 20:48:42 +0300 Subject: Protocol: reimplemented push_string and push_fpi1. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Ramūnas Mažeikis --- src/common/protocol.c | 20 ++++++++++++++++++-- 1 file changed, 18 insertions(+), 2 deletions(-) (limited to 'src/common') diff --git a/src/common/protocol.c b/src/common/protocol.c index a7cb84f..2b4e3bf 100644 --- a/src/common/protocol.c +++ b/src/common/protocol.c @@ -30,6 +30,7 @@ #include "protocol.h" #include "protocol_private.h" #include "net.h" +#include "util.h" #define READ_AS(type, from) (*((type*)(from))) @@ -57,12 +58,27 @@ int push_data(enum tlv_type type) static int push_string(struct tlv_packet *packet, const char *str) { - return 0; + size_t strsize = strlen(str); + int ret = 0; + + if (strsize + packet->offset >= packet->size) { + ret = E_TLV_OVERFLOW; + } else { + memcpy(packet->data, str, strsize); + } + return ret; } static int push_fpi1(struct tlv_packet *packet, const char *num) { - return 0; + int ret = 0; + + if (packet->offset + sizeof(fpi1_t) >= packet->size) { + ret = E_TLV_OVERFLOW; + } else { + memcpy(packet->data, num, sizeof(fpi1_t)); + } + return ret; } static int push_timestamp(struct tlv_packet *packet, const char *data) -- cgit v1.2.3 From 54f0ba9d41b446b83090dc0f3b220db9c82491d0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ram=C5=ABnas=20Ma=C5=BEeikis?= Date: Wed, 22 May 2019 20:52:26 +0300 Subject: Protocol: tossed a bunch of function out the window. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Ramūnas Mažeikis --- src/common/protocol.c | 47 +------------------------------------------ src/common/protocol_private.h | 6 ------ 2 files changed, 1 insertion(+), 52 deletions(-) (limited to 'src/common') diff --git a/src/common/protocol.c b/src/common/protocol.c index 2b4e3bf..5498704 100644 --- a/src/common/protocol.c +++ b/src/common/protocol.c @@ -56,57 +56,12 @@ int push_data(enum tlv_type type) return ret; } -static int push_string(struct tlv_packet *packet, const char *str) -{ - size_t strsize = strlen(str); - int ret = 0; - - if (strsize + packet->offset >= packet->size) { - ret = E_TLV_OVERFLOW; - } else { - memcpy(packet->data, str, strsize); - } - return ret; -} - -static int push_fpi1(struct tlv_packet *packet, const char *num) -{ - int ret = 0; - - if (packet->offset + sizeof(fpi1_t) >= packet->size) { - ret = E_TLV_OVERFLOW; - } else { - memcpy(packet->data, num, sizeof(fpi1_t)); - } - return ret; -} - -static int push_timestamp(struct tlv_packet *packet, const char *data) -{ - return 0; -} - -static int push_request(struct tlv_packet *packet, const char *data) -{ - return 0; -} - -static int push_reply(struct tlv_packet *packet, const char *data) -{ - return 0; -} - -static int push_uuid(struct tlv_packet *packet, const char *data) -{ - return 0; -} - size_t parse_tlv(const char *data, size_t cursor, struct tlv *t) { return 0; } -int clear_data() +void clear_data(struct tlv_packet *packet) { return 0; } diff --git a/src/common/protocol_private.h b/src/common/protocol_private.h index a31103a..206046f 100644 --- a/src/common/protocol_private.h +++ b/src/common/protocol_private.h @@ -3,12 +3,6 @@ #include "protocol_private.h" -int push_string(struct tlv_packet *packet, const char *str); -int push_fpi1(struct tlv_packet *packet, const char *num); -int push_timestamp(struct tlv_packet *packet, const char *data); -int push_request(struct tlv_packet *packet, const char *data); -int push_reply(struct tlv_packet *packet, const char *data); -int push_uuid(struct tlv_packet *packet, const char *data); int push_bytes(struct tlv_packet *packet, size_t size); int push_tlv_header(struct tlv_packet *packet, enum tlv_type type, size_t size); -- cgit v1.2.3 From db5f3e534c1efd31a582d2309b2bc892cc2c8317 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ram=C5=ABnas=20Ma=C5=BEeikis?= Date: Wed, 22 May 2019 21:13:45 +0300 Subject: Protocol: reimplemented get_tlv and added tlv_data_size. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Ramūnas Mažeikis --- src/common/protocol.c | 38 +++++++++++++++++++++++++++++++------- 1 file changed, 31 insertions(+), 7 deletions(-) (limited to 'src/common') diff --git a/src/common/protocol.c b/src/common/protocol.c index 5498704..8fbd197 100644 --- a/src/common/protocol.c +++ b/src/common/protocol.c @@ -34,9 +34,11 @@ #define READ_AS(type, from) (*((type*)(from))) -int push_data(enum tlv_type type) +int push_tlv(struct tlv_packet *packet, enum tlv_type type, char *data) { int ret = 0; + size_t size; + switch (type) { case TEXT: break; @@ -56,11 +58,6 @@ int push_data(enum tlv_type type) return ret; } -size_t parse_tlv(const char *data, size_t cursor, struct tlv *t) -{ - return 0; -} - void clear_data(struct tlv_packet *packet) { return 0; @@ -78,5 +75,32 @@ static int push_tlv_header(struct tlv_packet *packet, enum tlv_type type, size_t int get_tlv(struct tlv_parser *parser, struct tlv *ret) { - return 0; + int ret = 0; + + if (parser->offset + sizeof(ret->type) + sizeof(ret->length) >= parser->size) { + ret = E_TLV_OVERFLOW; + } else { + ret->type = memcpy(&ret->type, parser->data + parser->offset, sizeof(ret->type)); + parser->size += sizeof(ret->type); + ret->length = memcpy(&ret->length, parser->data + parser->offset, sizeof(ret->length)); + parser->offset += sizeof(ret->length); + if (parser->offset + ret->length >= parser->size) { + ret = E_TLV_OVERFLOW; + } else { + memcpy(ret->data, parser->data, ret->length); + } + } + return ret; } + +size_t tlv_data_size(struct tlv_parser *parser) +{ + size_t size; + + if (parser->offset + sizeof(enum tlv_type) + sizeof(size_t) >= parser->size) { + size = 0; + } else { + memcpy(&size, parser->data + parser->offset + sizeof(enum tlv_type), sizeof(size_t)); + } + return size; +} \ No newline at end of file -- cgit v1.2.3 From 5fee4a9996158479fe5503c9acace5733660f9e9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ram=C5=ABnas=20Ma=C5=BEeikis?= Date: Wed, 22 May 2019 21:21:25 +0300 Subject: Protocol: reimplemented push_bytes and push_tlv_header. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Ramūnas Mažeikis --- src/common/protocol.c | 27 +++++++++++++++++++++++---- src/common/protocol_private.h | 2 +- 2 files changed, 24 insertions(+), 5 deletions(-) (limited to 'src/common') diff --git a/src/common/protocol.c b/src/common/protocol.c index 8fbd197..e71938c 100644 --- a/src/common/protocol.c +++ b/src/common/protocol.c @@ -60,17 +60,36 @@ int push_tlv(struct tlv_packet *packet, enum tlv_type type, char *data) void clear_data(struct tlv_packet *packet) { - return 0; + packet->offset = 0; + packet->type = 0; + memset(packet->data, 0, packet->size); } -static int push_bytes(struct tlv_packet *packet, size_t size) +static int push_bytes(struct tlv_packet *packet, char *data, size_t size) { - return 0; + int ret = 0; + + if (packet->offset + size >= packet->size) { + ret = E_TLV_OVERFLOW; + } else { + memcpy(packet->data + packet->offset, data, size); + packet->offset += size; + } } static int push_tlv_header(struct tlv_packet *packet, enum tlv_type type, size_t size) { - return 0; + int ret = 0; + + if (packet->offset + sizeof(type) + sizeof(size) >= packet->size) { + ret = E_TLV_OVERFLOW; + } else { + memcpy(packet->data + packet->size, type, sizeof(type)); + packet->offset += sizeof(type); + memcpy(packet->data + packet->offset, size, sizeof(size)); + packet->offset += sizeof(size); + } + return ret; } int get_tlv(struct tlv_parser *parser, struct tlv *ret) diff --git a/src/common/protocol_private.h b/src/common/protocol_private.h index 206046f..de086cd 100644 --- a/src/common/protocol_private.h +++ b/src/common/protocol_private.h @@ -3,7 +3,7 @@ #include "protocol_private.h" -int push_bytes(struct tlv_packet *packet, size_t size); +int push_bytes(struct tlv_packet *packet, char *data, size_t size); int push_tlv_header(struct tlv_packet *packet, enum tlv_type type, size_t size); #endif /* PROTOCOL_PRIVATE_H */ \ No newline at end of file -- cgit v1.2.3 From 323292cb8a1191e1c74c7d42c6e54f589d8023d1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ram=C5=ABnas=20Ma=C5=BEeikis?= Date: Wed, 22 May 2019 21:29:06 +0300 Subject: Protocol: finished reimplementation. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Now protocol only deals with parsing and forming of packets. Signed-off-by: Ramūnas Mažeikis --- src/common/protocol.c | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) (limited to 'src/common') diff --git a/src/common/protocol.c b/src/common/protocol.c index e71938c..d3317e3 100644 --- a/src/common/protocol.c +++ b/src/common/protocol.c @@ -30,7 +30,7 @@ #include "protocol.h" #include "protocol_private.h" #include "net.h" -#include "util.h" +#include "utils.h" #define READ_AS(type, from) (*((type*)(from))) @@ -41,20 +41,28 @@ int push_tlv(struct tlv_packet *packet, enum tlv_type type, char *data) switch (type) { case TEXT: + size = strlen(data); break; case FPI1: + size = sizeof(fpi1_t); break; case TIMESTAMP: + size = sizeof(time_t); break; case REQUEST: + size = sizeof(msg_idx_t); break; case REPLY: + size = sizeof(msg_idx_t) + strlen(data + sizeof(msg_idx_t)); break; case UUID: + size = sizeof(uuid_t); break; default: ret = E_UNKNOWN_TYPE; } + ret |= push_tlv_header(packet, type, size); + ret |= push_bytes(packet, data, size); return ret; } -- cgit v1.2.3 From 446157d793c30386f994743f5a8e6ab64e66507f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ram=C5=ABnas=20Ma=C5=BEeikis?= Date: Wed, 22 May 2019 21:35:46 +0300 Subject: Protocol: updated docs for functions that survived redesign. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Ramūnas Mažeikis --- src/common/protocol_private.h | 13 +++++++++++++ 1 file changed, 13 insertions(+) (limited to 'src/common') diff --git a/src/common/protocol_private.h b/src/common/protocol_private.h index de086cd..fe28aa0 100644 --- a/src/common/protocol_private.h +++ b/src/common/protocol_private.h @@ -3,7 +3,20 @@ #include "protocol_private.h" +/** + * Convenience function that pushes bytes to the end of a packet and reports + * potential overflow. + * + * In case of detected overflow nothing is done to the packet. + */ int push_bytes(struct tlv_packet *packet, char *data, size_t size); + +/** + * Convenience function that forms a tlv header at the end of a packet. Reports + * potential overflow. + * + * In case of detected overflow nothing is done to the packet. + */ int push_tlv_header(struct tlv_packet *packet, enum tlv_type type, size_t size); #endif /* PROTOCOL_PRIVATE_H */ \ No newline at end of file -- cgit v1.2.3 From 5e22764d79e42345d512216f07880fdd8db2edf2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ram=C5=ABnas=20Ma=C5=BEeikis?= Date: Wed, 22 May 2019 21:41:19 +0300 Subject: Protocol: fixed a off-by-one error when copying a string. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Ramūnas Mažeikis --- src/common/protocol.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src/common') diff --git a/src/common/protocol.c b/src/common/protocol.c index d3317e3..8680be7 100644 --- a/src/common/protocol.c +++ b/src/common/protocol.c @@ -41,7 +41,7 @@ int push_tlv(struct tlv_packet *packet, enum tlv_type type, char *data) switch (type) { case TEXT: - size = strlen(data); + size = strlen(data) + 1; break; case FPI1: size = sizeof(fpi1_t); -- cgit v1.2.3 From 3397ca1e68f69259cca56751af73f3f0706b6831 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ram=C5=ABnas=20Ma=C5=BEeikis?= Date: Wed, 22 May 2019 21:46:23 +0300 Subject: Protocol: updated get_tlv and more docs. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Ramūnas Mažeikis --- src/common/protocol.c | 2 ++ 1 file changed, 2 insertions(+) (limited to 'src/common') diff --git a/src/common/protocol.c b/src/common/protocol.c index 8680be7..bae38d8 100644 --- a/src/common/protocol.c +++ b/src/common/protocol.c @@ -106,6 +106,8 @@ int get_tlv(struct tlv_parser *parser, struct tlv *ret) if (parser->offset + sizeof(ret->type) + sizeof(ret->length) >= parser->size) { ret = E_TLV_OVERFLOW; + } else if (parser -> offset == parser->size) { + ret = END_OF_PACKET; } else { ret->type = memcpy(&ret->type, parser->data + parser->offset, sizeof(ret->type)); parser->size += sizeof(ret->type); -- cgit v1.2.3 From b25865cc827f4a6a9c31f3d92a4e443485fd5d93 Mon Sep 17 00:00:00 2001 From: Gediminas Jakutis Date: Sun, 26 May 2019 14:46:36 +0300 Subject: common: cosmetic changes. Signed-off-by: Gediminas Jakutis --- src/common/protocol.c | 4 +--- src/common/protocol_private.h | 28 +++++++++++++++++++++++++++- src/common/utils.c | 20 ++++++++++++++++++++ 3 files changed, 48 insertions(+), 4 deletions(-) (limited to 'src/common') diff --git a/src/common/protocol.c b/src/common/protocol.c index bae38d8..b2e0d40 100644 --- a/src/common/protocol.c +++ b/src/common/protocol.c @@ -32,8 +32,6 @@ #include "net.h" #include "utils.h" -#define READ_AS(type, from) (*((type*)(from))) - int push_tlv(struct tlv_packet *packet, enum tlv_type type, char *data) { int ret = 0; @@ -132,4 +130,4 @@ size_t tlv_data_size(struct tlv_parser *parser) memcpy(&size, parser->data + parser->offset + sizeof(enum tlv_type), sizeof(size_t)); } return size; -} \ No newline at end of file +} diff --git a/src/common/protocol_private.h b/src/common/protocol_private.h index fe28aa0..51d5431 100644 --- a/src/common/protocol_private.h +++ b/src/common/protocol_private.h @@ -1,3 +1,29 @@ +/* + * Usurpataion --- clinet-server protocol implementation. + * + * Copyright (C) 2019 Ramūnas Mažeikis + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; version 2.1 + * of the License. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA + */ + +/** + * Common parts of protocol implementation. Handling of anything that actually + * deals with connection descriptor has to be implemented by device and daemon + * separately. + */ + #ifndef PROTOCOL_PRIVATE_H #define PROTOCOL_PRIVATE_H @@ -19,4 +45,4 @@ int push_bytes(struct tlv_packet *packet, char *data, size_t size); */ int push_tlv_header(struct tlv_packet *packet, enum tlv_type type, size_t size); -#endif /* PROTOCOL_PRIVATE_H */ \ No newline at end of file +#endif /* PROTOCOL_PRIVATE_H */ diff --git a/src/common/utils.c b/src/common/utils.c index 0619517..7522404 100644 --- a/src/common/utils.c +++ b/src/common/utils.c @@ -1,3 +1,23 @@ +/* + * Usurpataion --- utility functions. + * + * Copyright (C) 2019 Ramūnas Mažeikis + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; version 2.1 + * of the License. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA + */ + #include "utils.h" #include "string.h" -- cgit v1.2.3