aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/src/msg.c
diff options
context:
space:
mode:
authorEgor Tensin <Egor.Tensin@gmail.com>2022-08-28 15:14:07 +0200
committerEgor Tensin <Egor.Tensin@gmail.com>2022-08-28 15:14:07 +0200
commit0ff63a9ceff4c8fcd679b52cb1c03d96675f52f0 (patch)
tree2b0d1fb32b09988f652228a40508dbcef9c1032e /src/msg.c
parentnet: use MSG_NOSIGNAL (diff)
downloadcimple-0ff63a9ceff4c8fcd679b52cb1c03d96675f52f0.tar.gz
cimple-0ff63a9ceff4c8fcd679b52cb1c03d96675f52f0.zip
holy crap, it actually kinda works now
Previously, I had a stupid system where I would create a thread after every accept(), and put worker descriptors in a queue. A special "scheduler" thread would then pick them out, and give out jobs to complete. The problem was, of course, I couldn't conveniently poll job status from workers. I thought about using poll(), but that turned out to be a horribly complicated API. How do I deal with partial reads, for example? I don't honestly know. Then it hit me that I could just use the threads that handle accept()ed connections as "worker threads", which would synchronously schedule jobs and wait for them to complete. This solves every problem and removes the need for a lot of inter-thread synchronization magic. It even works now, holy crap! You can launch and terminate workers at will, and they will pick up new jobs automatically. As a side not, msg_recv_and_handle turned out to be too limiting and complicated for me, so I got rid of that, and do normal msg_recv/msg_send calls.
Diffstat (limited to 'src/msg.c')
-rw-r--r--src/msg.c55
1 files changed, 27 insertions, 28 deletions
diff --git a/src/msg.c b/src/msg.c
index 863d141..c37cfb5 100644
--- a/src/msg.c
+++ b/src/msg.c
@@ -5,6 +5,28 @@
#include <stdlib.h>
#include <string.h>
+void msg_success(struct msg *msg)
+{
+ msg->argc = 0;
+ msg->argv = NULL;
+}
+
+void msg_error(struct msg *msg)
+{
+ msg->argc = -1;
+ msg->argv = NULL;
+}
+
+int msg_is_success(const struct msg *msg)
+{
+ return msg->argc == 0;
+}
+
+int msg_is_error(const struct msg *msg)
+{
+ return msg->argc < 0;
+}
+
static int msg_copy_argv(struct msg *msg, char **argv)
{
msg->argv = calloc(msg->argc, sizeof(char *));
@@ -147,15 +169,15 @@ free_buf:
return ret;
}
-int msg_send_and_wait(int fd, const struct msg *msg, int *result)
+int msg_send_and_wait(int fd, const struct msg *request, struct msg *response)
{
int ret = 0;
- ret = msg_send(fd, msg);
+ ret = msg_send(fd, request);
if (ret < 0)
return ret;
- ret = net_recv_static(fd, result, sizeof(*result));
+ ret = msg_recv(fd, response);
if (ret < 0)
return ret;
@@ -184,32 +206,9 @@ free_buf:
return ret;
}
-int msg_recv_and_handle(int fd, msg_handler handler, void *arg)
-{
- struct msg msg;
- int result;
- int ret = 0;
-
- ret = msg_recv(fd, &msg);
- if (ret < 0)
- return ret;
-
- result = handler(&msg, arg);
-
- ret = net_send_buf(fd, &result, sizeof(result));
- if (ret < 0)
- goto free_msg;
-
-free_msg:
- msg_free(&msg);
-
- return ret;
-}
-
-int msg_dump_unknown(const struct msg *msg)
+void msg_dump(const struct msg *msg)
{
- print_log("Received an unknown message:\n");
+ print_log("Message[%d]:\n", msg->argc);
for (int i = 0; i < msg->argc; ++i)
print_log("\t%s\n", msg->argv[i]);
- return -1;
}