aboutsummaryrefslogtreecommitdiffstats
path: root/src/daemon.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/daemon.c')
-rw-r--r--src/daemon.c153
1 files changed, 22 insertions, 131 deletions
diff --git a/src/daemon.c b/src/daemon.c
index 8c1269e..44c3c11 100644
--- a/src/daemon.c
+++ b/src/daemon.c
@@ -11,10 +11,10 @@
#include "daemon.h"
#include "loop.h"
+#include "protocol.h"
+#include "socket.h"
#include "term.h"
-static int runes_daemon_open_socket(char *sock_name);
-static void runes_daemon_close_socket(RunesDaemon *sock);
static int runes_daemon_handle_request(void *t);
RunesDaemon *runes_daemon_new(RunesLoop *loop, RunesWindowBackend *wb)
@@ -25,7 +25,7 @@ RunesDaemon *runes_daemon_new(RunesLoop *loop, RunesWindowBackend *wb)
daemon->loop = loop;
daemon->wb = wb;
daemon->sock_name = runes_get_daemon_socket_name();
- daemon->sock = runes_daemon_open_socket(daemon->sock_name);
+ daemon->sock = runes_socket_server_open(daemon->sock_name);
runes_daemon_init_loop(daemon, loop);
return daemon;
@@ -39,151 +39,42 @@ void runes_daemon_init_loop(RunesDaemon *daemon, RunesLoop *loop)
void runes_socket_delete(RunesDaemon *daemon)
{
- runes_daemon_close_socket(daemon);
+ runes_socket_server_close(daemon->sock, daemon->sock_name);
free(daemon->sock_name);
free(daemon);
}
-static int runes_daemon_open_socket(char *sock_name)
-{
- char *dir, *slash;
- int s;
- struct sockaddr_un server;
-
- if (strlen(sock_name) + 1 > MAX_SOCKET_PATH_LEN) {
- runes_die("socket path %s is too long", sock_name);
- }
-
- dir = strdup(sock_name);
- slash = strrchr(dir, '/');
- if (slash == NULL) {
- runes_die("socket path %s must be an absolute path", sock_name);
- }
- *slash = '\0';
- runes_mkdir_p(dir);
- free(dir);
-
- unlink(sock_name);
-
- s = socket(AF_UNIX, SOCK_STREAM, 0);
- if (s < 0) {
- runes_die("couldn't create socket: %s", strerror(errno));
- }
-
- server.sun_family = AF_UNIX;
- strcpy(server.sun_path, sock_name);
- if (bind(s, (struct sockaddr*)(&server), sizeof(struct sockaddr_un))) {
- runes_die("couldn't bind to socket %s: %s", sock_name,
- strerror(errno));
- }
-
- if (chmod(sock_name, S_IRUSR|S_IWUSR)) {
- runes_die("couldn't chmod socket %s: %s", sock_name,
- strerror(errno));
- }
-
- if (listen(s, 5)) {
- runes_die("couldn't listen on socket %s: %s", sock_name,
- strerror(errno));
- }
-
- return s;
-}
-
-static void runes_daemon_close_socket(RunesDaemon *daemon)
-{
- close(daemon->sock);
- unlink(daemon->sock_name);
-}
-
static int runes_daemon_handle_request(void *t)
{
RunesDaemon *daemon = (RunesDaemon *)t;
- struct sockaddr_un client;
- socklen_t len = sizeof(client);
- ssize_t bytes;
- uint32_t argc, argv_len;
- char **argv, *argv_buf;
-
- daemon->client_sock = accept(
- daemon->sock, (struct sockaddr*)(&client), &len);
- if (daemon->client_sock < 0) {
- runes_die("couldn't accept connection: %s", strerror(errno));
- }
+ int client_sock;
+ char *buf;
+ size_t len;
+ struct runes_protocol_message msg;
+ RunesTerm *new_term;
- bytes = recv(daemon->client_sock, (void*)(&argc), sizeof(argc), 0);
- if (bytes < (int)sizeof(argc)) {
- runes_warn("invalid message received: got %d bytes, expected 4",
- bytes);
- close(daemon->client_sock);
- return 1;
- }
+ client_sock = runes_socket_server_accept(daemon->sock);
- argc = ntohl(argc);
- if (argc > 1024) {
- runes_warn("invalid message received: argc = %d, must be < 1024",
- argc);
- close(daemon->client_sock);
- return 1;
- }
- argv = malloc(argc * sizeof(char*));
-
- bytes = recv(daemon->client_sock, (void*)(&argv_len), sizeof(argv_len), 0);
- if (bytes < (int)sizeof(argc)) {
- runes_warn("invalid message received: got %d bytes, expected 4",
- bytes);
- close(daemon->client_sock);
- free(argv);
+ if (!runes_protocol_read_packet(client_sock, &buf, &len)) {
+ runes_warn("invalid packet received");
return 1;
}
- argv_len = ntohl(argv_len);
- if (argv_len > 131072) {
- runes_warn("invalid message received: argv_len = %d, must be < %d",
- argv_len, 131072);
- close(daemon->client_sock);
- free(argv);
- return 1;
- }
- argv_buf = malloc(argv_len + 1);
-
- bytes = recv(daemon->client_sock, argv_buf, argv_len, 0);
- if (bytes < argv_len) {
- runes_warn("invalid message received: got %d bytes, expected %d",
- bytes, argv_len);
- close(daemon->client_sock);
- free(argv);
- free(argv_buf);
+ runes_socket_client_close(client_sock);
+
+ if (!runes_protocol_parse_message(buf, len, &msg)) {
+ runes_warn("couldn't parse message from client");
+ free(buf);
return 1;
}
- close(daemon->client_sock);
-
- if (argc > 0) {
- size_t offset = 0;
- int i;
-
- for (i = 0; i < (int)argc; ++i) {
- char *next_null;
-
- if (offset >= argv_len) {
- runes_die("args in argv_buf don't match argc of %d", argc);
- }
- argv[i] = argv_buf + offset;
- next_null = memchr(argv_buf + offset, '\0', argv_len - offset);
- if (!next_null) {
- runes_die("args in argv_buf don't match argc of %d", argc);
- }
- offset = next_null - argv_buf + 1;
- }
-
- runes_term_register_with_loop(
- runes_term_new(argc, argv, NULL, NULL, daemon->wb), daemon->loop);
- }
+ new_term = runes_term_new(
+ msg.argc, msg.argv, msg.envp, msg.cwd, daemon->wb);
+ runes_term_register_with_loop(new_term, daemon->loop);
- free(argv);
- free(argv_buf);
+ free(buf);
+ runes_protocol_free_message(&msg);
return 1;
}