chiark / gitweb /
bus: support temporarily const errors that don't need to be freed but require deep...
[elogind.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_FREE, &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         message_reset_containers(m);
147         free(m->root_container.signature);
148
149         free(m->peeked_signature);
150
151         bus_creds_done(&m->creds);
152         free(m);
153 }
154
155 static void *message_extend_fields(sd_bus_message *m, size_t align, size_t sz) {
156         void *op, *np;
157         size_t old_size, new_size, start;
158
159         assert(m);
160
161         if (m->poisoned)
162                 return NULL;
163
164         old_size = sizeof(struct bus_header) + m->header->fields_size;
165         start = ALIGN_TO(old_size, align);
166         new_size = start + sz;
167
168         if (old_size == new_size)
169                 return (uint8_t*) m->header + old_size;
170
171         if (new_size > (size_t) ((uint32_t) -1))
172                 goto poison;
173
174         if (m->free_header) {
175                 np = realloc(m->header, ALIGN8(new_size));
176                 if (!np)
177                         goto poison;
178         } else {
179                 /* Initially, the header is allocated as part of of
180                  * the sd_bus_message itself, let's replace it by
181                  * dynamic data */
182
183                 np = malloc(ALIGN8(new_size));
184                 if (!np)
185                         goto poison;
186
187                 memcpy(np, m->header, sizeof(struct bus_header));
188         }
189
190         /* Zero out padding */
191         if (start > old_size)
192                 memset((uint8_t*) np + old_size, 0, start - old_size);
193
194         op = m->header;
195         m->header = np;
196         m->header->fields_size = new_size - sizeof(struct bus_header);
197
198         /* Adjust quick access pointers */
199         m->path = adjust_pointer(m->path, op, old_size, m->header);
200         m->interface = adjust_pointer(m->interface, op, old_size, m->header);
201         m->member = adjust_pointer(m->member, op, old_size, m->header);
202         m->destination = adjust_pointer(m->destination, op, old_size, m->header);
203         m->sender = adjust_pointer(m->sender, op, old_size, m->header);
204         m->error.name = adjust_pointer(m->error.name, op, old_size, m->header);
205
206         m->free_header = true;
207
208         return (uint8_t*) np + start;
209
210 poison:
211         m->poisoned = true;
212         return NULL;
213 }
214
215 static int message_append_field_string(
216                 sd_bus_message *m,
217                 uint8_t h,
218                 char type,
219                 const char *s,
220                 const char **ret) {
221
222         size_t l;
223         uint8_t *p;
224
225         assert(m);
226
227         l = strlen(s);
228         if (l > (size_t) (uint32_t) -1)
229                 return -EINVAL;
230
231         /* field id byte + signature length + signature 's' + NUL + string length + string + NUL */
232         p = message_extend_fields(m, 8, 4 + 4 + l + 1);
233         if (!p)
234                 return -ENOMEM;
235
236         p[0] = h;
237         p[1] = 1;
238         p[2] = type;
239         p[3] = 0;
240
241         ((uint32_t*) p)[1] = l;
242         memcpy(p + 8, s, l + 1);
243
244         if (ret)
245                 *ret = (char*) p + 8;
246
247         return 0;
248 }
249
250 static int message_append_field_signature(
251                 sd_bus_message *m,
252                 uint8_t h,
253                 const char *s,
254                 const char **ret) {
255
256         size_t l;
257         uint8_t *p;
258
259         assert(m);
260
261         l = strlen(s);
262         if (l > 255)
263                 return -EINVAL;
264
265         /* field id byte + signature length + signature 'g' + NUL + string length + string + NUL */
266         p = message_extend_fields(m, 8, 4 + 1 + l + 1);
267         if (!p)
268                 return -ENOMEM;
269
270         p[0] = h;
271         p[1] = 1;
272         p[2] = SD_BUS_TYPE_SIGNATURE;
273         p[3] = 0;
274         p[4] = l;
275         memcpy(p + 5, s, l + 1);
276
277         if (ret)
278                 *ret = (const char*) p + 5;
279
280         return 0;
281 }
282
283 static int message_append_field_uint32(sd_bus_message *m, uint8_t h, uint32_t x) {
284         uint8_t *p;
285
286         assert(m);
287
288         /* field id byte + signature length + signature 'u' + NUL + value */
289         p = message_extend_fields(m, 8, 4 + 4);
290         if (!p)
291                 return -ENOMEM;
292
293         p[0] = h;
294         p[1] = 1;
295         p[2] = SD_BUS_TYPE_UINT32;
296         p[3] = 0;
297
298         ((uint32_t*) p)[1] = x;
299
300         return 0;
301 }
302
303 int bus_message_from_header(
304                 sd_bus *bus,
305                 void *buffer,
306                 size_t length,
307                 int *fds,
308                 unsigned n_fds,
309                 const struct ucred *ucred,
310                 const char *label,
311                 size_t extra,
312                 sd_bus_message **ret) {
313
314         sd_bus_message *m;
315         struct bus_header *h;
316         size_t a, label_sz;
317
318         assert(buffer || length <= 0);
319         assert(fds || n_fds <= 0);
320         assert(ret);
321
322         if (length < sizeof(struct bus_header))
323                 return -EBADMSG;
324
325         h = buffer;
326         if (h->version != 1)
327                 return -EBADMSG;
328
329         if (h->serial == 0)
330                 return -EBADMSG;
331
332         if (h->type == _SD_BUS_MESSAGE_TYPE_INVALID)
333                 return -EBADMSG;
334
335         if (h->endian != SD_BUS_LITTLE_ENDIAN &&
336             h->endian != SD_BUS_BIG_ENDIAN)
337                 return -EBADMSG;
338
339         a = ALIGN(sizeof(sd_bus_message)) + ALIGN(extra);
340
341         if (label) {
342                 label_sz = strlen(label);
343                 a += label_sz + 1;
344         }
345
346         m = malloc0(a);
347         if (!m)
348                 return -ENOMEM;
349
350         m->n_ref = 1;
351         m->sealed = true;
352         m->header = h;
353         m->fds = fds;
354         m->n_fds = n_fds;
355
356         if (ucred) {
357                 m->creds.uid = ucred->uid;
358                 m->creds.pid = ucred->pid;
359                 m->creds.gid = ucred->gid;
360                 m->creds.mask |= SD_BUS_CREDS_UID | SD_BUS_CREDS_PID | SD_BUS_CREDS_GID;
361         }
362
363         if (label) {
364                 m->creds.label = (char*) m + ALIGN(sizeof(sd_bus_message)) + ALIGN(extra);
365                 memcpy(m->creds.label, label, label_sz + 1);
366
367                 m->creds.mask |= SD_BUS_CREDS_SELINUX_CONTEXT;
368         }
369
370         if (bus)
371                 m->bus = sd_bus_ref(bus);
372
373         *ret = m;
374         return 0;
375 }
376
377 int bus_message_from_malloc(
378                 sd_bus *bus,
379                 void *buffer,
380                 size_t length,
381                 int *fds,
382                 unsigned n_fds,
383                 const struct ucred *ucred,
384                 const char *label,
385                 sd_bus_message **ret) {
386
387         sd_bus_message *m;
388         size_t sz;
389         int r;
390
391         r = bus_message_from_header(bus, buffer, length, fds, n_fds, ucred, label, 0, &m);
392         if (r < 0)
393                 return r;
394
395         if (length != BUS_MESSAGE_SIZE(m)) {
396                 r = -EBADMSG;
397                 goto fail;
398         }
399
400         sz = length - sizeof(struct bus_header) - ALIGN8(BUS_MESSAGE_FIELDS_SIZE(m));
401         if (sz > 0) {
402                 m->n_body_parts = 1;
403                 m->body.data = (uint8_t*) buffer + sizeof(struct bus_header) + ALIGN8(BUS_MESSAGE_FIELDS_SIZE(m));
404                 m->body.size = sz;
405                 m->body.sealed = true;
406                 m->body.memfd = -1;
407         }
408
409         m->n_iovec = 1;
410         m->iovec = m->iovec_fixed;
411         m->iovec[0].iov_base = buffer;
412         m->iovec[0].iov_len = length;
413
414         r = bus_message_parse_fields(m);
415         if (r < 0)
416                 goto fail;
417
418         /* We take possession of the memory and fds now */
419         m->free_header = true;
420         m->free_fds = true;
421
422         *ret = m;
423         return 0;
424
425 fail:
426         message_free(m);
427         return r;
428 }
429
430 static sd_bus_message *message_new(sd_bus *bus, uint8_t type) {
431         sd_bus_message *m;
432
433         m = malloc0(ALIGN(sizeof(sd_bus_message)) + sizeof(struct bus_header));
434         if (!m)
435                 return NULL;
436
437         m->n_ref = 1;
438         m->header = (struct bus_header*) ((uint8_t*) m + ALIGN(sizeof(struct sd_bus_message)));
439         m->header->endian = SD_BUS_NATIVE_ENDIAN;
440         m->header->type = type;
441         m->header->version = bus ? bus->message_version : 1;
442         m->allow_fds = !bus || bus->can_fds || (bus->state != BUS_HELLO && bus->state != BUS_RUNNING);
443
444         if (bus)
445                 m->bus = sd_bus_ref(bus);
446
447         return m;
448 }
449
450 _public_ int sd_bus_message_new_signal(
451                 sd_bus *bus,
452                 const char *path,
453                 const char *interface,
454                 const char *member,
455                 sd_bus_message **m) {
456
457         sd_bus_message *t;
458         int r;
459
460         assert_return(!bus || bus->state != BUS_UNSET, -ENOTCONN);
461         assert_return(object_path_is_valid(path), -EINVAL);
462         assert_return(interface_name_is_valid(interface), -EINVAL);
463         assert_return(member_name_is_valid(member), -EINVAL);
464         assert_return(m, -EINVAL);
465
466         t = message_new(bus, SD_BUS_MESSAGE_SIGNAL);
467         if (!t)
468                 return -ENOMEM;
469
470         t->header->flags |= SD_BUS_MESSAGE_NO_REPLY_EXPECTED;
471
472         r = message_append_field_string(t, SD_BUS_MESSAGE_HEADER_PATH, SD_BUS_TYPE_OBJECT_PATH, path, &t->path);
473         if (r < 0)
474                 goto fail;
475         r = message_append_field_string(t, SD_BUS_MESSAGE_HEADER_INTERFACE, SD_BUS_TYPE_STRING, interface, &t->interface);
476         if (r < 0)
477                 goto fail;
478         r = message_append_field_string(t, SD_BUS_MESSAGE_HEADER_MEMBER, SD_BUS_TYPE_STRING, member, &t->member);
479         if (r < 0)
480                 goto fail;
481
482         *m = t;
483         return 0;
484
485 fail:
486         sd_bus_message_unref(t);
487         return r;
488 }
489
490 _public_ int sd_bus_message_new_method_call(
491                 sd_bus *bus,
492                 const char *destination,
493                 const char *path,
494                 const char *interface,
495                 const char *member,
496                 sd_bus_message **m) {
497
498         sd_bus_message *t;
499         int r;
500
501         assert_return(!bus || bus->state != BUS_UNSET, -ENOTCONN);
502         assert_return(!destination || service_name_is_valid(destination), -EINVAL);
503         assert_return(object_path_is_valid(path), -EINVAL);
504         assert_return(!interface || interface_name_is_valid(interface), -EINVAL);
505         assert_return(member_name_is_valid(member), -EINVAL);
506         assert_return(m, -EINVAL);
507
508         t = message_new(bus, SD_BUS_MESSAGE_METHOD_CALL);
509         if (!t)
510                 return -ENOMEM;
511
512         r = message_append_field_string(t, SD_BUS_MESSAGE_HEADER_PATH, SD_BUS_TYPE_OBJECT_PATH, path, &t->path);
513         if (r < 0)
514                 goto fail;
515         r = message_append_field_string(t, SD_BUS_MESSAGE_HEADER_MEMBER, SD_BUS_TYPE_STRING, member, &t->member);
516         if (r < 0)
517                 goto fail;
518
519         if (interface) {
520                 r = message_append_field_string(t, SD_BUS_MESSAGE_HEADER_INTERFACE, SD_BUS_TYPE_STRING, interface, &t->interface);
521                 if (r < 0)
522                         goto fail;
523         }
524
525         if (destination) {
526                 r = message_append_field_string(t, SD_BUS_MESSAGE_HEADER_DESTINATION, SD_BUS_TYPE_STRING, destination, &t->destination);
527                 if (r < 0)
528                         goto fail;
529         }
530
531         *m = t;
532         return 0;
533
534 fail:
535         message_free(t);
536         return r;
537 }
538
539 static int message_new_reply(
540                 sd_bus_message *call,
541                 uint8_t type,
542                 sd_bus_message **m) {
543
544         sd_bus_message *t;
545         int r;
546
547         assert_return(call, -EINVAL);
548         assert_return(call->sealed, -EPERM);
549         assert_return(call->header->type == SD_BUS_MESSAGE_METHOD_CALL, -EINVAL);
550         assert_return(!call->bus || call->bus->state != BUS_UNSET, -ENOTCONN);
551         assert_return(m, -EINVAL);
552
553         t = message_new(call->bus, type);
554         if (!t)
555                 return -ENOMEM;
556
557         t->header->flags |= SD_BUS_MESSAGE_NO_REPLY_EXPECTED;
558         t->reply_serial = BUS_MESSAGE_SERIAL(call);
559
560         r = message_append_field_uint32(t, SD_BUS_MESSAGE_HEADER_REPLY_SERIAL, t->reply_serial);
561         if (r < 0)
562                 goto fail;
563
564         if (call->sender) {
565                 r = message_append_field_string(t, SD_BUS_MESSAGE_HEADER_DESTINATION, SD_BUS_TYPE_STRING, call->sender, &t->destination);
566                 if (r < 0)
567                         goto fail;
568         }
569
570         t->dont_send = !!(call->header->flags & SD_BUS_MESSAGE_NO_REPLY_EXPECTED);
571
572         *m = t;
573         return 0;
574
575 fail:
576         message_free(t);
577         return r;
578 }
579
580 _public_ int sd_bus_message_new_method_return(
581                 sd_bus_message *call,
582                 sd_bus_message **m) {
583
584         return message_new_reply(call, SD_BUS_MESSAGE_METHOD_RETURN, m);
585 }
586
587 _public_ int sd_bus_message_new_method_error(
588                 sd_bus_message *call,
589                 const sd_bus_error *e,
590                 sd_bus_message **m) {
591
592         sd_bus_message *t;
593         int r;
594
595         assert_return(sd_bus_error_is_set(e), -EINVAL);
596         assert_return(m, -EINVAL);
597
598         r = message_new_reply(call, SD_BUS_MESSAGE_METHOD_ERROR, &t);
599         if (r < 0)
600                 return r;
601
602         r = message_append_field_string(t, SD_BUS_MESSAGE_HEADER_ERROR_NAME, SD_BUS_TYPE_STRING, e->name, &t->error.name);
603         if (r < 0)
604                 goto fail;
605
606         if (e->message) {
607                 r = message_append_basic(t, SD_BUS_TYPE_STRING, e->message, (const void**) &t->error.message);
608                 if (r < 0)
609                         goto fail;
610         }
611
612         t->error._need_free = -1;
613
614         *m = t;
615         return 0;
616
617 fail:
618         message_free(t);
619         return r;
620 }
621
622 _public_ int sd_bus_message_new_method_errorf(
623                 sd_bus_message *call,
624                 sd_bus_message **m,
625                 const char *name,
626                 const char *format,
627                 ...) {
628
629         _cleanup_free_ sd_bus_error error = SD_BUS_ERROR_NULL;
630         va_list ap;
631
632         assert_return(name, -EINVAL);
633         assert_return(m, -EINVAL);
634
635         va_start(ap, format);
636         bus_error_setfv(&error, name, format, ap);
637         va_end(ap);
638
639         return sd_bus_message_new_method_error(call, &error, m);
640 }
641
642 _public_ int sd_bus_message_new_method_errno(
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(call, p, m);
652
653         sd_bus_error_set_errno(&berror, error);
654
655         return sd_bus_message_new_method_error(call, &berror, m);
656 }
657
658 _public_ int sd_bus_message_new_method_errnof(
659                 sd_bus_message *call,
660                 sd_bus_message **m,
661                 int error,
662                 const char *format,
663                 ...) {
664
665         _cleanup_free_ sd_bus_error berror = SD_BUS_ERROR_NULL;
666         va_list ap;
667
668         va_start(ap, format);
669         bus_error_set_errnofv(&berror, error, format, ap);
670         va_end(ap);
671
672         return sd_bus_message_new_method_error(call, &berror, m);
673 }
674
675 int bus_message_new_synthetic_error(
676                 sd_bus *bus,
677                 uint64_t serial,
678                 const sd_bus_error *e,
679                 sd_bus_message **m) {
680
681         sd_bus_message *t;
682         int r;
683
684         assert(sd_bus_error_is_set(e));
685         assert(m);
686
687         t = message_new(bus, SD_BUS_MESSAGE_METHOD_ERROR);
688         if (!t)
689                 return -ENOMEM;
690
691         t->header->flags |= SD_BUS_MESSAGE_NO_REPLY_EXPECTED;
692         t->reply_serial = serial;
693
694         r = message_append_field_uint32(t, SD_BUS_MESSAGE_HEADER_REPLY_SERIAL, t->reply_serial);
695         if (r < 0)
696                 goto fail;
697
698         if (bus && bus->unique_name) {
699                 r = message_append_field_string(t, SD_BUS_MESSAGE_HEADER_DESTINATION, SD_BUS_TYPE_STRING, bus->unique_name, &t->destination);
700                 if (r < 0)
701                         goto fail;
702         }
703
704         r = message_append_field_string(t, SD_BUS_MESSAGE_HEADER_ERROR_NAME, SD_BUS_TYPE_STRING, e->name, &t->error.name);
705         if (r < 0)
706                 goto fail;
707
708         if (e->message) {
709                 r = message_append_basic(t, SD_BUS_TYPE_STRING, e->message, (const void**) &t->error.message);
710                 if (r < 0)
711                         goto fail;
712         }
713
714         t->error._need_free = -1;
715
716         *m = t;
717         return 0;
718
719 fail:
720         message_free(t);
721         return r;
722 }
723
724 _public_ sd_bus_message* sd_bus_message_ref(sd_bus_message *m) {
725         assert_return(m, NULL);
726
727         assert(m->n_ref > 0);
728         m->n_ref++;
729
730         return m;
731 }
732
733 _public_ sd_bus_message* sd_bus_message_unref(sd_bus_message *m) {
734         assert_return(m, NULL);
735
736         assert(m->n_ref > 0);
737         m->n_ref--;
738
739         if (m->n_ref <= 0)
740                 message_free(m);
741
742         return NULL;
743 }
744
745 _public_ int sd_bus_message_get_type(sd_bus_message *m, uint8_t *type) {
746         assert_return(m, -EINVAL);
747         assert_return(type, -EINVAL);
748
749         *type = m->header->type;
750         return 0;
751 }
752
753 _public_ int sd_bus_message_get_serial(sd_bus_message *m, uint64_t *serial) {
754         assert_return(m, -EINVAL);
755         assert_return(serial, -EINVAL);
756         assert_return(m->header->serial != 0, -ENOENT);
757
758         *serial = BUS_MESSAGE_SERIAL(m);
759         return 0;
760 }
761
762 _public_ int sd_bus_message_get_reply_serial(sd_bus_message *m, uint64_t *serial) {
763         assert_return(m, -EINVAL);
764         assert_return(serial, -EINVAL);
765         assert_return(m->reply_serial != 0, -ENOENT);
766
767         *serial = m->reply_serial;
768         return 0;
769 }
770
771 _public_ int sd_bus_message_get_no_reply(sd_bus_message *m) {
772         assert_return(m, -EINVAL);
773
774         return m->header->type == SD_BUS_MESSAGE_METHOD_CALL ? !!(m->header->flags & SD_BUS_MESSAGE_NO_REPLY_EXPECTED) : 0;
775 }
776
777 _public_ int sd_bus_message_get_no_auto_start(sd_bus_message *m) {
778         assert_return(m, -EINVAL);
779
780         return !!(m->header->flags & SD_BUS_MESSAGE_NO_AUTO_START);
781 }
782
783 _public_ const char *sd_bus_message_get_path(sd_bus_message *m) {
784         assert_return(m, NULL);
785
786         return m->path;
787 }
788
789 _public_ const char *sd_bus_message_get_interface(sd_bus_message *m) {
790         assert_return(m, NULL);
791
792         return m->interface;
793 }
794
795 _public_ const char *sd_bus_message_get_member(sd_bus_message *m) {
796         assert_return(m, NULL);
797
798         return m->member;
799 }
800
801 _public_ const char *sd_bus_message_get_destination(sd_bus_message *m) {
802         assert_return(m, NULL);
803
804         return m->destination;
805 }
806
807 _public_ const char *sd_bus_message_get_sender(sd_bus_message *m) {
808         assert_return(m, NULL);
809
810         return m->sender;
811 }
812
813 _public_ const sd_bus_error *sd_bus_message_get_error(sd_bus_message *m) {
814         assert_return(m, NULL);
815         assert_return(sd_bus_error_is_set(&m->error), NULL);
816
817         return &m->error;
818 }
819
820 _public_ int sd_bus_message_get_monotonic_timestamp(sd_bus_message *m, uint64_t *usec) {
821         assert_return(m, -EINVAL);
822         assert_return(usec, -EINVAL);
823         assert_return(m->monotonic > 0, -ENODATA);
824
825         *usec = m->monotonic;
826         return 0;
827 }
828
829 _public_ int sd_bus_message_get_realtime_timestamp(sd_bus_message *m, uint64_t *usec) {
830         assert_return(m, -EINVAL);
831         assert_return(usec, -EINVAL);
832         assert_return(m->realtime > 0, -ENODATA);
833
834         *usec = m->realtime;
835         return 0;
836 }
837
838 _public_ sd_bus_creds *sd_bus_message_get_creds(sd_bus_message *m) {
839         assert_return(m, NULL);
840
841         if (m->creds.mask == 0)
842                 return NULL;
843
844         return &m->creds;
845 }
846
847 _public_ int sd_bus_message_is_signal(sd_bus_message *m,
848                                       const char *interface,
849                                       const char *member) {
850         assert_return(m, -EINVAL);
851
852         if (m->header->type != SD_BUS_MESSAGE_SIGNAL)
853                 return 0;
854
855         if (interface && (!m->interface || !streq(m->interface, interface)))
856                 return 0;
857
858         if (member &&  (!m->member || !streq(m->member, member)))
859                 return 0;
860
861         return 1;
862 }
863
864 _public_ int sd_bus_message_is_method_call(sd_bus_message *m,
865                                            const char *interface,
866                                            const char *member) {
867         assert_return(m, -EINVAL);
868
869         if (m->header->type != SD_BUS_MESSAGE_METHOD_CALL)
870                 return 0;
871
872         if (interface && (!m->interface || !streq(m->interface, interface)))
873                 return 0;
874
875         if (member &&  (!m->member || !streq(m->member, member)))
876                 return 0;
877
878         return 1;
879 }
880
881 _public_ int sd_bus_message_is_method_error(sd_bus_message *m, const char *name) {
882         assert_return(m, -EINVAL);
883
884         if (m->header->type != SD_BUS_MESSAGE_METHOD_ERROR)
885                 return 0;
886
887         if (name && (!m->error.name || !streq(m->error.name, name)))
888                 return 0;
889
890         return 1;
891 }
892
893 _public_ int sd_bus_message_set_no_reply(sd_bus_message *m, int b) {
894         assert_return(m, -EINVAL);
895         assert_return(!m->sealed, -EPERM);
896         assert_return(m->header->type == SD_BUS_MESSAGE_METHOD_CALL, -EPERM);
897
898         if (b)
899                 m->header->flags |= SD_BUS_MESSAGE_NO_REPLY_EXPECTED;
900         else
901                 m->header->flags &= ~SD_BUS_MESSAGE_NO_REPLY_EXPECTED;
902
903         return 0;
904 }
905
906 _public_ int sd_bus_message_set_no_auto_start(sd_bus_message *m, int b) {
907         assert_return(m, -EINVAL);
908         assert_return(!m->sealed, -EPERM);
909
910         if (b)
911                 m->header->flags |= SD_BUS_MESSAGE_NO_AUTO_START;
912         else
913                 m->header->flags &= ~SD_BUS_MESSAGE_NO_AUTO_START;
914
915         return 0;
916 }
917
918 static struct bus_container *message_get_container(sd_bus_message *m) {
919         assert(m);
920
921         if (m->n_containers == 0)
922                 return &m->root_container;
923
924         assert(m->containers);
925         return m->containers + m->n_containers - 1;
926 }
927
928 struct bus_body_part *message_append_part(sd_bus_message *m) {
929         struct bus_body_part *part;
930
931         assert(m);
932
933         if (m->poisoned)
934                 return NULL;
935
936         if (m->n_body_parts <= 0) {
937                 part = &m->body;
938                 zero(*part);
939         } else {
940                 assert(m->body_end);
941
942                 part = new0(struct bus_body_part, 1);
943                 if (!part) {
944                         m->poisoned = true;
945                         return NULL;
946                 }
947
948                 m->body_end->next = part;
949         }
950
951         part->memfd = -1;
952         m->body_end = part;
953         m->n_body_parts ++;
954
955         return part;
956 }
957
958 static void part_zero(struct bus_body_part *part, size_t sz) {
959         assert(part);
960         assert(sz > 0);
961         assert(sz < 8);
962
963         /* All other fields can be left in their defaults */
964         assert(!part->data);
965         assert(part->memfd < 0);
966
967         part->size = sz;
968         part->is_zero = true;
969         part->sealed = true;
970 }
971
972 static int part_make_space(
973                 struct sd_bus_message *m,
974                 struct bus_body_part *part,
975                 size_t sz,
976                 void **q) {
977
978         void *n;
979         int r;
980
981         assert(m);
982         assert(part);
983         assert(!part->sealed);
984
985         if (m->poisoned)
986                 return -ENOMEM;
987
988         if (!part->data && part->memfd < 0)
989                 part->memfd = bus_kernel_pop_memfd(m->bus, &part->data, &part->mapped);
990
991         if (part->memfd >= 0) {
992                 uint64_t u = sz;
993
994                 r = ioctl(part->memfd, KDBUS_CMD_MEMFD_SIZE_SET, &u);
995                 if (r < 0) {
996                         m->poisoned = true;
997                         return -errno;
998                 }
999
1000                 if (!part->data || sz > part->mapped) {
1001                         size_t psz = PAGE_ALIGN(sz > 0 ? sz : 1);
1002
1003                         if (part->mapped <= 0)
1004                                 n = mmap(NULL, psz, PROT_READ|PROT_WRITE, MAP_SHARED, part->memfd, 0);
1005                         else
1006                                 n = mremap(part->data, part->mapped, psz, MREMAP_MAYMOVE);
1007
1008                         if (n == MAP_FAILED) {
1009                                 m->poisoned = true;
1010                                 return -errno;
1011                         }
1012
1013                         part->mapped = psz;
1014                         part->data = n;
1015                 }
1016
1017                 part->munmap_this = true;
1018         } else {
1019                 n = realloc(part->data, MAX(sz, 1u));
1020                 if (!n) {
1021                         m->poisoned = true;
1022                         return -ENOMEM;
1023                 }
1024
1025                 part->data = n;
1026                 part->free_this = true;
1027         }
1028
1029         if (q)
1030                 *q = part->data ? (uint8_t*) part->data + part->size : NULL;
1031
1032         part->size = sz;
1033         return 0;
1034 }
1035
1036 static void message_extend_containers(sd_bus_message *m, size_t expand) {
1037         struct bus_container *c;
1038
1039         assert(m);
1040
1041         if (expand <= 0)
1042                 return;
1043
1044         /* Update counters */
1045         for (c = m->containers; c < m->containers + m->n_containers; c++)
1046                 if (c->array_size)
1047                         *c->array_size += expand;
1048 }
1049
1050 static void *message_extend_body(sd_bus_message *m, size_t align, size_t sz) {
1051         struct bus_body_part *part = NULL;
1052         size_t start_body, end_body, padding, start_part, end_part, added;
1053         bool add_new_part;
1054         void *p;
1055         int r;
1056
1057         assert(m);
1058         assert(align > 0);
1059         assert(!m->sealed);
1060
1061         if (m->poisoned)
1062                 return NULL;
1063
1064         start_body = ALIGN_TO((size_t) m->header->body_size, align);
1065         end_body = start_body + sz;
1066
1067         padding = start_body - m->header->body_size;
1068         added = padding + sz;
1069
1070         /* Check for 32bit overflows */
1071         if (end_body > (size_t) ((uint32_t) -1)) {
1072                 m->poisoned = true;
1073                 return NULL;
1074         }
1075
1076         add_new_part =
1077                 m->n_body_parts <= 0 ||
1078                 m->body_end->sealed ||
1079                 padding != ALIGN_TO(m->body_end->size, align) - m->body_end->size;
1080
1081         if (add_new_part) {
1082                 if (padding > 0) {
1083                         part = message_append_part(m);
1084                         if (!part)
1085                                 return NULL;
1086
1087                         part_zero(part, padding);
1088                 }
1089
1090                 part = message_append_part(m);
1091                 if (!part)
1092                         return NULL;
1093
1094                 r = part_make_space(m, part, sz, &p);
1095                 if (r < 0)
1096                         return NULL;
1097         } else {
1098                 struct bus_container *c;
1099                 void *op;
1100                 size_t os;
1101
1102                 part = m->body_end;
1103                 op = part->data;
1104                 os = part->size;
1105
1106                 start_part = ALIGN_TO(part->size, align);
1107                 end_part = start_part + sz;
1108
1109                 r = part_make_space(m, part, end_part, &p);
1110                 if (r < 0)
1111                         return NULL;
1112
1113                 if (padding > 0) {
1114                         memset(p, 0, padding);
1115                         p = (uint8_t*) p + padding;
1116                 }
1117
1118                 /* Readjust pointers */
1119                 for (c = m->containers; c < m->containers + m->n_containers; c++)
1120                         c->array_size = adjust_pointer(c->array_size, op, os, part->data);
1121
1122                 m->error.message = (const char*) adjust_pointer(m->error.message, op, os, part->data);
1123         }
1124
1125         m->header->body_size = end_body;
1126         message_extend_containers(m, added);
1127
1128         return p;
1129 }
1130
1131 int message_append_basic(sd_bus_message *m, char type, const void *p, const void **stored) {
1132         struct bus_container *c;
1133         ssize_t align, sz;
1134         uint32_t k;
1135         void *a;
1136         int fd = -1;
1137         uint32_t fdi = 0;
1138         int r;
1139
1140         assert_return(m, -EINVAL);
1141         assert_return(!m->sealed, -EPERM);
1142         assert_return(bus_type_is_basic(type), -EINVAL);
1143         assert_return(!m->poisoned, -ESTALE);
1144
1145         c = message_get_container(m);
1146
1147         if (c->signature && c->signature[c->index]) {
1148                 /* Container signature is already set */
1149
1150                 if (c->signature[c->index] != type)
1151                         return -ENXIO;
1152         } else {
1153                 char *e;
1154
1155                 /* Maybe we can append to the signature? But only if this is the top-level container*/
1156                 if (c->enclosing != 0)
1157                         return -ENXIO;
1158
1159                 e = strextend(&c->signature, CHAR_TO_STR(type), NULL);
1160                 if (!e) {
1161                         m->poisoned = true;
1162                         return -ENOMEM;
1163                 }
1164         }
1165
1166         switch (type) {
1167
1168         case SD_BUS_TYPE_STRING:
1169                 /* To make things easy we'll serialize a NULL string
1170                  * into the empty string */
1171                 p = strempty(p);
1172
1173                 /* Fall through... */
1174         case SD_BUS_TYPE_OBJECT_PATH:
1175
1176                 if (!p) {
1177                         r = -EINVAL;
1178                         goto fail;
1179                 }
1180
1181                 align = 4;
1182                 sz = 4 + strlen(p) + 1;
1183                 break;
1184
1185         case SD_BUS_TYPE_SIGNATURE:
1186
1187                 if (!p) {
1188                         r = -EINVAL;
1189                         goto fail;
1190                 }
1191
1192                 align = 1;
1193                 sz = 1 + strlen(p) + 1;
1194                 break;
1195
1196         case SD_BUS_TYPE_BOOLEAN:
1197
1198                 if (!p) {
1199                         r = -EINVAL;
1200                         goto fail;
1201                 }
1202
1203                 align = sz = 4;
1204
1205                 assert_cc(sizeof(int) == sizeof(uint32_t));
1206                 memcpy(&k, p, 4);
1207                 k = !!k;
1208                 p = &k;
1209                 break;
1210
1211         case SD_BUS_TYPE_UNIX_FD: {
1212                 int z, *f;
1213
1214                 if (!p) {
1215                         r = -EINVAL;
1216                         goto fail;
1217                 }
1218
1219                 if (!m->allow_fds) {
1220                         r = -ENOTSUP;
1221                         goto fail;
1222                 }
1223
1224                 align = sz = 4;
1225
1226                 z = *(int*) p;
1227                 if (z < 0) {
1228                         r = -EINVAL;
1229                         goto fail;
1230                 }
1231
1232                 fd = fcntl(z, F_DUPFD_CLOEXEC, 3);
1233                 if (fd < 0) {
1234                         r = -errno;
1235                         goto fail;
1236                 }
1237
1238                 f = realloc(m->fds, sizeof(int) * (m->n_fds + 1));
1239                 if (!f) {
1240                         m->poisoned = true;
1241                         r = -ENOMEM;
1242                         goto fail;
1243                 }
1244
1245                 fdi = m->n_fds;
1246                 f[fdi] = fd;
1247                 m->fds = f;
1248                 m->free_fds = true;
1249                 break;
1250         }
1251
1252         default:
1253                 if (!p) {
1254                         r = -EINVAL;
1255                         goto fail;
1256                 }
1257
1258                 align = bus_type_get_alignment(type);
1259                 sz = bus_type_get_size(type);
1260                 break;
1261         }
1262
1263         assert(align > 0);
1264         assert(sz > 0);
1265
1266         a = message_extend_body(m, align, sz);
1267         if (!a) {
1268                 r = -ENOMEM;
1269                 goto fail;
1270         }
1271
1272         if (type == SD_BUS_TYPE_STRING || type == SD_BUS_TYPE_OBJECT_PATH) {
1273                 *(uint32_t*) a = sz - 5;
1274                 memcpy((uint8_t*) a + 4, p, sz - 4);
1275
1276                 if (stored)
1277                         *stored = (const uint8_t*) a + 4;
1278
1279         } else if (type == SD_BUS_TYPE_SIGNATURE) {
1280                 *(uint8_t*) a = sz - 1;
1281                 memcpy((uint8_t*) a + 1, p, sz - 1);
1282
1283                 if (stored)
1284                         *stored = (const uint8_t*) a + 1;
1285         } else if (type == SD_BUS_TYPE_UNIX_FD) {
1286                 *(uint32_t*) a = fdi;
1287
1288                 if (stored)
1289                         *stored = a;
1290
1291                 m->n_fds ++;
1292
1293         } else {
1294                 memcpy(a, p, sz);
1295
1296                 if (stored)
1297                         *stored = a;
1298         }
1299
1300         if (c->enclosing != SD_BUS_TYPE_ARRAY)
1301                 c->index++;
1302
1303         return 0;
1304
1305 fail:
1306         if (fd >= 0)
1307                 close_nointr_nofail(fd);
1308
1309         return r;
1310 }
1311
1312 _public_ int sd_bus_message_append_basic(sd_bus_message *m, char type, const void *p) {
1313         return message_append_basic(m, type, p, NULL);
1314 }
1315
1316 _public_ int sd_bus_message_append_string_space(
1317                 sd_bus_message *m,
1318                 size_t size,
1319                 char **s) {
1320
1321         struct bus_container *c;
1322         void *a;
1323
1324         assert_return(m, -EINVAL);
1325         assert_return(s, -EINVAL);
1326         assert_return(!m->sealed, -EPERM);
1327         assert_return(!m->poisoned, -ESTALE);
1328
1329         c = message_get_container(m);
1330
1331         if (c->signature && c->signature[c->index]) {
1332                 /* Container signature is already set */
1333
1334                 if (c->signature[c->index] != SD_BUS_TYPE_STRING)
1335                         return -ENXIO;
1336         } else {
1337                 char *e;
1338
1339                 /* Maybe we can append to the signature? But only if this is the top-level container*/
1340                 if (c->enclosing != 0)
1341                         return -ENXIO;
1342
1343                 e = strextend(&c->signature, CHAR_TO_STR(SD_BUS_TYPE_STRING), NULL);
1344                 if (!e) {
1345                         m->poisoned = true;
1346                         return -ENOMEM;
1347                 }
1348         }
1349
1350         a = message_extend_body(m, 4, 4 + size + 1);
1351         if (!a)
1352                 return -ENOMEM;
1353
1354         *(uint32_t*) a = size;
1355         *s = (char*) a + 4;
1356
1357         (*s)[size] = 0;
1358
1359         if (c->enclosing != SD_BUS_TYPE_ARRAY)
1360                 c->index++;
1361
1362         return 0;
1363 }
1364
1365 _public_ int sd_bus_message_append_string_iovec(
1366                 sd_bus_message *m,
1367                 const struct iovec *iov,
1368                 unsigned n) {
1369
1370         size_t size;
1371         unsigned i;
1372         char *p;
1373         int r;
1374
1375         assert_return(m, -EINVAL);
1376         assert_return(!m->sealed, -EPERM);
1377         assert_return(iov || n == 0, -EINVAL);
1378         assert_return(!m->poisoned, -ESTALE);
1379
1380         size = IOVEC_TOTAL_SIZE(iov, n);
1381
1382         r = sd_bus_message_append_string_space(m, size, &p);
1383         if (r < 0)
1384                 return r;
1385
1386         for (i = 0; i < n; i++) {
1387
1388                 if (iov[i].iov_base)
1389                         memcpy(p, iov[i].iov_base, iov[i].iov_len);
1390                 else
1391                         memset(p, ' ', iov[i].iov_len);
1392
1393                 p += iov[i].iov_len;
1394         }
1395
1396         return 0;
1397 }
1398
1399 static int bus_message_open_array(
1400                 sd_bus_message *m,
1401                 struct bus_container *c,
1402                 const char *contents,
1403                 uint32_t **array_size) {
1404
1405         unsigned nindex;
1406         void *a, *op;
1407         int alignment;
1408         size_t os;
1409         struct bus_body_part *o;
1410
1411         assert(m);
1412         assert(c);
1413         assert(contents);
1414         assert(array_size);
1415
1416         if (!signature_is_single(contents, true))
1417                 return -EINVAL;
1418
1419         alignment = bus_type_get_alignment(contents[0]);
1420         if (alignment < 0)
1421                 return alignment;
1422
1423         if (c->signature && c->signature[c->index]) {
1424
1425                 /* Verify the existing signature */
1426
1427                 if (c->signature[c->index] != SD_BUS_TYPE_ARRAY)
1428                         return -ENXIO;
1429
1430                 if (!startswith(c->signature + c->index + 1, contents))
1431                         return -ENXIO;
1432
1433                 nindex = c->index + 1 + strlen(contents);
1434         } else {
1435                 char *e;
1436
1437                 if (c->enclosing != 0)
1438                         return -ENXIO;
1439
1440                 /* Extend the existing signature */
1441
1442                 e = strextend(&c->signature, CHAR_TO_STR(SD_BUS_TYPE_ARRAY), contents, NULL);
1443                 if (!e) {
1444                         m->poisoned = true;
1445                         return -ENOMEM;
1446                 }
1447
1448                 nindex = e - c->signature;
1449         }
1450
1451         a = message_extend_body(m, 4, 4);
1452         if (!a)
1453                 return -ENOMEM;
1454
1455         o = m->body_end;
1456         op = m->body_end->data;
1457         os = m->body_end->size;
1458
1459         /* Add alignment between size and first element */
1460         if (!message_extend_body(m, alignment, 0))
1461                 return -ENOMEM;
1462
1463         if (c->enclosing != SD_BUS_TYPE_ARRAY)
1464                 c->index = nindex;
1465
1466         /* location of array size might have changed so let's readjust a */
1467         if (o == m->body_end)
1468                 a = adjust_pointer(a, op, os, m->body_end->data);
1469
1470         *(uint32_t*) a = 0;
1471         *array_size = a;
1472         return 0;
1473 }
1474
1475 static int bus_message_open_variant(
1476                 sd_bus_message *m,
1477                 struct bus_container *c,
1478                 const char *contents) {
1479
1480         size_t l;
1481         void *a;
1482
1483         assert(m);
1484         assert(c);
1485         assert(contents);
1486
1487         if (!signature_is_single(contents, false))
1488                 return -EINVAL;
1489
1490         if (*contents == SD_BUS_TYPE_DICT_ENTRY_BEGIN)
1491                 return -EINVAL;
1492
1493         if (c->signature && c->signature[c->index]) {
1494
1495                 if (c->signature[c->index] != SD_BUS_TYPE_VARIANT)
1496                         return -ENXIO;
1497
1498         } else {
1499                 char *e;
1500
1501                 if (c->enclosing != 0)
1502                         return -ENXIO;
1503
1504                 e = strextend(&c->signature, CHAR_TO_STR(SD_BUS_TYPE_VARIANT), NULL);
1505                 if (!e) {
1506                         m->poisoned = true;
1507                         return -ENOMEM;
1508                 }
1509         }
1510
1511         l = strlen(contents);
1512         a = message_extend_body(m, 1, 1 + l + 1);
1513         if (!a)
1514                 return -ENOMEM;
1515
1516         *(uint8_t*) a = l;
1517         memcpy((uint8_t*) a + 1, contents, l + 1);
1518
1519         if (c->enclosing != SD_BUS_TYPE_ARRAY)
1520                 c->index++;
1521
1522         return 0;
1523 }
1524
1525 static int bus_message_open_struct(
1526                 sd_bus_message *m,
1527                 struct bus_container *c,
1528                 const char *contents) {
1529
1530         size_t nindex;
1531
1532         assert(m);
1533         assert(c);
1534         assert(contents);
1535
1536         if (!signature_is_valid(contents, false))
1537                 return -EINVAL;
1538
1539         if (c->signature && c->signature[c->index]) {
1540                 size_t l;
1541
1542                 l = strlen(contents);
1543
1544                 if (c->signature[c->index] != SD_BUS_TYPE_STRUCT_BEGIN ||
1545                     !startswith(c->signature + c->index + 1, contents) ||
1546                     c->signature[c->index + 1 + l] != SD_BUS_TYPE_STRUCT_END)
1547                         return -ENXIO;
1548
1549                 nindex = c->index + 1 + l + 1;
1550         } else {
1551                 char *e;
1552
1553                 if (c->enclosing != 0)
1554                         return -ENXIO;
1555
1556                 e = strextend(&c->signature, CHAR_TO_STR(SD_BUS_TYPE_STRUCT_BEGIN), contents, CHAR_TO_STR(SD_BUS_TYPE_STRUCT_END), NULL);
1557                 if (!e) {
1558                         m->poisoned = true;
1559                         return -ENOMEM;
1560                 }
1561
1562                 nindex = e - c->signature;
1563         }
1564
1565         /* Align contents to 8 byte boundary */
1566         if (!message_extend_body(m, 8, 0))
1567                 return -ENOMEM;
1568
1569         if (c->enclosing != SD_BUS_TYPE_ARRAY)
1570                 c->index = nindex;
1571
1572         return 0;
1573 }
1574
1575 static int bus_message_open_dict_entry(
1576                 sd_bus_message *m,
1577                 struct bus_container *c,
1578                 const char *contents) {
1579
1580         size_t nindex;
1581
1582         assert(m);
1583         assert(c);
1584         assert(contents);
1585
1586         if (!signature_is_pair(contents))
1587                 return -EINVAL;
1588
1589         if (c->enclosing != SD_BUS_TYPE_ARRAY)
1590                 return -ENXIO;
1591
1592         if (c->signature && c->signature[c->index]) {
1593                 size_t l;
1594
1595                 l = strlen(contents);
1596
1597                 if (c->signature[c->index] != SD_BUS_TYPE_DICT_ENTRY_BEGIN ||
1598                     !startswith(c->signature + c->index + 1, contents) ||
1599                     c->signature[c->index + 1 + l] != SD_BUS_TYPE_DICT_ENTRY_END)
1600                         return -ENXIO;
1601
1602                 nindex = c->index + 1 + l + 1;
1603         } else
1604                 return -ENXIO;
1605
1606         /* Align contents to 8 byte boundary */
1607         if (!message_extend_body(m, 8, 0))
1608                 return -ENOMEM;
1609
1610         if (c->enclosing != SD_BUS_TYPE_ARRAY)
1611                 c->index = nindex;
1612
1613         return 0;
1614 }
1615
1616 _public_ int sd_bus_message_open_container(
1617                 sd_bus_message *m,
1618                 char type,
1619                 const char *contents) {
1620
1621         struct bus_container *c, *w;
1622         uint32_t *array_size = NULL;
1623         char *signature;
1624         size_t before;
1625         int r;
1626
1627         assert_return(m, -EINVAL);
1628         assert_return(!m->sealed, -EPERM);
1629         assert_return(contents, -EINVAL);
1630         assert_return(!m->poisoned, -ESTALE);
1631
1632         /* Make sure we have space for one more container */
1633         w = realloc(m->containers, sizeof(struct bus_container) * (m->n_containers + 1));
1634         if (!w) {
1635                 m->poisoned = true;
1636                 return -ENOMEM;
1637         }
1638
1639         m->containers = w;
1640
1641         c = message_get_container(m);
1642
1643         signature = strdup(contents);
1644         if (!signature) {
1645                 m->poisoned = true;
1646                 return -ENOMEM;
1647         }
1648
1649         /* Save old index in the parent container, in case we have to
1650          * abort this container */
1651         c->saved_index = c->index;
1652         before = m->header->body_size;
1653
1654         if (type == SD_BUS_TYPE_ARRAY)
1655                 r = bus_message_open_array(m, c, contents, &array_size);
1656         else if (type == SD_BUS_TYPE_VARIANT)
1657                 r = bus_message_open_variant(m, c, contents);
1658         else if (type == SD_BUS_TYPE_STRUCT)
1659                 r = bus_message_open_struct(m, c, contents);
1660         else if (type == SD_BUS_TYPE_DICT_ENTRY)
1661                 r = bus_message_open_dict_entry(m, c, contents);
1662         else
1663                 r = -EINVAL;
1664
1665         if (r < 0) {
1666                 free(signature);
1667                 return r;
1668         }
1669
1670         /* OK, let's fill it in */
1671         w += m->n_containers++;
1672         w->enclosing = type;
1673         w->signature = signature;
1674         w->index = 0;
1675         w->array_size = array_size;
1676         w->before = before;
1677         w->begin = m->rindex;
1678
1679         return 0;
1680 }
1681
1682 _public_ int sd_bus_message_close_container(sd_bus_message *m) {
1683         struct bus_container *c;
1684
1685         assert_return(m, -EINVAL);
1686         assert_return(!m->sealed, -EPERM);
1687         assert_return(m->n_containers > 0, -EINVAL);
1688         assert_return(!m->poisoned, -ESTALE);
1689
1690         c = message_get_container(m);
1691         if (c->enclosing != SD_BUS_TYPE_ARRAY)
1692                 if (c->signature && c->signature[c->index] != 0)
1693                         return -EINVAL;
1694
1695         free(c->signature);
1696         m->n_containers--;
1697
1698         return 0;
1699 }
1700
1701 typedef struct {
1702         const char *types;
1703         unsigned n_struct;
1704         unsigned n_array;
1705 } TypeStack;
1706
1707 static int type_stack_push(TypeStack *stack, unsigned max, unsigned *i, const char *types, unsigned n_struct, unsigned n_array) {
1708         assert(stack);
1709         assert(max > 0);
1710
1711         if (*i >= max)
1712                 return -EINVAL;
1713
1714         stack[*i].types = types;
1715         stack[*i].n_struct = n_struct;
1716         stack[*i].n_array = n_array;
1717         (*i)++;
1718
1719         return 0;
1720 }
1721
1722 static int type_stack_pop(TypeStack *stack, unsigned max, unsigned *i, const char **types, unsigned *n_struct, unsigned *n_array) {
1723         assert(stack);
1724         assert(max > 0);
1725         assert(types);
1726         assert(n_struct);
1727         assert(n_array);
1728
1729         if (*i <= 0)
1730                 return 0;
1731
1732         (*i)--;
1733         *types = stack[*i].types;
1734         *n_struct = stack[*i].n_struct;
1735         *n_array = stack[*i].n_array;
1736
1737         return 1;
1738 }
1739
1740 int bus_message_append_ap(
1741                 sd_bus_message *m,
1742                 const char *types,
1743                 va_list ap) {
1744
1745         unsigned n_array, n_struct;
1746         TypeStack stack[BUS_CONTAINER_DEPTH];
1747         unsigned stack_ptr = 0;
1748         int r;
1749
1750         assert(m);
1751
1752         if (!types)
1753                 return 0;
1754
1755         n_array = (unsigned) -1;
1756         n_struct = strlen(types);
1757
1758         for (;;) {
1759                 const char *t;
1760
1761                 if (n_array == 0 || (n_array == (unsigned) -1 && n_struct == 0)) {
1762                         r = type_stack_pop(stack, ELEMENTSOF(stack), &stack_ptr, &types, &n_struct, &n_array);
1763                         if (r < 0)
1764                                 return r;
1765                         if (r == 0)
1766                                 break;
1767
1768                         r = sd_bus_message_close_container(m);
1769                         if (r < 0)
1770                                 return r;
1771
1772                         continue;
1773                 }
1774
1775                 t = types;
1776                 if (n_array != (unsigned) -1)
1777                         n_array --;
1778                 else {
1779                         types ++;
1780                         n_struct--;
1781                 }
1782
1783                 switch (*t) {
1784
1785                 case SD_BUS_TYPE_BYTE: {
1786                         uint8_t x;
1787
1788                         x = (uint8_t) va_arg(ap, int);
1789                         r = sd_bus_message_append_basic(m, *t, &x);
1790                         break;
1791                 }
1792
1793                 case SD_BUS_TYPE_BOOLEAN:
1794                 case SD_BUS_TYPE_INT32:
1795                 case SD_BUS_TYPE_UINT32:
1796                 case SD_BUS_TYPE_UNIX_FD: {
1797                         uint32_t x;
1798
1799                         /* We assume a boolean is the same as int32_t */
1800                         assert_cc(sizeof(int32_t) == sizeof(int));
1801
1802                         x = va_arg(ap, uint32_t);
1803                         r = sd_bus_message_append_basic(m, *t, &x);
1804                         break;
1805                 }
1806
1807                 case SD_BUS_TYPE_INT16:
1808                 case SD_BUS_TYPE_UINT16: {
1809                         uint16_t x;
1810
1811                         x = (uint16_t) va_arg(ap, int);
1812                         r = sd_bus_message_append_basic(m, *t, &x);
1813                         break;
1814                 }
1815
1816                 case SD_BUS_TYPE_INT64:
1817                 case SD_BUS_TYPE_UINT64:
1818                 case SD_BUS_TYPE_DOUBLE: {
1819                         uint64_t x;
1820
1821                         x = va_arg(ap, uint64_t);
1822                         r = sd_bus_message_append_basic(m, *t, &x);
1823                         break;
1824                 }
1825
1826                 case SD_BUS_TYPE_STRING:
1827                 case SD_BUS_TYPE_OBJECT_PATH:
1828                 case SD_BUS_TYPE_SIGNATURE: {
1829                         const char *x;
1830
1831                         x = va_arg(ap, const char*);
1832                         r = sd_bus_message_append_basic(m, *t, x);
1833                         break;
1834                 }
1835
1836                 case SD_BUS_TYPE_ARRAY: {
1837                         size_t k;
1838
1839                         r = signature_element_length(t + 1, &k);
1840                         if (r < 0)
1841                                 return r;
1842
1843                         {
1844                                 char s[k + 1];
1845                                 memcpy(s, t + 1, k);
1846                                 s[k] = 0;
1847
1848                                 r = sd_bus_message_open_container(m, SD_BUS_TYPE_ARRAY, s);
1849                                 if (r < 0)
1850                                         return r;
1851                         }
1852
1853                         if (n_array == (unsigned) -1) {
1854                                 types += k;
1855                                 n_struct -= k;
1856                         }
1857
1858                         r = type_stack_push(stack, ELEMENTSOF(stack), &stack_ptr, types, n_struct, n_array);
1859                         if (r < 0)
1860                                 return r;
1861
1862                         types = t + 1;
1863                         n_struct = k;
1864                         n_array = va_arg(ap, unsigned);
1865
1866                         break;
1867                 }
1868
1869                 case SD_BUS_TYPE_VARIANT: {
1870                         const char *s;
1871
1872                         s = va_arg(ap, const char*);
1873                         if (!s)
1874                                 return -EINVAL;
1875
1876                         r = sd_bus_message_open_container(m, SD_BUS_TYPE_VARIANT, s);
1877                         if (r < 0)
1878                                 return r;
1879
1880                         r = type_stack_push(stack, ELEMENTSOF(stack), &stack_ptr, types, n_struct, n_array);
1881                         if (r < 0)
1882                                 return r;
1883
1884                         types = s;
1885                         n_struct = strlen(s);
1886                         n_array = (unsigned) -1;
1887
1888                         break;
1889                 }
1890
1891                 case SD_BUS_TYPE_STRUCT_BEGIN:
1892                 case SD_BUS_TYPE_DICT_ENTRY_BEGIN: {
1893                         size_t k;
1894
1895                         r = signature_element_length(t, &k);
1896                         if (r < 0)
1897                                 return r;
1898
1899                         {
1900                                 char s[k - 1];
1901
1902                                 memcpy(s, t + 1, k - 2);
1903                                 s[k - 2] = 0;
1904
1905                                 r = sd_bus_message_open_container(m, *t == SD_BUS_TYPE_STRUCT_BEGIN ? SD_BUS_TYPE_STRUCT : SD_BUS_TYPE_DICT_ENTRY, s);
1906                                 if (r < 0)
1907                                         return r;
1908                         }
1909
1910                         if (n_array == (unsigned) -1) {
1911                                 types += k - 1;
1912                                 n_struct -= k - 1;
1913                         }
1914
1915                         r = type_stack_push(stack, ELEMENTSOF(stack), &stack_ptr, types, n_struct, n_array);
1916                         if (r < 0)
1917                                 return r;
1918
1919                         types = t + 1;
1920                         n_struct = k - 2;
1921                         n_array = (unsigned) -1;
1922
1923                         break;
1924                 }
1925
1926                 default:
1927                         r = -EINVAL;
1928                 }
1929
1930                 if (r < 0)
1931                         return r;
1932         }
1933
1934         return 1;
1935 }
1936
1937 _public_ int sd_bus_message_append(sd_bus_message *m, const char *types, ...) {
1938         va_list ap;
1939         int r;
1940
1941         assert_return(m, -EINVAL);
1942         assert_return(types, -EINVAL);
1943         assert_return(!m->sealed, -EPERM);
1944         assert_return(!m->poisoned, -ESTALE);
1945
1946         va_start(ap, types);
1947         r = bus_message_append_ap(m, types, ap);
1948         va_end(ap);
1949
1950         return r;
1951 }
1952
1953 _public_ int sd_bus_message_append_array_space(sd_bus_message *m,
1954                                                char type,
1955                                                size_t size,
1956                                                void **ptr) {
1957         ssize_t align, sz;
1958         void *a;
1959         int r;
1960
1961         assert_return(m, -EINVAL);
1962         assert_return(!m->sealed, -EPERM);
1963         assert_return(bus_type_is_trivial(type), -EINVAL);
1964         assert_return(ptr || size == 0, -EINVAL);
1965         assert_return(!m->poisoned, -ESTALE);
1966
1967         align = bus_type_get_alignment(type);
1968         sz = bus_type_get_size(type);
1969
1970         assert_se(align > 0);
1971         assert_se(sz > 0);
1972
1973         if (size % sz != 0)
1974                 return -EINVAL;
1975
1976         r = sd_bus_message_open_container(m, SD_BUS_TYPE_ARRAY, CHAR_TO_STR(type));
1977         if (r < 0)
1978                 return r;
1979
1980         a = message_extend_body(m, align, size);
1981         if (!a)
1982                 return -ENOMEM;
1983
1984         r = sd_bus_message_close_container(m);
1985         if (r < 0)
1986                 return r;
1987
1988         *ptr = a;
1989         return 0;
1990 }
1991
1992 _public_ int sd_bus_message_append_array(sd_bus_message *m,
1993                                          char type,
1994                                          const void *ptr,
1995                                          size_t size) {
1996         int r;
1997         void *p;
1998
1999         assert_return(m, -EINVAL);
2000         assert_return(!m->sealed, -EPERM);
2001         assert_return(bus_type_is_trivial(type), -EINVAL);
2002         assert_return(ptr || size == 0, -EINVAL);
2003         assert_return(!m->poisoned, -ESTALE);
2004
2005         r = sd_bus_message_append_array_space(m, type, size, &p);
2006         if (r < 0)
2007                 return r;
2008
2009         if (size > 0)
2010                 memcpy(p, ptr, size);
2011
2012         return 0;
2013 }
2014
2015 _public_ int sd_bus_message_append_array_iovec(
2016                 sd_bus_message *m,
2017                 char type,
2018                 const struct iovec *iov,
2019                 unsigned n) {
2020
2021         size_t size;
2022         unsigned i;
2023         void *p;
2024         int r;
2025
2026         assert_return(m, -EINVAL);
2027         assert_return(!m->sealed, -EPERM);
2028         assert_return(bus_type_is_trivial(type), -EINVAL);
2029         assert_return(iov || n == 0, -EINVAL);
2030         assert_return(!m->poisoned, -ESTALE);
2031
2032         size = IOVEC_TOTAL_SIZE(iov, n);
2033
2034         r = sd_bus_message_append_array_space(m, type, size, &p);
2035         if (r < 0)
2036                 return r;
2037
2038         for (i = 0; i < n; i++) {
2039
2040                 if (iov[i].iov_base)
2041                         memcpy(p, iov[i].iov_base, iov[i].iov_len);
2042                 else
2043                         memset(p, 0, iov[i].iov_len);
2044
2045                 p = (uint8_t*) p + iov[i].iov_len;
2046         }
2047
2048         return 0;
2049 }
2050
2051 _public_ int sd_bus_message_append_array_memfd(sd_bus_message *m,
2052                                                char type,
2053                                                sd_memfd *memfd) {
2054         _cleanup_close_ int copy_fd = -1;
2055         struct bus_body_part *part;
2056         ssize_t align, sz;
2057         uint64_t size;
2058         void *a;
2059         int r;
2060
2061         if (!m)
2062                 return -EINVAL;
2063         if (!memfd)
2064                 return -EINVAL;
2065         if (m->sealed)
2066                 return -EPERM;
2067         if (!bus_type_is_trivial(type))
2068                 return -EINVAL;
2069         if (m->poisoned)
2070                 return -ESTALE;
2071
2072         r = sd_memfd_set_sealed(memfd, true);
2073         if (r < 0)
2074                 return r;
2075
2076         copy_fd = sd_memfd_dup_fd(memfd);
2077         if (copy_fd < 0)
2078                 return copy_fd;
2079
2080         r = sd_memfd_get_size(memfd, &size);
2081         if (r < 0)
2082                 return r;
2083
2084         align = bus_type_get_alignment(type);
2085         sz = bus_type_get_size(type);
2086
2087         assert_se(align > 0);
2088         assert_se(sz > 0);
2089
2090         if (size % sz != 0)
2091                 return -EINVAL;
2092
2093         if (size > (uint64_t) (uint32_t) -1)
2094                 return -EINVAL;
2095
2096         r = sd_bus_message_open_container(m, SD_BUS_TYPE_ARRAY, CHAR_TO_STR(type));
2097         if (r < 0)
2098                 return r;
2099
2100         a = message_extend_body(m, align, 0);
2101         if (!a)
2102                 return -ENOMEM;
2103
2104         part = message_append_part(m);
2105         if (!part)
2106                 return -ENOMEM;
2107
2108         part->memfd = copy_fd;
2109         part->sealed = true;
2110         part->size = size;
2111         copy_fd = -1;
2112
2113         message_extend_containers(m, size);
2114         m->header->body_size += size;
2115
2116         return sd_bus_message_close_container(m);
2117 }
2118
2119 _public_ int sd_bus_message_append_string_memfd(sd_bus_message *m, sd_memfd *memfd) {
2120         _cleanup_close_ int copy_fd = -1;
2121         struct bus_body_part *part;
2122         struct bus_container *c;
2123         uint64_t size;
2124         void *a;
2125         int r;
2126
2127         assert_return(m, -EINVAL);
2128         assert_return(memfd, -EINVAL);
2129         assert_return(!m->sealed, -EPERM);
2130         assert_return(!m->poisoned, -ESTALE);
2131
2132         r = sd_memfd_set_sealed(memfd, true);
2133         if (r < 0)
2134                 return r;
2135
2136         copy_fd = sd_memfd_dup_fd(memfd);
2137         if (copy_fd < 0)
2138                 return copy_fd;
2139
2140         r = sd_memfd_get_size(memfd, &size);
2141         if (r < 0)
2142                 return r;
2143
2144         /* We require this to be NUL terminated */
2145         if (size == 0)
2146                 return -EINVAL;
2147
2148         if (size > (uint64_t) (uint32_t) -1)
2149                 return -EINVAL;
2150
2151         c = message_get_container(m);
2152         if (c->signature && c->signature[c->index]) {
2153                 /* Container signature is already set */
2154
2155                 if (c->signature[c->index] != SD_BUS_TYPE_STRING)
2156                         return -ENXIO;
2157         } else {
2158                 char *e;
2159
2160                 /* Maybe we can append to the signature? But only if this is the top-level container*/
2161                 if (c->enclosing != 0)
2162                         return -ENXIO;
2163
2164                 e = strextend(&c->signature, CHAR_TO_STR(SD_BUS_TYPE_STRING), NULL);
2165                 if (!e) {
2166                         m->poisoned = true;
2167                         return -ENOMEM;
2168                 }
2169         }
2170
2171         a = message_extend_body(m, 4, 4);
2172         if (!a)
2173                 return -ENOMEM;
2174
2175         *(uint32_t*) a = size - 1;
2176
2177         part = message_append_part(m);
2178         if (!part)
2179                 return -ENOMEM;
2180
2181         part->memfd = copy_fd;
2182         part->sealed = true;
2183         part->size = size;
2184         copy_fd = -1;
2185
2186         message_extend_containers(m, size);
2187         m->header->body_size += size;
2188
2189         if (c->enclosing != SD_BUS_TYPE_ARRAY)
2190                 c->index++;
2191
2192         return 0;
2193 }
2194
2195 _public_ int sd_bus_message_append_strv(sd_bus_message *m, char **l) {
2196         char **i;
2197         int r;
2198
2199         assert_return(m, -EINVAL);
2200         assert_return(!m->sealed, -EPERM);
2201         assert_return(!m->poisoned, -ESTALE);
2202
2203         r = sd_bus_message_open_container(m, 'a', "s");
2204         if (r < 0)
2205                 return r;
2206
2207         STRV_FOREACH(i, l) {
2208                 r = sd_bus_message_append_basic(m, 's', *i);
2209                 if (r < 0)
2210                         return r;
2211         }
2212
2213         return sd_bus_message_close_container(m);
2214 }
2215
2216 int bus_body_part_map(struct bus_body_part *part) {
2217         void *p;
2218         size_t psz;
2219
2220         assert_se(part);
2221
2222         if (part->data)
2223                 return 0;
2224
2225         if (part->size <= 0)
2226                 return 0;
2227
2228         /* For smaller zero parts (as used for padding) we don't need to map anything... */
2229         if (part->memfd < 0 && part->is_zero && part->size < 8) {
2230                 static const uint8_t zeroes[7] = { };
2231                 part->data = (void*) zeroes;
2232                 return 0;
2233         }
2234
2235         psz = PAGE_ALIGN(part->size);
2236
2237         if (part->memfd >= 0)
2238                 p = mmap(NULL, psz, PROT_READ, MAP_SHARED, part->memfd, 0);
2239         else if (part->is_zero)
2240                 p = mmap(NULL, psz, PROT_READ, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0);
2241         else
2242                 return -EINVAL;
2243
2244         if (p == MAP_FAILED)
2245                 return -errno;
2246
2247         part->mapped = psz;
2248         part->data = p;
2249         part->munmap_this = true;
2250
2251         return 0;
2252 }
2253
2254 void bus_body_part_unmap(struct bus_body_part *part) {
2255
2256         assert_se(part);
2257
2258         if (part->memfd < 0)
2259                 return;
2260
2261         if (!part->data)
2262                 return;
2263
2264         if (!part->munmap_this)
2265                 return;
2266
2267         assert_se(munmap(part->data, part->mapped) == 0);
2268
2269         part->data = NULL;
2270         part->mapped = 0;
2271         part->munmap_this = false;
2272
2273         return;
2274 }
2275
2276 static int buffer_peek(const void *p, uint32_t sz, size_t *rindex, size_t align, size_t nbytes, void **r) {
2277         size_t k, start, end;
2278
2279         assert(rindex);
2280         assert(align > 0);
2281
2282         start = ALIGN_TO((size_t) *rindex, align);
2283         end = start + nbytes;
2284
2285         if (end > sz)
2286                 return -EBADMSG;
2287
2288         /* Verify that padding is 0 */
2289         for (k = *rindex; k < start; k++)
2290                 if (((const uint8_t*) p)[k] != 0)
2291                         return -EBADMSG;
2292
2293         if (r)
2294                 *r = (uint8_t*) p + start;
2295
2296         *rindex = end;
2297
2298         return 1;
2299 }
2300
2301 static bool message_end_of_signature(sd_bus_message *m) {
2302         struct bus_container *c;
2303
2304         assert(m);
2305
2306         c = message_get_container(m);
2307         return !c->signature || c->signature[c->index] == 0;
2308 }
2309
2310 static bool message_end_of_array(sd_bus_message *m, size_t index) {
2311         struct bus_container *c;
2312
2313         assert(m);
2314
2315         c = message_get_container(m);
2316         if (!c->array_size)
2317                 return false;
2318
2319         return index >= c->begin + BUS_MESSAGE_BSWAP32(m, *c->array_size);
2320 }
2321
2322 _public_ int sd_bus_message_at_end(sd_bus_message *m, int complete) {
2323         assert_return(m, -EINVAL);
2324         assert_return(m->sealed, -EPERM);
2325
2326         if (complete && m->n_containers > 0)
2327                 return false;
2328
2329         if (message_end_of_signature(m))
2330                 return true;
2331
2332         if (message_end_of_array(m, m->rindex))
2333                 return true;
2334
2335         return false;
2336 }
2337
2338 static struct bus_body_part* find_part(sd_bus_message *m, size_t index, size_t sz, void **p) {
2339         struct bus_body_part *part;
2340         size_t begin;
2341         int r;
2342
2343         assert(m);
2344
2345         if (m->cached_rindex_part && index >= m->cached_rindex_part_begin) {
2346                 part = m->cached_rindex_part;
2347                 begin = m->cached_rindex_part_begin;
2348         } else {
2349                 part = &m->body;
2350                 begin = 0;
2351         }
2352
2353         while (part) {
2354                 if (index < begin)
2355                         return NULL;
2356
2357                 if (index + sz <= begin + part->size) {
2358
2359                         r = bus_body_part_map(part);
2360                         if (r < 0)
2361                                 return NULL;
2362
2363                         if (p)
2364                                 *p = (uint8_t*) part->data + index - begin;
2365
2366                         m->cached_rindex_part = part;
2367                         m->cached_rindex_part_begin = begin;
2368
2369                         return part;
2370                 }
2371
2372                 begin += part->size;
2373                 part = part->next;
2374         }
2375
2376         return NULL;
2377 }
2378
2379 static int message_peek_body(
2380                 sd_bus_message *m,
2381                 size_t *rindex,
2382                 size_t align,
2383                 size_t nbytes,
2384                 void **ret) {
2385
2386         size_t k, start, end, padding;
2387         struct bus_body_part *part;
2388         uint8_t *q;
2389
2390         assert(m);
2391         assert(rindex);
2392         assert(align > 0);
2393
2394         if (message_end_of_array(m, *rindex))
2395                 return 0;
2396
2397         start = ALIGN_TO((size_t) *rindex, align);
2398         padding = start - *rindex;
2399         end = start + nbytes;
2400
2401         if (end > BUS_MESSAGE_BODY_SIZE(m))
2402                 return -EBADMSG;
2403
2404         part = find_part(m, *rindex, padding, (void**) &q);
2405         if (!part)
2406                 return -EBADMSG;
2407
2408         if (q) {
2409                 /* Verify padding */
2410                 for (k = 0; k < padding; k++)
2411                         if (q[k] != 0)
2412                                 return -EBADMSG;
2413         }
2414
2415         part = find_part(m, start, nbytes, (void**) &q);
2416         if (!part || !q)
2417                 return -EBADMSG;
2418
2419         *rindex = end;
2420
2421         if (ret)
2422                 *ret = q;
2423
2424         return 1;
2425 }
2426
2427 static bool validate_nul(const char *s, size_t l) {
2428
2429         /* Check for NUL chars in the string */
2430         if (memchr(s, 0, l))
2431                 return false;
2432
2433         /* Check for NUL termination */
2434         if (s[l] != 0)
2435                 return false;
2436
2437         return true;
2438 }
2439
2440 static bool validate_string(const char *s, size_t l) {
2441
2442         if (!validate_nul(s, l))
2443                 return false;
2444
2445         /* Check if valid UTF8 */
2446         if (!utf8_is_valid(s))
2447                 return false;
2448
2449         return true;
2450 }
2451
2452 static bool validate_signature(const char *s, size_t l) {
2453
2454         if (!validate_nul(s, l))
2455                 return false;
2456
2457         /* Check if valid signature */
2458         if (!signature_is_valid(s, true))
2459                 return false;
2460
2461         return true;
2462 }
2463
2464 static bool validate_object_path(const char *s, size_t l) {
2465
2466         if (!validate_nul(s, l))
2467                 return false;
2468
2469         if (!object_path_is_valid(s))
2470                 return false;
2471
2472         return true;
2473 }
2474
2475 _public_ int sd_bus_message_read_basic(sd_bus_message *m, char type, void *p) {
2476         struct bus_container *c;
2477         void *q;
2478         int r;
2479
2480         assert_return(m, -EINVAL);
2481         assert_return(m->sealed, -EPERM);
2482         assert_return(bus_type_is_basic(type), -EINVAL);
2483
2484         if (message_end_of_signature(m))
2485                 return -ENXIO;
2486
2487         if (message_end_of_array(m, m->rindex))
2488                 return 0;
2489
2490         c = message_get_container(m);
2491         if (c->signature[c->index] != type)
2492                 return -ENXIO;
2493
2494         switch (type) {
2495
2496         case SD_BUS_TYPE_STRING:
2497         case SD_BUS_TYPE_OBJECT_PATH: {
2498                 uint32_t l;
2499                 size_t rindex;
2500
2501                 rindex = m->rindex;
2502                 r = message_peek_body(m, &rindex, 4, 4, &q);
2503                 if (r <= 0)
2504                         return r;
2505
2506                 l = BUS_MESSAGE_BSWAP32(m, *(uint32_t*) q);
2507                 r = message_peek_body(m, &rindex, 1, l+1, &q);
2508                 if (r < 0)
2509                         return r;
2510                 if (r == 0)
2511                         return -EBADMSG;
2512
2513                 if (type == SD_BUS_TYPE_OBJECT_PATH) {
2514                         if (!validate_object_path(q, l))
2515                                 return -EBADMSG;
2516                 } else {
2517                         if (!validate_string(q, l))
2518                                 return -EBADMSG;
2519                 }
2520
2521                 m->rindex = rindex;
2522                 if (p)
2523                         *(const char**) p = q;
2524
2525                 break;
2526         }
2527
2528         case SD_BUS_TYPE_SIGNATURE: {
2529                 uint8_t l;
2530                 size_t rindex;
2531
2532                 rindex = m->rindex;
2533                 r = message_peek_body(m, &rindex, 1, 1, &q);
2534                 if (r <= 0)
2535                         return r;
2536
2537                 l = *(uint8_t*) q;
2538                 r = message_peek_body(m, &rindex, 1, l+1, &q);
2539                 if (r < 0)
2540                         return r;
2541                 if (r == 0)
2542                         return -EBADMSG;
2543
2544                 if (!validate_signature(q, l))
2545                         return -EBADMSG;
2546
2547                 m->rindex = rindex;
2548
2549                 if (p)
2550                         *(const char**) p = q;
2551                 break;
2552         }
2553
2554         default: {
2555                 ssize_t sz, align;
2556                 size_t rindex;
2557
2558                 align = bus_type_get_alignment(type);
2559                 sz = bus_type_get_size(type);
2560                 assert(align > 0 && sz > 0);
2561
2562                 rindex = m->rindex;
2563                 r = message_peek_body(m, &rindex, align, sz, &q);
2564                 if (r <= 0)
2565                         return r;
2566
2567                 switch (type) {
2568
2569                 case SD_BUS_TYPE_BYTE:
2570                         if (p)
2571                                 *(uint8_t*) p = *(uint8_t*) q;
2572                         break;
2573
2574                 case SD_BUS_TYPE_BOOLEAN:
2575                         if (p)
2576                                 *(int*) p = !!*(uint32_t*) q;
2577                         break;
2578
2579                 case SD_BUS_TYPE_INT16:
2580                 case SD_BUS_TYPE_UINT16:
2581                         if (p)
2582                                 *(uint16_t*) p = BUS_MESSAGE_BSWAP16(m, *(uint16_t*) q);
2583                         break;
2584
2585                 case SD_BUS_TYPE_INT32:
2586                 case SD_BUS_TYPE_UINT32:
2587                         if (p)
2588                                 *(uint32_t*) p = BUS_MESSAGE_BSWAP32(m, *(uint32_t*) q);
2589                         break;
2590
2591                 case SD_BUS_TYPE_INT64:
2592                 case SD_BUS_TYPE_UINT64:
2593                 case SD_BUS_TYPE_DOUBLE:
2594                         if (p)
2595                                 *(uint64_t*) p = BUS_MESSAGE_BSWAP64(m, *(uint64_t*) q);
2596                         break;
2597
2598                 case SD_BUS_TYPE_UNIX_FD: {
2599                         uint32_t j;
2600
2601                         j = BUS_MESSAGE_BSWAP32(m, *(uint32_t*) q);
2602                         if (j >= m->n_fds)
2603                                 return -EBADMSG;
2604
2605                         if (p)
2606                                 *(int*) p = m->fds[j];
2607                         break;
2608                 }
2609
2610                 default:
2611                         assert_not_reached("Unknown basic type...");
2612                 }
2613
2614                 m->rindex = rindex;
2615
2616                 break;
2617         }
2618         }
2619
2620         if (c->enclosing != SD_BUS_TYPE_ARRAY)
2621                 c->index++;
2622
2623         return 1;
2624 }
2625
2626 static int bus_message_enter_array(
2627                 sd_bus_message *m,
2628                 struct bus_container *c,
2629                 const char *contents,
2630                 uint32_t **array_size) {
2631
2632         size_t rindex;
2633         void *q;
2634         int r, alignment;
2635
2636         assert(m);
2637         assert(c);
2638         assert(contents);
2639         assert(array_size);
2640
2641         if (!signature_is_single(contents, true))
2642                 return -EINVAL;
2643
2644         alignment = bus_type_get_alignment(contents[0]);
2645         if (alignment < 0)
2646                 return alignment;
2647
2648         if (!c->signature || c->signature[c->index] == 0)
2649                 return 0;
2650
2651         if (c->signature[c->index] != SD_BUS_TYPE_ARRAY)
2652                 return -ENXIO;
2653
2654         if (!startswith(c->signature + c->index + 1, contents))
2655                 return -ENXIO;
2656
2657         rindex = m->rindex;
2658         r = message_peek_body(m, &rindex, 4, 4, &q);
2659         if (r <= 0)
2660                 return r;
2661
2662         if (BUS_MESSAGE_BSWAP32(m, *(uint32_t*) q) > BUS_ARRAY_MAX_SIZE)
2663                 return -EBADMSG;
2664
2665         r = message_peek_body(m, &rindex, alignment, 0, NULL);
2666         if (r < 0)
2667                 return r;
2668         if (r == 0)
2669                 return -EBADMSG;
2670
2671         if (c->enclosing != SD_BUS_TYPE_ARRAY)
2672                 c->index += 1 + strlen(contents);
2673
2674         m->rindex = rindex;
2675
2676         *array_size = (uint32_t*) q;
2677
2678         return 1;
2679 }
2680
2681 static int bus_message_enter_variant(
2682                 sd_bus_message *m,
2683                 struct bus_container *c,
2684                 const char *contents) {
2685
2686         size_t rindex;
2687         uint8_t l;
2688         void *q;
2689         int r;
2690
2691         assert(m);
2692         assert(c);
2693         assert(contents);
2694
2695         if (!signature_is_single(contents, false))
2696                 return -EINVAL;
2697
2698         if (*contents == SD_BUS_TYPE_DICT_ENTRY_BEGIN)
2699                 return -EINVAL;
2700
2701         if (!c->signature || c->signature[c->index] == 0)
2702                 return 0;
2703
2704         if (c->signature[c->index] != SD_BUS_TYPE_VARIANT)
2705                 return -ENXIO;
2706
2707         rindex = m->rindex;
2708         r = message_peek_body(m, &rindex, 1, 1, &q);
2709         if (r <= 0)
2710                 return r;
2711
2712         l = *(uint8_t*) q;
2713         r = message_peek_body(m, &rindex, 1, l+1, &q);
2714         if (r < 0)
2715                 return r;
2716         if (r == 0)
2717                 return -EBADMSG;
2718
2719         if (!validate_signature(q, l))
2720                 return -EBADMSG;
2721
2722         if (!streq(q, contents))
2723                 return -ENXIO;
2724
2725         if (c->enclosing != SD_BUS_TYPE_ARRAY)
2726                 c->index++;
2727
2728         m->rindex = rindex;
2729
2730         return 1;
2731 }
2732
2733 static int bus_message_enter_struct(
2734                 sd_bus_message *m,
2735                 struct bus_container *c,
2736                 const char *contents) {
2737
2738         size_t l;
2739         int r;
2740
2741         assert(m);
2742         assert(c);
2743         assert(contents);
2744
2745         if (!signature_is_valid(contents, false))
2746                 return -EINVAL;
2747
2748         if (!c->signature || c->signature[c->index] == 0)
2749                 return 0;
2750
2751         l = strlen(contents);
2752
2753         if (c->signature[c->index] != SD_BUS_TYPE_STRUCT_BEGIN ||
2754             !startswith(c->signature + c->index + 1, contents) ||
2755             c->signature[c->index + 1 + l] != SD_BUS_TYPE_STRUCT_END)
2756                 return -ENXIO;
2757
2758         r = message_peek_body(m, &m->rindex, 8, 0, NULL);
2759         if (r <= 0)
2760                 return r;
2761
2762         if (c->enclosing != SD_BUS_TYPE_ARRAY)
2763                 c->index += 1 + l + 1;
2764
2765         return 1;
2766 }
2767
2768 static int bus_message_enter_dict_entry(
2769                 sd_bus_message *m,
2770                 struct bus_container *c,
2771                 const char *contents) {
2772
2773         size_t l;
2774         int r;
2775
2776         assert(m);
2777         assert(c);
2778         assert(contents);
2779
2780         if (!signature_is_pair(contents))
2781                 return -EINVAL;
2782
2783         if (c->enclosing != SD_BUS_TYPE_ARRAY)
2784                 return -ENXIO;
2785
2786         if (!c->signature || c->signature[c->index] == 0)
2787                 return 0;
2788
2789         l = strlen(contents);
2790
2791         if (c->signature[c->index] != SD_BUS_TYPE_DICT_ENTRY_BEGIN ||
2792             !startswith(c->signature + c->index + 1, contents) ||
2793             c->signature[c->index + 1 + l] != SD_BUS_TYPE_DICT_ENTRY_END)
2794                 return -ENXIO;
2795
2796         r = message_peek_body(m, &m->rindex, 8, 0, NULL);
2797         if (r <= 0)
2798                 return r;
2799
2800         if (c->enclosing != SD_BUS_TYPE_ARRAY)
2801                 c->index += 1 + l + 1;
2802
2803         return 1;
2804 }
2805
2806 _public_ int sd_bus_message_enter_container(sd_bus_message *m,
2807                                             char type,
2808                                             const char *contents) {
2809         struct bus_container *c, *w;
2810         uint32_t *array_size = NULL;
2811         char *signature;
2812         size_t before;
2813         int r;
2814
2815         assert_return(m, -EINVAL);
2816         assert_return(m->sealed, -EPERM);
2817         assert_return(type != 0 || !contents, -EINVAL);
2818
2819         if (type == 0 || !contents) {
2820                 const char *cc;
2821                 char tt;
2822
2823                 /* Allow entering into anonymous containers */
2824                 r = sd_bus_message_peek_type(m, &tt, &cc);
2825                 if (r <= 0)
2826                         return r;
2827
2828                 if (type != 0 && type != tt)
2829                         return -ENXIO;
2830
2831                 if (contents && !streq(contents, cc))
2832                         return -ENXIO;
2833
2834                 type = tt;
2835                 contents = cc;
2836         }
2837
2838         /*
2839          * We enforce a global limit on container depth, that is much
2840          * higher than the 32 structs and 32 arrays the specification
2841          * mandates. This is simpler to implement for us, and we need
2842          * this only to ensure our container array doesn't grow
2843          * without bounds. We are happy to return any data from a
2844          * message as long as the data itself is valid, even if the
2845          * overall message might be not.
2846          *
2847          * Note that the message signature is validated when
2848          * parsing the headers, and that validation does check the
2849          * 32/32 limit.
2850          *
2851          * Note that the specification defines no limits on the depth
2852          * of stacked variants, but we do.
2853          */
2854         if (m->n_containers >= BUS_CONTAINER_DEPTH)
2855                 return -EBADMSG;
2856
2857         w = realloc(m->containers, sizeof(struct bus_container) * (m->n_containers + 1));
2858         if (!w)
2859                 return -ENOMEM;
2860         m->containers = w;
2861
2862         if (message_end_of_signature(m))
2863                 return -ENXIO;
2864
2865         if (message_end_of_array(m, m->rindex))
2866                 return 0;
2867
2868         c = message_get_container(m);
2869
2870         signature = strdup(contents);
2871         if (!signature)
2872                 return -ENOMEM;
2873
2874         c->saved_index = c->index;
2875         before = m->rindex;
2876
2877         if (type == SD_BUS_TYPE_ARRAY)
2878                 r = bus_message_enter_array(m, c, contents, &array_size);
2879         else if (type == SD_BUS_TYPE_VARIANT)
2880                 r = bus_message_enter_variant(m, c, contents);
2881         else if (type == SD_BUS_TYPE_STRUCT)
2882                 r = bus_message_enter_struct(m, c, contents);
2883         else if (type == SD_BUS_TYPE_DICT_ENTRY)
2884                 r = bus_message_enter_dict_entry(m, c, contents);
2885         else
2886                 r = -EINVAL;
2887
2888         if (r <= 0) {
2889                 free(signature);
2890                 return r;
2891         }
2892
2893         /* OK, let's fill it in */
2894         w += m->n_containers++;
2895         w->enclosing = type;
2896         w->signature = signature;
2897         w->index = 0;
2898         w->array_size = array_size;
2899         w->before = before;
2900         w->begin = m->rindex;
2901
2902         return 1;
2903 }
2904
2905 _public_ int sd_bus_message_exit_container(sd_bus_message *m) {
2906         struct bus_container *c;
2907
2908         assert_return(m, -EINVAL);
2909         assert_return(m->sealed, -EPERM);
2910         assert_return(m->n_containers > 0, -ENXIO);
2911
2912         c = message_get_container(m);
2913         if (c->enclosing == SD_BUS_TYPE_ARRAY) {
2914                 uint32_t l;
2915
2916                 l = BUS_MESSAGE_BSWAP32(m, *c->array_size);
2917                 if (c->begin + l != m->rindex)
2918                         return -EBUSY;
2919
2920         } else {
2921                 if (c->signature && c->signature[c->index] != 0)
2922                         return -EBUSY;
2923         }
2924
2925         free(c->signature);
2926         m->n_containers--;
2927
2928         return 1;
2929 }
2930
2931 static void message_quit_container(sd_bus_message *m) {
2932         struct bus_container *c;
2933
2934         assert(m);
2935         assert(m->sealed);
2936         assert(m->n_containers > 0);
2937
2938         c = message_get_container(m);
2939
2940         /* Undo seeks */
2941         assert(m->rindex >= c->before);
2942         m->rindex = c->before;
2943
2944         /* Free container */
2945         free(c->signature);
2946         m->n_containers--;
2947
2948         /* Correct index of new top-level container */
2949         c = message_get_container(m);
2950         c->index = c->saved_index;
2951 }
2952
2953 _public_ int sd_bus_message_peek_type(sd_bus_message *m, char *type, const char **contents) {
2954         struct bus_container *c;
2955         int r;
2956
2957         assert_return(m, -EINVAL);
2958         assert_return(m->sealed, -EPERM);
2959
2960         if (message_end_of_signature(m))
2961                 goto eof;
2962
2963         if (message_end_of_array(m, m->rindex))
2964                 goto eof;
2965
2966         c = message_get_container(m);
2967
2968         if (bus_type_is_basic(c->signature[c->index])) {
2969                 if (contents)
2970                         *contents = NULL;
2971                 if (type)
2972                         *type = c->signature[c->index];
2973                 return 1;
2974         }
2975
2976         if (c->signature[c->index] == SD_BUS_TYPE_ARRAY) {
2977
2978                 if (contents) {
2979                         size_t l;
2980                         char *sig;
2981
2982                         r = signature_element_length(c->signature+c->index+1, &l);
2983                         if (r < 0)
2984                                 return r;
2985
2986                         assert(l >= 1);
2987
2988                         sig = strndup(c->signature + c->index + 1, l);
2989                         if (!sig)
2990                                 return -ENOMEM;
2991
2992                         free(m->peeked_signature);
2993                         m->peeked_signature = sig;
2994
2995                         *contents = sig;
2996                 }
2997
2998                 if (type)
2999                         *type = SD_BUS_TYPE_ARRAY;
3000
3001                 return 1;
3002         }
3003
3004         if (c->signature[c->index] == SD_BUS_TYPE_STRUCT_BEGIN ||
3005             c->signature[c->index] == SD_BUS_TYPE_DICT_ENTRY_BEGIN) {
3006
3007                 if (contents) {
3008                         size_t l;
3009                         char *sig;
3010
3011                         r = signature_element_length(c->signature+c->index, &l);
3012                         if (r < 0)
3013                                 return r;
3014
3015                         assert(l >= 2);
3016                         sig = strndup(c->signature + c->index + 1, l - 2);
3017                         if (!sig)
3018                                 return -ENOMEM;
3019
3020                         free(m->peeked_signature);
3021                         m->peeked_signature = sig;
3022
3023                         *contents = sig;
3024                 }
3025
3026                 if (type)
3027                         *type = c->signature[c->index] == SD_BUS_TYPE_STRUCT_BEGIN ? SD_BUS_TYPE_STRUCT : SD_BUS_TYPE_DICT_ENTRY;
3028
3029                 return 1;
3030         }
3031
3032         if (c->signature[c->index] == SD_BUS_TYPE_VARIANT) {
3033                 if (contents) {
3034                         size_t rindex, l;
3035                         void *q;
3036
3037                         rindex = m->rindex;
3038                         r = message_peek_body(m, &rindex, 1, 1, &q);
3039                         if (r < 0)
3040                                 return r;
3041                         if (r == 0)
3042                                 goto eof;
3043
3044                         l = *(uint8_t*) q;
3045                         r = message_peek_body(m, &rindex, 1, l+1, &q);
3046                         if (r < 0)
3047                                 return r;
3048                         if (r == 0)
3049                                 return -EBADMSG;
3050
3051                         if (!validate_signature(q, l))
3052                                 return -EBADMSG;
3053
3054                         *contents = q;
3055                 }
3056
3057                 if (type)
3058                         *type = SD_BUS_TYPE_VARIANT;
3059
3060                 return 1;
3061         }
3062
3063         return -EINVAL;
3064
3065 eof:
3066         if (type)
3067                 *type = 0;
3068         if (contents)
3069                 *contents = NULL;
3070         return 0;
3071 }
3072
3073 _public_ int sd_bus_message_rewind(sd_bus_message *m, int complete) {
3074         struct bus_container *c;
3075
3076         assert_return(m, -EINVAL);
3077         assert_return(m->sealed, -EPERM);
3078
3079         if (complete) {
3080                 message_reset_containers(m);
3081                 m->rindex = 0;
3082                 m->root_container.index = 0;
3083
3084                 c = message_get_container(m);
3085         } else {
3086                 c = message_get_container(m);
3087
3088                 c->index = 0;
3089                 m->rindex = c->begin;
3090         }
3091
3092         return !isempty(c->signature);
3093 }
3094
3095 static int message_read_ap(
3096                 sd_bus_message *m,
3097                 const char *types,
3098                 va_list ap) {
3099
3100         unsigned n_array, n_struct;
3101         TypeStack stack[BUS_CONTAINER_DEPTH];
3102         unsigned stack_ptr = 0;
3103         unsigned n_loop = 0;
3104         int r;
3105
3106         assert(m);
3107
3108         if (isempty(types))
3109                 return 0;
3110
3111         /* Ideally, we'd just call ourselves recursively on every
3112          * complex type. However, the state of a va_list that is
3113          * passed to a function is undefined after that function
3114          * returns. This means we need to docode the va_list linearly
3115          * in a single stackframe. We hence implement our own
3116          * home-grown stack in an array. */
3117
3118         n_array = (unsigned) -1; /* lenght of current array entries */
3119         n_struct = strlen(types); /* length of current struct contents signature */
3120
3121         for (;;) {
3122                 const char *t;
3123
3124                 n_loop++;
3125
3126                 if (n_array == 0 || (n_array == (unsigned) -1 && n_struct == 0)) {
3127                         r = type_stack_pop(stack, ELEMENTSOF(stack), &stack_ptr, &types, &n_struct, &n_array);
3128                         if (r < 0)
3129                                 return r;
3130                         if (r == 0)
3131                                 break;
3132
3133                         r = sd_bus_message_exit_container(m);
3134                         if (r < 0)
3135                                 return r;
3136
3137                         continue;
3138                 }
3139
3140                 t = types;
3141                 if (n_array != (unsigned) -1)
3142                         n_array --;
3143                 else {
3144                         types ++;
3145                         n_struct--;
3146                 }
3147
3148                 switch (*t) {
3149
3150                 case SD_BUS_TYPE_BYTE:
3151                 case SD_BUS_TYPE_BOOLEAN:
3152                 case SD_BUS_TYPE_INT16:
3153                 case SD_BUS_TYPE_UINT16:
3154                 case SD_BUS_TYPE_INT32:
3155                 case SD_BUS_TYPE_UINT32:
3156                 case SD_BUS_TYPE_INT64:
3157                 case SD_BUS_TYPE_UINT64:
3158                 case SD_BUS_TYPE_DOUBLE:
3159                 case SD_BUS_TYPE_STRING:
3160                 case SD_BUS_TYPE_OBJECT_PATH:
3161                 case SD_BUS_TYPE_SIGNATURE:
3162                 case SD_BUS_TYPE_UNIX_FD: {
3163                         void *p;
3164
3165                         p = va_arg(ap, void*);
3166                         r = sd_bus_message_read_basic(m, *t, p);
3167                         if (r < 0)
3168                                 return r;
3169                         if (r == 0) {
3170                                 if (n_loop <= 1)
3171                                         return 0;
3172
3173                                 return -ENXIO;
3174                         }
3175
3176                         break;
3177                 }
3178
3179                 case SD_BUS_TYPE_ARRAY: {
3180                         size_t k;
3181
3182                         r = signature_element_length(t + 1, &k);
3183                         if (r < 0)
3184                                 return r;
3185
3186                         {
3187                                 char s[k + 1];
3188                                 memcpy(s, t + 1, k);
3189                                 s[k] = 0;
3190
3191                                 r = sd_bus_message_enter_container(m, SD_BUS_TYPE_ARRAY, s);
3192                                 if (r < 0)
3193                                         return r;
3194                                 if (r == 0) {
3195                                         if (n_loop <= 1)
3196                                                 return 0;
3197
3198                                         return -ENXIO;
3199                                 }
3200                         }
3201
3202                         if (n_array == (unsigned) -1) {
3203                                 types += k;
3204                                 n_struct -= k;
3205                         }
3206
3207                         r = type_stack_push(stack, ELEMENTSOF(stack), &stack_ptr, types, n_struct, n_array);
3208                         if (r < 0)
3209                                 return r;
3210
3211                         types = t + 1;
3212                         n_struct = k;
3213                         n_array = va_arg(ap, unsigned);
3214
3215                         break;
3216                 }
3217
3218                 case SD_BUS_TYPE_VARIANT: {
3219                         const char *s;
3220
3221                         s = va_arg(ap, const char *);
3222                         if (!s)
3223                                 return -EINVAL;
3224
3225                         r = sd_bus_message_enter_container(m, SD_BUS_TYPE_VARIANT, s);
3226                         if (r < 0)
3227                                 return r;
3228                         if (r == 0) {
3229                                 if (n_loop <= 1)
3230                                         return 0;
3231
3232                                 return -ENXIO;
3233                         }
3234
3235                         r = type_stack_push(stack, ELEMENTSOF(stack), &stack_ptr, types, n_struct, n_array);
3236                         if (r < 0)
3237                                 return r;
3238
3239                         types = s;
3240                         n_struct = strlen(s);
3241                         n_array = (unsigned) -1;
3242
3243                         break;
3244                 }
3245
3246                 case SD_BUS_TYPE_STRUCT_BEGIN:
3247                 case SD_BUS_TYPE_DICT_ENTRY_BEGIN: {
3248                         size_t k;
3249
3250                         r = signature_element_length(t, &k);
3251                         if (r < 0)
3252                                 return r;
3253
3254                         {
3255