chiark / gitweb /
bus: enable SO_PASSCRED only if we are not connected to a bus
[elogind.git] / src / libsystemd-bus / bus-socket.c
1 /*-*- Mode: C; c-basic-offset: 8; indent-tabs-mode: nil -*-*/
2
3 /***
4   This file is part of systemd.
5
6   Copyright 2013 Lennart Poettering
7
8   systemd is free software; you can redistribute it and/or modify it
9   under the terms of the GNU Lesser General Public License as published by
10   the Free Software Foundation; either version 2.1 of the License, or
11   (at your option) any later version.
12
13   systemd is distributed in the hope that it will be useful, but
14   WITHOUT ANY WARRANTY; without even the implied warranty of
15   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16   Lesser General Public License for more details.
17
18   You should have received a copy of the GNU Lesser General Public License
19   along with systemd; If not, see <http://www.gnu.org/licenses/>.
20 ***/
21
22 #include <endian.h>
23 #include <assert.h>
24 #include <stdlib.h>
25 #include <unistd.h>
26 #include <sys/poll.h>
27 #include <byteswap.h>
28
29 #include "util.h"
30 #include "macro.h"
31 #include "missing.h"
32 #include "strv.h"
33
34 #include "sd-bus.h"
35 #include "bus-socket.h"
36 #include "bus-internal.h"
37 #include "bus-message.h"
38
39 static void iovec_advance(struct iovec *iov, unsigned *idx, size_t size) {
40
41         while (size > 0) {
42                 struct iovec *i = iov + *idx;
43
44                 if (i->iov_len > size) {
45                         i->iov_base = (uint8_t*) i->iov_base + size;
46                         i->iov_len -= size;
47                         return;
48                 }
49
50                 size -= i->iov_len;
51
52                 i->iov_base = NULL;
53                 i->iov_len = 0;
54
55                 (*idx) ++;
56         }
57 }
58
59 static int bus_socket_write_auth(sd_bus *b) {
60         struct msghdr mh;
61         ssize_t k;
62
63         assert(b);
64         assert(b->state == BUS_AUTHENTICATING);
65
66         if (b->auth_index >= ELEMENTSOF(b->auth_iovec))
67                 return 0;
68
69         if (b->auth_timeout == 0)
70                 b->auth_timeout = now(CLOCK_MONOTONIC) + BUS_DEFAULT_TIMEOUT;
71
72         zero(mh);
73         mh.msg_iov = b->auth_iovec + b->auth_index;
74         mh.msg_iovlen = ELEMENTSOF(b->auth_iovec) - b->auth_index;
75
76         k = sendmsg(b->fd, &mh, MSG_DONTWAIT|MSG_NOSIGNAL);
77         if (k < 0)
78                 return errno == EAGAIN ? 0 : -errno;
79
80         iovec_advance(b->auth_iovec, &b->auth_index, (size_t) k);
81
82         return 1;
83 }
84
85 static int bus_socket_auth_verify(sd_bus *b) {
86         char *e, *f, *start;
87         sd_id128_t peer;
88         unsigned i;
89         int r;
90
91         /* We expect two response lines: "OK" and possibly
92          * "AGREE_UNIX_FD" */
93
94         e = memmem(b->rbuffer, b->rbuffer_size, "\r\n", 2);
95         if (!e)
96                 return 0;
97
98         if (b->negotiate_fds) {
99                 f = memmem(e + 2, b->rbuffer_size - (e - (char*) b->rbuffer) - 2, "\r\n", 2);
100                 if (!f)
101                         return 0;
102
103                 start = f + 2;
104         } else {
105                 f = NULL;
106                 start = e + 2;
107         }
108
109         /* Nice! We got all the lines we need. First check the OK
110          * line */
111
112         if (e - (char*) b->rbuffer != 3 + 32)
113                 return -EPERM;
114
115         if (memcmp(b->rbuffer, "OK ", 3))
116                 return -EPERM;
117
118         for (i = 0; i < 32; i += 2) {
119                 int x, y;
120
121                 x = unhexchar(((char*) b->rbuffer)[3 + i]);
122                 y = unhexchar(((char*) b->rbuffer)[3 + i + 1]);
123
124                 if (x < 0 || y < 0)
125                         return -EINVAL;
126
127                 peer.bytes[i/2] = ((uint8_t) x << 4 | (uint8_t) y);
128         }
129
130         if (!sd_id128_equal(b->peer, SD_ID128_NULL) &&
131             !sd_id128_equal(b->peer, peer))
132                 return -EPERM;
133
134         b->peer = peer;
135
136         /* And possibly check the second line, too */
137
138         if (f)
139                 b->can_fds =
140                         (f - e == sizeof("\r\nAGREE_UNIX_FD") - 1) &&
141                         memcmp(e + 2, "AGREE_UNIX_FD", sizeof("AGREE_UNIX_FD") - 1) == 0;
142
143         b->rbuffer_size -= (start - (char*) b->rbuffer);
144         memmove(b->rbuffer, start, b->rbuffer_size);
145
146         r = bus_start_running(b);
147         if (r < 0)
148                 return r;
149
150         return 1;
151 }
152
153 static int bus_socket_read_auth(sd_bus *b) {
154         struct msghdr mh;
155         struct iovec iov;
156         size_t n;
157         ssize_t k;
158         int r;
159         void *p;
160
161         assert(b);
162
163         r = bus_socket_auth_verify(b);
164         if (r != 0)
165                 return r;
166
167         n = MAX(3 + 32 + 2 + sizeof("AGREE_UNIX_FD") - 1 + 2, b->rbuffer_size * 2);
168
169         if (n > BUS_AUTH_SIZE_MAX)
170                 n = BUS_AUTH_SIZE_MAX;
171
172         if (b->rbuffer_size >= n)
173                 return -ENOBUFS;
174
175         p = realloc(b->rbuffer, n);
176         if (!p)
177                 return -ENOMEM;
178
179         b->rbuffer = p;
180
181         zero(iov);
182         iov.iov_base = (uint8_t*) b->rbuffer + b->rbuffer_size;
183         iov.iov_len = n - b->rbuffer_size;
184
185         zero(mh);
186         mh.msg_iov = &iov;
187         mh.msg_iovlen = 1;
188
189         k = recvmsg(b->fd, &mh, MSG_DONTWAIT|MSG_NOSIGNAL);
190         if (k < 0)
191                 return errno == EAGAIN ? 0 : -errno;
192         if (k == 0)
193                 return -ECONNRESET;
194
195         b->rbuffer_size += k;
196
197         r = bus_socket_auth_verify(b);
198         if (r != 0)
199                 return r;
200
201         return 1;
202 }
203
204 static int bus_socket_setup(sd_bus *b) {
205         int enable;
206
207         assert(b);
208
209         /* Enable SO_PASSCRED + SO_PASSEC. We try this on any
210          * socket, just in case. */
211         enable = !b->bus_client;
212         setsockopt(b->fd, SOL_SOCKET, SO_PASSCRED, &enable, sizeof(enable));
213         setsockopt(b->fd, SOL_SOCKET, SO_PASSSEC, &enable, sizeof(enable));
214
215         /* Increase the buffers to a MB */
216         fd_inc_rcvbuf(b->fd, 1024*1024);
217         fd_inc_sndbuf(b->fd, 1024*1024);
218
219         return 0;
220 }
221
222 static int bus_socket_start_auth(sd_bus *b) {
223         static const char auth_prefix[] = "\0AUTH EXTERNAL ";
224         static const char auth_suffix_with_unix_fd[] = "\r\nNEGOTIATE_UNIX_FD\r\nBEGIN\r\n";
225         static const char auth_suffix_without_unix_fd[] = "\r\nBEGIN\r\n";
226
227         char text[20 + 1]; /* enough space for a 64bit integer plus NUL */
228         size_t l;
229         const char *auth_suffix;
230         int domain = 0, r;
231         socklen_t sl;
232
233         assert(b);
234
235         b->state = BUS_AUTHENTICATING;
236
237         sl = sizeof(domain);
238         r = getsockopt(b->fd, SOL_SOCKET, SO_DOMAIN, &domain, &sl);
239         if (r < 0)
240                 return -errno;
241
242         if (domain != AF_UNIX)
243                 b->negotiate_fds = false;
244
245         snprintf(text, sizeof(text), "%llu", (unsigned long long) geteuid());
246         char_array_0(text);
247
248         l = strlen(text);
249         b->auth_uid = hexmem(text, l);
250         if (!b->auth_uid)
251                 return -ENOMEM;
252
253         auth_suffix = b->negotiate_fds ? auth_suffix_with_unix_fd : auth_suffix_without_unix_fd;
254
255         b->auth_iovec[0].iov_base = (void*) auth_prefix;
256         b->auth_iovec[0].iov_len = sizeof(auth_prefix) -1;
257         b->auth_iovec[1].iov_base = (void*) b->auth_uid;
258         b->auth_iovec[1].iov_len = l * 2;
259         b->auth_iovec[2].iov_base = (void*) auth_suffix;
260         b->auth_iovec[2].iov_len = strlen(auth_suffix);
261         b->auth_size = sizeof(auth_prefix) - 1 + l * 2 + sizeof(auth_suffix) - 1;
262
263         return bus_socket_write_auth(b);
264 }
265
266 int bus_socket_connect(sd_bus *b) {
267         int r;
268
269         assert(b);
270         assert(b->fd < 0);
271         assert(b->sockaddr.sa.sa_family != AF_UNSPEC);
272
273         b->fd = socket(b->sockaddr.sa.sa_family, SOCK_STREAM|SOCK_CLOEXEC|SOCK_NONBLOCK, 0);
274         if (b->fd < 0)
275                 return -errno;
276
277         r = bus_socket_setup(b);
278         if (r < 0)
279                 return r;
280
281         r = connect(b->fd, &b->sockaddr.sa, b->sockaddr_size);
282         if (r < 0) {
283                 if (errno == EINPROGRESS)
284                         return 1;
285
286                 return -errno;
287         }
288
289         return bus_socket_start_auth(b);
290 }
291
292 int bus_socket_exec(sd_bus *b) {
293         int s[2];
294         pid_t pid;
295
296         assert(b);
297         assert(b->fd < 0);
298         assert(b->exec_path);
299
300         b->fd = socketpair(AF_UNIX, SOCK_STREAM|SOCK_NONBLOCK|SOCK_CLOEXEC, 0, s);
301         if (b->fd < 0)
302                 return -errno;
303
304         pid = fork();
305         if (pid < 0) {
306                 close_pipe(s);
307                 return -errno;
308         }
309         if (pid == 0) {
310                 /* Child */
311
312                 close_all_fds(s, 2);
313                 close_nointr_nofail(s[0]);
314
315                 assert_se(dup3(s[1], STDIN_FILENO, 0) == STDIN_FILENO);
316                 assert_se(dup3(s[1], STDOUT_FILENO, 0) == STDOUT_FILENO);
317
318                 if (s[1] != STDIN_FILENO && s[1] != STDOUT_FILENO)
319                         close_nointr_nofail(s[1]);
320
321                 fd_cloexec(STDIN_FILENO, false);
322                 fd_cloexec(STDOUT_FILENO, false);
323                 fd_nonblock(STDIN_FILENO, false);
324                 fd_nonblock(STDOUT_FILENO, false);
325
326                 if (b->exec_argv)
327                         execvp(b->exec_path, b->exec_argv);
328                 else {
329                         const char *argv[] = { b->exec_path, NULL };
330                         execvp(b->exec_path, (char**) argv);
331                 }
332
333                 _exit(EXIT_FAILURE);
334         }
335
336         close_nointr_nofail(s[1]);
337         b->fd = s[0];
338
339         return bus_socket_start_auth(b);
340 }
341
342 int bus_socket_take_fd(sd_bus *b) {
343         int  r;
344         assert(b);
345
346         r = bus_socket_setup(b);
347         if (r < 0)
348                 return r;
349
350         return bus_socket_start_auth(b);
351 }
352
353 int bus_socket_write_message(sd_bus *bus, sd_bus_message *m, size_t *idx) {
354         struct msghdr mh;
355         struct iovec *iov;
356         ssize_t k;
357         size_t n;
358         unsigned j;
359
360         assert(bus);
361         assert(m);
362         assert(idx);
363         assert(bus->state == BUS_RUNNING || bus->state == BUS_HELLO);
364
365         if (*idx >= m->size)
366                 return 0;
367         zero(mh);
368
369         if (m->n_fds > 0) {
370                 struct cmsghdr *control;
371                 control = alloca(CMSG_SPACE(sizeof(int) * m->n_fds));
372
373                 mh.msg_control = control;
374                 control->cmsg_level = SOL_SOCKET;
375                 control->cmsg_type = SCM_RIGHTS;
376                 mh.msg_controllen = control->cmsg_len = CMSG_LEN(sizeof(int) * m->n_fds);
377                 memcpy(CMSG_DATA(control), m->fds, sizeof(int) * m->n_fds);
378         }
379
380         n = m->n_iovec * sizeof(struct iovec);
381         iov = alloca(n);
382         memcpy(iov, m->iovec, n);
383
384         j = 0;
385         iovec_advance(iov, &j, *idx);
386
387         mh.msg_iov = iov;
388         mh.msg_iovlen = m->n_iovec;
389
390         k = sendmsg(bus->fd, &mh, MSG_DONTWAIT|MSG_NOSIGNAL);
391         if (k < 0)
392                 return errno == EAGAIN ? 0 : -errno;
393
394         *idx += (size_t) k;
395         return 1;
396 }
397
398 static int bus_socket_read_message_need(sd_bus *bus, size_t *need) {
399         uint32_t a, b;
400         uint8_t e;
401         uint64_t sum;
402
403         assert(bus);
404         assert(need);
405         assert(bus->state == BUS_RUNNING || bus->state == BUS_HELLO);
406
407         if (bus->rbuffer_size < sizeof(struct bus_header)) {
408                 *need = sizeof(struct bus_header) + 8;
409
410                 /* Minimum message size:
411                  *
412                  * Header +
413                  *
414                  *  Method Call: +2 string headers
415                  *       Signal: +3 string headers
416                  * Method Error: +1 string headers
417                  *               +1 uint32 headers
418                  * Method Reply: +1 uint32 headers
419                  *
420                  * A string header is at least 9 bytes
421                  * A uint32 header is at least 8 bytes
422                  *
423                  * Hence the minimum message size of a valid message
424                  * is header + 8 bytes */
425
426                 return 0;
427         }
428
429         a = ((const uint32_t*) bus->rbuffer)[1];
430         b = ((const uint32_t*) bus->rbuffer)[3];
431
432         e = ((const uint8_t*) bus->rbuffer)[0];
433         if (e == SD_BUS_LITTLE_ENDIAN) {
434                 a = le32toh(a);
435                 b = le32toh(b);
436         } else if (e == SD_BUS_BIG_ENDIAN) {
437                 a = be32toh(a);
438                 b = be32toh(b);
439         } else
440                 return -EBADMSG;
441
442         sum = (uint64_t) sizeof(struct bus_header) + (uint64_t) ALIGN_TO(b, 8) + (uint64_t) a;
443         if (sum >= BUS_MESSAGE_SIZE_MAX)
444                 return -ENOBUFS;
445
446         *need = (size_t) sum;
447         return 0;
448 }
449
450 static int bus_socket_make_message(sd_bus *bus, size_t size, sd_bus_message **m) {
451         sd_bus_message *t;
452         void *b;
453         int r;
454
455         assert(bus);
456         assert(m);
457         assert(bus->rbuffer_size >= size);
458         assert(bus->state == BUS_RUNNING || bus->state == BUS_HELLO);
459
460         if (bus->rbuffer_size > size) {
461                 b = memdup((const uint8_t*) bus->rbuffer + size,
462                            bus->rbuffer_size - size);
463                 if (!b)
464                         return -ENOMEM;
465         } else
466                 b = NULL;
467
468         r = bus_message_from_malloc(bus->rbuffer, size,
469                                     bus->fds, bus->n_fds,
470                                     bus->ucred_valid ? &bus->ucred : NULL,
471                                     bus->label[0] ? bus->label : NULL,
472                                     &t);
473         if (r < 0) {
474                 free(b);
475                 return r;
476         }
477
478         bus->rbuffer = b;
479         bus->rbuffer_size -= size;
480
481         bus->fds = NULL;
482         bus->n_fds = 0;
483
484         *m = t;
485         return 1;
486 }
487
488 int bus_socket_read_message(sd_bus *bus, sd_bus_message **m) {
489         struct msghdr mh;
490         struct iovec iov;
491         ssize_t k;
492         size_t need;
493         int r;
494         void *b;
495         union {
496                 struct cmsghdr cmsghdr;
497                 uint8_t buf[CMSG_SPACE(sizeof(int) * BUS_FDS_MAX) +
498                             CMSG_SPACE(sizeof(struct ucred)) +
499                             CMSG_SPACE(NAME_MAX)]; /*selinux label */
500         } control;
501         struct cmsghdr *cmsg;
502
503         assert(bus);
504         assert(m);
505         assert(bus->state == BUS_RUNNING || bus->state == BUS_HELLO);
506
507         r = bus_socket_read_message_need(bus, &need);
508         if (r < 0)
509                 return r;
510
511         if (bus->rbuffer_size >= need)
512                 return bus_socket_make_message(bus, need, m);
513
514         b = realloc(bus->rbuffer, need);
515         if (!b)
516                 return -ENOMEM;
517
518         bus->rbuffer = b;
519
520         zero(iov);
521         iov.iov_base = (uint8_t*) bus->rbuffer + bus->rbuffer_size;
522         iov.iov_len = need - bus->rbuffer_size;
523
524         zero(mh);
525         mh.msg_iov = &iov;
526         mh.msg_iovlen = 1;
527         mh.msg_control = &control;
528         mh.msg_controllen = sizeof(control);
529
530         k = recvmsg(bus->fd, &mh, MSG_DONTWAIT|MSG_NOSIGNAL|MSG_CMSG_CLOEXEC);
531         if (k < 0)
532                 return errno == EAGAIN ? 0 : -errno;
533         if (k == 0)
534                 return -ECONNRESET;
535
536         bus->rbuffer_size += k;
537
538         for (cmsg = CMSG_FIRSTHDR(&mh); cmsg; cmsg = CMSG_NXTHDR(&mh, cmsg)) {
539                 if (cmsg->cmsg_level == SOL_SOCKET &&
540                     cmsg->cmsg_type == SCM_RIGHTS) {
541                         int n, *f;
542
543                         n = (cmsg->cmsg_len - CMSG_LEN(0)) / sizeof(int);
544
545                         f = realloc(bus->fds, sizeof(int) + (bus->n_fds + n));
546                         if (!f) {
547                                 close_many((int*) CMSG_DATA(cmsg), n);
548                                 return -ENOMEM;
549                         }
550
551                         memcpy(f + bus->n_fds, CMSG_DATA(cmsg), n * sizeof(int));
552                         bus->fds = f;
553                         bus->n_fds += n;
554                 } else if (cmsg->cmsg_level == SOL_SOCKET &&
555                     cmsg->cmsg_type == SCM_CREDENTIALS &&
556                     cmsg->cmsg_len == CMSG_LEN(sizeof(struct ucred))) {
557
558                         memcpy(&bus->ucred, CMSG_DATA(cmsg), sizeof(struct ucred));
559                         bus->ucred_valid = true;
560
561                 } else if (cmsg->cmsg_level == SOL_SOCKET &&
562                          cmsg->cmsg_type == SCM_SECURITY) {
563
564                         size_t l;
565                         l = cmsg->cmsg_len - CMSG_LEN(0);
566                         memcpy(&bus->label, CMSG_DATA(cmsg), l);
567                         bus->label[l] = 0;
568                 }
569         }
570
571         r = bus_socket_read_message_need(bus, &need);
572         if (r < 0)
573                 return r;
574
575         if (bus->rbuffer_size >= need)
576                 return bus_socket_make_message(bus, need, m);
577
578         return 1;
579 }
580
581 int bus_socket_process_opening(sd_bus *b) {
582         int error = 0;
583         socklen_t slen = sizeof(error);
584         struct pollfd p;
585         int r;
586
587         assert(b);
588         assert(b->state == BUS_OPENING);
589
590         zero(p);
591         p.fd = b->fd;
592         p.events = POLLOUT;
593
594         r = poll(&p, 1, 0);
595         if (r < 0)
596                 return -errno;
597
598         if (!(p.revents & (POLLOUT|POLLERR|POLLHUP)))
599                 return 0;
600
601         r = getsockopt(b->fd, SOL_SOCKET, SO_ERROR, &error, &slen);
602         if (r < 0)
603                 b->last_connect_error = errno;
604         else if (error != 0)
605                 b->last_connect_error = error;
606         else if (p.revents & (POLLERR|POLLHUP))
607                 b->last_connect_error = ECONNREFUSED;
608         else
609                 return bus_socket_start_auth(b);
610
611         return bus_next_address(b);
612 }
613
614 int bus_socket_process_authenticating(sd_bus *b) {
615         int r;
616
617         assert(b);
618         assert(b->state == BUS_AUTHENTICATING);
619
620         if (now(CLOCK_MONOTONIC) >= b->auth_timeout)
621                 return -ETIMEDOUT;
622
623         r = bus_socket_write_auth(b);
624         if (r != 0)
625                 return r;
626
627         return bus_socket_read_auth(b);
628 }