jsfw/net.c

435 lines
13 KiB
C
Raw Normal View History

2022-08-29 17:27:03 -05:00
#include "net.h"
2022-08-30 17:54:56 -05:00
2022-10-07 18:36:53 -05:00
#include "util.h"
2022-10-12 15:28:50 -05:00
#include <stdbool.h>
2022-08-30 11:28:29 -05:00
#include <stdio.h>
2022-10-07 18:36:53 -05:00
#include <string.h>
2022-08-29 17:27:03 -05:00
// Deserialize the message in buf, buf must be at least 4 aligned. Returns -1 on error, otherwise returns 0
// and writes result to dst
2022-08-31 11:59:06 -05:00
int msg_deserialize(const uint8_t *buf, size_t len, Message *restrict dst) {
2022-10-12 12:33:18 -05:00
{
2022-10-12 15:28:50 -05:00
if (len <= MAGIC_SIZE) {
2022-10-12 12:33:18 -05:00
return -1;
}
2022-10-12 15:28:50 -05:00
if (*(MAGIC_TYPE *)buf != MAGIC_BEG) {
2022-10-12 12:33:18 -05:00
printf("NET: No magic in message\n");
return -1;
}
buf += MAGIC_SIZE;
len -= MAGIC_SIZE;
}
2022-08-29 17:27:03 -05:00
// Decrement len so that it becomes the len of the data without the code.
2022-08-30 08:37:34 -05:00
if (len-- < 1)
return -1;
2022-08-29 17:27:03 -05:00
// This ensures that only a byte is read instead of a full enum value
2022-10-12 15:28:50 -05:00
uint8_t code_byte = buf[0];
MessageCode code = (MessageCode)code_byte;
uint32_t size = 0;
2022-08-30 08:37:34 -05:00
2023-03-18 12:41:17 -05:00
uint16_t abs, rel, key, *buf16;
uint8_t index, slot;
2022-08-30 11:28:29 -05:00
2022-08-30 08:37:34 -05:00
switch (code) {
case DeviceInfo:
if (len < 7)
2022-08-30 08:37:34 -05:00
return -1;
2023-03-18 12:41:17 -05:00
slot = buf[2];
index = buf[3];
// buf + 4: a byte for, code, padding, slot, index
buf16 = (uint16_t *)(buf + 4);
abs = buf16[0];
rel = buf16[1];
key = buf16[2];
2022-10-07 18:36:53 -05:00
buf += 12;
2022-08-30 08:37:34 -05:00
if (MSS_DEVICE_INFO(abs, rel, key) > len)
return -1;
2022-08-30 11:28:29 -05:00
dst->device_info.code = code;
2023-03-18 12:41:17 -05:00
dst->device_info.slot = slot;
2022-10-07 18:36:53 -05:00
dst->device_info.index = index;
2022-08-30 08:37:34 -05:00
dst->device_info.abs_count = abs;
dst->device_info.rel_count = rel;
dst->device_info.key_count = key;
// SOA in c but serialized as AOS
for (int i = 0; i < abs; i++) {
// buf + 4: 2 bytes for id and 2 bytes of padding
uint32_t *buf32 = (uint32_t *)(buf + 4);
2022-08-30 08:37:34 -05:00
2022-08-30 17:54:56 -05:00
dst->device_info.abs_id[i] = *(uint16_t *)buf;
2022-08-30 08:37:34 -05:00
dst->device_info.abs_min[i] = buf32[0];
dst->device_info.abs_max[i] = buf32[1];
dst->device_info.abs_fuzz[i] = buf32[2];
dst->device_info.abs_flat[i] = buf32[3];
dst->device_info.abs_res[i] = buf32[4];
buf += 24;
2022-08-30 08:37:34 -05:00
}
2022-08-30 17:54:56 -05:00
for (int i = 0; i < rel; i++) {
dst->device_info.rel_id[i] = *(uint16_t *)buf;
buf += 2;
}
2022-08-30 08:37:34 -05:00
2022-08-30 17:54:56 -05:00
for (int i = 0; i < key; i++) {
dst->device_info.key_id[i] = *(uint16_t *)buf;
buf += 2;
}
2022-08-30 08:37:34 -05:00
2022-10-12 12:33:18 -05:00
size = MSS_DEVICE_INFO(abs, rel, key) + 1;
break;
2022-08-30 08:37:34 -05:00
case DeviceReport:
if (len < 7)
2022-08-30 08:37:34 -05:00
return -1;
2022-08-30 11:28:29 -05:00
2023-03-18 12:41:17 -05:00
slot = buf[2];
index = buf[3];
// buf + 4: a byte for, code, padding, slot and index
buf16 = (uint16_t *)(buf + 4);
abs = buf16[0];
rel = buf16[1];
key = buf16[2];
2022-10-07 18:36:53 -05:00
buf += 12;
2022-08-30 11:28:29 -05:00
if (len < MSS_DEVICE_REPORT(abs, rel, key))
return -1;
dst->device_report.code = code;
2023-03-18 12:41:17 -05:00
dst->device_report.slot = slot;
2022-10-07 18:36:53 -05:00
dst->device_report.index = index;
2022-08-30 11:28:29 -05:00
dst->device_report.abs_count = abs;
dst->device_report.rel_count = rel;
dst->device_report.key_count = key;
for (int i = 0; i < abs; i++) {
dst->device_report.abs[i] = *(uint32_t *)buf;
buf += 4;
}
for (int i = 0; i < rel; i++) {
dst->device_report.rel[i] = *(uint32_t *)buf;
buf += 4;
}
for (int i = 0; i < key; i++)
dst->device_report.key[i] = *(buf++);
2022-10-12 12:33:18 -05:00
buf += align_4(key) - key;
size = MSS_DEVICE_REPORT(abs, rel, key) + 1;
break;
2022-08-30 08:37:34 -05:00
case ControllerState:
if (len < MSS_CONTROLLER_STATE)
return -1;
dst->code = code;
2022-10-07 18:36:53 -05:00
dst->controller_state.index = *(uint16_t *)(buf + 2);
dst->controller_state.led[0] = buf[4];
dst->controller_state.led[1] = buf[5];
dst->controller_state.led[2] = buf[6];
dst->controller_state.small_rumble = buf[7];
dst->controller_state.big_rumble = buf[8];
dst->controller_state.flash_on = buf[9];
dst->controller_state.flash_off = buf[10];
2022-10-12 15:28:50 -05:00
size = MSS_CONTROLLER_STATE + 1;
2022-10-12 12:33:18 -05:00
buf += size;
break;
2022-10-07 18:36:53 -05:00
case Request: {
if (len < 3)
return -1;
dst->code = code;
dst->request.request_count = *(uint16_t *)(buf + 2);
buf += 4; // 1 bytes for code, 1 byte for padding and 2 bytes for count
2023-03-18 10:31:33 -05:00
int count = dst->request.request_count;
TagList *reqs = malloc(count * sizeof(TagList));
2022-10-07 18:36:53 -05:00
// The length of the message, will be updated as we read more.
int expected_len = 3;
for (int i = 0; i < dst->request.request_count; i++) {
expected_len += 2;
if (len < expected_len) {
return -1;
}
2023-03-18 10:31:33 -05:00
TagList *tags = &reqs[i];
tags->count = *(uint16_t *)buf;
tags->tags = malloc(tags->count * sizeof(char *));
2022-10-07 18:36:53 -05:00
buf += 2;
2023-03-18 10:31:33 -05:00
for (int j = 0; j < tags->count; j++) {
expected_len += 2;
if (len < expected_len) {
return -1;
}
uint16_t str_len = *(uint16_t *)buf;
buf += 2;
expected_len += align_2(str_len);
if (len < expected_len) {
return -1;
}
2022-10-07 18:36:53 -05:00
2023-03-18 10:31:33 -05:00
char *str = malloc(str_len + 1);
str[str_len] = '\0';
2022-10-07 18:36:53 -05:00
2023-03-18 10:31:33 -05:00
strncpy(str, (char *)buf, str_len);
2022-10-07 18:36:53 -05:00
2023-03-18 10:31:33 -05:00
tags->tags[j] = str;
2022-10-12 12:33:18 -05:00
2023-03-18 10:31:33 -05:00
buf += align_2(str_len);
}
2022-10-07 18:36:53 -05:00
}
2023-03-18 10:31:33 -05:00
dst->request.requests = reqs;
2022-10-12 15:28:50 -05:00
size = expected_len + 1;
2022-10-12 12:33:18 -05:00
break;
2022-10-07 18:36:53 -05:00
}
case DeviceDestroy:
if (len < MSS_DESTROY)
return -1;
dst->code = code;
dst->destroy.index = *(uint16_t *)(buf + 2);
2022-10-12 15:28:50 -05:00
size = MSS_DESTROY + 1;
2022-10-12 12:33:18 -05:00
buf += size;
break;
2022-08-30 08:37:34 -05:00
default:
return -1;
2022-08-29 17:27:03 -05:00
}
2022-10-12 12:33:18 -05:00
2023-03-18 12:41:17 -05:00
if (align_m(size) + MAGIC_SIZE > len + 1) {
2022-10-12 12:33:18 -05:00
return -1;
}
2023-03-18 12:41:17 -05:00
// WARN: This is technically bad, but should be ok nonetheless
MAGIC_TYPE *mbuf = (MAGIC_TYPE *)align_m((uintptr_t)buf);
if (*mbuf != MAGIC_END) {
2022-10-12 12:33:18 -05:00
printf("NET: Magic not found\n");
return -1;
}
2023-03-18 12:41:17 -05:00
return align_m(size) + 2 * MAGIC_SIZE;
2022-08-29 17:27:03 -05:00
}
// Serialize the message msg in buf, buf must be at least 4 aligned. Returns -1 on error (buf not big enough);
2022-08-31 11:59:06 -05:00
int msg_serialize(uint8_t *restrict buf, size_t len, const Message *msg) {
2022-10-12 12:33:18 -05:00
// If len is less than the two magic and the code we can't serialize any message
if (len < MAGIC_SIZE * 2 + 1)
2022-08-30 08:37:34 -05:00
return -1;
2022-10-12 15:28:50 -05:00
*(MAGIC_TYPE *)buf = MAGIC_BEG;
2022-10-12 12:33:18 -05:00
buf += MAGIC_SIZE;
len -= MAGIC_SIZE + 1;
2022-08-30 17:54:56 -05:00
uint16_t abs, rel, key, *buf16;
2022-10-12 12:33:18 -05:00
uint32_t size;
2022-08-30 11:28:29 -05:00
2022-08-30 08:37:34 -05:00
switch (msg->code) {
2022-08-30 11:28:29 -05:00
case DeviceInfo:
abs = msg->device_info.abs_count;
rel = msg->device_info.rel_count;
key = msg->device_info.key_count;
if (len < MSS_DEVICE_INFO(abs, rel, key))
2022-08-29 17:27:03 -05:00
return -1;
2022-08-30 08:37:34 -05:00
2022-08-31 11:59:06 -05:00
buf[0] = (uint8_t)msg->code;
2023-03-18 12:41:17 -05:00
// 1 byte of padding
buf[2] = (uint8_t)msg->device_info.slot;
buf[3] = (uint8_t)msg->device_info.index;
// buf + 4: a byte for, code, padding, slot, index
buf16 = (uint16_t *)(buf + 4);
buf16[0] = abs;
buf16[1] = rel;
buf16[2] = key;
2022-10-07 18:36:53 -05:00
buf += 12;
2022-08-30 08:37:34 -05:00
// Back to 4 aligned
2022-08-30 08:37:34 -05:00
for (int i = 0; i < abs; i++) {
// buf + 4: 2 bytes for id and 2 bytes of padding
uint32_t *buf32 = (uint32_t *)(buf + 4);
2022-08-30 17:54:56 -05:00
*(uint16_t *)buf = msg->device_info.abs_id[i];
2022-08-30 08:37:34 -05:00
buf32[0] = msg->device_info.abs_min[i];
buf32[1] = msg->device_info.abs_max[i];
buf32[2] = msg->device_info.abs_fuzz[i];
buf32[3] = msg->device_info.abs_flat[i];
buf32[4] = msg->device_info.abs_res[i];
buf += 24;
2022-08-30 08:37:34 -05:00
}
// Still 4 aligned
2022-08-30 17:54:56 -05:00
for (int i = 0; i < rel; i++) {
*(uint16_t *)buf = msg->device_info.rel_id[i];
buf += 2;
}
2022-08-30 08:37:34 -05:00
2022-08-30 17:54:56 -05:00
for (int i = 0; i < key; i++) {
*(uint16_t *)buf = msg->device_info.key_id[i];
buf += 2;
}
2022-08-30 08:37:34 -05:00
2022-10-12 12:33:18 -05:00
size = MSS_DEVICE_INFO(abs, rel, key) + 1;
break;
2022-08-30 08:37:34 -05:00
case DeviceReport:
2022-08-30 11:28:29 -05:00
abs = msg->device_report.abs_count;
rel = msg->device_report.rel_count;
key = msg->device_report.key_count;
if (len < MSS_DEVICE_REPORT(abs, rel, key))
2022-08-30 08:37:34 -05:00
return -1;
2022-08-30 17:54:56 -05:00
2022-08-31 11:59:06 -05:00
buf[0] = (uint8_t)msg->code;
2023-03-18 12:41:17 -05:00
// 1 byte of padding
buf[2] = msg->device_report.slot;
buf[3] = msg->device_report.index;
// buf + 4: a byte for, code, padding, slot and index
buf16 = (uint16_t *)(buf + 4);
buf16[0] = abs;
buf16[1] = rel;
buf16[2] = key;
2022-10-07 18:36:53 -05:00
buf += 12;
// We're 4 aligned already
2022-08-30 11:28:29 -05:00
for (int i = 0; i < abs; i++) {
*(uint32_t *)buf = msg->device_report.abs[i];
buf += 4;
}
// Still 4 aligned
2022-08-30 11:28:29 -05:00
for (int i = 0; i < rel; i++) {
*(uint32_t *)buf = msg->device_report.rel[i];
buf += 4;
}
// Doesn't matter since we're writing individual bytes
2022-08-30 11:28:29 -05:00
for (int i = 0; i < key; i++)
*(buf++) = msg->device_report.key[i];
2022-10-12 12:33:18 -05:00
size = MSS_DEVICE_REPORT(abs, rel, key) + 1;
buf += align_4(key) - key;
break;
2022-08-30 08:37:34 -05:00
case ControllerState:
if (len < MSS_CONTROLLER_STATE)
return -1;
buf[0] = (uint8_t)msg->code;
2022-10-07 18:36:53 -05:00
*(uint16_t *)(buf + 2) = msg->controller_state.index;
buf[4] = msg->controller_state.led[0];
buf[5] = msg->controller_state.led[1];
buf[6] = msg->controller_state.led[2];
buf[7] = msg->controller_state.small_rumble;
buf[8] = msg->controller_state.big_rumble;
buf[9] = msg->controller_state.flash_on;
buf[10] = msg->controller_state.flash_off;
2022-10-12 15:28:50 -05:00
size = MSS_CONTROLLER_STATE + 1;
2022-10-12 12:33:18 -05:00
buf += size;
break;
2022-10-07 18:36:53 -05:00
case Request: {
int expected_len = MSS_REQUEST(msg->request.request_count);
if (len < expected_len)
return -1;
2023-03-18 10:31:33 -05:00
buf[0] = (uint8_t)msg->code;
buf += 2;
*(uint16_t *)buf = msg->request.request_count;
buf += 2;
2022-10-07 18:36:53 -05:00
for (int i = 0; i < msg->request.request_count; i++) {
2023-03-18 10:31:33 -05:00
uint16_t tag_count = msg->request.requests[i].count;
char **tags = msg->request.requests[i].tags;
*(uint16_t *)buf = tag_count;
buf += 2;
2022-10-07 18:36:53 -05:00
2023-03-18 10:31:33 -05:00
for (int j = 0; j < tag_count; j++) {
int str_len = strlen(tags[j]);
int byte_len = align_2(str_len);
expected_len += 2 + byte_len;
if (len < expected_len) {
return -1;
}
*(uint16_t *)buf = str_len;
buf += 2;
strncpy((char *)buf, tags[j], str_len);
buf += byte_len;
}
2022-10-07 18:36:53 -05:00
}
2023-03-18 10:31:33 -05:00
size = expected_len + 1;
2022-10-12 12:33:18 -05:00
break;
2022-10-07 18:36:53 -05:00
}
case DeviceDestroy:
if (len < MSS_DESTROY)
return -1;
buf[0] = (uint8_t)msg->code;
*(uint16_t *)(buf + 2) = msg->controller_state.index;
2022-10-12 15:28:50 -05:00
size = MSS_DESTROY + 1;
2022-10-12 12:33:18 -05:00
buf += size;
break;
2022-08-30 08:37:34 -05:00
default:
2022-08-30 11:28:29 -05:00
printf("ERR(msg_serialize): Trying to serialize unknown message of code %d\n", msg->code);
2022-08-30 08:37:34 -05:00
return -1;
2022-08-29 17:27:03 -05:00
}
2022-10-12 12:33:18 -05:00
2023-03-18 12:41:17 -05:00
if (align_m(size) + MAGIC_SIZE > len) {
2022-10-12 12:33:18 -05:00
return -1;
}
2023-03-18 12:41:17 -05:00
MAGIC_TYPE *mbuf = (MAGIC_TYPE *)align_m((uintptr_t)buf);
*mbuf = MAGIC_END;
2022-10-12 12:33:18 -05:00
2023-03-18 12:41:17 -05:00
return align_m(size) + MAGIC_SIZE * 2;
2022-08-29 17:27:03 -05:00
}
2022-10-07 18:36:53 -05:00
void msg_free(Message *msg) {
if (msg->code == Request) {
for (int i = 0; i < msg->request.request_count; i++) {
2023-03-18 10:31:33 -05:00
for (int j = 0; j < msg->request.requests[i].count; j++) {
free(msg->request.requests[i].tags[j]);
}
free(msg->request.requests[i].tags);
2022-10-07 18:36:53 -05:00
}
free(msg->request.requests);
}
}
2022-10-12 12:33:18 -05:00
2022-10-12 15:28:50 -05:00
void print_message_buffer(const uint8_t *buf, int len) {
2022-10-12 12:33:18 -05:00
bool last_beg = false;
for (int i = 0; i < len; i++) {
if (i + MAGIC_SIZE <= len) {
MAGIC_TYPE magic = *(MAGIC_TYPE *)(&buf[i]);
if (magic == MAGIC_BEG) {
printf(" \033[32m%08X\033[0m", magic);
i += MAGIC_SIZE - 1;
last_beg = true;
continue;
} else if (magic == MAGIC_END) {
printf(" \033[32m%08X\033[0m", magic);
i += MAGIC_SIZE - 1;
continue;
}
}
if (last_beg) {
last_beg = false;
printf(" \033[034m%02X\033[0m", buf[i]);
} else {
printf(" %02X", buf[i]);
}
}
}