]> git.ipfire.org Git - thirdparty/systemd.git/blob - src/libsystemd-bus/bus-message.c
core: convert PID 1 to libsystemd-bus
[thirdparty/systemd.git] / src / libsystemd-bus / bus-message.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 <errno.h>
23 #include <fcntl.h>
24 #include <sys/mman.h>
25
26 #include "util.h"
27 #include "utf8.h"
28 #include "strv.h"
29 #include "time-util.h"
30 #include "cgroup-util.h"
31
32 #include "sd-bus.h"
33 #include "bus-message.h"
34 #include "bus-internal.h"
35 #include "bus-type.h"
36 #include "bus-signature.h"
37
38 static int message_append_basic(sd_bus_message *m, char type, const void *p, const void **stored);
39
40 static void *adjust_pointer(const void *p, void *old_base, size_t sz, void *new_base) {
41
42 if (p == NULL)
43 return NULL;
44
45 if (old_base == new_base)
46 return (void*) p;
47
48 if ((uint8_t*) p < (uint8_t*) old_base)
49 return (void*) p;
50
51 if ((uint8_t*) p >= (uint8_t*) old_base + sz)
52 return (void*) p;
53
54 return (uint8_t*) new_base + ((uint8_t*) p - (uint8_t*) old_base);
55 }
56
57 static void message_free_part(sd_bus_message *m, struct bus_body_part *part) {
58 assert(m);
59 assert(part);
60
61 if (part->memfd >= 0) {
62 /* If we can reuse the memfd, try that. For that it
63 * can't be sealed yet. */
64
65 if (!part->sealed)
66 bus_kernel_push_memfd(m->bus, part->memfd, part->data, part->mapped);
67 else {
68 if (part->mapped > 0)
69 assert_se(munmap(part->data, part->mapped) == 0);
70
71 close_nointr_nofail(part->memfd);
72 }
73
74 } else if (part->munmap_this)
75 munmap(part->data, part->mapped);
76 else if (part->free_this)
77 free(part->data);
78
79 if (part != &m->body)
80 free(part);
81 }
82
83 static void message_reset_parts(sd_bus_message *m) {
84 struct bus_body_part *part;
85
86 assert(m);
87
88 part = &m->body;
89 while (m->n_body_parts > 0) {
90 struct bus_body_part *next = part->next;
91 message_free_part(m, part);
92 part = next;
93 m->n_body_parts--;
94 }
95
96 m->body_end = NULL;
97
98 m->cached_rindex_part = NULL;
99 m->cached_rindex_part_begin = 0;
100 }
101
102 static void message_reset_containers(sd_bus_message *m) {
103 unsigned i;
104
105 assert(m);
106
107 for (i = 0; i < m->n_containers; i++)
108 free(m->containers[i].signature);
109
110 free(m->containers);
111 m->containers = NULL;
112
113 m->n_containers = 0;
114 m->root_container.index = 0;
115 }
116
117 static void message_free(sd_bus_message *m) {
118 assert(m);
119
120 if (m->free_header)
121 free(m->header);
122
123 message_reset_parts(m);
124
125 if (m->free_kdbus)
126 free(m->kdbus);
127
128 if (m->release_kdbus) {
129 uint64_t off;
130
131 off = (uint8_t *)m->kdbus - (uint8_t *)m->bus->kdbus_buffer;
132 ioctl(m->bus->input_fd, KDBUS_CMD_MSG_RELEASE, &off);
133 }
134
135 if (m->bus)
136 sd_bus_unref(m->bus);
137
138 if (m->free_fds) {
139 close_many(m->fds, m->n_fds);
140 free(m->fds);
141 }
142
143 if (m->iovec != m->iovec_fixed)
144 free(m->iovec);
145
146 free(m->cmdline_array);
147
148 message_reset_containers(m);
149 free(m->root_container.signature);
150
151 free(m->peeked_signature);
152
153 free(m->unit);
154 free(m->user_unit);
155 free(m->session);
156 free(m);
157 }
158
159 static void *message_extend_fields(sd_bus_message *m, size_t align, size_t sz) {
160 void *op, *np;
161 size_t old_size, new_size, start;
162
163 assert(m);
164
165 if (m->poisoned)
166 return NULL;
167
168 old_size = sizeof(struct bus_header) + m->header->fields_size;
169 start = ALIGN_TO(old_size, align);
170 new_size = start + sz;
171
172 if (old_size == new_size)
173 return (uint8_t*) m->header + old_size;
174
175 if (new_size > (size_t) ((uint32_t) -1))
176 goto poison;
177
178 if (m->free_header) {
179 np = realloc(m->header, ALIGN8(new_size));
180 if (!np)
181 goto poison;
182 } else {
183 /* Initially, the header is allocated as part of of
184 * the sd_bus_message itself, let's replace it by
185 * dynamic data */
186
187 np = malloc(ALIGN8(new_size));
188 if (!np)
189 goto poison;
190
191 memcpy(np, m->header, sizeof(struct bus_header));
192 }
193
194 /* Zero out padding */
195 if (start > old_size)
196 memset((uint8_t*) np + old_size, 0, start - old_size);
197
198 op = m->header;
199 m->header = np;
200 m->header->fields_size = new_size - sizeof(struct bus_header);
201
202 /* Adjust quick access pointers */
203 m->path = adjust_pointer(m->path, op, old_size, m->header);
204 m->interface = adjust_pointer(m->interface, op, old_size, m->header);
205 m->member = adjust_pointer(m->member, op, old_size, m->header);
206 m->destination = adjust_pointer(m->destination, op, old_size, m->header);
207 m->sender = adjust_pointer(m->sender, op, old_size, m->header);
208 m->error.name = adjust_pointer(m->error.name, op, old_size, m->header);
209
210 m->free_header = true;
211
212 return (uint8_t*) np + start;
213
214 poison:
215 m->poisoned = true;
216 return NULL;
217 }
218
219 static int message_append_field_string(
220 sd_bus_message *m,
221 uint8_t h,
222 char type,
223 const char *s,
224 const char **ret) {
225
226 size_t l;
227 uint8_t *p;
228
229 assert(m);
230
231 l = strlen(s);
232 if (l > (size_t) (uint32_t) -1)
233 return -EINVAL;
234
235 /* field id byte + signature length + signature 's' + NUL + string length + string + NUL */
236 p = message_extend_fields(m, 8, 4 + 4 + l + 1);
237 if (!p)
238 return -ENOMEM;
239
240 p[0] = h;
241 p[1] = 1;
242 p[2] = type;
243 p[3] = 0;
244
245 ((uint32_t*) p)[1] = l;
246 memcpy(p + 8, s, l + 1);
247
248 if (ret)
249 *ret = (char*) p + 8;
250
251 return 0;
252 }
253
254 static int message_append_field_signature(
255 sd_bus_message *m,
256 uint8_t h,
257 const char *s,
258 const char **ret) {
259
260 size_t l;
261 uint8_t *p;
262
263 assert(m);
264
265 l = strlen(s);
266 if (l > 255)
267 return -EINVAL;
268
269 /* field id byte + signature length + signature 'g' + NUL + string length + string + NUL */
270 p = message_extend_fields(m, 8, 4 + 1 + l + 1);
271 if (!p)
272 return -ENOMEM;
273
274 p[0] = h;
275 p[1] = 1;
276 p[2] = SD_BUS_TYPE_SIGNATURE;
277 p[3] = 0;
278 p[4] = l;
279 memcpy(p + 5, s, l + 1);
280
281 if (ret)
282 *ret = (const char*) p + 5;
283
284 return 0;
285 }
286
287 static int message_append_field_uint32(sd_bus_message *m, uint8_t h, uint32_t x) {
288 uint8_t *p;
289
290 assert(m);
291
292 /* field id byte + signature length + signature 'u' + NUL + value */
293 p = message_extend_fields(m, 8, 4 + 4);
294 if (!p)
295 return -ENOMEM;
296
297 p[0] = h;
298 p[1] = 1;
299 p[2] = SD_BUS_TYPE_UINT32;
300 p[3] = 0;
301
302 ((uint32_t*) p)[1] = x;
303
304 return 0;
305 }
306
307 int bus_message_from_header(
308 void *buffer,
309 size_t length,
310 int *fds,
311 unsigned n_fds,
312 const struct ucred *ucred,
313 const char *label,
314 size_t extra,
315 sd_bus_message **ret) {
316
317 sd_bus_message *m;
318 struct bus_header *h;
319 size_t a, label_sz;
320
321 assert(buffer || length <= 0);
322 assert(fds || n_fds <= 0);
323 assert(ret);
324
325 if (length < sizeof(struct bus_header))
326 return -EBADMSG;
327
328 h = buffer;
329 if (h->version != 1)
330 return -EBADMSG;
331
332 if (h->serial == 0)
333 return -EBADMSG;
334
335 if (h->type == _SD_BUS_MESSAGE_TYPE_INVALID)
336 return -EBADMSG;
337
338 if (h->endian != SD_BUS_LITTLE_ENDIAN &&
339 h->endian != SD_BUS_BIG_ENDIAN)
340 return -EBADMSG;
341
342 a = ALIGN(sizeof(sd_bus_message)) + ALIGN(extra);
343
344 if (label) {
345 label_sz = strlen(label);
346 a += label_sz + 1;
347 }
348
349 m = malloc0(a);
350 if (!m)
351 return -ENOMEM;
352
353 m->n_ref = 1;
354 m->sealed = true;
355 m->header = h;
356 m->fds = fds;
357 m->n_fds = n_fds;
358
359 if (ucred) {
360 m->uid = ucred->uid;
361 m->pid = ucred->pid;
362 m->gid = ucred->gid;
363 m->uid_valid = m->gid_valid = true;
364 }
365
366 if (label) {
367 m->label = (char*) m + ALIGN(sizeof(sd_bus_message)) + ALIGN(extra);
368 memcpy(m->label, label, label_sz + 1);
369 }
370
371 *ret = m;
372 return 0;
373 }
374
375 int bus_message_from_malloc(
376 void *buffer,
377 size_t length,
378 int *fds,
379 unsigned n_fds,
380 const struct ucred *ucred,
381 const char *label,
382 sd_bus_message **ret) {
383
384 sd_bus_message *m;
385 int r;
386
387 r = bus_message_from_header(buffer, length, fds, n_fds, ucred, label, 0, &m);
388 if (r < 0)
389 return r;
390
391 if (length != BUS_MESSAGE_SIZE(m)) {
392 r = -EBADMSG;
393 goto fail;
394 }
395
396 m->n_body_parts = 1;
397 m->body.data = (uint8_t*) buffer + sizeof(struct bus_header) + ALIGN8(BUS_MESSAGE_FIELDS_SIZE(m));
398 m->body.size = length - sizeof(struct bus_header) - ALIGN8(BUS_MESSAGE_FIELDS_SIZE(m));
399 m->body.sealed = true;
400 m->body.memfd = -1;
401
402 m->n_iovec = 1;
403 m->iovec = m->iovec_fixed;
404 m->iovec[0].iov_base = buffer;
405 m->iovec[0].iov_len = length;
406
407 r = bus_message_parse_fields(m);
408 if (r < 0)
409 goto fail;
410
411 /* We take possession of the memory and fds now */
412 m->free_header = true;
413 m->free_fds = true;
414
415 *ret = m;
416 return 0;
417
418 fail:
419 message_free(m);
420 return r;
421 }
422
423 static sd_bus_message *message_new(sd_bus *bus, uint8_t type) {
424 sd_bus_message *m;
425
426 m = malloc0(ALIGN(sizeof(sd_bus_message)) + sizeof(struct bus_header));
427 if (!m)
428 return NULL;
429
430 m->n_ref = 1;
431 m->header = (struct bus_header*) ((uint8_t*) m + ALIGN(sizeof(struct sd_bus_message)));
432 m->header->endian = SD_BUS_NATIVE_ENDIAN;
433 m->header->type = type;
434 m->header->version = bus ? bus->message_version : 1;
435 m->allow_fds = !bus || bus->can_fds || (bus->state != BUS_HELLO && bus->state != BUS_RUNNING);
436
437 if (bus)
438 m->bus = sd_bus_ref(bus);
439
440 return m;
441 }
442
443 _public_ int sd_bus_message_new_signal(
444 sd_bus *bus,
445 const char *path,
446 const char *interface,
447 const char *member,
448 sd_bus_message **m) {
449
450 sd_bus_message *t;
451 int r;
452
453 assert_return(!bus || bus->state != BUS_UNSET, -ENOTCONN);
454 assert_return(object_path_is_valid(path), -EINVAL);
455 assert_return(interface_name_is_valid(interface), -EINVAL);
456 assert_return(member_name_is_valid(member), -EINVAL);
457 assert_return(m, -EINVAL);
458
459 t = message_new(bus, SD_BUS_MESSAGE_SIGNAL);
460 if (!t)
461 return -ENOMEM;
462
463 t->header->flags |= SD_BUS_MESSAGE_NO_REPLY_EXPECTED;
464
465 r = message_append_field_string(t, SD_BUS_MESSAGE_HEADER_PATH, SD_BUS_TYPE_OBJECT_PATH, path, &t->path);
466 if (r < 0)
467 goto fail;
468 r = message_append_field_string(t, SD_BUS_MESSAGE_HEADER_INTERFACE, SD_BUS_TYPE_STRING, interface, &t->interface);
469 if (r < 0)
470 goto fail;
471 r = message_append_field_string(t, SD_BUS_MESSAGE_HEADER_MEMBER, SD_BUS_TYPE_STRING, member, &t->member);
472 if (r < 0)
473 goto fail;
474
475 *m = t;
476 return 0;
477
478 fail:
479 sd_bus_message_unref(t);
480 return r;
481 }
482
483 _public_ int sd_bus_message_new_method_call(
484 sd_bus *bus,
485 const char *destination,
486 const char *path,
487 const char *interface,
488 const char *member,
489 sd_bus_message **m) {
490
491 sd_bus_message *t;
492 int r;
493
494 assert_return(!bus || bus->state != BUS_UNSET, -ENOTCONN);
495 assert_return(!destination || service_name_is_valid(destination), -EINVAL);
496 assert_return(object_path_is_valid(path), -EINVAL);
497 assert_return(!interface || interface_name_is_valid(interface), -EINVAL);
498 assert_return(member_name_is_valid(member), -EINVAL);
499 assert_return(m, -EINVAL);
500
501 t = message_new(bus, SD_BUS_MESSAGE_METHOD_CALL);
502 if (!t)
503 return -ENOMEM;
504
505 r = message_append_field_string(t, SD_BUS_MESSAGE_HEADER_PATH, SD_BUS_TYPE_OBJECT_PATH, path, &t->path);
506 if (r < 0)
507 goto fail;
508 r = message_append_field_string(t, SD_BUS_MESSAGE_HEADER_MEMBER, SD_BUS_TYPE_STRING, member, &t->member);
509 if (r < 0)
510 goto fail;
511
512 if (interface) {
513 r = message_append_field_string(t, SD_BUS_MESSAGE_HEADER_INTERFACE, SD_BUS_TYPE_STRING, interface, &t->interface);
514 if (r < 0)
515 goto fail;
516 }
517
518 if (destination) {
519 r = message_append_field_string(t, SD_BUS_MESSAGE_HEADER_DESTINATION, SD_BUS_TYPE_STRING, destination, &t->destination);
520 if (r < 0)
521 goto fail;
522 }
523
524 *m = t;
525 return 0;
526
527 fail:
528 message_free(t);
529 return r;
530 }
531
532 static int message_new_reply(
533 sd_bus *bus,
534 sd_bus_message *call,
535 uint8_t type,
536 sd_bus_message **m) {
537
538 sd_bus_message *t;
539 int r;
540
541 assert_return(!bus || bus->state != BUS_UNSET, -ENOTCONN);
542 assert_return(call, -EINVAL);
543 assert_return(call->sealed, -EPERM);
544 assert_return(call->header->type == SD_BUS_MESSAGE_METHOD_CALL, -EINVAL);
545 assert_return(m, -EINVAL);
546
547 t = message_new(bus, type);
548 if (!t)
549 return -ENOMEM;
550
551 t->header->flags |= SD_BUS_MESSAGE_NO_REPLY_EXPECTED;
552 t->reply_serial = BUS_MESSAGE_SERIAL(call);
553
554 r = message_append_field_uint32(t, SD_BUS_MESSAGE_HEADER_REPLY_SERIAL, t->reply_serial);
555 if (r < 0)
556 goto fail;
557
558 if (call->sender) {
559 r = message_append_field_string(t, SD_BUS_MESSAGE_HEADER_DESTINATION, SD_BUS_TYPE_STRING, call->sender, &t->destination);
560 if (r < 0)
561 goto fail;
562 }
563
564 t->dont_send = !!(call->header->flags & SD_BUS_MESSAGE_NO_REPLY_EXPECTED);
565
566 *m = t;
567 return 0;
568
569 fail:
570 message_free(t);
571 return r;
572 }
573
574 _public_ int sd_bus_message_new_method_return(
575 sd_bus *bus,
576 sd_bus_message *call,
577 sd_bus_message **m) {
578
579 return message_new_reply(bus, call, SD_BUS_MESSAGE_METHOD_RETURN, m);
580 }
581
582 _public_ int sd_bus_message_new_method_error(
583 sd_bus *bus,
584 sd_bus_message *call,
585 const sd_bus_error *e,
586 sd_bus_message **m) {
587
588 sd_bus_message *t;
589 int r;
590
591 assert_return(sd_bus_error_is_set(e), -EINVAL);
592 assert_return(m, -EINVAL);
593
594 r = message_new_reply(bus, call, SD_BUS_MESSAGE_METHOD_ERROR, &t);
595 if (r < 0)
596 return r;
597
598 r = message_append_field_string(t, SD_BUS_MESSAGE_HEADER_ERROR_NAME, SD_BUS_TYPE_STRING, e->name, &t->error.name);
599 if (r < 0)
600 goto fail;
601
602 if (e->message) {
603 r = message_append_basic(t, SD_BUS_TYPE_STRING, e->message, (const void**) &t->error.message);
604 if (r < 0)
605 goto fail;
606 }
607
608 *m = t;
609 return 0;
610
611 fail:
612 message_free(t);
613 return r;
614 }
615
616 _public_ int sd_bus_message_new_method_errorf(
617 sd_bus *bus,
618 sd_bus_message *call,
619 sd_bus_message **m,
620 const char *name,
621 const char *format,
622 ...) {
623
624 _cleanup_free_ sd_bus_error error = SD_BUS_ERROR_NULL;
625 va_list ap;
626 int r;
627
628 assert_return(name, -EINVAL);
629 assert_return(m, -EINVAL);
630
631 va_start(ap, format);
632 r = bus_error_setfv(&error, name, format, ap);
633 va_end(ap);
634
635 if (r < 0)
636 return r;
637
638 return sd_bus_message_new_method_error(bus, call, &error, m);
639 }
640
641 _public_ int sd_bus_message_new_method_errno(
642 sd_bus *bus,
643 sd_bus_message *call,
644 int error,
645 const sd_bus_error *p,
646 sd_bus_message **m) {
647
648 _cleanup_free_ sd_bus_error berror = SD_BUS_ERROR_NULL;
649
650 if (sd_bus_error_is_set(p))
651 return sd_bus_message_new_method_error(bus, call, p, m);
652
653 sd_bus_error_set_errno(&berror, error);
654
655 return sd_bus_message_new_method_error(bus, call, &berror, m);
656 }
657
658 _public_ int sd_bus_message_new_method_errnof(
659 sd_bus *bus,
660 sd_bus_message *call,
661 sd_bus_message **m,
662 int error,
663 const char *format,
664 ...) {
665
666 _cleanup_free_ sd_bus_error berror = SD_BUS_ERROR_NULL;
667 va_list ap;
668 int r;
669
670 va_start(ap, format);
671 r = bus_error_set_errnofv(&berror, error, format, ap);
672 va_end(ap);
673
674 if (r < 0)
675 return r;
676
677 return sd_bus_message_new_method_error(bus, call, &berror, m);
678 }
679
680 int bus_message_new_synthetic_error(
681 sd_bus *bus,
682 uint64_t serial,
683 const sd_bus_error *e,
684 sd_bus_message **m) {
685
686 sd_bus_message *t;
687 int r;
688
689 assert(sd_bus_error_is_set(e));
690 assert(m);
691
692 t = message_new(bus, SD_BUS_MESSAGE_METHOD_ERROR);
693 if (!t)
694 return -ENOMEM;
695
696 t->header->flags |= SD_BUS_MESSAGE_NO_REPLY_EXPECTED;
697 t->reply_serial = serial;
698
699 r = message_append_field_uint32(t, SD_BUS_MESSAGE_HEADER_REPLY_SERIAL, t->reply_serial);
700 if (r < 0)
701 goto fail;
702
703 if (bus && bus->unique_name) {
704 r = message_append_field_string(t, SD_BUS_MESSAGE_HEADER_DESTINATION, SD_BUS_TYPE_STRING, bus->unique_name, &t->destination);
705 if (r < 0)
706 goto fail;
707 }
708
709 r = message_append_field_string(t, SD_BUS_MESSAGE_HEADER_ERROR_NAME, SD_BUS_TYPE_STRING, e->name, &t->error.name);
710 if (r < 0)
711 goto fail;
712
713 if (e->message) {
714 r = message_append_basic(t, SD_BUS_TYPE_STRING, e->message, (const void**) &t->error.message);
715 if (r < 0)
716 goto fail;
717 }
718
719 *m = t;
720 return 0;
721
722 fail:
723 message_free(t);
724 return r;
725 }
726
727 _public_ sd_bus_message* sd_bus_message_ref(sd_bus_message *m) {
728 assert_return(m, NULL);
729
730 assert(m->n_ref > 0);
731 m->n_ref++;
732
733 return m;
734 }
735
736 _public_ sd_bus_message* sd_bus_message_unref(sd_bus_message *m) {
737 assert_return(m, NULL);
738
739 assert(m->n_ref > 0);
740 m->n_ref--;
741
742 if (m->n_ref <= 0)
743 message_free(m);
744
745 return NULL;
746 }
747
748 _public_ int sd_bus_message_get_type(sd_bus_message *m, uint8_t *type) {
749 assert_return(m, -EINVAL);
750 assert_return(type, -EINVAL);
751
752 *type = m->header->type;
753 return 0;
754 }
755
756 _public_ int sd_bus_message_get_serial(sd_bus_message *m, uint64_t *serial) {
757 assert_return(m, -EINVAL);
758 assert_return(serial, -EINVAL);
759 assert_return(m->header->serial != 0, -ENOENT);
760
761 *serial = BUS_MESSAGE_SERIAL(m);
762 return 0;
763 }
764
765 _public_ int sd_bus_message_get_reply_serial(sd_bus_message *m, uint64_t *serial) {
766 assert_return(m, -EINVAL);
767 assert_return(serial, -EINVAL);
768 assert_return(m->reply_serial != 0, -ENOENT);
769
770 *serial = m->reply_serial;
771 return 0;
772 }
773
774 _public_ int sd_bus_message_get_no_reply(sd_bus_message *m) {
775 assert_return(m, -EINVAL);
776
777 return m->header->type == SD_BUS_MESSAGE_METHOD_CALL ? !!(m->header->flags & SD_BUS_MESSAGE_NO_REPLY_EXPECTED) : 0;
778 }
779
780 _public_ int sd_bus_message_get_no_auto_start(sd_bus_message *m) {
781 assert_return(m, -EINVAL);
782
783 return !!(m->header->flags & SD_BUS_MESSAGE_NO_AUTO_START);
784 }
785
786 _public_ const char *sd_bus_message_get_path(sd_bus_message *m) {
787 assert_return(m, NULL);
788
789 return m->path;
790 }
791
792 _public_ const char *sd_bus_message_get_interface(sd_bus_message *m) {
793 assert_return(m, NULL);
794
795 return m->interface;
796 }
797
798 _public_ const char *sd_bus_message_get_member(sd_bus_message *m) {
799 assert_return(m, NULL);
800
801 return m->member;
802 }
803
804 _public_ const char *sd_bus_message_get_destination(sd_bus_message *m) {
805 assert_return(m, NULL);
806
807 return m->destination;
808 }
809
810 _public_ const char *sd_bus_message_get_sender(sd_bus_message *m) {
811 assert_return(m, NULL);
812
813 return m->sender;
814 }
815
816 _public_ const sd_bus_error *sd_bus_message_get_error(sd_bus_message *m) {
817 assert_return(m, NULL);
818 assert_return(sd_bus_error_is_set(&m->error), NULL);
819
820 return &m->error;
821 }
822
823 _public_ int sd_bus_message_get_uid(sd_bus_message *m, uid_t *uid) {
824 assert_return(m, -EINVAL);
825 assert_return(uid, -EINVAL);
826 assert_return(m->uid_valid, -ESRCH);
827
828 *uid = m->uid;
829 return 0;
830 }
831
832 _public_ int sd_bus_message_get_gid(sd_bus_message *m, gid_t *gid) {
833 assert_return(m, -EINVAL);
834 assert_return(gid, -EINVAL);
835 assert_return(m->gid_valid, -ESRCH);
836
837 *gid = m->gid;
838 return 0;
839 }
840
841 _public_ int sd_bus_message_get_pid(sd_bus_message *m, pid_t *pid) {
842 assert_return(m, -EINVAL);
843 assert_return(pid, -EINVAL);
844 assert_return(m->pid > 0, -ESRCH);
845
846 *pid = m->pid;
847 return 0;
848 }
849
850 _public_ int sd_bus_message_get_tid(sd_bus_message *m, pid_t *tid) {
851 assert_return(m, -EINVAL);
852 assert_return(tid, -EINVAL);
853 assert_return(m->tid > 0, -ESRCH);
854
855 *tid = m->tid;
856 return 0;
857 }
858
859 _public_ int sd_bus_message_get_pid_starttime(sd_bus_message *m, uint64_t *usec) {
860 assert_return(m, -EINVAL);
861 assert_return(usec, -EINVAL);
862 assert_return(m->pid_starttime > 0, -ESRCH);
863
864 *usec = m->pid_starttime;
865 return 0;
866 }
867
868 _public_ int sd_bus_message_get_selinux_context(sd_bus_message *m, const char **ret) {
869 assert_return(m, -EINVAL);
870 assert_return(m->label, -ESRCH);
871
872 *ret = m->label;
873 return 0;
874 }
875
876 _public_ int sd_bus_message_get_monotonic_timestamp(sd_bus_message *m, uint64_t *usec) {
877 assert_return(m, -EINVAL);
878 assert_return(usec, -EINVAL);
879 assert_return(m->monotonic > 0, -ESRCH);
880
881 *usec = m->monotonic;
882 return 0;
883 }
884
885 _public_ int sd_bus_message_get_realtime_timestamp(sd_bus_message *m, uint64_t *usec) {
886 assert_return(m, -EINVAL);
887 assert_return(usec, -EINVAL);
888 assert_return(m->realtime > 0, -ESRCH);
889
890 *usec = m->realtime;
891 return 0;
892 }
893
894 _public_ int sd_bus_message_get_comm(sd_bus_message *m, const char **ret) {
895 assert_return(m, -EINVAL);
896 assert_return(ret, -EINVAL);
897 assert_return(m->comm, -ESRCH);
898
899 *ret = m->comm;
900 return 0;
901 }
902
903 _public_ int sd_bus_message_get_tid_comm(sd_bus_message *m, const char **ret) {
904 assert_return(m, -EINVAL);
905 assert_return(ret, -EINVAL);
906 assert_return(m->tid_comm, -ESRCH);
907
908 *ret = m->tid_comm;
909 return 0;
910 }
911
912 _public_ int sd_bus_message_get_exe(sd_bus_message *m, const char **ret) {
913 assert_return(m, -EINVAL);
914 assert_return(ret, -EINVAL);
915 assert_return(m->exe, -ESRCH);
916
917 *ret = m->exe;
918 return 0;
919 }
920
921 _public_ int sd_bus_message_get_cgroup(sd_bus_message *m, const char **ret) {
922 assert_return(m, -EINVAL);
923 assert_return(ret, -EINVAL);
924 assert_return(m->cgroup, -ESRCH);
925
926 *ret = m->cgroup;
927 return 0;
928 }
929
930 _public_ int sd_bus_message_get_unit(sd_bus_message *m, const char **ret) {
931 int r;
932
933 assert_return(m, -EINVAL);
934 assert_return(ret, -EINVAL);
935 assert_return(m->cgroup, -ESRCH);
936
937 if (!m->unit) {
938 r = cg_path_get_unit(m->cgroup, &m->unit);
939 if (r < 0)
940 return r;
941 }
942
943 *ret = m->unit;
944 return 0;
945 }
946
947 _public_ int sd_bus_message_get_user_unit(sd_bus_message *m, const char **ret) {
948 int r;
949
950 assert_return(m, -EINVAL);
951 assert_return(ret, -EINVAL);
952 assert_return(m->cgroup, -ESRCH);
953
954 if (!m->user_unit) {
955 r = cg_path_get_user_unit(m->cgroup, &m->user_unit);
956 if (r < 0)
957 return r;
958 }
959
960 *ret = m->user_unit;
961 return 0;
962 }
963
964 _public_ int sd_bus_message_get_session(sd_bus_message *m, const char **ret) {
965 int r;
966
967 assert_return(m, -EINVAL);
968 assert_return(ret, -EINVAL);
969 assert_return(m->cgroup, -ESRCH);
970
971 if (!m->session) {
972 r = cg_path_get_session(m->cgroup, &m->session);
973 if (r < 0)
974 return r;
975 }
976
977 *ret = m->session;
978 return 0;
979 }
980
981 _public_ int sd_bus_message_get_owner_uid(sd_bus_message *m, uid_t *uid) {
982 assert_return(m, -EINVAL);
983 assert_return(uid, -EINVAL);
984 assert_return(m->cgroup, -ESRCH);
985
986 return cg_path_get_owner_uid(m->cgroup, uid);
987 }
988
989 _public_ int sd_bus_message_get_cmdline(sd_bus_message *m, char ***cmdline) {
990 size_t n, i;
991 const char *p;
992 bool first;
993
994 assert_return(m, -EINVAL);
995 assert_return(m->cmdline, -ESRCH);
996
997 for (p = m->cmdline, n = 0; p < m->cmdline + m->cmdline_length; p++)
998 if (*p == 0)
999 n++;
1000
1001 m->cmdline_array = new(char*, n + 1);
1002 if (!m->cmdline_array)
1003 return -ENOMEM;
1004
1005 for (p = m->cmdline, i = 0, first = true; p < m->cmdline + m->cmdline_length; p++) {
1006 if (first)
1007 m->cmdline_array[i++] = (char*) p;
1008
1009 first = *p == 0;
1010 }
1011
1012 m->cmdline_array[i] = NULL;
1013 *cmdline = m->cmdline_array;
1014
1015 return 0;
1016 }
1017
1018 _public_ int sd_bus_message_get_audit_sessionid(sd_bus_message *m, uint32_t *sessionid) {
1019 assert_return(m, -EINVAL);
1020 assert_return(sessionid, -EINVAL);
1021 assert_return(m->audit, -ESRCH);
1022
1023 *sessionid = m->audit->sessionid;
1024 return 0;
1025 }
1026
1027 _public_ int sd_bus_message_get_audit_loginuid(sd_bus_message *m, uid_t *uid) {
1028 assert_return(m, -EINVAL);
1029 assert_return(uid, -EINVAL);
1030 assert_return(m->audit, -ESRCH);
1031
1032 *uid = m->audit->loginuid;
1033 return 0;
1034 }
1035
1036 _public_ int sd_bus_message_has_effective_cap(sd_bus_message *m, int capability) {
1037 unsigned sz;
1038
1039 assert_return(m, -EINVAL);
1040 assert_return(capability < 0, -EINVAL);
1041 assert_return(!m->capability, -ESRCH);
1042
1043 sz = m->capability_size / 4;
1044 if ((unsigned) capability >= sz*8)
1045 return 0;
1046
1047 return !!(m->capability[2 * sz + (capability / 8)] & (1 << (capability % 8)));
1048 }
1049
1050 _public_ int sd_bus_message_is_signal(sd_bus_message *m,
1051 const char *interface,
1052 const char *member) {
1053 assert_return(m, -EINVAL);
1054
1055 if (m->header->type != SD_BUS_MESSAGE_SIGNAL)
1056 return 0;
1057
1058 if (interface && (!m->interface || !streq(m->interface, interface)))
1059 return 0;
1060
1061 if (member && (!m->member || !streq(m->member, member)))
1062 return 0;
1063
1064 return 1;
1065 }
1066
1067 _public_ int sd_bus_message_is_method_call(sd_bus_message *m,
1068 const char *interface,
1069 const char *member) {
1070 assert_return(m, -EINVAL);
1071
1072 if (m->header->type != SD_BUS_MESSAGE_METHOD_CALL)
1073 return 0;
1074
1075 if (interface && (!m->interface || !streq(m->interface, interface)))
1076 return 0;
1077
1078 if (member && (!m->member || !streq(m->member, member)))
1079 return 0;
1080
1081 return 1;
1082 }
1083
1084 _public_ int sd_bus_message_is_method_error(sd_bus_message *m, const char *name) {
1085 assert_return(m, -EINVAL);
1086
1087 if (m->header->type != SD_BUS_MESSAGE_METHOD_ERROR)
1088 return 0;
1089
1090 if (name && (!m->error.name || !streq(m->error.name, name)))
1091 return 0;
1092
1093 return 1;
1094 }
1095
1096 _public_ int sd_bus_message_set_no_reply(sd_bus_message *m, int b) {
1097 assert_return(m, -EINVAL);
1098 assert_return(!m->sealed, -EPERM);
1099 assert_return(m->header->type == SD_BUS_MESSAGE_METHOD_CALL, -EPERM);
1100
1101 if (b)
1102 m->header->flags |= SD_BUS_MESSAGE_NO_REPLY_EXPECTED;
1103 else
1104 m->header->flags &= ~SD_BUS_MESSAGE_NO_REPLY_EXPECTED;
1105
1106 return 0;
1107 }
1108
1109 _public_ int sd_bus_message_set_no_auto_start(sd_bus_message *m, int b) {
1110 assert_return(m, -EINVAL);
1111 assert_return(!m->sealed, -EPERM);
1112
1113 if (b)
1114 m->header->flags |= SD_BUS_MESSAGE_NO_AUTO_START;
1115 else
1116 m->header->flags &= ~SD_BUS_MESSAGE_NO_AUTO_START;
1117
1118 return 0;
1119 }
1120
1121 static struct bus_container *message_get_container(sd_bus_message *m) {
1122 assert(m);
1123
1124 if (m->n_containers == 0)
1125 return &m->root_container;
1126
1127 assert(m->containers);
1128 return m->containers + m->n_containers - 1;
1129 }
1130
1131 struct bus_body_part *message_append_part(sd_bus_message *m) {
1132 struct bus_body_part *part;
1133
1134 assert(m);
1135
1136 if (m->poisoned)
1137 return NULL;
1138
1139 if (m->n_body_parts <= 0) {
1140 part = &m->body;
1141 zero(*part);
1142 } else {
1143 assert(m->body_end);
1144
1145 part = new0(struct bus_body_part, 1);
1146 if (!part) {
1147 m->poisoned = true;
1148 return NULL;
1149 }
1150
1151 m->body_end->next = part;
1152 }
1153
1154 part->memfd = -1;
1155 m->body_end = part;
1156 m->n_body_parts ++;
1157
1158 return part;
1159 }
1160
1161 static void part_zero(struct bus_body_part *part, size_t sz) {
1162 assert(part);
1163 assert(sz > 0);
1164 assert(sz < 8);
1165
1166 /* All other fields can be left in their defaults */
1167 assert(!part->data);
1168 assert(part->memfd < 0);
1169
1170 part->size = sz;
1171 part->is_zero = true;
1172 part->sealed = true;
1173 }
1174
1175 static int part_make_space(
1176 struct sd_bus_message *m,
1177 struct bus_body_part *part,
1178 size_t sz,
1179 void **q) {
1180
1181 void *n;
1182 int r;
1183
1184 assert(m);
1185 assert(part);
1186 assert(!part->sealed);
1187
1188 if (m->poisoned)
1189 return -ENOMEM;
1190
1191 if (!part->data && part->memfd < 0)
1192 part->memfd = bus_kernel_pop_memfd(m->bus, &part->data, &part->mapped);
1193
1194 if (part->memfd >= 0) {
1195 uint64_t u = sz;
1196
1197 r = ioctl(part->memfd, KDBUS_CMD_MEMFD_SIZE_SET, &u);
1198 if (r < 0) {
1199 m->poisoned = true;
1200 return -errno;
1201 }
1202
1203 if (!part->data || sz > part->mapped) {
1204 size_t psz = PAGE_ALIGN(sz > 0 ? sz : 1);
1205
1206 if (part->mapped <= 0)
1207 n = mmap(NULL, psz, PROT_READ|PROT_WRITE, MAP_SHARED, part->memfd, 0);
1208 else
1209 n = mremap(part->data, part->mapped, psz, MREMAP_MAYMOVE);
1210
1211 if (n == MAP_FAILED) {
1212 m->poisoned = true;
1213 return -errno;
1214 }
1215
1216 part->mapped = psz;
1217 part->data = n;
1218 }
1219
1220 part->munmap_this = true;
1221 } else {
1222 n = realloc(part->data, MAX(sz, 1u));
1223 if (!n) {
1224 m->poisoned = true;
1225 return -ENOMEM;
1226 }
1227
1228 part->data = n;
1229 part->free_this = true;
1230 }
1231
1232 if (q)
1233 *q = part->data ? (uint8_t*) part->data + part->size : NULL;
1234
1235 part->size = sz;
1236 return 0;
1237 }
1238
1239 static void message_extend_containers(sd_bus_message *m, size_t expand) {
1240 struct bus_container *c;
1241
1242 assert(m);
1243
1244 if (expand <= 0)
1245 return;
1246
1247 /* Update counters */
1248 for (c = m->containers; c < m->containers + m->n_containers; c++)
1249 if (c->array_size)
1250 *c->array_size += expand;
1251 }
1252
1253 static void *message_extend_body(sd_bus_message *m, size_t align, size_t sz) {
1254 struct bus_body_part *part = NULL;
1255 size_t start_body, end_body, padding, start_part, end_part, added;
1256 bool add_new_part;
1257 void *p;
1258 int r;
1259
1260 assert(m);
1261 assert(align > 0);
1262 assert(!m->sealed);
1263
1264 if (m->poisoned)
1265 return NULL;
1266
1267 start_body = ALIGN_TO((size_t) m->header->body_size, align);
1268 end_body = start_body + sz;
1269
1270 padding = start_body - m->header->body_size;
1271 added = padding + sz;
1272
1273 /* Check for 32bit overflows */
1274 if (end_body > (size_t) ((uint32_t) -1)) {
1275 m->poisoned = true;
1276 return NULL;
1277 }
1278
1279 add_new_part =
1280 m->n_body_parts <= 0 ||
1281 m->body_end->sealed ||
1282 padding != ALIGN_TO(m->body_end->size, align) - m->body_end->size;
1283
1284 if (add_new_part) {
1285 if (padding > 0) {
1286 part = message_append_part(m);
1287 if (!part)
1288 return NULL;
1289
1290 part_zero(part, padding);
1291 }
1292
1293 part = message_append_part(m);
1294 if (!part)
1295 return NULL;
1296
1297 r = part_make_space(m, part, sz, &p);
1298 if (r < 0)
1299 return NULL;
1300 } else {
1301 struct bus_container *c;
1302 void *op;
1303 size_t os;
1304
1305 part = m->body_end;
1306 op = part->data;
1307 os = part->size;
1308
1309 start_part = ALIGN_TO(part->size, align);
1310 end_part = start_part + sz;
1311
1312 r = part_make_space(m, part, end_part, &p);
1313 if (r < 0)
1314 return NULL;
1315
1316 if (padding > 0) {
1317 memset(p, 0, padding);
1318 p = (uint8_t*) p + padding;
1319 }
1320
1321 /* Readjust pointers */
1322 for (c = m->containers; c < m->containers + m->n_containers; c++)
1323 c->array_size = adjust_pointer(c->array_size, op, os, part->data);
1324
1325 m->error.message = (const char*) adjust_pointer(m->error.message, op, os, part->data);
1326 }
1327
1328 m->header->body_size = end_body;
1329 message_extend_containers(m, added);
1330
1331 return p;
1332 }
1333
1334 int message_append_basic(sd_bus_message *m, char type, const void *p, const void **stored) {
1335 struct bus_container *c;
1336 ssize_t align, sz;
1337 uint32_t k;
1338 void *a;
1339 int fd = -1;
1340 uint32_t fdi = 0;
1341 int r;
1342
1343 assert_return(m, -EINVAL);
1344 assert_return(!m->sealed, -EPERM);
1345 assert_return(bus_type_is_basic(type), -EINVAL);
1346 assert_return(!m->poisoned, -ESTALE);
1347
1348 c = message_get_container(m);
1349
1350 if (c->signature && c->signature[c->index]) {
1351 /* Container signature is already set */
1352
1353 if (c->signature[c->index] != type)
1354 return -ENXIO;
1355 } else {
1356 char *e;
1357
1358 /* Maybe we can append to the signature? But only if this is the top-level container*/
1359 if (c->enclosing != 0)
1360 return -ENXIO;
1361
1362 e = strextend(&c->signature, CHAR_TO_STR(type), NULL);
1363 if (!e) {
1364 m->poisoned = true;
1365 return -ENOMEM;
1366 }
1367 }
1368
1369 switch (type) {
1370
1371 case SD_BUS_TYPE_STRING:
1372 /* To make things easy we'll serialize a NULL string
1373 * into the empty string */
1374 p = strempty(p);
1375
1376 /* Fall through... */
1377 case SD_BUS_TYPE_OBJECT_PATH:
1378
1379 if (!p) {
1380 r = -EINVAL;
1381 goto fail;
1382 }
1383
1384 align = 4;
1385 sz = 4 + strlen(p) + 1;
1386 break;
1387
1388 case SD_BUS_TYPE_SIGNATURE:
1389
1390 if (!p) {
1391 r = -EINVAL;
1392 goto fail;
1393 }
1394
1395 align = 1;
1396 sz = 1 + strlen(p) + 1;
1397 break;
1398
1399 case SD_BUS_TYPE_BOOLEAN:
1400
1401 if (!p) {
1402 r = -EINVAL;
1403 goto fail;
1404 }
1405
1406 align = sz = 4;
1407
1408 assert_cc(sizeof(int) == sizeof(uint32_t));
1409 memcpy(&k, p, 4);
1410 k = !!k;
1411 p = &k;
1412 break;
1413
1414 case SD_BUS_TYPE_UNIX_FD: {
1415 int z, *f;
1416
1417 if (!p) {
1418 r = -EINVAL;
1419 goto fail;
1420 }
1421
1422 if (!m->allow_fds) {
1423 r = -ENOTSUP;
1424 goto fail;
1425 }
1426
1427 align = sz = 4;
1428
1429 z = *(int*) p;
1430 if (z < 0) {
1431 r = -EINVAL;
1432 goto fail;
1433 }
1434
1435 fd = fcntl(z, F_DUPFD_CLOEXEC, 3);
1436 if (fd < 0) {
1437 r = -errno;
1438 goto fail;
1439 }
1440
1441 f = realloc(m->fds, sizeof(int) * (m->n_fds + 1));
1442 if (!f) {
1443 m->poisoned = true;
1444 r = -ENOMEM;
1445 goto fail;
1446 }
1447
1448 fdi = m->n_fds;
1449 f[fdi] = fd;
1450 m->fds = f;
1451 m->free_fds = true;
1452 break;
1453 }
1454
1455 default:
1456 if (!p) {
1457 r = -EINVAL;
1458 goto fail;
1459 }
1460
1461 align = bus_type_get_alignment(type);
1462 sz = bus_type_get_size(type);
1463 break;
1464 }
1465
1466 assert(align > 0);
1467 assert(sz > 0);
1468
1469 a = message_extend_body(m, align, sz);
1470 if (!a) {
1471 r = -ENOMEM;
1472 goto fail;
1473 }
1474
1475 if (type == SD_BUS_TYPE_STRING || type == SD_BUS_TYPE_OBJECT_PATH) {
1476 *(uint32_t*) a = sz - 5;
1477 memcpy((uint8_t*) a + 4, p, sz - 4);
1478
1479 if (stored)
1480 *stored = (const uint8_t*) a + 4;
1481
1482 } else if (type == SD_BUS_TYPE_SIGNATURE) {
1483 *(uint8_t*) a = sz - 1;
1484 memcpy((uint8_t*) a + 1, p, sz - 1);
1485
1486 if (stored)
1487 *stored = (const uint8_t*) a + 1;
1488 } else if (type == SD_BUS_TYPE_UNIX_FD) {
1489 *(uint32_t*) a = fdi;
1490
1491 if (stored)
1492 *stored = a;
1493
1494 m->n_fds ++;
1495
1496 } else {
1497 memcpy(a, p, sz);
1498
1499 if (stored)
1500 *stored = a;
1501 }
1502
1503 if (c->enclosing != SD_BUS_TYPE_ARRAY)
1504 c->index++;
1505
1506 return 0;
1507
1508 fail:
1509 if (fd >= 0)
1510 close_nointr_nofail(fd);
1511
1512 return r;
1513 }
1514
1515 _public_ int sd_bus_message_append_basic(sd_bus_message *m, char type, const void *p) {
1516 return message_append_basic(m, type, p, NULL);
1517 }
1518
1519 _public_ int sd_bus_message_append_string_space(
1520 sd_bus_message *m,
1521 size_t size,
1522 char **s) {
1523
1524 struct bus_container *c;
1525 void *a;
1526
1527 assert_return(m, -EINVAL);
1528 assert_return(s, -EINVAL);
1529 assert_return(!m->sealed, -EPERM);
1530 assert_return(!m->poisoned, -ESTALE);
1531
1532 c = message_get_container(m);
1533
1534 if (c->signature && c->signature[c->index]) {
1535 /* Container signature is already set */
1536
1537 if (c->signature[c->index] != SD_BUS_TYPE_STRING)
1538 return -ENXIO;
1539 } else {
1540 char *e;
1541
1542 /* Maybe we can append to the signature? But only if this is the top-level container*/
1543 if (c->enclosing != 0)
1544 return -ENXIO;
1545
1546 e = strextend(&c->signature, CHAR_TO_STR(SD_BUS_TYPE_STRING), NULL);
1547 if (!e) {
1548 m->poisoned = true;
1549 return -ENOMEM;
1550 }
1551 }
1552
1553 a = message_extend_body(m, 4, 4 + size + 1);
1554 if (!a)
1555 return -ENOMEM;
1556
1557 *(uint32_t*) a = size;
1558 *s = (char*) a + 4;
1559
1560 (*s)[size] = 0;
1561
1562 if (c->enclosing != SD_BUS_TYPE_ARRAY)
1563 c->index++;
1564
1565 return 0;
1566 }
1567
1568 _public_ int sd_bus_message_append_string_iovec(
1569 sd_bus_message *m,
1570 const struct iovec *iov,
1571 unsigned n) {
1572
1573 size_t size;
1574 unsigned i;
1575 char *p;
1576 int r;
1577
1578 assert_return(m, -EINVAL);
1579 assert_return(!m->sealed, -EPERM);
1580 assert_return(iov || n == 0, -EINVAL);
1581 assert_return(!m->poisoned, -ESTALE);
1582
1583 size = IOVEC_TOTAL_SIZE(iov, n);
1584
1585 r = sd_bus_message_append_string_space(m, size, &p);
1586 if (r < 0)
1587 return r;
1588
1589 for (i = 0; i < n; i++) {
1590
1591 if (iov[i].iov_base)
1592 memcpy(p, iov[i].iov_base, iov[i].iov_len);
1593 else
1594 memset(p, ' ', iov[i].iov_len);
1595
1596 p += iov[i].iov_len;
1597 }
1598
1599 return 0;
1600 }
1601
1602 static int bus_message_open_array(
1603 sd_bus_message *m,
1604 struct bus_container *c,
1605 const char *contents,
1606 uint32_t **array_size) {
1607
1608 unsigned nindex;
1609 void *a, *op;
1610 int alignment;
1611 size_t os;
1612 struct bus_body_part *o;
1613
1614 assert(m);
1615 assert(c);
1616 assert(contents);
1617 assert(array_size);
1618
1619 if (!signature_is_single(contents, true))
1620 return -EINVAL;
1621
1622 alignment = bus_type_get_alignment(contents[0]);
1623 if (alignment < 0)
1624 return alignment;
1625
1626 if (c->signature && c->signature[c->index]) {
1627
1628 /* Verify the existing signature */
1629
1630 if (c->signature[c->index] != SD_BUS_TYPE_ARRAY)
1631 return -ENXIO;
1632
1633 if (!startswith(c->signature + c->index + 1, contents))
1634 return -ENXIO;
1635
1636 nindex = c->index + 1 + strlen(contents);
1637 } else {
1638 char *e;
1639
1640 if (c->enclosing != 0)
1641 return -ENXIO;
1642
1643 /* Extend the existing signature */
1644
1645 e = strextend(&c->signature, CHAR_TO_STR(SD_BUS_TYPE_ARRAY), contents, NULL);
1646 if (!e) {
1647 m->poisoned = true;
1648 return -ENOMEM;
1649 }
1650
1651 nindex = e - c->signature;
1652 }
1653
1654 a = message_extend_body(m, 4, 4);
1655 if (!a)
1656 return -ENOMEM;
1657
1658 o = m->body_end;
1659 op = m->body_end->data;
1660 os = m->body_end->size;
1661
1662 /* Add alignment between size and first element */
1663 if (!message_extend_body(m, alignment, 0))
1664 return -ENOMEM;
1665
1666 if (c->enclosing != SD_BUS_TYPE_ARRAY)
1667 c->index = nindex;
1668
1669 /* location of array size might have changed so let's readjust a */
1670 if (o == m->body_end)
1671 a = adjust_pointer(a, op, os, m->body_end->data);
1672
1673 *(uint32_t*) a = 0;
1674 *array_size = a;
1675 return 0;
1676 }
1677
1678 static int bus_message_open_variant(
1679 sd_bus_message *m,
1680 struct bus_container *c,
1681 const char *contents) {
1682
1683 size_t l;
1684 void *a;
1685
1686 assert(m);
1687 assert(c);
1688 assert(contents);
1689
1690 if (!signature_is_single(contents, false))
1691 return -EINVAL;
1692
1693 if (*contents == SD_BUS_TYPE_DICT_ENTRY_BEGIN)
1694 return -EINVAL;
1695
1696 if (c->signature && c->signature[c->index]) {
1697
1698 if (c->signature[c->index] != SD_BUS_TYPE_VARIANT)
1699 return -ENXIO;
1700
1701 } else {
1702 char *e;
1703
1704 if (c->enclosing != 0)
1705 return -ENXIO;
1706
1707 e = strextend(&c->signature, CHAR_TO_STR(SD_BUS_TYPE_VARIANT), NULL);
1708 if (!e) {
1709 m->poisoned = true;
1710 return -ENOMEM;
1711 }
1712 }
1713
1714 l = strlen(contents);
1715 a = message_extend_body(m, 1, 1 + l + 1);
1716 if (!a)
1717 return -ENOMEM;
1718
1719 *(uint8_t*) a = l;
1720 memcpy((uint8_t*) a + 1, contents, l + 1);
1721
1722 if (c->enclosing != SD_BUS_TYPE_ARRAY)
1723 c->index++;
1724
1725 return 0;
1726 }
1727
1728 static int bus_message_open_struct(
1729 sd_bus_message *m,
1730 struct bus_container *c,
1731 const char *contents) {
1732
1733 size_t nindex;
1734
1735 assert(m);
1736 assert(c);
1737 assert(contents);
1738
1739 if (!signature_is_valid(contents, false))
1740 return -EINVAL;
1741
1742 if (c->signature && c->signature[c->index]) {
1743 size_t l;
1744
1745 l = strlen(contents);
1746
1747 if (c->signature[c->index] != SD_BUS_TYPE_STRUCT_BEGIN ||
1748 !startswith(c->signature + c->index + 1, contents) ||
1749 c->signature[c->index + 1 + l] != SD_BUS_TYPE_STRUCT_END)
1750 return -ENXIO;
1751
1752 nindex = c->index + 1 + l + 1;
1753 } else {
1754 char *e;
1755
1756 if (c->enclosing != 0)
1757 return -ENXIO;
1758
1759 e = strextend(&c->signature, CHAR_TO_STR(SD_BUS_TYPE_STRUCT_BEGIN), contents, CHAR_TO_STR(SD_BUS_TYPE_STRUCT_END), NULL);
1760 if (!e) {
1761 m->poisoned = true;
1762 return -ENOMEM;
1763 }
1764
1765 nindex = e - c->signature;
1766 }
1767
1768 /* Align contents to 8 byte boundary */
1769 if (!message_extend_body(m, 8, 0))
1770 return -ENOMEM;
1771
1772 if (c->enclosing != SD_BUS_TYPE_ARRAY)
1773 c->index = nindex;
1774
1775 return 0;
1776 }
1777
1778 static int bus_message_open_dict_entry(
1779 sd_bus_message *m,
1780 struct bus_container *c,
1781 const char *contents) {
1782
1783 size_t nindex;
1784
1785 assert(m);
1786 assert(c);
1787 assert(contents);
1788
1789 if (!signature_is_pair(contents))
1790 return -EINVAL;
1791
1792 if (c->enclosing != SD_BUS_TYPE_ARRAY)
1793 return -ENXIO;
1794
1795 if (c->signature && c->signature[c->index]) {
1796 size_t l;
1797
1798 l = strlen(contents);
1799
1800 if (c->signature[c->index] != SD_BUS_TYPE_DICT_ENTRY_BEGIN ||
1801 !startswith(c->signature + c->index + 1, contents) ||
1802 c->signature[c->index + 1 + l] != SD_BUS_TYPE_DICT_ENTRY_END)
1803 return -ENXIO;
1804
1805 nindex = c->index + 1 + l + 1;
1806 } else
1807 return -ENXIO;
1808
1809 /* Align contents to 8 byte boundary */
1810 if (!message_extend_body(m, 8, 0))
1811 return -ENOMEM;
1812
1813 if (c->enclosing != SD_BUS_TYPE_ARRAY)
1814 c->index = nindex;
1815
1816 return 0;
1817 }
1818
1819 _public_ int sd_bus_message_open_container(
1820 sd_bus_message *m,
1821 char type,
1822 const char *contents) {
1823
1824 struct bus_container *c, *w;
1825 uint32_t *array_size = NULL;
1826 char *signature;
1827 size_t before;
1828 int r;
1829
1830 assert_return(m, -EINVAL);
1831 assert_return(!m->sealed, -EPERM);
1832 assert_return(contents, -EINVAL);
1833 assert_return(!m->poisoned, -ESTALE);
1834
1835 /* Make sure we have space for one more container */
1836 w = realloc(m->containers, sizeof(struct bus_container) * (m->n_containers + 1));
1837 if (!w) {
1838 m->poisoned = true;
1839 return -ENOMEM;
1840 }
1841
1842 m->containers = w;
1843
1844 c = message_get_container(m);
1845
1846 signature = strdup(contents);
1847 if (!signature) {
1848 m->poisoned = true;
1849 return -ENOMEM;
1850 }
1851
1852 /* Save old index in the parent container, in case we have to
1853 * abort this container */
1854 c->saved_index = c->index;
1855 before = m->header->body_size;
1856
1857 if (type == SD_BUS_TYPE_ARRAY)
1858 r = bus_message_open_array(m, c, contents, &array_size);
1859 else if (type == SD_BUS_TYPE_VARIANT)
1860 r = bus_message_open_variant(m, c, contents);
1861 else if (type == SD_BUS_TYPE_STRUCT)
1862 r = bus_message_open_struct(m, c, contents);
1863 else if (type == SD_BUS_TYPE_DICT_ENTRY)
1864 r = bus_message_open_dict_entry(m, c, contents);
1865 else
1866 r = -EINVAL;
1867
1868 if (r < 0) {
1869 free(signature);
1870 return r;
1871 }
1872
1873 /* OK, let's fill it in */
1874 w += m->n_containers++;
1875 w->enclosing = type;
1876 w->signature = signature;
1877 w->index = 0;
1878 w->array_size = array_size;
1879 w->before = before;
1880 w->begin = m->rindex;
1881
1882 return 0;
1883 }
1884
1885 _public_ int sd_bus_message_close_container(sd_bus_message *m) {
1886 struct bus_container *c;
1887
1888 assert_return(m, -EINVAL);
1889 assert_return(!m->sealed, -EPERM);
1890 assert_return(m->n_containers > 0, -EINVAL);
1891 assert_return(!m->poisoned, -ESTALE);
1892
1893 c = message_get_container(m);
1894 if (c->enclosing != SD_BUS_TYPE_ARRAY)
1895 if (c->signature && c->signature[c->index] != 0)
1896 return -EINVAL;
1897
1898 free(c->signature);
1899 m->n_containers--;
1900
1901 return 0;
1902 }
1903
1904 typedef struct {
1905 const char *types;
1906 unsigned n_struct;
1907 unsigned n_array;
1908 } TypeStack;
1909
1910 static int type_stack_push(TypeStack *stack, unsigned max, unsigned *i, const char *types, unsigned n_struct, unsigned n_array) {
1911 assert(stack);
1912 assert(max > 0);
1913
1914 if (*i >= max)
1915 return -EINVAL;
1916
1917 stack[*i].types = types;
1918 stack[*i].n_struct = n_struct;
1919 stack[*i].n_array = n_array;
1920 (*i)++;
1921
1922 return 0;
1923 }
1924
1925 static int type_stack_pop(TypeStack *stack, unsigned max, unsigned *i, const char **types, unsigned *n_struct, unsigned *n_array) {
1926 assert(stack);
1927 assert(max > 0);
1928 assert(types);
1929 assert(n_struct);
1930 assert(n_array);
1931
1932 if (*i <= 0)
1933 return 0;
1934
1935 (*i)--;
1936 *types = stack[*i].types;
1937 *n_struct = stack[*i].n_struct;
1938 *n_array = stack[*i].n_array;
1939
1940 return 1;
1941 }
1942
1943 int bus_message_append_ap(
1944 sd_bus_message *m,
1945 const char *types,
1946 va_list ap) {
1947
1948 unsigned n_array, n_struct;
1949 TypeStack stack[BUS_CONTAINER_DEPTH];
1950 unsigned stack_ptr = 0;
1951 int r;
1952
1953 assert(m);
1954
1955 if (!types)
1956 return 0;
1957
1958 n_array = (unsigned) -1;
1959 n_struct = strlen(types);
1960
1961 for (;;) {
1962 const char *t;
1963
1964 if (n_array == 0 || (n_array == (unsigned) -1 && n_struct == 0)) {
1965 r = type_stack_pop(stack, ELEMENTSOF(stack), &stack_ptr, &types, &n_struct, &n_array);
1966 if (r < 0)
1967 return r;
1968 if (r == 0)
1969 break;
1970
1971 r = sd_bus_message_close_container(m);
1972 if (r < 0)
1973 return r;
1974
1975 continue;
1976 }
1977
1978 t = types;
1979 if (n_array != (unsigned) -1)
1980 n_array --;
1981 else {
1982 types ++;
1983 n_struct--;
1984 }
1985
1986 switch (*t) {
1987
1988 case SD_BUS_TYPE_BYTE: {
1989 uint8_t x;
1990
1991 x = (uint8_t) va_arg(ap, int);
1992 r = sd_bus_message_append_basic(m, *t, &x);
1993 break;
1994 }
1995
1996 case SD_BUS_TYPE_BOOLEAN:
1997 case SD_BUS_TYPE_INT32:
1998 case SD_BUS_TYPE_UINT32:
1999 case SD_BUS_TYPE_UNIX_FD: {
2000 uint32_t x;
2001
2002 /* We assume a boolean is the same as int32_t */
2003 assert_cc(sizeof(int32_t) == sizeof(int));
2004
2005 x = va_arg(ap, uint32_t);
2006 r = sd_bus_message_append_basic(m, *t, &x);
2007 break;
2008 }
2009
2010 case SD_BUS_TYPE_INT16:
2011 case SD_BUS_TYPE_UINT16: {
2012 uint16_t x;
2013
2014 x = (uint16_t) va_arg(ap, int);
2015 r = sd_bus_message_append_basic(m, *t, &x);
2016 break;
2017 }
2018
2019 case SD_BUS_TYPE_INT64:
2020 case SD_BUS_TYPE_UINT64:
2021 case SD_BUS_TYPE_DOUBLE: {
2022 uint64_t x;
2023
2024 x = va_arg(ap, uint64_t);
2025 r = sd_bus_message_append_basic(m, *t, &x);
2026 break;
2027 }
2028
2029 case SD_BUS_TYPE_STRING:
2030 case SD_BUS_TYPE_OBJECT_PATH:
2031 case SD_BUS_TYPE_SIGNATURE: {
2032 const char *x;
2033
2034 x = va_arg(ap, const char*);
2035 r = sd_bus_message_append_basic(m, *t, x);
2036 break;
2037 }
2038
2039 case SD_BUS_TYPE_ARRAY: {
2040 size_t k;
2041
2042 r = signature_element_length(t + 1, &k);
2043 if (r < 0)
2044 return r;
2045
2046 {
2047 char s[k + 1];
2048 memcpy(s, t + 1, k);
2049 s[k] = 0;
2050
2051 r = sd_bus_message_open_container(m, SD_BUS_TYPE_ARRAY, s);
2052 if (r < 0)
2053 return r;
2054 }
2055
2056 if (n_array == (unsigned) -1) {
2057 types += k;
2058 n_struct -= k;
2059 }
2060
2061 r = type_stack_push(stack, ELEMENTSOF(stack), &stack_ptr, types, n_struct, n_array);
2062 if (r < 0)
2063 return r;
2064
2065 types = t + 1;
2066 n_struct = k;
2067 n_array = va_arg(ap, unsigned);
2068
2069 break;
2070 }
2071
2072 case SD_BUS_TYPE_VARIANT: {
2073 const char *s;
2074
2075 s = va_arg(ap, const char*);
2076 if (!s)
2077 return -EINVAL;
2078
2079 r = sd_bus_message_open_container(m, SD_BUS_TYPE_VARIANT, s);
2080 if (r < 0)
2081 return r;
2082
2083 r = type_stack_push(stack, ELEMENTSOF(stack), &stack_ptr, types, n_struct, n_array);
2084 if (r < 0)
2085 return r;
2086
2087 types = s;
2088 n_struct = strlen(s);
2089 n_array = (unsigned) -1;
2090
2091 break;
2092 }
2093
2094 case SD_BUS_TYPE_STRUCT_BEGIN:
2095 case SD_BUS_TYPE_DICT_ENTRY_BEGIN: {
2096 size_t k;
2097
2098 r = signature_element_length(t, &k);
2099 if (r < 0)
2100 return r;
2101
2102 {
2103 char s[k - 1];
2104
2105 memcpy(s, t + 1, k - 2);
2106 s[k - 2] = 0;
2107
2108 r = sd_bus_message_open_container(m, *t == SD_BUS_TYPE_STRUCT_BEGIN ? SD_BUS_TYPE_STRUCT : SD_BUS_TYPE_DICT_ENTRY, s);
2109 if (r < 0)
2110 return r;
2111 }
2112
2113 if (n_array == (unsigned) -1) {
2114 types += k - 1;
2115 n_struct -= k - 1;
2116 }
2117
2118 r = type_stack_push(stack, ELEMENTSOF(stack), &stack_ptr, types, n_struct, n_array);
2119 if (r < 0)
2120 return r;
2121
2122 types = t + 1;
2123 n_struct = k - 2;
2124 n_array = (unsigned) -1;
2125
2126 break;
2127 }
2128
2129 default:
2130 r = -EINVAL;
2131 }
2132
2133 if (r < 0)
2134 return r;
2135 }
2136
2137 return 0;
2138 }
2139
2140 _public_ int sd_bus_message_append(sd_bus_message *m, const char *types, ...) {
2141 va_list ap;
2142 int r;
2143
2144 assert_return(m, -EINVAL);
2145 assert_return(types, -EINVAL);
2146 assert_return(!m->sealed, -EPERM);
2147 assert_return(!m->poisoned, -ESTALE);
2148
2149 va_start(ap, types);
2150 r = bus_message_append_ap(m, types, ap);
2151 va_end(ap);
2152
2153 return r;
2154 }
2155
2156 _public_ int sd_bus_message_append_array_space(sd_bus_message *m,
2157 char type,
2158 size_t size,
2159 void **ptr) {
2160 ssize_t align, sz;
2161 void *a;
2162 int r;
2163
2164 assert_return(m, -EINVAL);
2165 assert_return(!m->sealed, -EPERM);
2166 assert_return(bus_type_is_trivial(type), -EINVAL);
2167 assert_return(ptr || size == 0, -EINVAL);
2168 assert_return(!m->poisoned, -ESTALE);
2169
2170 align = bus_type_get_alignment(type);
2171 sz = bus_type_get_size(type);
2172
2173 assert_se(align > 0);
2174 assert_se(sz > 0);
2175
2176 if (size % sz != 0)
2177 return -EINVAL;
2178
2179 r = sd_bus_message_open_container(m, SD_BUS_TYPE_ARRAY, CHAR_TO_STR(type));
2180 if (r < 0)
2181 return r;
2182
2183 a = message_extend_body(m, align, size);
2184 if (!a)
2185 return -ENOMEM;
2186
2187 r = sd_bus_message_close_container(m);
2188 if (r < 0)
2189 return r;
2190
2191 *ptr = a;
2192 return 0;
2193 }
2194
2195 _public_ int sd_bus_message_append_array(sd_bus_message *m,
2196 char type,
2197 const void *ptr,
2198 size_t size) {
2199 int r;
2200 void *p;
2201
2202 assert_return(m, -EINVAL);
2203 assert_return(!m->sealed, -EPERM);
2204 assert_return(bus_type_is_trivial(type), -EINVAL);
2205 assert_return(ptr || size == 0, -EINVAL);
2206 assert_return(!m->poisoned, -ESTALE);
2207
2208 r = sd_bus_message_append_array_space(m, type, size, &p);
2209 if (r < 0)
2210 return r;
2211
2212 if (size > 0)
2213 memcpy(p, ptr, size);
2214
2215 return 0;
2216 }
2217
2218 _public_ int sd_bus_message_append_array_iovec(
2219 sd_bus_message *m,
2220 char type,
2221 const struct iovec *iov,
2222 unsigned n) {
2223
2224 size_t size;
2225 unsigned i;
2226 void *p;
2227 int r;
2228
2229 assert_return(m, -EINVAL);
2230 assert_return(!m->sealed, -EPERM);
2231 assert_return(bus_type_is_trivial(type), -EINVAL);
2232 assert_return(iov || n == 0, -EINVAL);
2233 assert_return(!m->poisoned, -ESTALE);
2234
2235 size = IOVEC_TOTAL_SIZE(iov, n);
2236
2237 r = sd_bus_message_append_array_space(m, type, size, &p);
2238 if (r < 0)
2239 return r;
2240
2241 for (i = 0; i < n; i++) {
2242
2243 if (iov[i].iov_base)
2244 memcpy(p, iov[i].iov_base, iov[i].iov_len);
2245 else
2246 memset(p, 0, iov[i].iov_len);
2247
2248 p = (uint8_t*) p + iov[i].iov_len;
2249 }
2250
2251 return 0;
2252 }
2253
2254 _public_ int sd_bus_message_append_array_memfd(sd_bus_message *m,
2255 char type,
2256 sd_memfd *memfd) {
2257 _cleanup_close_ int copy_fd = -1;
2258 struct bus_body_part *part;
2259 ssize_t align, sz;
2260 uint64_t size;
2261 void *a;
2262 int r;
2263
2264 if (!m)
2265 return -EINVAL;
2266 if (!memfd)
2267 return -EINVAL;
2268 if (m->sealed)
2269 return -EPERM;
2270 if (!bus_type_is_trivial(type))
2271 return -EINVAL;
2272 if (m->poisoned)
2273 return -ESTALE;
2274
2275 r = sd_memfd_set_sealed(memfd, true);
2276 if (r < 0)
2277 return r;
2278
2279 copy_fd = sd_memfd_dup_fd(memfd);
2280 if (copy_fd < 0)
2281 return copy_fd;
2282
2283 r = sd_memfd_get_size(memfd, &size);
2284 if (r < 0)
2285 return r;
2286
2287 align = bus_type_get_alignment(type);
2288 sz = bus_type_get_size(type);
2289
2290 assert_se(align > 0);
2291 assert_se(sz > 0);
2292
2293 if (size % sz != 0)
2294 return -EINVAL;
2295
2296 if (size > (uint64_t) (uint32_t) -1)
2297 return -EINVAL;
2298
2299 r = sd_bus_message_open_container(m, SD_BUS_TYPE_ARRAY, CHAR_TO_STR(type));
2300 if (r < 0)
2301 return r;
2302
2303 a = message_extend_body(m, align, 0);
2304 if (!a)
2305 return -ENOMEM;
2306
2307 part = message_append_part(m);
2308 if (!part)
2309 return -ENOMEM;
2310
2311 part->memfd = copy_fd;
2312 part->sealed = true;
2313 part->size = size;
2314 copy_fd = -1;
2315
2316 message_extend_containers(m, size);
2317 m->header->body_size += size;
2318
2319 return sd_bus_message_close_container(m);
2320 }
2321
2322 _public_ int sd_bus_message_append_string_memfd(sd_bus_message *m, sd_memfd *memfd) {
2323 _cleanup_close_ int copy_fd = -1;
2324 struct bus_body_part *part;
2325 struct bus_container *c;
2326 uint64_t size;
2327 void *a;
2328 int r;
2329
2330 assert_return(m, -EINVAL);
2331 assert_return(memfd, -EINVAL);
2332 assert_return(!m->sealed, -EPERM);
2333 assert_return(!m->poisoned, -ESTALE);
2334
2335 r = sd_memfd_set_sealed(memfd, true);
2336 if (r < 0)
2337 return r;
2338
2339 copy_fd = sd_memfd_dup_fd(memfd);
2340 if (copy_fd < 0)
2341 return copy_fd;
2342
2343 r = sd_memfd_get_size(memfd, &size);
2344 if (r < 0)
2345 return r;
2346
2347 /* We require this to be NUL terminated */
2348 if (size == 0)
2349 return -EINVAL;
2350
2351 if (size > (uint64_t) (uint32_t) -1)
2352 return -EINVAL;
2353
2354 c = message_get_container(m);
2355 if (c->signature && c->signature[c->index]) {
2356 /* Container signature is already set */
2357
2358 if (c->signature[c->index] != SD_BUS_TYPE_STRING)
2359 return -ENXIO;
2360 } else {
2361 char *e;
2362
2363 /* Maybe we can append to the signature? But only if this is the top-level container*/
2364 if (c->enclosing != 0)
2365 return -ENXIO;
2366
2367 e = strextend(&c->signature, CHAR_TO_STR(SD_BUS_TYPE_STRING), NULL);
2368 if (!e) {
2369 m->poisoned = true;
2370 return -ENOMEM;
2371 }
2372 }
2373
2374 a = message_extend_body(m, 4, 4);
2375 if (!a)
2376 return -ENOMEM;
2377
2378 *(uint32_t*) a = size - 1;
2379
2380 part = message_append_part(m);
2381 if (!part)
2382 return -ENOMEM;
2383
2384 part->memfd = copy_fd;
2385 part->sealed = true;
2386 part->size = size;
2387 copy_fd = -1;
2388
2389 message_extend_containers(m, size);
2390 m->header->body_size += size;
2391
2392 if (c->enclosing != SD_BUS_TYPE_ARRAY)
2393 c->index++;
2394
2395 return 0;
2396 }
2397
2398 _public_ int sd_bus_message_append_strv(sd_bus_message *m, char **l) {
2399 char **i;
2400 int r;
2401
2402 assert_return(m, -EINVAL);
2403 assert_return(!m->sealed, -EPERM);
2404 assert_return(!m->poisoned, -ESTALE);
2405
2406 r = sd_bus_message_open_container(m, 'a', "s");
2407 if (r < 0)
2408 return r;
2409
2410 STRV_FOREACH(i, l) {
2411 r = sd_bus_message_append_basic(m, 's', *i);
2412 if (r < 0)
2413 return r;
2414 }
2415
2416 return sd_bus_message_close_container(m);
2417 }
2418
2419 int bus_body_part_map(struct bus_body_part *part) {
2420 void *p;
2421 size_t psz;
2422
2423 assert_se(part);
2424
2425 if (part->data)
2426 return 0;
2427
2428 if (part->size <= 0)
2429 return 0;
2430
2431 /* For smaller zero parts (as used for padding) we don't need to map anything... */
2432 if (part->memfd < 0 && part->is_zero && part->size < 8) {
2433 static const uint8_t zeroes[7] = { };
2434 part->data = (void*) zeroes;
2435 return 0;
2436 }
2437
2438 psz = PAGE_ALIGN(part->size);
2439
2440 if (part->memfd >= 0)
2441 p = mmap(NULL, psz, PROT_READ, MAP_SHARED, part->memfd, 0);
2442 else if (part->is_zero)
2443 p = mmap(NULL, psz, PROT_READ, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0);
2444 else
2445 return -EINVAL;
2446
2447 if (p == MAP_FAILED)
2448 return -errno;
2449
2450 part->mapped = psz;
2451 part->data = p;
2452 part->munmap_this = true;
2453
2454 return 0;
2455 }
2456
2457 void bus_body_part_unmap(struct bus_body_part *part) {
2458
2459 assert_se(part);
2460
2461 if (part->memfd < 0)
2462 return;
2463
2464 if (!part->data)
2465 return;
2466
2467 if (!part->munmap_this)
2468 return;
2469
2470 assert_se(munmap(part->data, part->mapped) == 0);
2471
2472 part->data = NULL;
2473 part->mapped = 0;
2474 part->munmap_this = false;
2475
2476 return;
2477 }
2478
2479 static int buffer_peek(const void *p, uint32_t sz, size_t *rindex, size_t align, size_t nbytes, void **r) {
2480 size_t k, start, end;
2481
2482 assert(rindex);
2483 assert(align > 0);
2484
2485 start = ALIGN_TO((size_t) *rindex, align);
2486 end = start + nbytes;
2487
2488 if (end > sz)
2489 return -EBADMSG;
2490
2491 /* Verify that padding is 0 */
2492 for (k = *rindex; k < start; k++)
2493 if (((const uint8_t*) p)[k] != 0)
2494 return -EBADMSG;
2495
2496 if (r)
2497 *r = (uint8_t*) p + start;
2498
2499 *rindex = end;
2500
2501 return 1;
2502 }
2503
2504 static bool message_end_of_signature(sd_bus_message *m) {
2505 struct bus_container *c;
2506
2507 assert(m);
2508
2509 c = message_get_container(m);
2510 return !c->signature || c->signature[c->index] == 0;
2511 }
2512
2513 static bool message_end_of_array(sd_bus_message *m, size_t index) {
2514 struct bus_container *c;
2515
2516 assert(m);
2517
2518 c = message_get_container(m);
2519 if (!c->array_size)
2520 return false;
2521
2522 return index >= c->begin + BUS_MESSAGE_BSWAP32(m, *c->array_size);
2523 }
2524
2525 _public_ int sd_bus_message_at_end(sd_bus_message *m, int complete) {
2526 assert_return(m, -EINVAL);
2527 assert_return(m->sealed, -EPERM);
2528
2529 if (complete && m->n_containers > 0)
2530 return false;
2531
2532 if (message_end_of_signature(m))
2533 return true;
2534
2535 if (message_end_of_array(m, m->rindex))
2536 return true;
2537
2538 return false;
2539 }
2540
2541 static struct bus_body_part* find_part(sd_bus_message *m, size_t index, size_t sz, void **p) {
2542 struct bus_body_part *part;
2543 size_t begin;
2544 int r;
2545
2546 assert(m);
2547
2548 if (m->cached_rindex_part && index >= m->cached_rindex_part_begin) {
2549 part = m->cached_rindex_part;
2550 begin = m->cached_rindex_part_begin;
2551 } else {
2552 part = &m->body;
2553 begin = 0;
2554 }
2555
2556 while (part) {
2557 if (index < begin)
2558 return NULL;
2559
2560 if (index + sz <= begin + part->size) {
2561
2562 r = bus_body_part_map(part);
2563 if (r < 0)
2564 return NULL;
2565
2566 if (p)
2567 *p = (uint8_t*) part->data + index - begin;
2568
2569 m->cached_rindex_part = part;
2570 m->cached_rindex_part_begin = begin;
2571
2572 return part;
2573 }
2574
2575 begin += part->size;
2576 part = part->next;
2577 }
2578
2579 return NULL;
2580 }
2581
2582 static int message_peek_body(
2583 sd_bus_message *m,
2584 size_t *rindex,
2585 size_t align,
2586 size_t nbytes,
2587 void **ret) {
2588
2589 size_t k, start, end, padding;
2590 struct bus_body_part *part;
2591 uint8_t *q;
2592
2593 assert(m);
2594 assert(rindex);
2595 assert(align > 0);
2596
2597 if (message_end_of_array(m, *rindex))
2598 return 0;
2599
2600 start = ALIGN_TO((size_t) *rindex, align);
2601 padding = start - *rindex;
2602 end = start + nbytes;
2603
2604 if (end > BUS_MESSAGE_BODY_SIZE(m))
2605 return -EBADMSG;
2606
2607 part = find_part(m, *rindex, padding, (void**) &q);
2608 if (!part)
2609 return -EBADMSG;
2610
2611 if (q) {
2612 /* Verify padding */
2613 for (k = 0; k < padding; k++)
2614 if (q[k] != 0)
2615 return -EBADMSG;
2616 }
2617
2618 part = find_part(m, start, nbytes, (void**) &q);
2619 if (!part || !q)
2620 return -EBADMSG;
2621
2622 *rindex = end;
2623
2624 if (ret)
2625 *ret = q;
2626
2627 return 1;
2628 }
2629
2630 static bool validate_nul(const char *s, size_t l) {
2631
2632 /* Check for NUL chars in the string */
2633 if (memchr(s, 0, l))
2634 return false;
2635
2636 /* Check for NUL termination */
2637 if (s[l] != 0)
2638 return false;
2639
2640 return true;
2641 }
2642
2643 static bool validate_string(const char *s, size_t l) {
2644
2645 if (!validate_nul(s, l))
2646 return false;
2647
2648 /* Check if valid UTF8 */
2649 if (!utf8_is_valid(s))
2650 return false;
2651
2652 return true;
2653 }
2654
2655 static bool validate_signature(const char *s, size_t l) {
2656
2657 if (!validate_nul(s, l))
2658 return false;
2659
2660 /* Check if valid signature */
2661 if (!signature_is_valid(s, true))
2662 return false;
2663
2664 return true;
2665 }
2666
2667 static bool validate_object_path(const char *s, size_t l) {
2668
2669 if (!validate_nul(s, l))
2670 return false;
2671
2672 if (!object_path_is_valid(s))
2673 return false;
2674
2675 return true;
2676 }
2677
2678 _public_ int sd_bus_message_read_basic(sd_bus_message *m, char type, void *p) {
2679 struct bus_container *c;
2680 void *q;
2681 int r;
2682
2683 assert_return(m, -EINVAL);
2684 assert_return(m->sealed, -EPERM);
2685 assert_return(bus_type_is_basic(type), -EINVAL);
2686
2687 if (message_end_of_signature(m))
2688 return -ENXIO;
2689
2690 if (message_end_of_array(m, m->rindex))
2691 return 0;
2692
2693 c = message_get_container(m);
2694 if (c->signature[c->index] != type)
2695 return -ENXIO;
2696
2697 switch (type) {
2698
2699 case SD_BUS_TYPE_STRING:
2700 case SD_BUS_TYPE_OBJECT_PATH: {
2701 uint32_t l;
2702 size_t rindex;
2703
2704 rindex = m->rindex;
2705 r = message_peek_body(m, &rindex, 4, 4, &q);
2706 if (r <= 0)
2707 return r;
2708
2709 l = BUS_MESSAGE_BSWAP32(m, *(uint32_t*) q);
2710 r = message_peek_body(m, &rindex, 1, l+1, &q);
2711 if (r < 0)
2712 return r;
2713 if (r == 0)
2714 return -EBADMSG;
2715
2716 if (type == SD_BUS_TYPE_OBJECT_PATH) {
2717 if (!validate_object_path(q, l))
2718 return -EBADMSG;
2719 } else {
2720 if (!validate_string(q, l))
2721 return -EBADMSG;
2722 }
2723
2724 m->rindex = rindex;
2725 if (p)
2726 *(const char**) p = q;
2727
2728 break;
2729 }
2730
2731 case SD_BUS_TYPE_SIGNATURE: {
2732 uint8_t l;
2733 size_t rindex;
2734
2735 rindex = m->rindex;
2736 r = message_peek_body(m, &rindex, 1, 1, &q);
2737 if (r <= 0)
2738 return r;
2739
2740 l = *(uint8_t*) q;
2741 r = message_peek_body(m, &rindex, 1, l+1, &q);
2742 if (r < 0)
2743 return r;
2744 if (r == 0)
2745 return -EBADMSG;
2746
2747 if (!validate_signature(q, l))
2748 return -EBADMSG;
2749
2750 m->rindex = rindex;
2751
2752 if (p)
2753 *(const char**) p = q;
2754 break;
2755 }
2756
2757 default: {
2758 ssize_t sz, align;
2759 size_t rindex;
2760
2761 align = bus_type_get_alignment(type);
2762 sz = bus_type_get_size(type);
2763 assert(align > 0 && sz > 0);
2764
2765 rindex = m->rindex;
2766 r = message_peek_body(m, &rindex, align, sz, &q);
2767 if (r <= 0)
2768 return r;
2769
2770 switch (type) {
2771
2772 case SD_BUS_TYPE_BYTE:
2773 if (p)
2774 *(uint8_t*) p = *(uint8_t*) q;
2775 break;
2776
2777 case SD_BUS_TYPE_BOOLEAN:
2778 if (p)
2779 *(int*) p = !!*(uint32_t*) q;
2780 break;
2781
2782 case SD_BUS_TYPE_INT16:
2783 case SD_BUS_TYPE_UINT16:
2784 if (p)
2785 *(uint16_t*) p = BUS_MESSAGE_BSWAP16(m, *(uint16_t*) q);
2786 break;
2787
2788 case SD_BUS_TYPE_INT32:
2789 case SD_BUS_TYPE_UINT32:
2790 if (p)
2791 *(uint32_t*) p = BUS_MESSAGE_BSWAP32(m, *(uint32_t*) q);
2792 break;
2793
2794 case SD_BUS_TYPE_INT64:
2795 case SD_BUS_TYPE_UINT64:
2796 case SD_BUS_TYPE_DOUBLE:
2797 if (p)
2798 *(uint64_t*) p = BUS_MESSAGE_BSWAP64(m, *(uint64_t*) q);
2799 break;
2800
2801 case SD_BUS_TYPE_UNIX_FD: {
2802 uint32_t j;
2803
2804 j = BUS_MESSAGE_BSWAP32(m, *(uint32_t*) q);
2805 if (j >= m->n_fds)
2806 return -EBADMSG;
2807
2808 if (p)
2809 *(int*) p = m->fds[j];
2810 break;
2811 }
2812
2813 default:
2814 assert_not_reached("Unknown basic type...");
2815 }
2816
2817 m->rindex = rindex;
2818
2819 break;
2820 }
2821 }
2822
2823 if (c->enclosing != SD_BUS_TYPE_ARRAY)
2824 c->index++;
2825
2826 return 1;
2827 }
2828
2829 static int bus_message_enter_array(
2830 sd_bus_message *m,
2831 struct bus_container *c,
2832 const char *contents,
2833 uint32_t **array_size) {
2834
2835 size_t rindex;
2836 void *q;
2837 int r, alignment;
2838
2839 assert(m);
2840 assert(c);
2841 assert(contents);
2842 assert(array_size);
2843
2844 if (!signature_is_single(contents, true))
2845 return -EINVAL;
2846
2847 alignment = bus_type_get_alignment(contents[0]);
2848 if (alignment < 0)
2849 return alignment;
2850
2851 if (!c->signature || c->signature[c->index] == 0)
2852 return 0;
2853
2854 if (c->signature[c->index] != SD_BUS_TYPE_ARRAY)
2855 return -ENXIO;
2856
2857 if (!startswith(c->signature + c->index + 1, contents))
2858 return -ENXIO;
2859
2860 rindex = m->rindex;
2861 r = message_peek_body(m, &rindex, 4, 4, &q);
2862 if (r <= 0)
2863 return r;
2864
2865 if (BUS_MESSAGE_BSWAP32(m, *(uint32_t*) q) > BUS_ARRAY_MAX_SIZE)
2866 return -EBADMSG;
2867
2868 r = message_peek_body(m, &rindex, alignment, 0, NULL);
2869 if (r < 0)
2870 return r;
2871 if (r == 0)
2872 return -EBADMSG;
2873
2874 if (c->enclosing != SD_BUS_TYPE_ARRAY)
2875 c->index += 1 + strlen(contents);
2876
2877 m->rindex = rindex;
2878
2879 *array_size = (uint32_t*) q;
2880
2881 return 1;
2882 }
2883
2884 static int bus_message_enter_variant(
2885 sd_bus_message *m,
2886 struct bus_container *c,
2887 const char *contents) {
2888
2889 size_t rindex;
2890 uint8_t l;
2891 void *q;
2892 int r;
2893
2894 assert(m);
2895 assert(c);
2896 assert(contents);
2897
2898 if (!signature_is_single(contents, false))
2899 return -EINVAL;
2900
2901 if (*contents == SD_BUS_TYPE_DICT_ENTRY_BEGIN)
2902 return -EINVAL;
2903
2904 if (!c->signature || c->signature[c->index] == 0)
2905 return 0;
2906
2907 if (c->signature[c->index] != SD_BUS_TYPE_VARIANT)
2908 return -ENXIO;
2909
2910 rindex = m->rindex;
2911 r = message_peek_body(m, &rindex, 1, 1, &q);
2912 if (r <= 0)
2913 return r;
2914
2915 l = *(uint8_t*) q;
2916 r = message_peek_body(m, &rindex, 1, l+1, &q);
2917 if (r < 0)
2918 return r;
2919 if (r == 0)
2920 return -EBADMSG;
2921
2922 if (!validate_signature(q, l))
2923 return -EBADMSG;
2924
2925 if (!streq(q, contents))
2926 return -ENXIO;
2927
2928 if (c->enclosing != SD_BUS_TYPE_ARRAY)
2929 c->index++;
2930
2931 m->rindex = rindex;
2932
2933 return 1;
2934 }
2935
2936 static int bus_message_enter_struct(
2937 sd_bus_message *m,
2938 struct bus_container *c,
2939 const char *contents) {
2940
2941 size_t l;
2942 int r;
2943
2944 assert(m);
2945 assert(c);
2946 assert(contents);
2947
2948 if (!signature_is_valid(contents, false))
2949 return -EINVAL;
2950
2951 if (!c->signature || c->signature[c->index] == 0)
2952 return 0;
2953
2954 l = strlen(contents);
2955
2956 if (c->signature[c->index] != SD_BUS_TYPE_STRUCT_BEGIN ||
2957 !startswith(c->signature + c->index + 1, contents) ||
2958 c->signature[c->index + 1 + l] != SD_BUS_TYPE_STRUCT_END)
2959 return -ENXIO;
2960
2961 r = message_peek_body(m, &m->rindex, 8, 0, NULL);
2962 if (r <= 0)
2963 return r;
2964
2965 if (c->enclosing != SD_BUS_TYPE_ARRAY)
2966 c->index += 1 + l + 1;
2967
2968 return 1;
2969 }
2970
2971 static int bus_message_enter_dict_entry(
2972 sd_bus_message *m,
2973 struct bus_container *c,
2974 const char *contents) {
2975
2976 size_t l;
2977 int r;
2978
2979 assert(m);
2980 assert(c);
2981 assert(contents);
2982
2983 if (!signature_is_pair(contents))
2984 return -EINVAL;
2985
2986 if (c->enclosing != SD_BUS_TYPE_ARRAY)
2987 return -ENXIO;
2988
2989 if (!c->signature || c->signature[c->index] == 0)
2990 return 0;
2991
2992 l = strlen(contents);
2993
2994 if (c->signature[c->index] != SD_BUS_TYPE_DICT_ENTRY_BEGIN ||
2995 !startswith(c->signature + c->index + 1, contents) ||
2996 c->signature[c->index + 1 + l] != SD_BUS_TYPE_DICT_ENTRY_END)
2997 return -ENXIO;
2998
2999 r = message_peek_body(m, &m->rindex, 8, 0, NULL);
3000 if (r <= 0)
3001 return r;
3002
3003 if (c->enclosing != SD_BUS_TYPE_ARRAY)
3004 c->index += 1 + l + 1;
3005
3006 return 1;
3007 }
3008
3009 _public_ int sd_bus_message_enter_container(sd_bus_message *m,
3010 char type,
3011 const char *contents) {
3012 struct bus_container *c, *w;
3013 uint32_t *array_size = NULL;
3014 char *signature;
3015 size_t before;
3016 int r;
3017
3018 assert_return(m, -EINVAL);
3019 assert_return(m->sealed, -EPERM);
3020 assert_return(type != 0 || !contents, -EINVAL);
3021
3022 if (type == 0 || !contents) {
3023 const char *cc;
3024 char tt;
3025
3026 /* Allow entering into anonymous containers */
3027 r = sd_bus_message_peek_type(m, &tt, &cc);
3028 if (r <= 0)
3029 return r;
3030
3031 if (type != 0 && type != tt)
3032 return -ENXIO;
3033
3034 if (contents && !streq(contents, cc))
3035 return -ENXIO;
3036
3037 type = tt;
3038 contents = cc;
3039 }
3040
3041 /*
3042 * We enforce a global limit on container depth, that is much
3043 * higher than the 32 structs and 32 arrays the specification
3044 * mandates. This is simpler to implement for us, and we need
3045 * this only to ensure our container array doesn't grow
3046 * without bounds. We are happy to return any data from a
3047 * message as long as the data itself is valid, even if the
3048 * overall message might be not.
3049 *
3050 * Note that the message signature is validated when
3051 * parsing the headers, and that validation does check the
3052 * 32/32 limit.
3053 *
3054 * Note that the specification defines no limits on the depth
3055 * of stacked variants, but we do.
3056 */
3057 if (m->n_containers >= BUS_CONTAINER_DEPTH)
3058 return -EBADMSG;
3059
3060 w = realloc(m->containers, sizeof(struct bus_container) * (m->n_containers + 1));
3061 if (!w)
3062 return -ENOMEM;
3063 m->containers = w;
3064
3065 if (message_end_of_signature(m))
3066 return -ENXIO;
3067
3068 if (message_end_of_array(m, m->rindex))
3069 return 0;
3070
3071 c = message_get_container(m);
3072
3073 signature = strdup(contents);
3074 if (!signature)
3075 return -ENOMEM;
3076
3077 c->saved_index = c->index;
3078 before = m->rindex;
3079
3080 if (type == SD_BUS_TYPE_ARRAY)
3081 r = bus_message_enter_array(m, c, contents, &array_size);
3082 else if (type == SD_BUS_TYPE_VARIANT)
3083 r = bus_message_enter_variant(m, c, contents);
3084 else if (type == SD_BUS_TYPE_STRUCT)
3085 r = bus_message_enter_struct(m, c, contents);
3086 else if (type == SD_BUS_TYPE_DICT_ENTRY)
3087 r = bus_message_enter_dict_entry(m, c, contents);
3088 else
3089 r = -EINVAL;
3090
3091 if (r <= 0) {
3092 free(signature);
3093 return r;
3094 }
3095
3096 /* OK, let's fill it in */
3097 w += m->n_containers++;
3098 w->enclosing = type;
3099 w->signature = signature;
3100 w->index = 0;
3101 w->array_size = array_size;
3102 w->before = before;
3103 w->begin = m->rindex;
3104
3105 return 1;
3106 }
3107
3108 _public_ int sd_bus_message_exit_container(sd_bus_message *m) {
3109 struct bus_container *c;
3110
3111 assert_return(m, -EINVAL);
3112 assert_return(m->sealed, -EPERM);
3113 assert_return(m->n_containers > 0, -ENXIO);
3114
3115 c = message_get_container(m);
3116 if (c->enclosing == SD_BUS_TYPE_ARRAY) {
3117 uint32_t l;
3118
3119 l = BUS_MESSAGE_BSWAP32(m, *c->array_size);
3120 if (c->begin + l != m->rindex)
3121 return -EBUSY;
3122
3123 } else {
3124 if (c->signature && c->signature[c->index] != 0)
3125 return -EBUSY;
3126 }
3127
3128 free(c->signature);
3129 m->n_containers--;
3130
3131 return 1;
3132 }
3133
3134 static void message_quit_container(sd_bus_message *m) {
3135 struct bus_container *c;
3136
3137 assert(m);
3138 assert(m->sealed);
3139 assert(m->n_containers > 0);
3140
3141 c = message_get_container(m);
3142
3143 /* Undo seeks */
3144 assert(m->rindex >= c->before);
3145 m->rindex = c->before;
3146
3147 /* Free container */
3148 free(c->signature);
3149 m->n_containers--;
3150
3151 /* Correct index of new top-level container */
3152 c = message_get_container(m);
3153 c->index = c->saved_index;
3154 }
3155
3156 _public_ int sd_bus_message_peek_type(sd_bus_message *m, char *type, const char **contents) {
3157 struct bus_container *c;
3158 int r;
3159
3160 assert_return(m, -EINVAL);
3161 assert_return(m->sealed, -EPERM);
3162
3163 if (message_end_of_signature(m))
3164 goto eof;
3165
3166 if (message_end_of_array(m, m->rindex))
3167 goto eof;
3168
3169 c = message_get_container(m);
3170
3171 if (bus_type_is_basic(c->signature[c->index])) {
3172 if (contents)
3173 *contents = NULL;
3174 if (type)
3175 *type = c->signature[c->index];
3176 return 1;
3177 }
3178
3179 if (c->signature[c->index] == SD_BUS_TYPE_ARRAY) {
3180
3181 if (contents) {
3182 size_t l;
3183 char *sig;
3184
3185 r = signature_element_length(c->signature+c->index+1, &l);
3186 if (r < 0)
3187 return r;
3188
3189 assert(l >= 1);
3190
3191 sig = strndup(c->signature + c->index + 1, l);
3192 if (!sig)
3193 return -ENOMEM;
3194
3195 free(m->peeked_signature);
3196 m->peeked_signature = sig;
3197
3198 *contents = sig;
3199 }
3200
3201 if (type)
3202 *type = SD_BUS_TYPE_ARRAY;
3203
3204 return 1;
3205 }
3206
3207 if (c->signature[c->index] == SD_BUS_TYPE_STRUCT_BEGIN ||
3208 c->signature[c->index] == SD_BUS_TYPE_DICT_ENTRY_BEGIN) {
3209
3210 if (contents) {
3211 size_t l;
3212 char *sig;
3213
3214 r = signature_element_length(c->signature+c->index, &l);
3215 if (r < 0)
3216 return r;
3217
3218 assert(l >= 2);
3219 sig = strndup(c->signature + c->index + 1, l - 2);
3220 if (!sig)
3221 return -ENOMEM;
3222
3223 free(m->peeked_signature);
3224 m->peeked_signature = sig;
3225
3226 *contents = sig;
3227 }
3228
3229 if (type)
3230 *type = c->signature[c->index] == SD_BUS_TYPE_STRUCT_BEGIN ? SD_BUS_TYPE_STRUCT : SD_BUS_TYPE_DICT_ENTRY;
3231
3232 return 1;
3233 }
3234
3235 if (c->signature[c->index] == SD_BUS_TYPE_VARIANT) {
3236 if (contents) {
3237 size_t rindex, l;
3238 void *q;
3239
3240 rindex = m->rindex;
3241 r = message_peek_body(m, &rindex, 1, 1, &q);
3242 if (r < 0)
3243 return r;
3244 if (r == 0)
3245 goto eof;
3246
3247 l = *(uint8_t*) q;
3248 r = message_peek_body(m, &rindex, 1, l+1, &q);
3249 if (r < 0)
3250 return r;
3251 if (r == 0)
3252 return -EBADMSG;
3253
3254 if (!validate_signature(q, l))
3255 return -EBADMSG;
3256
3257 *contents = q;
3258 }
3259
3260 if (type)
3261 *type = SD_BUS_TYPE_VARIANT;
3262
3263 return 1;
3264 }
3265
3266 return -EINVAL;
3267
3268 eof:
3269 if (type)
3270 *type = 0;
3271 if (contents)
3272 *contents = NULL;
3273 return 0;
3274 }
3275
3276 _public_ int sd_bus_message_rewind(sd_bus_message *m, int complete) {
3277 struct bus_container *c;
3278
3279 assert_return(m, -EINVAL);
3280 assert_return(m->sealed, -EPERM);
3281
3282 if (complete) {
3283 message_reset_containers(m);
3284 m->rindex = 0;
3285 m->root_container.index = 0;
3286
3287 c = message_get_container(m);
3288 } else {
3289 c = message_get_container(m);
3290
3291 c->index = 0;
3292 m->rindex = c->begin;
3293 }
3294
3295 return !isempty(c->signature);
3296 }
3297
3298 static int message_read_ap(
3299 sd_bus_message *m,
3300 const char *types,
3301 va_list ap) {
3302
3303 unsigned n_array, n_struct;
3304 TypeStack stack[BUS_CONTAINER_DEPTH];
3305 unsigned stack_ptr = 0;
3306 unsigned n_loop = 0;
3307 int r;
3308
3309 assert(m);
3310
3311 if (isempty(types))
3312 return 0;
3313
3314 /* Ideally, we'd just call ourselves recursively on every
3315 * complex type. However, the state of a va_list that is
3316 * passed to a function is undefined after that function
3317 * returns. This means we need to docode the va_list linearly
3318 * in a single stackframe. We hence implement our own
3319 * home-grown stack in an array. */
3320
3321 n_array = (unsigned) -1; /* lenght of current array entries */
3322 n_struct = strlen(types); /* length of current struct contents signature */
3323
3324 for (;;) {
3325 const char *t;
3326
3327 n_loop++;
3328
3329 if (n_array == 0 || (n_array == (unsigned) -1 && n_struct == 0)) {
3330 r = type_stack_pop(stack, ELEMENTSOF(stack), &stack_ptr, &types, &n_struct, &n_array);
3331 if (r < 0)
3332 return r;
3333 if (r == 0)
3334 break;
3335
3336 r = sd_bus_message_exit_container(m);
3337 if (r < 0)
3338 return r;
3339
3340 continue;
3341 }
3342
3343 t = types;
3344 if (n_array != (unsigned) -1)
3345 n_array --;
3346 else {
3347 types ++;
3348 n_struct--;
3349 }
3350
3351 switch (*t) {
3352
3353 case SD_BUS_TYPE_BYTE:
3354 case SD_BUS_TYPE_BOOLEAN:
3355 case SD_BUS_TYPE_INT16:
3356 case SD_BUS_TYPE_UINT16:
3357 case SD_BUS_TYPE_INT32:
3358 case SD_BUS_TYPE_UINT32:
3359 case SD_BUS_TYPE_INT64:
3360 case SD_BUS_TYPE_UINT64:
3361 case SD_BUS_TYPE_DOUBLE:
3362 case SD_BUS_TYPE_STRING:
3363 case SD_BUS_TYPE_OBJECT_PATH:
3364 case SD_BUS_TYPE_SIGNATURE:
3365 case SD_BUS_TYPE_UNIX_FD: {
3366 void *p;
3367
3368 p = va_arg(ap, void*);
3369 r = sd_bus_message_read_basic(m, *t, p);
3370 if (r < 0)
3371 return r;
3372 if (r == 0) {
3373 if (n_loop <= 1)
3374 return 0;
3375
3376 return -ENXIO;
3377 }
3378
3379 break;
3380 }
3381
3382 case SD_BUS_TYPE_ARRAY: {
3383 size_t k;
3384
3385 r = signature_element_length(t + 1, &k);
3386 if (r < 0)
3387 return r;
3388
3389 {
3390 char s[k + 1];
3391 memcpy(s, t + 1, k);
3392 s[k] = 0;
3393
3394 r = sd_bus_message_enter_container(m, SD_BUS_TYPE_ARRAY, s);
3395 if (r < 0)
3396 return r;
3397 if (r == 0) {
3398 if (n_loop <= 1)
3399 return 0;
3400
3401 return -ENXIO;
3402 }
3403 }
3404
3405 if (n_array == (unsigned) -1) {
3406 types += k;
3407 n_struct -= k;
3408 }
3409
3410 r = type_stack_push(stack, ELEMENTSOF(stack), &stack_ptr, types, n_struct, n_array);
3411 if (r < 0)
3412 return r;
3413
3414 types = t + 1;
3415 n_struct = k;
3416 n_array = va_arg(ap, unsigned);
3417
3418 break;
3419 }
3420
3421 case SD_BUS_TYPE_VARIANT: {
3422 const char *s;
3423
3424 s = va_arg(ap, const char *);
3425 if (!s)
3426 return -EINVAL;
3427
3428 r = sd_bus_message_enter_container(m, SD_BUS_TYPE_VARIANT, s);
3429 if (r < 0)
3430 return r;
3431 if (r == 0) {
3432 if (n_loop <= 1)
3433 return 0;
3434
3435 return -ENXIO;
3436 }
3437
3438 r = type_stack_push(stack, ELEMENTSOF(stack), &stack_ptr, types, n_struct, n_array);
3439 if (r < 0)
3440 return r;
3441
3442 types = s;
3443 n_struct = strlen(s);
3444 n_array = (unsigned) -1;
3445
3446 break;
3447 }
3448
3449 case SD_BUS_TYPE_STRUCT_BEGIN:
3450 case SD_BUS_TYPE_DICT_ENTRY_BEGIN: {
3451 size_t k;
3452
3453 r = signature_element_length(t, &k);
3454 if (r < 0)
3455 return r;
3456
3457 {
3458 char s[k - 1];
3459 memcpy(s, t + 1, k - 2);
3460 s[k - 2] = 0;
3461
3462 r = sd_bus_message_enter_container(m, *t == SD_BUS_TYPE_STRUCT_BEGIN ? SD_BUS_TYPE_STRUCT : SD_BUS_TYPE_DICT_ENTRY, s);
3463 if (r < 0)
3464 return r;
3465 if (r == 0) {
3466 if (n_loop <= 1)
3467 return 0;
3468 return -ENXIO;
3469 }
3470 }
3471
3472 if (n_array == (unsigned) -1) {
3473 types += k - 1;
3474 n_struct -= k - 1;
3475 }
3476
3477 r = type_stack_push(stack, ELEMENTSOF(stack), &stack_ptr, types, n_struct, n_array);
3478 if (r < 0)
3479 return r;
3480
3481 types = t + 1;
3482 n_struct = k - 2;
3483 n_array = (unsigned) -1;
3484
3485 break;
3486 }
3487
3488 default:
3489 return -EINVAL;
3490 }
3491 }
3492
3493 return 1;
3494 }
3495
3496 _public_ int sd_bus_message_read(sd_bus_message *m, const char *types, ...) {
3497 va_list ap;
3498 int r;
3499
3500 assert_return(m, -EINVAL);
3501 assert_return(m->sealed, -EPERM);
3502 assert_return(types, -EINVAL);
3503
3504 va_start(ap, types);
3505 r = message_read_ap(m, types, ap);
3506 va_end(ap);
3507
3508 return r;
3509 }
3510
3511 _public_ int sd_bus_message_skip(sd_bus_message *m, const char *types) {
3512 int r;
3513
3514 assert_return(m, -EINVAL);
3515 assert_return(m->sealed, -EPERM);
3516 assert_return(types, -EINVAL);
3517
3518 if (isempty(types))
3519 return 0;
3520
3521 switch (*types) {
3522
3523 case SD_BUS_TYPE_BYTE:
3524 case SD_BUS_TYPE_BOOLEAN:
3525 case SD_BUS_TYPE_INT16:
3526 case SD_BUS_TYPE_UINT16:
3527 case SD_BUS_TYPE_INT32:
3528 case SD_BUS_TYPE_UINT32:
3529 case SD_BUS_TYPE_INT64:
3530 case SD_BUS_TYPE_UINT64:
3531 case SD_BUS_TYPE_DOUBLE:
3532 case SD_BUS_TYPE_STRING:
3533 case SD_BUS_TYPE_OBJECT_PATH:
3534 case SD_BUS_TYPE_SIGNATURE:
3535 case SD_BUS_TYPE_UNIX_FD:
3536
3537 r = sd_bus_message_read_basic(m, *types, NULL);
3538 if (r <= 0)
3539 return r;
3540
3541 r = sd_bus_message_skip(m, types + 1);
3542 if (r < 0)
3543 return r;
3544
3545 return 1;
3546
3547 case SD_BUS_TYPE_ARRAY: {
3548 size_t k;
3549
3550 r = signature_element_length(types + 1, &k);
3551 if (r < 0)
3552 return r;
3553
3554 {
3555 char s[k+1];
3556 memcpy(s, types+1, k);
3557 s[k] = 0;
3558
3559 r = sd_bus_message_enter_container(m, SD_BUS_TYPE_ARRAY, s);
3560 if (r <= 0)
3561 return r;
3562
3563 for (;;) {
3564 r = sd_bus_message_skip(m, s);
3565 if (r < 0)
3566 return r;
3567 if (r == 0)
3568 break;
3569 }
3570
3571 r = sd_bus_message_exit_container(m);
3572 if (r < 0)
3573 return r;
3574 }
3575
3576 r = sd_bus_message_skip(m, types + 1 + k);
3577 if (r < 0)
3578 return r;
3579
3580 return 1;
3581 }
3582
3583 case SD_BUS_TYPE_VARIANT: {
3584 const char *contents;
3585 char x;
3586
3587 r = sd_bus_message_peek_type(m, &x, &contents);
3588 if (r <= 0)
3589 return r;
3590
3591 if (x != SD_BUS_TYPE_VARIANT)
3592 return -ENXIO;
3593
3594 r = sd_bus_message_enter_container(m, SD_BUS_TYPE_VARIANT, contents);
3595 if (r <= 0)
3596 return r;
3597
3598 r = sd_bus_message_skip(m, contents);
3599 if (r < 0)
3600 return r;
3601 assert(r != 0);
3602
3603 r = sd_bus_message_exit_container(m);
3604 if (r < 0)
3605 return r;
3606
3607 r = sd_bus_message_skip(m, types + 1);
3608 if (r < 0)
3609 return r;
3610
3611 return 1;
3612 }
3613
3614 case SD_BUS_TYPE_STRUCT_BEGIN:
3615 case SD_BUS_TYPE_DICT_ENTRY_BEGIN: {
3616 size_t k;
3617
3618 r = signature_element_length(types, &k);
3619 if (r < 0)
3620 return r;
3621
3622 {
3623 char s[k-1];
3624 memcpy(s, types+1, k-2);
3625 s[k-2] = 0;
3626
3627 r = sd_bus_message_enter_container(m, *types == SD_BUS_TYPE_STRUCT_BEGIN ? SD_BUS_TYPE_STRUCT : SD_BUS_TYPE_DICT_ENTRY, s);
3628 if (r <= 0)
3629 return r;
3630
3631 r = sd_bus_message_skip(m, s);
3632 if (r < 0)
3633 return r;
3634 assert(r != 0);
3635
3636 r = sd_bus_message_exit_container(m);
3637 if (r < 0)
3638 return r;
3639 }
3640
3641 r = sd_bus_message_skip(m, types + k);
3642 if (r < 0)
3643 return r;
3644
3645 return 1;
3646 }
3647
3648 default:
3649 return -EINVAL;
3650 }
3651 }
3652
3653 _public_ int sd_bus_message_read_array(sd_bus_message *m,
3654 char type,
3655 const void **ptr,
3656 size_t *size) {
3657 struct bus_container *c;
3658 void *p;
3659 size_t sz;
3660 ssize_t align;
3661 int r;
3662
3663 assert_return(m, -EINVAL);
3664 assert_return(m->sealed, -EPERM);
3665 assert_return(bus_type_is_trivial(type), -EINVAL);
3666 assert_return(ptr, -EINVAL);
3667 assert_return(size, -EINVAL);
3668 assert_return(!BUS_MESSAGE_NEED_BSWAP(m), -ENOTSUP);
3669
3670 align = bus_type_get_alignment(type);
3671 if (align < 0)
3672 return align;
3673
3674 r = sd_bus_message_enter_container(m, SD_BUS_TYPE_ARRAY, CHAR_TO_STR(type));
3675 if (r <= 0)
3676 return r;
3677
3678 c = message_get_container(m);
3679 sz = BUS_MESSAGE_BSWAP32(m, *c->array_size);
3680
3681 if (sz == 0)
3682 /* Zero length array, let's return some aligned
3683 * pointer that is not NULL */
3684 p = (uint8_t*) NULL + align;
3685 else {
3686 r = message_peek_body(m, &m->rindex, align, sz, &p);
3687 if (r < 0)
3688 goto fail;
3689 if (r == 0) {
3690 r = -EBADMSG;
3691 goto fail;
3692 }
3693 }
3694
3695 r = sd_bus_message_exit_container(m);
3696 if (r < 0)
3697 goto fail;
3698
3699 *ptr = (const void*) p;
3700 *size = sz;
3701
3702 return 1;
3703
3704 fail:
3705 message_quit_container(m);
3706 return r;
3707 }
3708
3709 static int message_peek_fields(
3710 sd_bus_message *m,
3711 size_t *rindex,
3712 size_t align,
3713 size_t nbytes,
3714 void **ret) {
3715
3716 assert(m);
3717 assert(rindex);
3718 assert(align > 0);
3719
3720 return buffer_peek(BUS_MESSAGE_FIELDS(m), BUS_MESSAGE_FIELDS_SIZE(m), rindex, align, nbytes, ret);
3721 }
3722
3723 static int message_peek_field_uint32(
3724 sd_bus_message *m,
3725 size_t *ri,
3726 uint32_t *ret) {
3727
3728 int r;
3729 void *q;
3730
3731 assert(m);
3732 assert(ri);
3733
3734 r = message_peek_fields(m, ri, 4, 4, &q);
3735 if (r < 0)
3736 return r;
3737
3738 if (ret)
3739 *ret = BUS_MESSAGE_BSWAP32(m, *(uint32_t*) q);
3740
3741 return 0;
3742 }
3743
3744 static int message_peek_field_string(
3745 sd_bus_message *m,
3746 bool (*validate)(const char *p),
3747 size_t *ri,
3748 const char **ret) {
3749
3750 uint32_t l;
3751 int r;
3752 void *q;
3753
3754 assert(m);
3755 assert(ri);
3756
3757 r = message_peek_field_uint32(m, ri, &l);
3758 if (r < 0)
3759 return r;
3760
3761 r = message_peek_fields(m, ri, 1, l+1, &q);
3762 if (r < 0)
3763 return r;
3764
3765 if (validate) {
3766 if (!validate_nul(q, l))
3767 return -EBADMSG;
3768
3769 if (!validate(q))
3770 return -EBADMSG;
3771 } else {
3772 if (!validate_string(q, l))
3773 return -EBADMSG;
3774 }
3775
3776 if (ret)
3777 *ret = q;
3778
3779 return 0;
3780 }
3781
3782 static int message_peek_field_signature(
3783 sd_bus_message *m,
3784 size_t *ri,
3785 const char **ret) {
3786
3787 size_t l;
3788 int r;
3789 void *q;
3790
3791 assert(m);
3792 assert(ri);
3793
3794 r = message_peek_fields(m, ri, 1, 1, &q);
3795 if (r < 0)
3796 return r;
3797
3798 l = *(uint8_t*) q;
3799 r = message_peek_fields(m, ri, 1, l+1, &q);
3800 if (r < 0)
3801 return r;
3802
3803 if (!validate_signature(q, l))
3804 return -EBADMSG;
3805
3806 if (ret)
3807 *ret = q;
3808
3809 return 0;
3810 }
3811
3812 static int message_skip_fields(
3813 sd_bus_message *m,
3814 size_t *ri,
3815 uint32_t array_size,
3816 const char **signature) {
3817
3818 size_t original_index;
3819 int r;
3820
3821 assert(m);
3822 assert(ri);
3823 assert(signature);
3824
3825 original_index = *ri;
3826
3827 for (;;) {
3828 char t;
3829 size_t l;
3830
3831 if (array_size != (uint32_t) -1 &&
3832 array_size <= *ri - original_index)
3833 return 0;
3834
3835 t = **signature;
3836 if (!t)
3837 return 0;
3838
3839 if (t == SD_BUS_TYPE_STRING) {
3840
3841 r = message_peek_field_string(m, NULL, ri, NULL);
3842 if (r < 0)
3843 return r;
3844
3845 (*signature)++;
3846
3847 } else if (t == SD_BUS_TYPE_OBJECT_PATH) {
3848
3849 r = message_peek_field_string(m, object_path_is_valid, ri, NULL);
3850 if (r < 0)
3851 return r;
3852
3853 (*signature)++;
3854
3855 } else if (t == SD_BUS_TYPE_SIGNATURE) {
3856
3857 r = message_peek_field_signature(m, ri, NULL);
3858 if (r < 0)
3859 return r;
3860
3861 (*signature)++;
3862
3863 } else if (bus_type_is_basic(t)) {
3864 ssize_t align, k;
3865
3866 align = bus_type_get_alignment(t);
3867 k = bus_type_get_size(t);
3868 assert(align > 0 && k > 0);
3869
3870 r = message_peek_fields(m, ri, align, k, NULL);
3871 if (r < 0)
3872 return r;
3873
3874 (*signature)++;
3875
3876 } else if (t == SD_BUS_TYPE_ARRAY) {
3877
3878 r = signature_element_length(*signature+1, &l);
3879 if (r < 0)
3880 return r;
3881
3882 assert(l >= 1);
3883 {
3884 char sig[l-1], *s;
3885 uint32_t nas;
3886 int alignment;
3887
3888 strncpy(sig, *signature + 1, l-1);
3889 s = sig;
3890
3891 alignment = bus_type_get_alignment(sig[0]);
3892 if (alignment < 0)
3893 return alignment;
3894
3895 r = message_peek_field_uint32(m, ri, &nas);
3896 if (r < 0)
3897 return r;
3898 if (nas > BUS_ARRAY_MAX_SIZE)
3899 return -EBADMSG;
3900
3901 r = message_peek_fields(m, ri, alignment, 0, NULL);
3902 if (r < 0)
3903 return r;
3904
3905 r = message_skip_fields(m, ri, nas, (const char**) &s);
3906 if (r < 0)
3907 return r;
3908 }
3909
3910 (*signature) += 1 + l;
3911
3912 } else if (t == SD_BUS_TYPE_VARIANT) {
3913 const char *s;
3914
3915 r = message_peek_field_signature(m, ri, &s);
3916 if (r < 0)
3917 return r;
3918
3919 r = message_skip_fields(m, ri, (uint32_t) -1, (const char**) &s);
3920 if (r < 0)
3921 return r;
3922
3923 (*signature)++;
3924
3925 } else if (t == SD_BUS_TYPE_STRUCT ||
3926 t == SD_BUS_TYPE_DICT_ENTRY) {
3927
3928 r = signature_element_length(*signature, &l);
3929 if (r < 0)
3930 return r;
3931
3932 assert(l >= 2);
3933 {
3934 char sig[l-1], *s;
3935 strncpy(sig, *signature + 1, l-1);
3936 s = sig;
3937
3938 r = message_skip_fields(m, ri, (uint32_t) -1, (const char**) &s);
3939 if (r < 0)
3940 return r;
3941 }
3942
3943 *signature += l;
3944 } else
3945 return -EINVAL;
3946 }
3947 }
3948
3949 int bus_message_parse_fields(sd_bus_message *m) {
3950 size_t ri;
3951 int r;
3952 uint32_t unix_fds = 0;
3953
3954 assert(m);
3955
3956 for (ri = 0; ri < BUS_MESSAGE_FIELDS_SIZE(m); ) {
3957 const char *signature;
3958 uint8_t *header;
3959
3960 r = message_peek_fields(m, &ri, 8, 1, (void**) &header);
3961 if (r < 0)
3962 return r;
3963
3964 r = message_peek_field_signature(m, &ri, &signature);
3965 if (r < 0)
3966 return r;
3967
3968 switch (*header) {
3969 case _SD_BUS_MESSAGE_HEADER_INVALID:
3970 return -EBADMSG;
3971
3972 case SD_BUS_MESSAGE_HEADER_PATH:
3973
3974 if (m->path)
3975 return -EBADMSG;
3976
3977 if (!streq(signature, "o"))
3978 return -EBADMSG;
3979
3980 r = message_peek_field_string(m, object_path_is_valid, &ri, &m->path);
3981 break;
3982
3983 case SD_BUS_MESSAGE_HEADER_INTERFACE:
3984
3985 if (m->interface)
3986 return -EBADMSG;
3987
3988 if (!streq(signature, "s"))
3989 return -EBADMSG;
3990
3991 r = message_peek_field_string(m, interface_name_is_valid, &ri, &m->interface);
3992 break;
3993
3994 case SD_BUS_MESSAGE_HEADER_MEMBER:
3995
3996 if (m->member)
3997 return -EBADMSG;
3998
3999 if (!streq(signature, "s"))
4000 return -EBADMSG;
4001
4002 r = message_peek_field_string(m, member_name_is_valid, &ri, &m->member);
4003 break;
4004
4005 case SD_BUS_MESSAGE_HEADER_ERROR_NAME:
4006
4007 if (m->error.name)
4008 return -EBADMSG;
4009
4010 if (!streq(signature, "s"))
4011 return -EBADMSG;
4012
4013 r = message_peek_field_string(m, error_name_is_valid, &ri, &m->error.name);
4014 break;
4015
4016 case SD_BUS_MESSAGE_HEADER_DESTINATION:
4017
4018 if (m->destination)
4019 return -EBADMSG;
4020
4021 if (!streq(signature, "s"))
4022 return -EBADMSG;
4023
4024 r = message_peek_field_string(m, sender_name_is_valid, &ri, &m->destination);
4025 break;
4026
4027 case SD_BUS_MESSAGE_HEADER_SENDER:
4028
4029 if (m->sender)
4030 return -EBADMSG;
4031
4032 if (!streq(signature, "s"))
4033 return -EBADMSG;
4034
4035 r = message_peek_field_string(m, sender_name_is_valid, &ri, &m->sender);
4036 break;
4037
4038
4039 case SD_BUS_MESSAGE_HEADER_SIGNATURE: {
4040 const char *s;
4041 char *c;
4042
4043 if (m->root_container.signature)
4044 return -EBADMSG;
4045
4046 if (!streq(signature, "g"))
4047 return -EBADMSG;
4048
4049 r = message_peek_field_signature(m, &ri, &s);
4050 if (r < 0)
4051 return r;
4052
4053 c = strdup(s);
4054 if (!c)
4055 return -ENOMEM;
4056
4057 free(m->root_container.signature);
4058 m->root_container.signature = c;
4059 break;
4060 }
4061
4062 case SD_BUS_MESSAGE_HEADER_REPLY_SERIAL:
4063 if (m->reply_serial != 0)
4064 return -EBADMSG;
4065
4066 if (!streq(signature, "u"))
4067 return -EBADMSG;
4068
4069 r = message_peek_field_uint32(m, &ri, &m->reply_serial);
4070 if (r < 0)
4071 return r;
4072
4073 if (m->reply_serial == 0)
4074 return -EBADMSG;
4075
4076 break;
4077
4078 case SD_BUS_MESSAGE_HEADER_UNIX_FDS:
4079 if (unix_fds != 0)
4080 return -EBADMSG;
4081
4082 if (!streq(signature, "u"))
4083 return -EBADMSG;
4084
4085 r = message_peek_field_uint32(m, &ri, &unix_fds);
4086 if (r < 0)
4087 return -EBADMSG;
4088
4089 if (unix_fds == 0)
4090 return -EBADMSG;
4091
4092 break;
4093
4094 default:
4095 r = message_skip_fields(m, &ri, (uint32_t) -1, (const char **) &signature);
4096 }
4097
4098 if (r < 0)
4099 return r;
4100 }
4101
4102 if (m->n_fds != unix_fds)
4103 return -EBADMSG;
4104
4105 if (isempty(m->root_container.signature) != (BUS_MESSAGE_BODY_SIZE(m) == 0))
4106 return -EBADMSG;
4107
4108 switch (m->header->type) {
4109
4110 case SD_BUS_MESSAGE_SIGNAL:
4111 if (!m->path || !m->interface || !m->member)
4112 return -EBADMSG;
4113 break;
4114
4115 case SD_BUS_MESSAGE_METHOD_CALL:
4116
4117 if (!m->path || !m->member)
4118 return -EBADMSG;
4119
4120 break;
4121
4122 case SD_BUS_MESSAGE_METHOD_RETURN:
4123
4124 if (m->reply_serial == 0)
4125 return -EBADMSG;
4126 break;
4127
4128 case SD_BUS_MESSAGE_METHOD_ERROR:
4129
4130 if (m->reply_serial == 0 || !m->error.name)
4131 return -EBADMSG;
4132 break;
4133 }
4134
4135 /* Try to read the error message, but if we can't it's a non-issue */
4136 if (m->header->type == SD_BUS_MESSAGE_METHOD_ERROR)
4137 sd_bus_message_read(m, "s", &m->error.message);
4138
4139 return 0;
4140 }
4141
4142 int bus_message_seal(sd_bus_message *m, uint64_t serial) {
4143 struct bus_body_part *part;
4144 size_t l, a;
4145 unsigned i;
4146 int r;
4147
4148 assert(m);
4149
4150 if (m->sealed)
4151 return -EPERM;
4152
4153 if (m->n_containers > 0)
4154 return -EBADMSG;
4155
4156 if (m->poisoned)
4157 return -ESTALE;
4158
4159 /* If there's a non-trivial signature set, then add it in here */
4160 if (!isempty(m->root_container.signature)) {
4161 r = message_append_field_signature(m, SD_BUS_MESSAGE_HEADER_SIGNATURE, m->root_container.signature, NULL);
4162 if (r < 0)
4163 return r;
4164 }
4165
4166 if (m->n_fds > 0) {
4167 r = message_append_field_uint32(m, SD_BUS_MESSAGE_HEADER_UNIX_FDS, m->n_fds);
4168 if (r < 0)
4169 return r;
4170 }
4171
4172 /* Add padding at the end of the fields part, since we know
4173 * the body needs to start at an 8 byte alignment. We made
4174 * sure we allocated enough space for this, so all we need to
4175 * do here is to zero it out. */
4176 l = BUS_MESSAGE_FIELDS_SIZE(m);
4177 a = ALIGN8(l) - l;
4178 if (a > 0)
4179 memset((uint8_t*) BUS_MESSAGE_FIELDS(m) + l, 0, a);
4180
4181 /* If this is something we can send as memfd, then let's seal
4182 the memfd now. Note that we can send memfds as payload only
4183 for directed messages, and not for broadcasts. */
4184 if (m->destination && m->bus && m->bus->use_memfd) {
4185 MESSAGE_FOREACH_PART(part, i, m)
4186 if (part->memfd >= 0 && !part->sealed && (part->size > MEMFD_MIN_SIZE || m->bus->use_memfd < 0)) {
4187 bus_body_part_unmap(part);
4188
4189 if (ioctl(part->memfd, KDBUS_CMD_MEMFD_SEAL_SET, 1) >= 0)
4190 part->sealed = true;
4191 }
4192 }
4193
4194 m->header->serial = serial;
4195 m->sealed = true;
4196
4197 return 0;
4198 }
4199
4200 _public_ int sd_bus_message_set_destination(sd_bus_message *m, const char *destination) {
4201 assert_return(m, -EINVAL);
4202 assert_return(destination, -EINVAL);
4203 assert_return(!m->sealed, -EPERM);
4204 assert_return(!m->destination, -EEXIST);
4205
4206 return message_append_field_string(m, SD_BUS_MESSAGE_HEADER_DESTINATION, SD_BUS_TYPE_STRING, destination, &m->destination);
4207 }
4208
4209 int bus_message_get_blob(sd_bus_message *m, void **buffer, size_t *sz) {
4210 size_t total;
4211 void *p, *e;
4212 unsigned i;
4213 struct bus_body_part *part;
4214
4215 assert(m);
4216 assert(buffer);
4217 assert(sz);
4218
4219 total = BUS_MESSAGE_SIZE(m);
4220
4221 p = malloc(total);
4222 if (!p)
4223 return -ENOMEM;
4224
4225 e = mempcpy(p, m->header, BUS_MESSAGE_BODY_BEGIN(m));
4226 MESSAGE_FOREACH_PART(part, i, m)
4227 e = mempcpy(e, part->data, part->size);
4228
4229 assert(total == (size_t) ((uint8_t*) e - (uint8_t*) p));
4230
4231 *buffer = p;
4232 *sz = total;
4233
4234 return 0;
4235 }
4236
4237 int bus_message_read_strv_extend(sd_bus_message *m, char ***l) {
4238 int r;
4239
4240 assert(m);
4241 assert(l);
4242
4243 r = sd_bus_message_enter_container(m, 'a', "s");
4244 if (r <= 0)
4245 return r;
4246
4247 for (;;) {
4248 const char *s;
4249
4250 r = sd_bus_message_read_basic(m, 's', &s);
4251 if (r < 0)
4252 return r;
4253 if (r == 0)
4254 break;
4255
4256 r = strv_extend(l, s);
4257 if (r < 0)
4258 return r;
4259 }
4260
4261 r = sd_bus_message_exit_container(m);
4262 if (r < 0)
4263 return r;
4264
4265 return 1;
4266 }
4267
4268 _public_ int sd_bus_message_read_strv(sd_bus_message *m, char ***l) {
4269 char **strv = NULL;
4270 int r;
4271
4272 assert_return(m, -EINVAL);
4273 assert_return(m->sealed, -EPERM);
4274 assert_return(l, -EINVAL);
4275
4276 r = bus_message_read_strv_extend(m, &strv);
4277 if (r <= 0) {
4278 strv_free(strv);
4279 return r;
4280 }
4281
4282 *l = strv;
4283 return 1;
4284 }
4285
4286 const char* bus_message_get_arg(sd_bus_message *m, unsigned i) {
4287 int r;
4288 const char *t = NULL;
4289 unsigned j;
4290
4291 assert(m);
4292
4293 r = sd_bus_message_rewind(m, true);
4294 if (r < 0)
4295 return NULL;
4296
4297 for (j = 0; j <= i; j++) {
4298 char type;
4299
4300 r = sd_bus_message_peek_type(m, &type, NULL);
4301 if (r < 0)
4302 return NULL;
4303
4304 if (type != SD_BUS_TYPE_STRING &&
4305 type != SD_BUS_TYPE_OBJECT_PATH &&
4306 type != SD_BUS_TYPE_SIGNATURE)
4307 return NULL;
4308
4309 r = sd_bus_message_read_basic(m, type, &t);
4310 if (r < 0)
4311 return NULL;
4312 }
4313
4314 return t;
4315 }
4316
4317 bool bus_header_is_complete(struct bus_header *h, size_t size) {
4318 size_t full;
4319
4320 assert(h);
4321 assert(size);
4322
4323 if (size < sizeof(struct bus_header))
4324 return false;
4325
4326 full = sizeof(struct bus_header) +
4327 (h->endian == SD_BUS_NATIVE_ENDIAN ? h->fields_size : bswap_32(h->fields_size));
4328
4329 return size >= full;
4330 }
4331
4332 int bus_header_message_size(struct bus_header *h, size_t *sum) {
4333 size_t fs, bs;
4334
4335 assert(h);
4336 assert(sum);
4337
4338 if (h->endian == SD_BUS_NATIVE_ENDIAN) {
4339 fs = h->fields_size;
4340 bs = h->body_size;
4341 } else if (h->endian == SD_BUS_REVERSE_ENDIAN) {
4342 fs = bswap_32(h->fields_size);
4343 bs = bswap_32(h->body_size);
4344 } else
4345 return -EBADMSG;
4346
4347 *sum = sizeof(struct bus_header) + ALIGN8(fs) + bs;
4348 return 0;
4349 }
4350
4351 _public_ int sd_bus_message_get_errno(sd_bus_message *m) {
4352 assert_return(m, -EINVAL);
4353
4354 if (m->header->type != SD_BUS_MESSAGE_METHOD_ERROR)
4355 return 0;
4356
4357 return sd_bus_error_get_errno(&m->error);
4358 }
4359
4360 _public_ const char* sd_bus_message_get_signature(sd_bus_message *m, int complete) {
4361 struct bus_container *c;
4362
4363 assert_return(m, NULL);
4364
4365 c = complete ? &m->root_container : message_get_container(m);
4366 return c->signature ?: "";
4367 }
4368
4369 _public_ int sd_bus_message_copy(sd_bus_message *m, sd_bus_message *source, int all) {
4370 bool done_something = false;
4371 int r;
4372
4373 assert_return(m, -EINVAL);
4374 assert_return(source, -EINVAL);
4375 assert_return(!m->sealed, -EPERM);
4376 assert_return(source->sealed, -EPERM);
4377
4378 do {
4379 const char *contents;
4380 char type;
4381 union {
4382 uint8_t u8;
4383 uint16_t u16;
4384 int16_t s16;
4385 uint32_t u32;
4386 int32_t s32;
4387 uint64_t u64;
4388 int64_t s64;
4389 double d64;
4390 const char *string;
4391 int i;
4392 } basic;
4393
4394 r = sd_bus_message_peek_type(source, &type, &contents);
4395 if (r < 0)
4396 return r;
4397 if (r == 0)
4398 break;
4399
4400 done_something = true;
4401
4402 if (bus_type_is_container(type) > 0) {
4403
4404 r = sd_bus_message_enter_container(source, type, contents);
4405 if (r < 0)
4406 return r;
4407
4408 r = sd_bus_message_open_container(m, type, contents);
4409 if (r < 0)
4410 return r;
4411
4412 r = sd_bus_message_copy(m, source, true);
4413 if (r < 0)
4414 return r;
4415
4416 r = sd_bus_message_close_container(m);
4417 if (r < 0)
4418 return r;
4419
4420 r = sd_bus_message_exit_container(source);
4421 if (r < 0)
4422 return r;
4423
4424 continue;
4425 }
4426
4427 r = sd_bus_message_read_basic(source, type, &basic);
4428 if (r < 0)
4429 return r;
4430
4431 assert(r > 0);
4432
4433 if (type == SD_BUS_TYPE_OBJECT_PATH ||
4434 type == SD_BUS_TYPE_SIGNATURE ||
4435 type == SD_BUS_TYPE_STRING)
4436 r = sd_bus_message_append_basic(m, type, basic.string);
4437 else
4438 r = sd_bus_message_append_basic(m, type, &basic);
4439
4440 if (r < 0)
4441 return r;
4442
4443 } while (all);
4444
4445 return done_something;
4446 }
4447
4448 _public_ int sd_bus_message_verify_type(sd_bus_message *m, char type, const char *contents) {
4449 const char *c;
4450 char t;
4451 int r;
4452
4453 assert_return(m, -EINVAL);
4454 assert_return(m->sealed, -EPERM);
4455 assert_return(!type || bus_type_is_valid(type), -EINVAL);
4456 assert_return(!contents || signature_is_valid(contents, true), -EINVAL);
4457 assert_return(type || contents, -EINVAL);
4458 assert_return(!contents || !type || bus_type_is_container(type), -EINVAL);
4459
4460 r = sd_bus_message_peek_type(m, &t, &c);
4461 if (r <= 0)
4462 return r;
4463
4464 if (type != 0 && type != t)
4465 return 0;
4466
4467 if (contents && !streq_ptr(contents, c))
4468 return 0;
4469
4470 return 1;
4471 }