1 /*
2 * Copyright (c) 1991, 1992 Paul Kranenburg <pk@cs.few.eur.nl>
3 * Copyright (c) 1993 Branko Lankester <branko@hacktic.nl>
4 * Copyright (c) 1993, 1994, 1995, 1996 Rick Sladkey <jrs@world.std.com>
5 * Copyright (c) 1996-1999 Wichert Akkerman <wichert@cistron.nl>
6 * Copyright (c) 1999 IBM Deutschland Entwicklung GmbH, IBM Corporation
7 * Linux for s390 port by D.J. Barrow
8 * <barrow_dj@mail.yahoo.com,djbarrow@de.ibm.com>
9 * Copyright (c) 1999-2023 The strace developers.
10 * All rights reserved.
11 *
12 * SPDX-License-Identifier: LGPL-2.1-or-later
13 */
14
15 #include "defs.h"
16 #include <limits.h>
17 #include <fcntl.h>
18 #include <stdarg.h>
19 #include <sys/stat.h>
20 #include <sys/sysmacros.h>
21 #ifdef HAVE_SYS_XATTR_H
22 # include <sys/xattr.h>
23 #endif
24 #include <sys/uio.h>
25
26 #include "largefile_wrappers.h"
27 #include "number_set.h"
28 #include "print_fields.h"
29 #include "print_utils.h"
30 #include "secontext.h"
31 #include "static_assert.h"
32 #include "string_to_uint.h"
33 #include "xlat.h"
34 #include "xstring.h"
35
36 const struct xlat_data *
37 find_xlat_val_ex(const struct xlat_data * const items, const char * const s,
38 const size_t num_items, const unsigned int flags)
39 {
40 for (size_t i = 0; i < num_items; i++) {
41 if (!(flags & FXL_CASE_SENSITIVE ? strcmp
42 : strcasecmp)(items[i].str, s))
43 return items + i;
44 }
45
46 return NULL;
47 }
48
49 uint64_t
50 find_arg_val_(const char *arg, const struct xlat_data *strs, size_t strs_size,
51 uint64_t default_val, uint64_t not_found)
52 {
53 if (!arg)
54 return default_val;
55
56 const struct xlat_data *res = find_xlat_val_ex(strs, arg, strs_size, 0);
57
58 return res ? res->val : not_found;
59 }
60
61 int
62 str2timescale_ex(const char *arg, int empty_dflt, int null_dflt,
63 int *width)
64 {
65 static const struct xlat_data units[] = {
66 { 1000000000U | (0ULL << 32), "s" },
67 { 1000000U | (3ULL << 32), "ms" },
68 { 1000U | (6ULL << 32), "us" },
69 { 1U | (9ULL << 32), "ns" },
70 };
71
72 if (!arg)
73 return null_dflt;
74 if (!arg[0])
75 return empty_dflt;
76
77 uint64_t res = find_arg_val(arg, units, null_dflt, -1ULL);
78
79 if (width && res != -1ULL)
80 *width = res >> 32;
81
82 return res & 0xffffffff;
83 }
84
85 int
86 ts_nz(const struct timespec *a)
87 {
88 return a->tv_sec || a->tv_nsec;
89 }
90
91 int
92 ts_cmp(const struct timespec *a, const struct timespec *b)
93 {
94 if (a->tv_sec < b->tv_sec
95 || (a->tv_sec == b->tv_sec && a->tv_nsec < b->tv_nsec))
96 return -1;
97 if (a->tv_sec > b->tv_sec
98 || (a->tv_sec == b->tv_sec && a->tv_nsec > b->tv_nsec))
99 return 1;
100 return 0;
101 }
102
103 double
104 ts_float(const struct timespec *tv)
105 {
106 return tv->tv_sec + tv->tv_nsec/1000000000.0;
107 }
108
109 void
110 ts_add(struct timespec *tv, const struct timespec *a, const struct timespec *b)
111 {
112 tv->tv_sec = a->tv_sec + b->tv_sec;
113 tv->tv_nsec = a->tv_nsec + b->tv_nsec;
114 if (tv->tv_nsec >= 1000000000) {
115 tv->tv_sec++;
116 tv->tv_nsec -= 1000000000;
117 }
118 }
119
120 void
121 ts_sub(struct timespec *tv, const struct timespec *a, const struct timespec *b)
122 {
123 tv->tv_sec = a->tv_sec - b->tv_sec;
124 tv->tv_nsec = a->tv_nsec - b->tv_nsec;
125 if (tv->tv_nsec < 0) {
126 tv->tv_sec--;
127 tv->tv_nsec += 1000000000;
128 }
129 }
130
131 void
132 ts_div(struct timespec *tv, const struct timespec *a, uint64_t n)
133 {
134 long long nsec = (a->tv_sec % n * 1000000000LL + a->tv_nsec + n / 2) / n;
135 tv->tv_sec = a->tv_sec / n + nsec / 1000000000;
136 tv->tv_nsec = nsec % 1000000000;
137 }
138
139 const struct timespec *
140 ts_min(const struct timespec *a, const struct timespec *b)
141 {
142 return ts_cmp(a, b) < 0 ? a : b;
143 }
144
145 const struct timespec *
146 ts_max(const struct timespec *a, const struct timespec *b)
147 {
148 return ts_cmp(a, b) > 0 ? a : b;
149 }
150
151 int
152 parse_ts(const char *s, struct timespec *t)
153 {
154 enum { NS_IN_S = 1000000000 };
155
156 static const char float_accept[] = "eE.-+0123456789";
157 static const char int_accept[] = "+0123456789";
158
159 size_t float_len = strspn(s, float_accept);
160 size_t int_len = strspn(s, int_accept);
161 char *endptr = NULL;
162 double float_val = -1;
163 long long int_val = -1;
164
165 if (float_len > int_len) {
166 errno = 0;
167
168 float_val = strtod(s, &endptr);
169
170 if (endptr == s || errno)
171 return -1;
172 if (float_val < 0)
173 return -1;
174 } else {
175 int_val = string_to_uint_ex(s, &endptr, LLONG_MAX, "smun");
176
177 if (int_val < 0)
178 return -1;
179 }
180
181 int scale = str2timescale_sfx(endptr, NULL);
182 if (scale <= 0)
183 return -1;
184
185 if (float_len > int_len) {
186 t->tv_sec = float_val / (NS_IN_S / scale);
187 t->tv_nsec = ((uint64_t) ((float_val -
188 (t->tv_sec * (NS_IN_S / scale)))
189 * scale)) % NS_IN_S;
190 } else {
191 t->tv_sec = int_val / (NS_IN_S / scale);
192 t->tv_nsec = (int_val % (NS_IN_S / scale)) * scale;
193 }
194
195 return 0;
196 }
197
198 #define ILOG10_ITER_(val_, div_, ret_, pow_) \
199 do { \
200 if ((val_) >= (div_)) { \
201 (val_) /= (div_); \
202 (ret_) += (pow_); \
203 } \
204 } while (0) \
205 /* End of ILOG10_ITER_ */
206
207 /* Returns 0 for 0. */
208 static int
209 ilog10(uint64_t val)
210 {
211 int ret = 0;
212
213 ILOG10_ITER_(val, 10000000000000000ULL, ret, 16);
214 ILOG10_ITER_(val, 100000000, ret, 8);
215 ILOG10_ITER_(val, 10000, ret, 4);
216 ILOG10_ITER_(val, 100, ret, 2);
217 ILOG10_ITER_(val, 10, ret, 1);
218
219 return ret;
220 }
221
222 void
223 print_ticks(uint64_t val, long freq, unsigned int precision)
224 {
225 PRINT_VAL_U(val);
226 if (xlat_verbose(xlat_verbosity) != XLAT_STYLE_RAW
227 && freq > 0 && val > 0) {
228 tprintf_comment("%" PRIu64 ".%0*" PRIu64 " s",
229 val / freq, precision, val % freq);
230 }
231 }
232
233 void
234 print_ticks_d(int64_t val, long freq, unsigned int precision)
235 {
236 PRINT_VAL_D(val);
237 /* freq > 1 to avoid special casing for val == */
238 if (xlat_verbose(xlat_verbosity) != XLAT_STYLE_RAW
239 && freq > 1 && val != 0) {
240 tprintf_comment("%s%lld.%0*lld s",
241 val < 0 ? "-" : "", llabs(val / freq),
242 precision, llabs(val % freq));
243 }
244 }
245
246 void
247 print_clock_t(uint64_t val)
248 {
249 static long clk_tck;
250 static int frac_width;
251
252 if (!clk_tck) {
253 errno = 0;
254 clk_tck = sysconf(_SC_CLK_TCK);
255 if (clk_tck == -1 && errno)
256 debug_func_perror_msg("sysconf(_SC_CLK_TCK)");
257 if (clk_tck == 0)
258 clk_tck = -1;
259 if (clk_tck > 0)
260 frac_width = MIN(ilog10(clk_tck), 9);
261 }
262
263 print_ticks(val, clk_tck, frac_width);
264 }
265
266 #if !defined HAVE_STPCPY
267 char *
268 stpcpy(char *dst, const char *src)
269 {
270 while ((*dst = *src++) != '\0')
271 dst++;
272 return dst;
273 }
274 #endif
275
276 /* Find a next bit which is set.
277 * Starts testing at cur_bit.
278 * Returns -1 if no more bits are set.
279 *
280 * We never touch bytes we don't need to.
281 * On big-endian, array is assumed to consist of
282 * current_wordsize wide words: for example, is current_wordsize is 4,
283 * the bytes are walked in 3,2,1,0, 7,6,5,4, 11,10,9,8 ... sequence.
284 * On little-endian machines, word size is immaterial.
285 */
286 int
287 next_set_bit(const void *bit_array, unsigned cur_bit, unsigned size_bits)
288 {
289 const unsigned endian = 1;
290 int little_endian = *(char *) (void *) &endian;
291
292 const uint8_t *array = bit_array;
293 unsigned pos = cur_bit / 8;
294 unsigned pos_xor_mask = little_endian ? 0 : current_wordsize-1;
295
296 for (;;) {
297 uint8_t bitmask;
298 uint8_t cur_byte;
299
300 if (cur_bit >= size_bits)
301 return -1;
302 cur_byte = array[pos ^ pos_xor_mask];
303 if (cur_byte == 0) {
304 cur_bit = (cur_bit + 8) & (-8);
305 pos++;
306 continue;
307 }
308 bitmask = 1 << (cur_bit & 7);
309 for (;;) {
310 if (cur_byte & bitmask)
311 return cur_bit;
312 cur_bit++;
313 if (cur_bit >= size_bits)
314 return -1;
315 bitmask <<= 1;
316 /* This check *can't be* optimized out: */
317 if (bitmask == 0)
318 break;
319 }
320 pos++;
321 }
322 }
323
324 /*
325 * Fetch 64bit argument at position arg_no and
326 * return the index of the next argument.
327 */
328 unsigned int
329 getllval(struct tcb *tcp, unsigned long long *val, unsigned int arg_no)
330 {
331 #if SIZEOF_KERNEL_LONG_T > 4
332 # ifndef current_klongsize
333 if (current_klongsize < SIZEOF_KERNEL_LONG_T) {
334 # if defined(AARCH64) || defined(POWERPC64) || defined(POWERPC64LE)
335 /* Align arg_no to the next even number. */
336 arg_no = (arg_no + 1) & 0xe;
337 # endif /* AARCH64 || POWERPC64 || POWERPC64LE */
338 *val = ULONG_LONG(tcp->u_arg[arg_no], tcp->u_arg[arg_no + 1]);
339 arg_no += 2;
340 } else
341 # endif /* !current_klongsize */
342 {
343 *val = tcp->u_arg[arg_no];
344 arg_no++;
345 }
346 #else /* SIZEOF_KERNEL_LONG_T == 4 */
347 # if defined __ARM_EABI__ \
348 || defined LINUX_MIPSO32 \
349 || defined POWERPC \
350 || defined XTENSA
351 /* Align arg_no to the next even number. */
352 arg_no = (arg_no + 1) & 0xe;
353 # elif defined SH
354 /*
355 * The SH4 ABI does allow long longs in odd-numbered registers, but
356 * does not allow them to be split between registers and memory - and
357 * there are only four argument registers for normal functions. As a
358 * result, pread, for example, takes an extra padding argument before
359 * the offset. This was changed late in the 2.4 series (around 2.4.20).
360 */
361 if (arg_no == 3)
362 arg_no++;
363 # endif /* __ARM_EABI__ || LINUX_MIPSO32 || POWERPC || XTENSA || SH */
364 *val = ULONG_LONG(tcp->u_arg[arg_no], tcp->u_arg[arg_no + 1]);
365 arg_no += 2;
366 #endif
367
368 return arg_no;
369 }
370
371 /*
372 * Print 64bit argument at position arg_no as a signed long long
373 * and return the index of the next argument.
374 */
375 unsigned int
376 print_arg_lld(struct tcb *tcp, unsigned int arg_no)
377 {
378 unsigned long long val = 0;
379
380 arg_no = getllval(tcp, &val, arg_no);
381 PRINT_VAL_D(val);
382 return arg_no;
383 }
384
385 /*
386 * Print 64bit argument at position arg_no as an unsigned long long
387 * and return the index of the next argument.
388 */
389 unsigned int
390 print_arg_llu(struct tcb *tcp, unsigned int arg_no)
391 {
392 unsigned long long val = 0;
393
394 arg_no = getllval(tcp, &val, arg_no);
395 PRINT_VAL_U(val);
396 return arg_no;
397 }
398
399 void
400 printaddr64(const uint64_t addr)
401 {
402 if (!addr)
403 tprint_null();
404 else
405 PRINT_VAL_X(addr);
406 }
407
408 #define DEF_PRINTNUM(name, type) \
409 bool \
410 printnum_ ## name(struct tcb *const tcp, const kernel_ulong_t addr, \
411 const char *const fmt) \
412 { \
413 type num; \
414 if (umove_or_printaddr(tcp, addr, &num)) \
415 return false; \
416 tprint_indirect_begin(); \
417 tprintf_string(fmt, num); \
418 tprint_indirect_end(); \
419 return true; \
420 }
421
422 #define DEF_PRINTNUM_ADDR(name, type) \
423 bool \
424 printnum_addr_ ## name(struct tcb *tcp, const kernel_ulong_t addr) \
425 { \
426 type num; \
427 if (umove_or_printaddr(tcp, addr, &num)) \
428 return false; \
429 tprint_indirect_begin(); \
430 printaddr64(num); \
431 tprint_indirect_end(); \
432 return true; \
433 }
434
435 #define DEF_PRINTPAIR(name, type) \
436 bool \
437 printpair_ ## name(struct tcb *const tcp, const kernel_ulong_t addr, \
438 const char *const fmt) \
439 { \
440 type pair[2]; \
441 if (umove_or_printaddr(tcp, addr, &pair)) \
442 return false; \
443 tprint_array_begin(); \
444 tprintf_string(fmt, pair[0]); \
445 tprint_array_next(); \
446 tprintf_string(fmt, pair[1]); \
447 tprint_array_end(); \
448 return true; \
449 }
450
451 DEF_PRINTNUM(int, int)
452 DEF_PRINTNUM_ADDR(int, unsigned int)
453 DEF_PRINTPAIR(int, int)
454 DEF_PRINTNUM(short, short)
455 DEF_PRINTNUM(int64, uint64_t)
456 DEF_PRINTNUM_ADDR(int64, uint64_t)
457 DEF_PRINTPAIR(int64, uint64_t)
458
459 bool
460 printnum_fd(struct tcb *const tcp, const kernel_ulong_t addr)
461 {
462 int fd;
463 if (umove_or_printaddr(tcp, addr, &fd))
464 return false;
465 tprint_indirect_begin();
466 printfd(tcp, fd);
467 tprint_indirect_end();
468 return true;
469 }
470
471 bool
472 printnum_pid(struct tcb *const tcp, const kernel_ulong_t addr, enum pid_type type)
473 {
474 int pid;
475 if (umove_or_printaddr(tcp, addr, &pid))
476 return false;
477 tprint_indirect_begin();
478 printpid(tcp, pid, type);
479 tprint_indirect_end();
480 return true;
481 }
482
483 /**
484 * Prints time to a (static internal) buffer and returns pointer to it.
485 * Returns NULL if the provided time specification is not correct.
486 *
487 * @param sec Seconds since epoch.
488 * @param part_sec Amount of second parts since the start of a second.
489 * @param max_part_sec Maximum value of a valid part_sec.
490 * @param width 1 + floor(log10(max_part_sec)).
491 * @return Pointer to a statically allocated string on success,
492 * NULL on error.
493 */
494 static const char *
495 sprinttime_ex(const long long sec, const unsigned long long part_sec,
496 const unsigned int max_part_sec, const int width)
497 {
498 static char buf[sizeof(int) * 3 * 6 + sizeof(part_sec) * 3
499 + sizeof("+0000")];
500
501 if ((sec == 0 && part_sec == 0) || part_sec > max_part_sec)
502 return NULL;
503
504 time_t t = (time_t) sec;
505 struct tm *tmp = (sec == t) ? localtime(&t) : NULL;
506 if (!tmp)
507 return NULL;
508
509 size_t pos = strftime(buf, sizeof(buf), "%FT%T", tmp);
510 if (!pos)
511 return NULL;
512
513 if (part_sec > 0)
514 pos += xsnprintf(buf + pos, sizeof(buf) - pos, ".%0*llu",
515 width, part_sec);
516
517 return strftime(buf + pos, sizeof(buf) - pos, "%z", tmp) ? buf : NULL;
518 }
519
520 const char *
521 sprinttime(long long sec)
522 {
523 return sprinttime_ex(sec, 0, 0, 0);
524 }
525
526 const char *
527 sprinttime_usec(long long sec, unsigned long long usec)
528 {
529 return sprinttime_ex(sec, usec, 999999, 6);
530 }
531
532 const char *
533 sprinttime_nsec(long long sec, unsigned long long nsec)
534 {
535 return sprinttime_ex(sec, nsec, 999999999, 9);
536 }
537
538 void
539 print_uuid(const unsigned char *uuid)
540 {
541 const char str[] = {
542 BYTE_HEX_CHARS(uuid[0]),
543 BYTE_HEX_CHARS(uuid[1]),
544 BYTE_HEX_CHARS(uuid[2]),
545 BYTE_HEX_CHARS(uuid[3]),
546 '-',
547 BYTE_HEX_CHARS(uuid[4]),
548 BYTE_HEX_CHARS(uuid[5]),
549 '-',
550 BYTE_HEX_CHARS(uuid[6]),
551 BYTE_HEX_CHARS(uuid[7]),
552 '-',
553 BYTE_HEX_CHARS(uuid[8]),
554 BYTE_HEX_CHARS(uuid[9]),
555 '-',
556 BYTE_HEX_CHARS(uuid[10]),
557 BYTE_HEX_CHARS(uuid[11]),
558 BYTE_HEX_CHARS(uuid[12]),
559 BYTE_HEX_CHARS(uuid[13]),
560 BYTE_HEX_CHARS(uuid[14]),
561 BYTE_HEX_CHARS(uuid[15]),
562 '\0'
563 };
564
565 tprints_string(str);
566 }
567
568 enum sock_proto
569 getfdproto(struct tcb *tcp, int fd)
570 {
571 #ifdef HAVE_SYS_XATTR_H
572 size_t bufsize = 256;
573 char buf[bufsize];
574 ssize_t r;
575 char path[sizeof("/proc/%u/fd/%u") + 2 * sizeof(int)*3];
576
577 if (fd < 0)
578 return SOCK_PROTO_UNKNOWN;
579
580 xsprintf(path, "/proc/%u/fd/%u", get_proc_pid(tcp->pid), fd);
581 r = getxattr(path, "system.sockprotoname", buf, bufsize - 1);
582 if (r <= 0)
583 return SOCK_PROTO_UNKNOWN;
584 else {
585 /*
586 * This is a protection for the case when the kernel
587 * side does not append a null byte to the buffer.
588 */
589 buf[r] = '\0';
590
591 return get_proto_by_name(buf);
592 }
593 #else
594 return SOCK_PROTO_UNKNOWN;
595 #endif
596 }
597
598 static unsigned long
599 get_inode_of_socket_path(const char *path)
600 {
601 const char *str = STR_STRIP_PREFIX(path, "socket:[");
602 char *end;
603 size_t len;
604 unsigned long r;
605
606 if ((str != path)
607 && (len = strlen(str))
608 && (str[len - 1] == ']')
609 && (r = strtoul(str, &end, 10))
610 && (end == &str[len - 1]))
611 return r;
612
613 return 0;
614 }
615
616 unsigned long
617 getfdinode(struct tcb *tcp, int fd)
618 {
619 char path[PATH_MAX + 1];
620
621 if (getfdpath(tcp, fd, path, sizeof(path)) >= 0)
622 return get_inode_of_socket_path(path);
623
624 return 0;
625 }
626
627 static void
628 print_string_in_angle_brackets(const char *str)
629 {
630 tprint_associated_info_begin();
631 tprints_string(str);
632 tprint_associated_info_end();
633 }
634
635 static bool
636 printsocket(struct tcb *tcp, int fd, const char *path)
637 {
638 unsigned long inode = get_inode_of_socket_path(path);
639 if (!inode)
640 return false;
641
642 const char *details = get_sockaddr_by_inode(tcp, fd, inode);
643 print_string_in_angle_brackets(details ?: path);
644
645 return true;
646 }
647
648 struct finfo *
649 get_finfo_for_dev(const char *path, struct finfo *finfo)
650 {
651 strace_stat_t st;
652
653 finfo->path = path;
654 finfo->type = FINFO_UNSET;
655 finfo->deleted = false;
656
657 if (path[0] != '/')
658 return finfo;
659
660 if (stat_file(path, &st)) {
661 debug_func_perror_msg("stat(\"%s\")", path);
662 return finfo;
663 }
664
665 switch (st.st_mode & S_IFMT) {
666 case S_IFBLK:
667 finfo->type = FINFO_DEV_BLK;
668 break;
669 case S_IFCHR:
670 finfo->type = FINFO_DEV_CHR;
671 break;
672 default:
673 return finfo;
674 }
675
676 finfo->dev.major = major(st.st_rdev);
677 finfo->dev.minor = minor(st.st_rdev);
678
679 return finfo;
680 }
681
682 static bool
683 printdev(struct tcb *tcp, int fd, const char *path, const struct finfo *finfo)
684 {
685 struct finfo finfo_buf;
686 if (!finfo)
687 finfo = get_finfo_for_dev(path, &finfo_buf);
688
689 switch (finfo->type) {
690 case FINFO_DEV_BLK:
691 case FINFO_DEV_CHR:
692 tprint_associated_info_begin();
693 print_quoted_string_ex(finfo->path, strlen(finfo->path),
694 QUOTE_OMIT_LEADING_TRAILING_QUOTES,
695 "<>");
696 tprint_associated_info_begin();
697 tprintf_string("%s %u:%u",
698 (finfo->type == FINFO_DEV_BLK)? "block" : "char",
699 finfo->dev.major, finfo->dev.minor);
700 tprint_associated_info_end();
701 tprint_associated_info_end();
702 return true;
703 default:
704 break;
705 }
706
707 return false;
708 }
709
710 typedef bool (*scan_fdinfo_fn)(const char *value, void *data);
711
712 static bool
713 scan_fdinfo(pid_t pid_of_fd, int fd, const char *search_pfx,
714 size_t search_pfx_len, scan_fdinfo_fn fn, void *data)
715 {
716 int proc_pid = 0;
717 translate_pid(NULL, pid_of_fd, PT_TID, &proc_pid);
718 if (!proc_pid)
719 return false;
720
721 char fdi_path[sizeof("/proc/%u/fdinfo/%u") + 2 * sizeof(int) * 3];
722 xsprintf(fdi_path, "/proc/%u/fdinfo/%u", proc_pid, fd);
723
724 FILE *f = fopen_stream(fdi_path, "r");
725 if (!f)
726 return false;
727
728 char *line = NULL;
729 size_t sz = 0;
730 bool result = false;
731
732 while (getline(&line, &sz, f) > 0) {
733 const char *value =
734 str_strip_prefix_len(line, search_pfx, search_pfx_len);
735 if (value != line && fn(value, data)) {
736 result = true;
737 break;
738 }
739 }
740
741 free(line);
742 fclose(f);
743
744 return result;
745 }
746
747 static bool
748 parse_fdinfo_pid(const char *value, void *data)
749 {
750 pid_t *pid = data;
751 *pid = string_to_uint_ex(value, NULL, INT_MAX, "\n");
752 return true;
753 }
754
755 pid_t
756 pidfd_get_pid(pid_t pid_of_fd, int fd)
757 {
758 static const char pid_pfx[] = "Pid:\t";
759 pid_t pid = -1;
760
761 scan_fdinfo(pid_of_fd, fd, pid_pfx, sizeof(pid_pfx) - 1,
762 parse_fdinfo_pid, &pid);
763 return pid;
764 }
765
766 static bool
767 printpidfd(pid_t pid_of_fd, int fd, const char *path)
768 {
769 static const char pidfd_path[] = "anon_inode:[pidfd]";
770
771 if (strcmp(path, pidfd_path))
772 return false;
773
774 pid_t pid = pidfd_get_pid(pid_of_fd, fd);
775 if (pid > 0) {
776 tprint_associated_info_begin();
777 tprints_string("pid:");
778 /*
779 * The pid translation is not needed because
780 * the pid is in strace's namespace.
781 */
782 printpid(NULL, pid, PT_TID);
783 tprint_associated_info_end();
784 } else {
785 print_string_in_angle_brackets(path);
786 }
787
788 return true;
789 }
790
791 static bool
792 print_fdinfo_sigmask(const char *value, void *data)
793 {
794 #ifdef WORDS_BIGENDIAN
795 unsigned int pos_xor_mask = current_wordsize - 1;
796 #else
797 unsigned int pos_xor_mask = 0;
798 #endif
799 size_t sigset_size = strlen(value) / 2;
800 uint8_t *sigmask = xmalloc(sigset_size);
801
802 for (size_t i = 0; i < sigset_size; ++i) {
803 uint8_t byte;
804 if (sscanf(value + i * 2, "%02hhx", &byte) != 1) {
805 free(sigmask);
806 return false;
807 }
808 sigmask[(sigset_size - 1 - i) ^ pos_xor_mask] = byte;
809 }
810
811 tprint_associated_info_begin();
812 tprints_string(sprintsigmask_n("signalfd:", sigmask, sigset_size));
813 tprint_associated_info_end();
814
815 free(sigmask);
816 return true;
817 }
818
819 static bool
820 printsignalfd(pid_t pid_of_fd, int fd, const char *path)
821 {
822 static const char signalfd_path[] = "anon_inode:[signalfd]";
823 static const char sigmask_pfx[] = "sigmask:\t";
824
825 if (strcmp(path, signalfd_path))
826 return false;
827
828 return scan_fdinfo(pid_of_fd, fd, sigmask_pfx, sizeof(sigmask_pfx) - 1,
829 print_fdinfo_sigmask, NULL);
830 }
831
832 static void
833 print_quoted_string_in_angle_brackets(const char *str, const bool deleted)
834 {
835 tprint_associated_info_begin();
836 print_quoted_string_ex(str, strlen(str),
837 QUOTE_OMIT_LEADING_TRAILING_QUOTES, "<>");
838 tprint_associated_info_end();
839
840 if (deleted)
841 tprints_string("(deleted)");
842 }
843
844 void
845 printfd_pid_with_finfo(struct tcb *tcp, pid_t pid, int fd, const struct finfo *finfo)
846 {
847 PRINT_VAL_D(fd);
848
849 char patha[PATH_MAX + 1];
850 bool deleted;
851 if (pid > 0 && !number_set_array_is_empty(decode_fd_set, 0)
852 && (finfo || (getfdpath_pid(pid, fd, patha, sizeof(patha), &deleted) >= 0))) {
853 const char *path = finfo? finfo->path: patha;
854 if (is_number_in_set(DECODE_FD_SOCKET, decode_fd_set) &&
855 printsocket(tcp, fd, path))
856 goto printed;
857 if (is_number_in_set(DECODE_FD_DEV, decode_fd_set) &&
858 printdev(tcp, fd, path, finfo))
859 goto printed;
860 if (is_number_in_set(DECODE_FD_PIDFD, decode_fd_set) &&
861 printpidfd(pid, fd, path))
862 goto printed;
863 if (is_number_in_set(DECODE_FD_SIGNALFD, decode_fd_set) &&
864 printsignalfd(pid, fd, path))
865 goto printed;
866 if (is_number_in_set(DECODE_FD_PATH, decode_fd_set))
867 print_quoted_string_in_angle_brackets(path,
868 finfo? finfo->deleted: deleted);
869 printed: ;
870 }
871
872 selinux_printfdcon(pid, fd);
873 }
874
875 void
876 printfd_pid_tracee_ns(struct tcb *tcp, pid_t pid, int fd)
877 {
878 int strace_pid = translate_pid(tcp, pid, PT_TGID, NULL);
879 printfd_pid(tcp, strace_pid, fd);
880 }
881
882 const char *
883 pid_to_str(pid_t pid)
884 {
885 if (!pid)
886 return "self";
887
888 static char buf[sizeof("-2147483648")];
889 xsprintf(buf, "%d", pid);
890 return buf;
891 }
892
893 size_t
894 proc_status_get_id_list(int proc_pid, int *id_buf, size_t id_buf_size,
895 const char *str, size_t str_size)
896 {
897 size_t n = 0;
898
899 if (!str_size)
900 str_size = strlen(str);
901
902 char status_path[PATH_MAX + 1];
903 xsprintf(status_path, "/proc/%s/status", pid_to_str(proc_pid));
904 FILE *f = fopen_stream(status_path, "r");
905 if (!f)
906 return 0;
907
908 char *line = NULL;
909 size_t linesize = 0;
910 char *p = NULL;
911
912 while (getline(&line, &linesize, f) > 0) {
913 if (strncmp(line, str, str_size) == 0) {
914 p = line + str_size;
915 break;
916 }
917 }
918
919 while (p) {
920 errno = 0;
921 long id = strtol(p, NULL, 10);
922
923 if (id < 0 || id > INT_MAX || errno) {
924 debug_func_perror_msg("converting \"%s\" to int", p);
925 break;
926 }
927
928 if (id_buf && n < id_buf_size)
929 id_buf[n] = (int) id;
930
931 n++;
932 strsep(&p, "\t");
933 }
934
935 free(line);
936 fclose(f);
937
938 return n;
939 }
940
941 /*
942 * Quote string `instr' of length `size'
943 * Write up to (3 + `size' * 4) bytes to `outstr' buffer.
944 *
945 * `escape_chars' specifies characters (in addition to characters with
946 * codes 0..31, 127..255, single and double quotes) that should be escaped.
947 *
948 * If QUOTE_0_TERMINATED `style' flag is set,
949 * treat `instr' as a NUL-terminated string,
950 * checking up to (`size' + 1) bytes of `instr'.
951 *
952 * If QUOTE_OMIT_LEADING_TRAILING_QUOTES `style' flag is set,
953 * do not add leading and trailing quoting symbols.
954 *
955 * Returns 0 if QUOTE_0_TERMINATED is set and NUL was seen, 1 otherwise.
956 * Note that if QUOTE_0_TERMINATED is not set, always returns 1.
957 */
958 int
959 string_quote(const char *instr, char *outstr, const unsigned int size,
960 const unsigned int style, const char *escape_chars)
961 {
962 const unsigned char *ustr = (const unsigned char *) instr;
963 char *s = outstr;
964 unsigned int i;
965 int usehex, c, eol;
966 bool printable;
967 enum xflag_opts xstyle = style & QUOTE_OVERWRITE_HEXSTR
968 ? ((style & QUOTE_HEXSTR_MASK)
969 >> QUOTE_HEXSTR_SHIFT)
970 : xflag;
971
972 if (style & QUOTE_0_TERMINATED)
973 eol = '\0';
974 else
975 eol = 0x100; /* this can never match a char */
976
977 usehex = 0;
978 if (xstyle == HEXSTR_ALL) {
979 usehex = 1;
980 } else if (xstyle == HEXSTR_NON_ASCII) {
981 /* Check for presence of symbol which require
982 to hex-quote the whole string. */
983 for (i = 0; i < size; ++i) {
984 c = ustr[i];
985 /* Check for NUL-terminated string. */
986 if (c == eol)
987 break;
988
989 /* Force hex unless c is printable or whitespace */
990 if (c > 0x7e) {
991 usehex = 1;
992 break;
993 }
994 /* In ASCII isspace is only these chars: "\t\n\v\f\r".
995 * They happen to have ASCII codes 9,10,11,12,13.
996 */
997 if (c < ' ' && (unsigned)(c - 9) >= 5) {
998 usehex = 1;
999 break;
1000 }
1001 }
1002 }
1003
1004 if (style & QUOTE_EMIT_COMMENT)
1005 s = stpcpy(s, " /* ");
1006 if (!(style & QUOTE_OMIT_LEADING_TRAILING_QUOTES))
1007 *s++ = '\"';
1008
1009 if (usehex) {
1010 /* Hex-quote the whole string. */
1011 for (i = 0; i < size; ++i) {
1012 c = ustr[i];
1013 /* Check for NUL-terminated string. */
1014 if (c == eol)
1015 goto asciz_ended;
1016 *s++ = '\\';
1017 *s++ = 'x';
1018 s = sprint_byte_hex(s, c);
1019 }
1020
1021 goto string_ended;
1022 }
1023
1024 for (i = 0; i < size; ++i) {
1025 c = ustr[i];
1026 /* Check for NUL-terminated string. */
1027 if (c == eol)
1028 goto asciz_ended;
1029 if ((i == (size - 1)) &&
1030 (style & QUOTE_OMIT_TRAILING_0) && (c == '\0'))
1031 goto asciz_ended;
1032 switch (c) {
1033 case '\"': case '\\':
1034 *s++ = '\\';
1035 *s++ = c;
1036 break;
1037 case '\f':
1038 *s++ = '\\';
1039 *s++ = 'f';
1040 break;
1041 case '\n':
1042 *s++ = '\\';
1043 *s++ = 'n';
1044 break;
1045 case '\r':
1046 *s++ = '\\';
1047 *s++ = 'r';
1048 break;
1049 case '\t':
1050 *s++ = '\\';
1051 *s++ = 't';
1052 break;
1053 case '\v':
1054 *s++ = '\\';
1055 *s++ = 'v';
1056 break;
1057 default:
1058 printable = is_print(c);
1059
1060 if (printable && escape_chars)
1061 printable = !strchr(escape_chars, c);
1062
1063 if (printable) {
1064 *s++ = c;
1065 } else {
1066 if (xstyle == HEXSTR_NON_ASCII_CHARS) {
1067 /* Print he\x */
1068 *s++ = '\\';
1069 *s++ = 'x';
1070 s = sprint_byte_hex(s, c);
1071 } else {
1072 /* Print \octal */
1073 *s++ = '\\';
1074 s = sprint_byte_oct(s, c,
1075 i + 1 < size
1076 && ustr[i + 1] >= '0'
1077 && ustr[i + 1] <= '7');
1078 }
1079 }
1080 }
1081 }
1082
1083 string_ended:
1084 if (!(style & QUOTE_OMIT_LEADING_TRAILING_QUOTES))
1085 *s++ = '\"';
1086 if (style & QUOTE_EMIT_COMMENT)
1087 s = stpcpy(s, " */");
1088 *s = '\0';
1089
1090 /* Return zero if we printed entire ASCIZ string (didn't truncate it) */
1091 if (style & QUOTE_0_TERMINATED && ustr[i] == '\0') {
1092 /* We didn't see NUL yet (otherwise we'd jump to 'asciz_ended')
1093 * but next char is NUL.
1094 */
1095 return 0;
1096 }
1097
1098 return 1;
1099
1100 asciz_ended:
1101 if (!(style & QUOTE_OMIT_LEADING_TRAILING_QUOTES))
1102 *s++ = '\"';
1103 if (style & QUOTE_EMIT_COMMENT)
1104 s = stpcpy(s, " */");
1105 *s = '\0';
1106 /* Return zero: we printed entire ASCIZ string (didn't truncate it) */
1107 return 0;
1108 }
1109
1110 #ifndef ALLOCA_CUTOFF
1111 # define ALLOCA_CUTOFF 4032
1112 #endif
1113 #define use_alloca(n) ((n) <= ALLOCA_CUTOFF)
1114
1115 /*
1116 * Quote string `str' of length `size' and print the result.
1117 *
1118 * If QUOTE_0_TERMINATED `style' flag is set,
1119 * treat `str' as a NUL-terminated string and
1120 * quote at most (`size' - 1) bytes.
1121 *
1122 * If QUOTE_OMIT_LEADING_TRAILING_QUOTES `style' flag is set,
1123 * do not add leading and trailing quoting symbols.
1124 *
1125 * Returns 0 if QUOTE_0_TERMINATED is set and NUL was seen, 1 otherwise.
1126 * Note that if QUOTE_0_TERMINATED is not set, always returns 1.
1127 */
1128 int
1129 print_quoted_string_ex(const char *str, unsigned int size,
1130 const unsigned int style, const char *escape_chars)
1131 {
1132 char *buf;
1133 char *outstr;
1134 unsigned int alloc_size;
1135 int rc;
1136
1137 if (size && style & QUOTE_0_TERMINATED)
1138 --size;
1139
1140 alloc_size = 4 * size;
1141 if (alloc_size / 4 != size) {
1142 error_func_msg("requested %u bytes exceeds %u bytes limit",
1143 size, -1U / 4);
1144 tprint_unavailable();
1145 return -1;
1146 }
1147 alloc_size += 1 + (style & QUOTE_OMIT_LEADING_TRAILING_QUOTES ? 0 : 2) +
1148 (style & QUOTE_EMIT_COMMENT ? 7 : 0);
1149
1150 if (use_alloca(alloc_size)) {
1151 outstr = alloca(alloc_size);
1152 buf = NULL;
1153 } else {
1154 outstr = buf = malloc(alloc_size);
1155 if (!buf) {
1156 error_func_msg("memory exhausted when tried to allocate"
1157 " %u bytes", alloc_size);
1158 tprint_unavailable();
1159 return -1;
1160 }
1161 }
1162
1163 rc = string_quote(str, outstr, size, style, escape_chars);
1164 tprints_string(outstr);
1165
1166 if (((style & (QUOTE_0_TERMINATED | QUOTE_EXPECT_TRAILING_0))
1167 == (QUOTE_0_TERMINATED | QUOTE_EXPECT_TRAILING_0)) && rc) {
1168 tprint_more_data_follows();
1169 }
1170
1171 free(buf);
1172 return rc;
1173 }
1174
1175 inline int
1176 print_quoted_string(const char *str, unsigned int size,
1177 const unsigned int style)
1178 {
1179 return print_quoted_string_ex(str, size, style, NULL);
1180 }
1181
1182 /*
1183 * Quote a NUL-terminated string `str' of length up to `size' - 1
1184 * and print the result.
1185 *
1186 * Returns 0 if NUL was seen, 1 otherwise.
1187 */
1188 int
1189 print_quoted_cstring(const char *str, unsigned int size)
1190 {
1191 int unterminated =
1192 print_quoted_string(str, size, QUOTE_0_TERMINATED);
1193
1194 if (unterminated)
1195 tprint_more_data_follows();
1196
1197 return unterminated;
1198 }
1199
1200 /*
1201 * Print path string specified by address `addr' and length `n'.
1202 * If path length exceeds `n', append `...' to the output.
1203 *
1204 * Returns the result of umovestr.
1205 */
1206 int
1207 printpathn(struct tcb *const tcp, const kernel_ulong_t addr, unsigned int n)
1208 {
1209 char path[PATH_MAX];
1210 int nul_seen;
1211
1212 if (!addr) {
1213 tprint_null();
1214 return -1;
1215 }
1216
1217 /* Cap path length to the path buffer size */
1218 if (n > sizeof(path) - 1)
1219 n = sizeof(path) - 1;
1220
1221 /* Fetch one byte more to find out whether path length > n. */
1222 nul_seen = umovestr(tcp, addr, n + 1, path);
1223 if (nul_seen < 0)
1224 printaddr(addr);
1225 else {
1226 path[n++] = !nul_seen;
1227 print_quoted_cstring(path, n);
1228
1229 if (nul_seen)
1230 selinux_printfilecon(tcp, path);
1231 }
1232
1233 return nul_seen;
1234 }
1235
1236 int
1237 printpath(struct tcb *const tcp, const kernel_ulong_t addr)
1238 {
1239 /* Size must correspond to char path[] size in printpathn */
1240 return printpathn(tcp, addr, PATH_MAX - 1);
1241 }
1242
1243 /*
1244 * Print string specified by address `addr' and length `len'.
1245 * If `user_style' has QUOTE_0_TERMINATED bit set, treat the string
1246 * as a NUL-terminated string.
1247 * Pass `user_style' on to `string_quote'.
1248 * Append `...' to the output if either the string length exceeds `max_strlen',
1249 * or QUOTE_0_TERMINATED bit is set and the string length exceeds `len'.
1250 *
1251 * Returns the result of umovestr if style has QUOTE_0_TERMINATED,
1252 * or the result of umoven otherwise.
1253 */
1254 int
1255 printstr_ex(struct tcb *const tcp, const kernel_ulong_t addr,
1256 const kernel_ulong_t len, const unsigned int user_style)
1257 {
1258 static char *str;
1259 static char *outstr;
1260
1261 unsigned int size;
1262 unsigned int style = user_style;
1263 int rc;
1264 int ellipsis;
1265
1266 if (!addr) {
1267 tprint_null();
1268 return -1;
1269 }
1270 /* Allocate static buffers if they are not allocated yet. */
1271 if (!str) {
1272 const unsigned int outstr_size =
1273 4 * max_strlen + /* for quotes and NUL */ 3;
1274 /*
1275 * We can assume that outstr_size / 4 == max_strlen
1276 * since we have a guarantee that max_strlen <= -1U / 4.
1277 */
1278
1279 str = xmalloc(max_strlen + 1);
1280 outstr = xmalloc(outstr_size);
1281 }
1282
1283 /* Fetch one byte more because string_quote may look one byte ahead. */
1284 size = max_strlen + 1;
1285
1286 if (size > len)
1287 size = len;
1288 if (style & QUOTE_0_TERMINATED)
1289 rc = umovestr(tcp, addr, size, str);
1290 else
1291 rc = umoven(tcp, addr, size, str);
1292
1293 if (rc < 0) {
1294 printaddr(addr);
1295 return rc;
1296 }
1297
1298 if (size > max_strlen)
1299 size = max_strlen;
1300 else
1301 str[size] = '\xff';
1302
1303 if ((style & (QUOTE_0_TERMINATED | QUOTE_EXPECT_TRAILING_0))
1304 == (QUOTE_0_TERMINATED | QUOTE_EXPECT_TRAILING_0)
1305 && size == len && size) {
1306 --size;
1307 }
1308
1309 /* If string_quote didn't see NUL and (it was supposed to be ASCIZ str
1310 * or we were requested to print more than -s NUM chars)...
1311 */
1312 ellipsis = string_quote(str, outstr, size, style, NULL)
1313 && len
1314 && ((style & (QUOTE_0_TERMINATED | QUOTE_EXPECT_TRAILING_0))
1315 || len > max_strlen);
1316
1317 tprints_string(outstr);
1318 if (ellipsis)
1319 tprint_more_data_follows();
1320
1321 return rc;
1322 }
1323
1324 bool
1325 print_nonzero_bytes(struct tcb *const tcp,
1326 void (*const prefix_fun)(void),
1327 const kernel_ulong_t start_addr,
1328 const unsigned int start_offs,
1329 const unsigned int total_len,
1330 const unsigned int style)
1331 {
1332 if (start_offs >= total_len)
1333 return false;
1334
1335 const kernel_ulong_t addr = start_addr + start_offs;
1336 const unsigned int len = total_len - start_offs;
1337 const unsigned int size = MIN(len, max_strlen);
1338
1339 char *str = malloc(len);
1340
1341 if (!str) {
1342 error_func_msg("memory exhausted when tried to allocate"
1343 " %u bytes", len);
1344 prefix_fun();
1345 tprint_unavailable();
1346 return true;
1347 }
1348
1349 bool ret = true;
1350
1351 if (umoven(tcp, addr, len, str)) {
1352 prefix_fun();
1353 tprint_unavailable();
1354 } else if (is_filled(str, 0, len)) {
1355 ret = false;
1356 } else {
1357 prefix_fun();
1358 tprintf_string("/* bytes %u..%u */ ", start_offs, total_len - 1);
1359
1360 print_quoted_string(str, size, style);
1361
1362 if (size < len)
1363 tprint_more_data_follows();
1364 }
1365
1366 free(str);
1367 return ret;
1368 }
1369
1370 void
1371 dumpiov_upto(struct tcb *const tcp, const int len, const kernel_ulong_t addr,
1372 kernel_ulong_t data_size)
1373 {
1374 #if ANY_WORDSIZE_LESS_THAN_KERNEL_LONG
1375 union {
1376 struct { uint32_t base; uint32_t len; } *iov32;
1377 struct { uint64_t base; uint64_t len; } *iov64;
1378 } iovu;
1379 # define iov iovu.iov64
1380 # define sizeof_iov \
1381 (current_wordsize == 4 ? (unsigned int) sizeof(*iovu.iov32) \
1382 : (unsigned int) sizeof(*iovu.iov64))
1383 # define iov_iov_base(i) \
1384 (current_wordsize == 4 ? (uint64_t) iovu.iov32[i].base : iovu.iov64[i].base)
1385 # define iov_iov_len(i) \
1386 (current_wordsize == 4 ? (uint64_t) iovu.iov32[i].len : iovu.iov64[i].len)
1387 #else
1388 struct iovec *iov;
1389 # define sizeof_iov ((unsigned int) sizeof(*iov))
1390 # define iov_iov_base(i) ptr_to_kulong(iov[i].iov_base)
1391 # define iov_iov_len(i) iov[i].iov_len
1392 #endif
1393 unsigned int size = sizeof_iov * len;
1394 if (size / sizeof_iov != (unsigned int) len) {
1395 error_func_msg("requested %u iovec elements exceeds"
1396 " %u iovec limit", len, -1U / sizeof_iov);
1397 return;
1398 }
1399
1400 iov = malloc(size);
1401 if (!iov) {
1402 error_func_msg("memory exhausted when tried to allocate"
1403 " %u bytes", size);
1404 return;
1405 }
1406 if (umoven(tcp, addr, size, iov) >= 0) {
1407 for (int i = 0; i < len; ++i) {
1408 kernel_ulong_t iov_len = iov_iov_len(i);
1409 if (iov_len > data_size)
1410 iov_len = data_size;
1411 if (!iov_len)
1412 break;
1413 data_size -= iov_len;
1414 /* include the buffer number to make it easy to
1415 * match up the trace with the source */
1416 tprintf_string(" * %" PRI_klu " bytes in buffer %d\n",
1417 iov_len, i);
1418 dumpstr(tcp, iov_iov_base(i), iov_len);
1419 }
1420 }
1421 free(iov);
1422 #undef sizeof_iov
1423 #undef iov_iov_base
1424 #undef iov_iov_len
1425 #undef iov
1426 }
1427
1428 void
1429 dumpstr(struct tcb *const tcp, const kernel_ulong_t addr,
1430 const kernel_ulong_t len)
1431 {
1432 /* xx xx xx xx xx xx xx xx xx xx xx xx xx xx xx xx 1234567890123456 */
1433 enum {
1434 HEX_BIT = 4,
1435
1436 DUMPSTR_GROUP_BYTES = 8,
1437 DUMPSTR_GROUPS = 2,
1438 DUMPSTR_WIDTH_BYTES = DUMPSTR_GROUP_BYTES * DUMPSTR_GROUPS,
1439
1440 /** Width of formatted dump in characters. */
1441 DUMPSTR_WIDTH_CHARS = DUMPSTR_WIDTH_BYTES +
1442 sizeof("xx") * DUMPSTR_WIDTH_BYTES + DUMPSTR_GROUPS,
1443
1444 DUMPSTR_GROUP_MASK = DUMPSTR_GROUP_BYTES - 1,
1445 DUMPSTR_BYTES_MASK = DUMPSTR_WIDTH_BYTES - 1,
1446
1447 /** Minimal width of the offset field in the output. */
1448 DUMPSTR_OFFS_MIN_CHARS = 5,
1449
1450 /** Arbitrarily chosen internal dumpstr buffer limit. */
1451 DUMPSTR_BUF_MAXSZ = 1 << 16,
1452 };
1453
1454 static_assert(!(DUMPSTR_BUF_MAXSZ % DUMPSTR_WIDTH_BYTES),
1455 "Maximum internal buffer size should be divisible "
1456 "by amount of bytes dumped per line");
1457 static_assert(!(DUMPSTR_GROUP_BYTES & DUMPSTR_GROUP_MASK),
1458 "DUMPSTR_GROUP_BYTES is not power of 2");
1459 static_assert(!(DUMPSTR_WIDTH_BYTES & DUMPSTR_BYTES_MASK),
1460 "DUMPSTR_WIDTH_BYTES is not power of 2");
1461
1462 if (len > len + DUMPSTR_WIDTH_BYTES || addr + len < addr) {
1463 debug_func_msg("len %" PRI_klu " at addr %#" PRI_klx
1464 " is too big, skipped", len, addr);
1465 return;
1466 }
1467
1468 static kernel_ulong_t strsize;
1469 static unsigned char *str;
1470
1471 const kernel_ulong_t alloc_size =
1472 MIN(ROUNDUP(len, DUMPSTR_WIDTH_BYTES), DUMPSTR_BUF_MAXSZ);
1473
1474 if (strsize < alloc_size) {
1475 free(str);
1476 str = malloc(alloc_size);
1477 if (!str) {
1478 strsize = 0;
1479 error_func_msg("memory exhausted when tried to allocate"
1480 " %" PRI_klu " bytes", alloc_size);
1481 return;
1482 }
1483 strsize = alloc_size;
1484 }
1485
1486 /**
1487 * Characters needed in order to print the offset field. We calculate
1488 * it this way in order to avoid ilog2_64 call most of the time.
1489 */
1490 const int offs_chars = len > (1 << (DUMPSTR_OFFS_MIN_CHARS * HEX_BIT))
1491 ? 1 + ilog2_klong(len - 1) / HEX_BIT : DUMPSTR_OFFS_MIN_CHARS;
1492 kernel_ulong_t i = 0;
1493 const unsigned char *src;
1494
1495 while (i < len) {
1496 /*
1497 * It is important to overwrite all the byte values, as we
1498 * re-use the buffer in order to avoid its re-initialisation.
1499 */
1500 static char outbuf[] = {
1501 [0 ... DUMPSTR_WIDTH_CHARS - 1] = ' ',
1502 '\0'
1503 };
1504 char *dst = outbuf;
1505
1506 /* Fetching data from tracee. */
1507 if (!i || (i % DUMPSTR_BUF_MAXSZ) == 0) {
1508 kernel_ulong_t fetch_size = MIN(len - i, alloc_size);
1509
1510 if (umoven(tcp, addr + i, fetch_size, str) < 0) {
1511 /*
1512 * Don't silently abort if we have printed
1513 * something already.
1514 */
1515 if (i)
1516 tprintf_string(" | <Cannot fetch %" PRI_klu
1517 " byte%s from pid %d"
1518 " @%#" PRI_klx ">\n",
1519 fetch_size,
1520 fetch_size == 1 ? "" : "s",
1521 tcp->pid, addr + i);
1522 return;
1523 }
1524 src = str;
1525 }
1526
1527 /* hex dump */
1528 do {
1529 if (i < len) {
1530 dst = sprint_byte_hex(dst, *src);
1531 } else {
1532 *dst++ = ' ';
1533 *dst++ = ' ';
1534 }
1535 dst++; /* space is there */
1536 i++;
1537 if ((i & DUMPSTR_GROUP_MASK) == 0)
1538 dst++; /* space is there */
1539 src++;
1540 } while (i & DUMPSTR_BYTES_MASK);
1541
1542 /* ASCII dump */
1543 i -= DUMPSTR_WIDTH_BYTES;
1544 src -= DUMPSTR_WIDTH_BYTES;
1545 do {
1546 if (i < len) {
1547 if (is_print(*src))
1548 *dst++ = *src;
1549 else
1550 *dst++ = '.';
1551 } else {
1552 *dst++ = ' ';
1553 }
1554 src++;
1555 } while (++i & DUMPSTR_BYTES_MASK);
1556
1557 tprintf_string(" | %0*" PRI_klx " %s |\n",
1558 offs_chars, i - DUMPSTR_WIDTH_BYTES, outbuf);
1559 }
1560 }
1561
1562 bool
1563 tfetch_mem64(struct tcb *const tcp, const uint64_t addr,
1564 const unsigned int len, void *const our_addr)
1565 {
1566 return addr && verbose(tcp) &&
1567 (entering(tcp) || !syserror(tcp)) &&
1568 !umoven(tcp, addr, len, our_addr);
1569 }
1570
1571 bool
1572 tfetch_mem64_ignore_syserror(struct tcb *const tcp, const uint64_t addr,
1573 const unsigned int len, void *const our_addr)
1574 {
1575 return addr && verbose(tcp) &&
1576 !umoven(tcp, addr, len, our_addr);
1577 }
1578
1579 int
1580 umoven_or_printaddr64(struct tcb *const tcp, const uint64_t addr,
1581 const unsigned int len, void *const our_addr)
1582 {
1583 if (tfetch_mem64(tcp, addr, len, our_addr))
1584 return 0;
1585 printaddr64(addr);
1586 return -1;
1587 }
1588
1589 int
1590 umoven_or_printaddr64_ignore_syserror(struct tcb *const tcp,
1591 const uint64_t addr,
1592 const unsigned int len,
1593 void *const our_addr)
1594 {
1595 if (tfetch_mem64_ignore_syserror(tcp, addr, len, our_addr))
1596 return 0;
1597 printaddr64(addr);
1598 return -1;
1599 }
1600
1601 int
1602 umoven_to_uint64_or_printaddr64(struct tcb *const tcp, const uint64_t addr,
1603 unsigned int len, uint64_t *const our_addr)
1604 {
1605 union {
1606 uint64_t val;
1607 uint8_t bytes[sizeof(uint64_t)];
1608 } data = { .val = 0 };
1609 const size_t offs = is_bigendian ? sizeof(data) - len : 0;
1610
1611 if (len <= sizeof(data) &&
1612 tfetch_mem64_ignore_syserror(tcp, addr, len, data.bytes + offs)) {
1613 *our_addr = data.val;
1614 return 0;
1615 }
1616 printaddr64(addr);
1617 return -1;
1618 }
1619
1620 bool
1621 print_int_array_member(struct tcb *tcp, void *elem_buf, size_t elem_size,
1622 void *data)
1623 {
1624 switch (elem_size) {
1625 case sizeof(int8_t): PRINT_VAL_D(*(int8_t *) elem_buf); break;
1626 case sizeof(int16_t): PRINT_VAL_D(*(int16_t *) elem_buf); break;
1627 case sizeof(int32_t): PRINT_VAL_D(*(int32_t *) elem_buf); break;
1628 case sizeof(int64_t): PRINT_VAL_D(*(int64_t *) elem_buf); break;
1629 default:
1630 error_func_msg("Unexpected elem_size: %zu", elem_size);
1631 return false;
1632 }
1633
1634 return true;
1635 }
1636
1637 bool
1638 print_uint_array_member(struct tcb *tcp, void *elem_buf, size_t elem_size,
1639 void *data)
1640 {
1641 switch (elem_size) {
1642 case sizeof(uint8_t): PRINT_VAL_U(*(uint8_t *) elem_buf); break;
1643 case sizeof(uint16_t): PRINT_VAL_U(*(uint16_t *) elem_buf); break;
1644 case sizeof(uint32_t): PRINT_VAL_U(*(uint32_t *) elem_buf); break;
1645 case sizeof(uint64_t): PRINT_VAL_U(*(uint64_t *) elem_buf); break;
1646 default:
1647 error_func_msg("Unexpected elem_size: %zu", elem_size);
1648 return false;
1649 }
1650
1651 return true;
1652 }
1653
1654 bool
1655 print_xint_array_member(struct tcb *tcp, void *elem_buf, size_t elem_size,
1656 void *data)
1657 {
1658 switch (elem_size) {
1659 case sizeof(uint8_t): PRINT_VAL_X(*(uint8_t *) elem_buf); break;
1660 case sizeof(uint16_t): PRINT_VAL_X(*(uint16_t *) elem_buf); break;
1661 case sizeof(uint32_t): PRINT_VAL_X(*(uint32_t *) elem_buf); break;
1662 case sizeof(uint64_t): PRINT_VAL_X(*(uint64_t *) elem_buf); break;
1663 default:
1664 error_func_msg("Unexpected elem_size: %zu", elem_size);
1665 return false;
1666 }
1667
1668 return true;
1669 }
1670
1671 bool
1672 print_fd_array_member(struct tcb *tcp, void *elem_buf, size_t elem_size,
1673 void *data)
1674 {
1675 printfd(tcp, *(int *) elem_buf);
1676 return true;
1677 }
1678
1679 /*
1680 * Iteratively fetch and print up to nmemb elements of elem_size size
1681 * from the array that starts at tracee's address start_addr.
1682 *
1683 * Array elements are being fetched to the address specified by elem_buf.
1684 *
1685 * The fetcher callback function specified by tfetch_mem_func should follow
1686 * the same semantics as tfetch_mem function.
1687 *
1688 * The printer callback function specified by print_func is expected
1689 * to print something; if it returns false, no more iterations will be made.
1690 *
1691 * The pointer specified by opaque_data is passed to each invocation
1692 * of print_func callback function.
1693 *
1694 * This function prints:
1695 * - "NULL", if start_addr is NULL;
1696 * - "[]", if nmemb is 0;
1697 * - start_addr, if nmemb * elem_size overflows or wraps around;
1698 * - start_addr, if the first tfetch_mem_func invocation returned false;
1699 * - elements of the array, delimited by ", ", with the array itself
1700 * enclosed with [] brackets.
1701 *
1702 * If abbrev(tcp) is true, then
1703 * - the maximum number of elements printed equals to max_strlen;
1704 * - "..." is printed instead of max_strlen+1 element
1705 * and no more iterations will be made.
1706 *
1707 * This function returns true only if tfetch_mem_func has returned true
1708 * at least once.
1709 */
1710 bool
1711 print_array_ex(struct tcb *const tcp,
1712 const kernel_ulong_t start_addr,
1713 const size_t nmemb,
1714 void *elem_buf,
1715 const size_t elem_size,
1716 tfetch_mem_fn tfetch_mem_func,
1717 print_fn print_func,
1718 void *const opaque_data,
1719 unsigned int flags,
1720 const struct xlat *index_xlat,
1721 const char *index_dflt)
1722 {
1723 if (!start_addr) {
1724 tprint_null();
1725 return false;
1726 }
1727
1728 if (!nmemb) {
1729 tprint_array_begin();
1730 if (flags & PAF_ARRAY_TRUNCATED)
1731 tprint_more_data_follows();
1732 tprint_array_end();
1733 return false;
1734 }
1735
1736 const size_t size = nmemb * elem_size;
1737 const kernel_ulong_t end_addr = start_addr + size;
1738
1739 if (end_addr <= start_addr || size / elem_size != nmemb) {
1740 if (tfetch_mem_func)
1741 printaddr(start_addr);
1742 else
1743 tprint_unavailable();
1744 return false;
1745 }
1746
1747 const kernel_ulong_t abbrev_end =
1748 (abbrev(tcp) && max_strlen < nmemb) ?
1749 start_addr + elem_size * max_strlen : end_addr;
1750 kernel_ulong_t cur;
1751 kernel_ulong_t idx = 0;
1752 enum xlat_style xlat_style = flags & XLAT_STYLE_MASK;
1753 bool truncated = false;
1754
1755 for (cur = start_addr; cur < end_addr; cur += elem_size, idx++) {
1756 if (cur != start_addr)
1757 tprint_array_next();
1758
1759 if (tfetch_mem_func) {
1760 if (!tfetch_mem_func(tcp, cur, elem_size, elem_buf)) {
1761 if (cur == start_addr)
1762 printaddr(cur);
1763 else {
1764 tprint_more_data_follows();
1765 printaddr_comment(cur);
1766 truncated = true;
1767 }
1768 break;
1769 }
1770 } else {
1771 elem_buf = (void *) (uintptr_t) cur;
1772 }
1773
1774 if (cur == start_addr)
1775 tprint_array_begin();
1776
1777 if (cur >= abbrev_end) {
1778 tprint_more_data_follows();
1779 cur = end_addr;
1780 truncated = true;
1781 break;
1782 }
1783
1784 if (flags & PAF_PRINT_INDICES) {
1785 tprint_array_index_begin();
1786
1787 if (!index_xlat) {
1788 print_xlat_ex(idx, NULL, xlat_style);
1789 } else {
1790 printxval_ex(index_xlat, idx, index_dflt,
1791 xlat_style);
1792 }
1793
1794 tprint_array_index_equal();
1795 }
1796
1797 bool break_needed =
1798 !print_func(tcp, elem_buf, elem_size, opaque_data);
1799
1800 if (flags & PAF_PRINT_INDICES)
1801 tprint_array_index_end();
1802
1803 if (break_needed) {
1804 cur = end_addr;
1805 break;
1806 }
1807 }
1808
1809 if ((cur != start_addr) || !tfetch_mem_func) {
1810 if ((flags & PAF_ARRAY_TRUNCATED) && !truncated) {
1811 if (cur != start_addr)
1812 tprint_array_next();
1813
1814 tprint_more_data_follows();
1815 }
1816
1817 tprint_array_end();
1818 }
1819
1820 return cur >= end_addr;
1821 }
1822
1823 int
1824 printargs(struct tcb *tcp)
1825 {
1826 const unsigned int n = n_args(tcp);
1827 for (unsigned int i = 0; i < n; ++i) {
1828 if (i)
1829 tprint_arg_next();
1830 PRINT_VAL_X(tcp->u_arg[i]);
1831 }
1832 return RVAL_DECODED;
1833 }
1834
1835 int
1836 printargs_u(struct tcb *tcp)
1837 {
1838 const unsigned int n = n_args(tcp);
1839 for (unsigned int i = 0; i < n; ++i) {
1840 if (i)
1841 tprint_arg_next();
1842 PRINT_VAL_U((unsigned int) tcp->u_arg[i]);
1843 }
1844 return RVAL_DECODED;
1845 }
1846
1847 int
1848 printargs_d(struct tcb *tcp)
1849 {
1850 const unsigned int n = n_args(tcp);
1851 for (unsigned int i = 0; i < n; ++i) {
1852 if (i)
1853 tprint_arg_next();
1854 PRINT_VAL_D((int) tcp->u_arg[i]);
1855 }
1856 return RVAL_DECODED;
1857 }
1858
1859 /* Print abnormal high bits of a kernel_ulong_t value. */
1860 void
1861 print_abnormal_hi(const kernel_ulong_t val)
1862 {
1863 if (current_klongsize > 4) {
1864 const unsigned int hi = (unsigned int) ((uint64_t) val >> 32);
1865 if (hi) {
1866 tprint_shift_begin();
1867 PRINT_VAL_X(hi);
1868 tprint_shift();
1869 PRINT_VAL_U(32);
1870 tprint_shift_end();
1871 tprint_flags_or();
1872 }
1873 }
1874 }
1875
1876 int
1877 read_int_from_file(const char *const fname, int *const pvalue)
1878 {
1879 const int fd = open_file(fname, O_RDONLY);
1880 if (fd < 0)
1881 return -1;
1882
1883 long lval;
1884 char buf[sizeof(lval) * 3];
1885 int n = read(fd, buf, sizeof(buf) - 1);
1886 int saved_errno = errno;
1887 close(fd);
1888
1889 if (n < 0) {
1890 errno = saved_errno;
1891 return -1;
1892 }
1893
1894 buf[n] = '\0';
1895 char *endptr = 0;
1896 errno = 0;
1897 lval = strtol(buf, &endptr, 10);
1898 if (!endptr || (*endptr && '\n' != *endptr)
1899 #if INT_MAX < LONG_MAX
1900 || lval > INT_MAX || lval < INT_MIN
1901 #endif
1902 || ERANGE == errno) {
1903 if (!errno)
1904 errno = EINVAL;
1905 return -1;
1906 }
1907
1908 *pvalue = (int) lval;
1909 return 0;
1910 }