minecraft-pi-reborn/media-layer/proxy/src/client/client.cpp

105 lines
2.8 KiB
C++
Raw Normal View History

2021-06-17 21:32:24 +00:00
#include <vector>
#include <cerrno>
#include <unistd.h>
#include <cstring>
#include <sys/prctl.h>
#include <csignal>
2022-05-14 02:36:12 +00:00
#include <exception>
2021-06-17 21:32:24 +00:00
#include "../common/common.h"
// Store Handlers
2022-07-13 21:02:18 +00:00
#define MAX_HANDLERS 100
static proxy_handler_t handlers[MAX_HANDLERS];
2021-06-17 21:32:24 +00:00
void _add_handler(unsigned char unique_id, proxy_handler_t handler) {
2022-07-13 21:02:18 +00:00
if (unique_id >= MAX_HANDLERS) {
PROXY_ERR("ID Too Big: %i", (int) unique_id);
2021-06-17 21:32:24 +00:00
}
2022-07-13 21:02:18 +00:00
if (handlers[unique_id] != NULL) {
PROXY_ERR("Duplicate ID: %i", (int) unique_id);
2021-06-17 21:32:24 +00:00
}
2022-06-04 02:25:22 +00:00
handlers[unique_id] = handler;
2021-06-17 21:32:24 +00:00
}
// Store Parent PID
static int parent_is_alive = 1;
static void sigusr1_handler(__attribute__((unused)) int sig) {
// Mark Parent As Dead
parent_is_alive = 0;
}
// Check State Of Proxy And Exit If Invalid
void _check_proxy_state() {
// Check Server State
if (!parent_is_alive) {
void_write_cache(); // Parent Is Dead, No Reason To Send A Dead Process Data
2022-04-15 01:12:42 +00:00
PROXY_ERR("Server Terminated");
2021-06-17 21:32:24 +00:00
}
}
2022-05-14 02:36:12 +00:00
// Exit Handler
static volatile int exit_requested = 0;
static void exit_handler(__attribute__((unused)) int signal_id) {
// Request Exit
exit_requested = 1;
}
2021-06-17 21:32:24 +00:00
// Main
int main(int argc, char *argv[]) {
2022-05-14 02:36:12 +00:00
// Install Signal Handlers
2022-06-04 02:25:22 +00:00
signal(SIGINT, SIG_IGN);
2022-05-14 02:36:12 +00:00
struct sigaction act_sigterm;
memset((void *) &act_sigterm, 0, sizeof (struct sigaction));
act_sigterm.sa_handler = &exit_handler;
sigaction(SIGTERM, &act_sigterm, NULL);
2021-06-17 21:32:24 +00:00
// Send Signal On Parent Death To Interrupt Connection Read/Write And Exit
prctl(PR_SET_PDEATHSIG, SIGUSR1);
struct sigaction sa;
2022-05-14 02:36:12 +00:00
memset((void *) &sa, 0, sizeof (struct sigaction));
2021-06-17 21:32:24 +00:00
sa.sa_flags = SA_NOCLDSTOP;
sa.sa_handler = &sigusr1_handler;
if (sigaction(SIGUSR1, &sa, NULL) == -1) {
PROXY_ERR("Unable To Install Signal Handler: %s", strerror(errno));
}
// Get Connection
if (argc != 3) {
2022-04-15 01:12:42 +00:00
PROXY_ERR("Invalid Arguments");
2021-06-17 21:32:24 +00:00
}
char *read_str = argv[1];
char *write_str = argv[2];
set_connection(atoi(read_str), atoi(write_str));
2022-04-15 01:12:42 +00:00
PROXY_INFO("Connected");
2021-06-17 21:32:24 +00:00
// Send Connection Message
write_string((char *) CONNECTED_MSG);
2021-06-23 21:52:31 +00:00
flush_write_cache();
2021-06-17 21:32:24 +00:00
// Loop
int running = is_connection_open();
2022-05-14 02:36:12 +00:00
while (running && !exit_requested) {
2021-06-17 21:32:24 +00:00
unsigned char unique_id = read_byte();
2022-07-13 21:02:18 +00:00
if (handlers[unique_id] != NULL) {
2021-06-17 21:32:24 +00:00
// Run Method
2022-06-04 02:25:22 +00:00
handlers[unique_id]();
2021-06-17 21:32:24 +00:00
// Check If Connection Is Still Open
if (!is_connection_open()) {
// Exit
running = 0;
2021-06-23 21:52:31 +00:00
} else {
// Flush Write Cache
flush_write_cache();
2021-06-17 21:32:24 +00:00
}
} else {
PROXY_ERR("Invalid Method ID: %i", (int) unique_id);
}
}
2022-05-14 02:36:12 +00:00
if (is_connection_open()) {
close_connection();
}
2021-06-17 21:32:24 +00:00
// Exit
2022-04-15 01:12:42 +00:00
PROXY_INFO("Stopped");
2021-06-17 21:32:24 +00:00
return 0;
}