annotate req.c @ 0:f1de39079243

misc: initial import
author David Demelier <markand@malikania.fr>
date Mon, 07 Jun 2021 09:41:37 +0200
parents
children 5afdb14df924
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
0
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
1 #define _BSD_SOURCE
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
2 #include <sys/socket.h>
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
3 #include <sys/time.h>
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
4 #include <sys/un.h>
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
5 #include <assert.h>
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
6 #include <errno.h>
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
7 #include <stdarg.h>
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
8 #include <stdio.h>
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
9 #include <string.h>
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
10 #include <unistd.h>
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
11
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
12 #include "req.h"
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
13 #include "project.h"
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
14 #include "worker.h"
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
15
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
16 static int sock;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
17
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
18 static struct req
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
19 ask(const char *fmt, ...)
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
20 {
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
21 assert(fmt);
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
22
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
23 struct req res = {0};
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
24 char buf[1024], *p;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
25 va_list ap;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
26 ssize_t bufsz = 0, nr;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
27
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
28 va_start(ap, fmt);
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
29 vsnprintf(buf, sizeof (buf), fmt, ap);
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
30 va_end(ap);
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
31
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
32 if (strlcat(buf, "\r\n\r\n", sizeof (buf)) >= sizeof (buf)) {
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
33 res.status = EMSGSIZE;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
34 return res;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
35 }
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
36
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
37 if (send(sock, buf, strlen(buf), MSG_NOSIGNAL) < 0) {
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
38 res.status = errno;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
39 return res;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
40 }
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
41
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
42 while ((nr = recv(sock, buf + bufsz, sizeof (buf) - bufsz, 0)) > 0) {
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
43 bufsz += nr;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
44
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
45 if ((size_t)bufsz >= sizeof (buf)) {
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
46 bufsz = 0;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
47 res.status = EMSGSIZE;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
48 break;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
49 }
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
50 }
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
51
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
52 buf[bufsz] = '\0';
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
53
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
54 /* Remove final '\r\n\r\n' */
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
55 if ((p = strstr(buf, "\r\n\r\n")))
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
56 *p = '\0';
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
57
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
58 /* Check and remove status. */
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
59 if (strncmp(buf, "ERR", 3) == 0)
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
60 res.status = -1;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
61 if ((p = strchr(buf, '\n')))
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
62 ++p;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
63 else
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
64 p = buf;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
65
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
66 strlcat(res.msg, p, sizeof (res.msg));
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
67
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
68 return res;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
69 }
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
70
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
71 int
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
72 req_connect(const char *path)
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
73 {
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
74 assert(path);
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
75
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
76 struct sockaddr_un sun;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
77 struct timeval tv = { .tv_sec = 3 };
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
78
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
79 if ((sock = socket(PF_LOCAL, SOCK_STREAM, 0)) < 0)
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
80 return -1;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
81
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
82 sun.sun_family = PF_LOCAL;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
83 strlcpy(sun.sun_path, path, sizeof (sun.sun_path));
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
84
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
85 if (setsockopt(sock, SOL_SOCKET, SO_RCVTIMEO, &tv, sizeof (tv)) < 0 ||
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
86 setsockopt(sock, SOL_SOCKET, SO_SNDTIMEO, &tv, sizeof (tv)) < 0)
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
87 return -1;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
88 if (connect(sock, (const struct sockaddr *)&sun, sizeof (sun)) < 0)
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
89 return -1;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
90
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
91 return 0;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
92 }
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
93
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
94 struct req
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
95 req_job_queue(const char *project, const char *tag)
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
96 {
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
97 assert(project);
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
98 assert(tag);
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
99
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
100 return ask("job-queue %s|%s", project, tag);
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
101 }
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
102
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
103 struct req
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
104 req_project_add(const struct project *p)
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
105 {
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
106 assert(p);
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
107
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
108 return ask("project-add %s|%s|%s|%s", p->name, p->desc, p->url, p->script);
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
109 }
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
110
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
111 struct req
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
112 req_project_list(struct project *pc, size_t *pcsz)
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
113 {
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
114 assert(pc);
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
115 assert(pcsz);
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
116
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
117 struct req req;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
118 char fmt[128], *token, *p = req.msg;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
119 size_t tot = 0;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
120
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
121 if ((req = ask("project-list")).status)
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
122 return req;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
123
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
124 snprintf(fmt, sizeof (fmt), "%%%zu[^|]|%%%zu[^|]|%%%zu[^|]|%%%zu[^\n]\n",
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
125 sizeof (pc->name), sizeof (pc->desc), sizeof (pc->url), sizeof (pc->script));
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
126
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
127 while ((token = strtok_r(p, "\n", &p)) && tot < *pcsz) {
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
128 if (sscanf(token, fmt, pc->name, pc->desc, pc->url, pc->script) == 4) {
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
129 ++pc;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
130 ++tot;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
131 }
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
132 }
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
133
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
134 *pcsz = tot;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
135
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
136 return req;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
137 }
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
138
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
139 struct req
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
140 req_worker_add(const struct worker *w)
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
141 {
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
142 assert(w);
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
143
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
144 return ask("worker-add %s|%s", w->name, w->desc);
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
145 }
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
146
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
147 struct req
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
148 req_worker_list(struct worker *wk, size_t *wksz)
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
149 {
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
150 assert(wk);
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
151 assert(wksz);
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
152
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
153 struct req req;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
154 char fmt[128], *token, *p = req.msg;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
155 size_t tot = 0;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
156
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
157 if ((req = ask("worker-list")).status)
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
158 return req;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
159
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
160 snprintf(fmt, sizeof (fmt), "%%%zu[^|]|%%%zu[^\n]\n",
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
161 sizeof (wk->name), sizeof (wk->desc));
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
162
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
163 while ((token = strtok_r(p, "\n", &p)) && tot < *wksz) {
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
164 if (sscanf(token, fmt, wk->name, wk->desc) == 2) {
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
165 wk++;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
166 tot++;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
167 }
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
168 }
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
169
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
170 *wksz = tot;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
171
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
172 return req;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
173 }
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
174
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
175 void
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
176 req_finish(void)
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
177 {
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
178 close(sock);
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
179 sock = 0;
f1de39079243 misc: initial import
David Demelier <markand@malikania.fr>
parents:
diff changeset
180 }