2022-08-31 16:24:26 -05:00
|
|
|
#include "const.h"
|
2022-08-30 17:54:56 -05:00
|
|
|
#include "hid.h"
|
|
|
|
#include "net.h"
|
|
|
|
#include "util.h"
|
|
|
|
|
2022-08-31 11:59:06 -05:00
|
|
|
#include <linux/input-event-codes.h>
|
2022-08-30 08:37:34 -05:00
|
|
|
#include <linux/input.h>
|
2022-08-30 12:08:36 -05:00
|
|
|
#include <netinet/in.h>
|
2022-08-29 18:06:25 -05:00
|
|
|
#include <netinet/tcp.h>
|
2022-08-30 12:08:36 -05:00
|
|
|
#include <poll.h>
|
2022-08-29 18:06:25 -05:00
|
|
|
#include <pthread.h>
|
|
|
|
#include <stdint.h>
|
|
|
|
#include <stdio.h>
|
2022-08-30 12:08:36 -05:00
|
|
|
#include <stdlib.h>
|
2022-08-29 18:06:25 -05:00
|
|
|
#include <string.h>
|
|
|
|
#include <sys/socket.h>
|
2022-08-30 12:08:36 -05:00
|
|
|
#include <unistd.h>
|
2022-08-29 17:27:03 -05:00
|
|
|
|
2022-09-11 04:23:31 -05:00
|
|
|
// Arguments for a connection thread
|
2022-08-29 17:27:03 -05:00
|
|
|
struct Connection {
|
2022-08-29 18:06:25 -05:00
|
|
|
int socket;
|
2022-08-29 17:27:03 -05:00
|
|
|
uint32_t id;
|
|
|
|
};
|
|
|
|
|
2022-08-29 18:06:25 -05:00
|
|
|
void *server_handle_conn(void *args_) {
|
|
|
|
struct Connection *args = args_;
|
2022-08-29 17:27:03 -05:00
|
|
|
|
2022-08-30 08:37:34 -05:00
|
|
|
printf("CONN(%u): start\n", args->id);
|
2022-08-29 18:06:25 -05:00
|
|
|
|
2022-08-31 16:24:26 -05:00
|
|
|
if (setsockopt(args->socket, SOL_SOCKET, SO_KEEPALIVE, &TCP_KEEPALIVE_ENABLE, sizeof(int)) != 0)
|
2022-08-29 18:06:25 -05:00
|
|
|
printf("ERR(server_handle_conn): Enabling socket keepalives on client\n");
|
2022-08-31 16:24:26 -05:00
|
|
|
if (setsockopt(args->socket, SOL_TCP, TCP_KEEPIDLE, &TCP_KEEPALIVE_IDLE_TIME, sizeof(int)) != 0)
|
|
|
|
printf("ERR(server_handle_conn): Setting initial idle-time value\n");
|
|
|
|
if (setsockopt(args->socket, SOL_TCP, TCP_KEEPCNT, &TCP_KEEPALIVE_RETRY_COUNT, sizeof(int)) != 0)
|
2022-08-29 18:06:25 -05:00
|
|
|
printf("ERR(server_handle_conn): Setting idle retry count\n");
|
2022-08-31 16:24:26 -05:00
|
|
|
if (setsockopt(args->socket, SOL_TCP, TCP_KEEPINTVL, &TCP_KEEPALIVE_RETRY_INTERVAL, sizeof(int)) != 0)
|
2022-08-29 18:06:25 -05:00
|
|
|
printf("ERR(server_handle_conn): Setting idle retry interval\n");
|
|
|
|
|
2022-08-31 16:24:26 -05:00
|
|
|
uint8_t buf[2048] __attribute__((aligned(4))) = {};
|
|
|
|
|
|
|
|
PhysicalDevice dev = get_device();
|
2022-08-30 08:37:34 -05:00
|
|
|
printf("CONN(%u): got device '%s'\n", args->id, dev.name);
|
2022-08-29 18:06:25 -05:00
|
|
|
|
2022-08-31 11:54:14 -05:00
|
|
|
char *closing_message = "";
|
|
|
|
|
2022-08-30 08:37:34 -05:00
|
|
|
int len = msg_serialize(buf, 2048, (Message *)&dev.device_info);
|
2022-08-31 11:59:06 -05:00
|
|
|
if (len > 0) {
|
|
|
|
if (write(args->socket, buf, len) == -1) {
|
2022-08-31 11:54:14 -05:00
|
|
|
perror("SERVER: Couldn't send device info, ");
|
|
|
|
closing_message = "Socket error";
|
|
|
|
goto conn_end;
|
|
|
|
}
|
|
|
|
} else {
|
|
|
|
perror("SERVER: Couldn't serialize device info, ");
|
|
|
|
closing_message = "Device info error";
|
|
|
|
goto conn_end;
|
|
|
|
}
|
2022-08-29 18:06:25 -05:00
|
|
|
|
2022-08-30 11:28:29 -05:00
|
|
|
struct pollfd pfds[2] = {};
|
|
|
|
struct pollfd *socket_poll = &pfds[0];
|
|
|
|
struct pollfd *event_poll = &pfds[1];
|
|
|
|
|
|
|
|
socket_poll->fd = args->socket;
|
|
|
|
socket_poll->events = POLLIN;
|
|
|
|
event_poll->fd = dev.event;
|
|
|
|
event_poll->events = POLLIN;
|
|
|
|
|
|
|
|
MessageDeviceReport report = {};
|
2022-08-30 12:08:36 -05:00
|
|
|
|
|
|
|
report.code = DeviceReport;
|
2022-08-30 11:28:29 -05:00
|
|
|
report.abs_count = dev.device_info.abs_count;
|
|
|
|
report.rel_count = dev.device_info.rel_count;
|
|
|
|
report.key_count = dev.device_info.key_count;
|
2022-08-30 08:37:34 -05:00
|
|
|
|
|
|
|
while (1) {
|
2022-08-30 11:28:29 -05:00
|
|
|
int rc = poll(pfds, 2, -1);
|
2022-08-30 17:54:56 -05:00
|
|
|
if (rc < 0) { // error (connection closed)
|
|
|
|
closing_message = "Poll error";
|
|
|
|
goto conn_end;
|
|
|
|
}
|
|
|
|
|
|
|
|
// Shutdown connection if we lost the peer
|
|
|
|
if (socket_poll->revents & POLLHUP || socket_poll->revents & POLLERR) {
|
|
|
|
closing_message = "Lost peer";
|
2022-08-29 18:06:25 -05:00
|
|
|
goto conn_end;
|
2022-08-30 17:54:56 -05:00
|
|
|
}
|
2022-08-29 18:06:25 -05:00
|
|
|
|
2022-08-30 11:28:29 -05:00
|
|
|
if (socket_poll->revents & POLLIN) {
|
2022-08-30 08:37:34 -05:00
|
|
|
int len = recv(args->socket, buf, 2048, 0);
|
2022-08-30 17:54:56 -05:00
|
|
|
|
|
|
|
if (len <= 0) {
|
|
|
|
closing_message = "Lost peer";
|
2022-08-30 08:37:34 -05:00
|
|
|
goto conn_end;
|
2022-08-30 17:54:56 -05:00
|
|
|
}
|
2022-08-30 08:37:34 -05:00
|
|
|
|
|
|
|
Message msg;
|
|
|
|
if (msg_deserialize(buf, len, &msg) == 0) {
|
|
|
|
|
2022-08-30 11:28:29 -05:00
|
|
|
if (msg.code == ControllerState) {
|
|
|
|
apply_controller_state(&dev, (MessageControllerState *)&msg);
|
2022-08-30 08:37:34 -05:00
|
|
|
} else {
|
|
|
|
printf("CONN(%d): Illegal message\n", args->id);
|
|
|
|
}
|
|
|
|
|
|
|
|
} else {
|
|
|
|
printf("CONN(%d): Couldn't parse message.\n", args->id);
|
|
|
|
}
|
|
|
|
}
|
2022-08-30 17:54:56 -05:00
|
|
|
|
|
|
|
// Shutdown connection if we lost the device
|
|
|
|
if (event_poll->revents & POLLHUP || event_poll->revents & POLLERR) {
|
|
|
|
closing_message = "Lost device";
|
|
|
|
goto conn_end;
|
|
|
|
}
|
|
|
|
|
2022-08-30 11:28:29 -05:00
|
|
|
if (event_poll->revents & POLLIN) {
|
|
|
|
struct input_event event;
|
2022-08-30 17:54:56 -05:00
|
|
|
|
|
|
|
int len = read(dev.event, &event, sizeof(struct input_event));
|
|
|
|
|
|
|
|
if (len <= 0) {
|
|
|
|
closing_message = "Lost device";
|
2022-08-30 11:28:29 -05:00
|
|
|
goto conn_end;
|
2022-08-30 17:54:56 -05:00
|
|
|
}
|
|
|
|
|
2022-08-30 11:28:29 -05:00
|
|
|
if (len < sizeof(struct input_event)) {
|
|
|
|
printf("CONN(%d): error reading event\n", args->id);
|
|
|
|
continue;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (event.type == EV_SYN) {
|
|
|
|
int len = msg_serialize(buf, 2048, (Message *)&report);
|
|
|
|
|
|
|
|
if (len < 0) {
|
|
|
|
printf("CONN(%d): Couldn't serialize report %d\n", args->id, len);
|
|
|
|
continue;
|
|
|
|
};
|
|
|
|
|
|
|
|
write(args->socket, buf, len);
|
|
|
|
} else if (event.type == EV_ABS) {
|
|
|
|
int index = dev.mapping.abs_indices[event.code];
|
2022-08-29 18:06:25 -05:00
|
|
|
|
2022-08-30 11:28:29 -05:00
|
|
|
if (index < 0) {
|
|
|
|
printf("CONN(%d): Invalid abs\n", args->id);
|
|
|
|
continue;
|
|
|
|
};
|
|
|
|
|
|
|
|
report.abs[index] = event.value;
|
|
|
|
} else if (event.type == EV_REL) {
|
|
|
|
int index = dev.mapping.rel_indices[event.code];
|
|
|
|
|
|
|
|
if (index < 0) {
|
|
|
|
printf("CONN(%d): Invalid rel\n", args->id);
|
|
|
|
continue;
|
|
|
|
};
|
|
|
|
|
|
|
|
report.rel[index] = event.value;
|
|
|
|
} else if (event.type == EV_KEY) {
|
|
|
|
int index = dev.mapping.key_indices[event.code];
|
|
|
|
|
|
|
|
if (index < 0) {
|
|
|
|
printf("CONN(%d): Invalid key\n", args->id);
|
|
|
|
continue;
|
|
|
|
};
|
|
|
|
report.key[index] = !!event.value;
|
|
|
|
}
|
2022-08-29 17:27:03 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2022-08-29 18:06:25 -05:00
|
|
|
conn_end:
|
2022-08-30 08:37:34 -05:00
|
|
|
shutdown(args->socket, SHUT_RDWR);
|
2022-08-30 17:54:56 -05:00
|
|
|
printf("CONN(%u): connection closed (%s)\n", args->id, closing_message);
|
2022-08-29 18:06:25 -05:00
|
|
|
return_device(&dev);
|
2022-08-29 17:27:03 -05:00
|
|
|
free(args);
|
|
|
|
return NULL;
|
|
|
|
}
|
|
|
|
|
|
|
|
void server_run(uint16_t port) {
|
2022-08-30 17:54:56 -05:00
|
|
|
printf("SERVER: start\n");
|
2022-08-29 18:06:25 -05:00
|
|
|
|
2022-08-29 17:27:03 -05:00
|
|
|
int sock = socket(AF_INET, SOCK_STREAM, 0);
|
2022-08-31 16:24:26 -05:00
|
|
|
if (sock < 0) {
|
2022-08-29 18:06:25 -05:00
|
|
|
panicf("Couldn't open socket\n");
|
2022-08-31 16:24:26 -05:00
|
|
|
}
|
2022-08-29 18:06:25 -05:00
|
|
|
|
2022-08-29 17:27:03 -05:00
|
|
|
struct sockaddr_in addr = {};
|
2022-08-29 18:06:25 -05:00
|
|
|
addr.sin_family = AF_INET;
|
|
|
|
addr.sin_addr.s_addr = htonl(INADDR_ANY);
|
|
|
|
addr.sin_port = htons(port);
|
|
|
|
|
2022-08-31 16:24:26 -05:00
|
|
|
if (bind(sock, (struct sockaddr *)&addr, sizeof(addr)) != 0) {
|
2022-08-29 17:27:03 -05:00
|
|
|
panicf("Couldn't bind to the socket\n");
|
2022-08-31 16:24:26 -05:00
|
|
|
}
|
2022-08-29 18:06:25 -05:00
|
|
|
|
2022-08-31 16:24:26 -05:00
|
|
|
if (listen(sock, 16) != 0) {
|
2022-08-29 17:27:03 -05:00
|
|
|
panicf("Couldn't listen on socket\n");
|
2022-08-31 16:24:26 -05:00
|
|
|
}
|
2022-08-29 17:27:03 -05:00
|
|
|
|
|
|
|
uint32_t ids = 0;
|
2022-08-29 18:06:25 -05:00
|
|
|
while (1) {
|
|
|
|
struct sockaddr con_addr;
|
|
|
|
socklen_t con_len = sizeof(con_addr);
|
2022-08-29 17:27:03 -05:00
|
|
|
struct Connection conn;
|
|
|
|
|
|
|
|
conn.socket = accept(sock, &con_addr, &con_len);
|
|
|
|
|
2022-08-29 18:06:25 -05:00
|
|
|
if (conn.socket >= 0) {
|
2022-08-30 17:54:56 -05:00
|
|
|
printf("SERVER: got connection\n");
|
2022-08-29 17:27:03 -05:00
|
|
|
|
|
|
|
conn.id = ids++;
|
|
|
|
|
2022-08-29 18:06:25 -05:00
|
|
|
struct Connection *conn_ptr = malloc(sizeof(struct Connection));
|
2022-08-29 17:27:03 -05:00
|
|
|
memcpy(conn_ptr, &conn, sizeof(struct Connection));
|
|
|
|
|
|
|
|
pthread_t thread;
|
|
|
|
pthread_create(&thread, NULL, server_handle_conn, conn_ptr);
|
|
|
|
} else {
|
|
|
|
printf("Couldn't accept connection (%d)\n", conn.socket);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|