GCC Code Coverage Report
Directory: ./ Exec Total Coverage
File: usr.bin/kdump/kdump.c Lines: 298 550 54.2 %
Date: 2017-11-07 Branches: 182 466 39.1 %

Line Branch Exec Source
1
/*	$OpenBSD: kdump.c,v 1.130 2017/04/28 13:53:05 mpi Exp $	*/
2
3
/*-
4
 * Copyright (c) 1988, 1993
5
 *	The Regents of the University of California.  All rights reserved.
6
 *
7
 * Redistribution and use in source and binary forms, with or without
8
 * modification, are permitted provided that the following conditions
9
 * are met:
10
 * 1. Redistributions of source code must retain the above copyright
11
 *    notice, this list of conditions and the following disclaimer.
12
 * 2. Redistributions in binary form must reproduce the above copyright
13
 *    notice, this list of conditions and the following disclaimer in the
14
 *    documentation and/or other materials provided with the distribution.
15
 * 3. Neither the name of the University nor the names of its contributors
16
 *    may be used to endorse or promote products derived from this software
17
 *    without specific prior written permission.
18
 *
19
 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
20
 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
21
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
22
 * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
23
 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
24
 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
25
 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
26
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
27
 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
28
 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
29
 * SUCH DAMAGE.
30
 */
31
32
#include <sys/param.h>	/* MAXCOMLEN nitems */
33
#include <sys/time.h>
34
#include <sys/signal.h>
35
#include <sys/uio.h>
36
#include <sys/ktrace.h>
37
#include <sys/ioctl.h>
38
#include <sys/malloc.h>
39
#include <sys/namei.h>
40
#include <sys/ptrace.h>
41
#include <sys/sem.h>
42
#include <sys/shm.h>
43
#include <sys/socket.h>
44
#include <sys/sysctl.h>
45
#include <sys/siginfo.h>
46
#include <sys/vmmeter.h>
47
#include <sys/tty.h>
48
#include <sys/wait.h>
49
#define PLEDGENAMES
50
#include <sys/pledge.h>
51
#undef PLEDGENAMES
52
#define _KERNEL
53
#include <errno.h>
54
#undef _KERNEL
55
#include <ddb/db_var.h>
56
#include <machine/cpu.h>
57
58
#include <ctype.h>
59
#include <err.h>
60
#include <fcntl.h>
61
#include <limits.h>
62
#include <netdb.h>
63
#include <poll.h>
64
#include <signal.h>
65
#include <stdio.h>
66
#include <stdlib.h>
67
#include <stdint.h>
68
#include <string.h>
69
#include <unistd.h>
70
#include <vis.h>
71
72
#include "ktrace.h"
73
#include "kdump.h"
74
#include "kdump_subr.h"
75
#include "extern.h"
76
77
int timestamp, decimal, iohex, fancy = 1, maxdata = INT_MAX;
78
int needtid, tail, basecol;
79
char *tracefile = DEF_TRACEFILE;
80
struct ktr_header ktr_header;
81
pid_t pid_opt = -1;
82
83
#define eqs(s1, s2)	(strcmp((s1), (s2)) == 0)
84
85
#include <sys/syscall.h>
86
87
#define KTRACE
88
#define PTRACE
89
#define NFSCLIENT
90
#define NFSSERVER
91
#define SYSVSEM
92
#define SYSVMSG
93
#define SYSVSHM
94
#define ACCOUNTING
95
#include <kern/syscalls.c>
96
#undef KTRACE
97
#undef PTRACE
98
#undef NFSCLIENT
99
#undef NFSSERVER
100
#undef SYSVSEM
101
#undef SYSVMSG
102
#undef SYSVSHM
103
#undef ACCOUNTING
104
105
106
static char *ptrace_ops[] = {
107
	"PT_TRACE_ME",	"PT_READ_I",	"PT_READ_D",	"PT_READ_U",
108
	"PT_WRITE_I",	"PT_WRITE_D",	"PT_WRITE_U",	"PT_CONTINUE",
109
	"PT_KILL",	"PT_ATTACH",	"PT_DETACH",	"PT_IO",
110
	"PT_SET_EVENT_MASK", "PT_GET_EVENT_MASK", "PT_GET_PROCESS_STATE",
111
	"PT_GET_THREAD_FIRST", "PT_GET_THREAD_NEXT",
112
};
113
114
static int fread_tail(void *, size_t, size_t);
115
static void dumpheader(struct ktr_header *);
116
static void ktrgenio(struct ktr_genio *, size_t);
117
static void ktrnamei(const char *, size_t);
118
static void ktrpsig(struct ktr_psig *);
119
static void ktrsyscall(struct ktr_syscall *, size_t);
120
static const char *kresolvsysctl(int, const int *);
121
static void ktrsysret(struct ktr_sysret *, size_t);
122
static void ktruser(struct ktr_user *, size_t);
123
static void ktrexec(const char*, size_t);
124
static void ktrpledge(struct ktr_pledge *, size_t);
125
static void usage(void);
126
static void ioctldecode(int);
127
static void ptracedecode(int);
128
static void atfd(int);
129
static void polltimeout(int);
130
static void wait4pid(int);
131
static void signame(int);
132
static void semctlname(int);
133
static void shmctlname(int);
134
static void semgetname(int);
135
static void flagsandmodename(int);
136
static void clockname(int);
137
static void sockoptlevelname(int);
138
static void ktraceopname(int);
139
140
static int screenwidth;
141
142
int
143
main(int argc, char *argv[])
144
{
145
	int ch, silent;
146
	size_t ktrlen, size;
147
	int trpoints = ALL_POINTS;
148
854
	const char *errstr;
149
	void *m;
150
151
427
	if (screenwidth == 0) {
152
427
		struct winsize ws;
153
154


2057
		if (fancy && ioctl(fileno(stderr), TIOCGWINSZ, &ws) != -1 &&
155
349
		    ws.ws_col > 8)
156
349
			screenwidth = ws.ws_col;
157
		else
158
			screenwidth = 80;
159
427
	}
160
161
846
	while ((ch = getopt(argc, argv, "f:dHlm:np:RTt:xX")) != -1)
162



419
		switch (ch) {
163
		case 'f':
164
419
			tracefile = optarg;
165
419
			break;
166
		case 'd':
167
			decimal = 1;
168
			break;
169
		case 'H':
170
			needtid = 1;
171
			break;
172
		case 'l':
173
			tail = 1;
174
			break;
175
		case 'm':
176
			maxdata = strtonum(optarg, 0, INT_MAX, &errstr);
177
			if (errstr)
178
				errx(1, "-m %s: %s", optarg, errstr);
179
			break;
180
		case 'n':
181
			fancy = 0;
182
			break;
183
		case 'p':
184
			pid_opt = strtonum(optarg, 1, INT_MAX, &errstr);
185
			if (errstr)
186
				errx(1, "-p %s: %s", optarg, errstr);
187
			break;
188
		case 'R':	/* relative timestamp */
189
			timestamp = timestamp == 1 ? 3 : 2;
190
			break;
191
		case 'T':
192
			timestamp = timestamp == 2 ? 3 : 1;
193
			break;
194
		case 't':
195
			trpoints = getpoints(optarg, DEF_POINTS);
196
			if (trpoints < 0)
197
				errx(1, "unknown trace point in %s", optarg);
198
			break;
199
		case 'x':
200
			iohex = 1;
201
			break;
202
		case 'X':
203
			iohex = 2;
204
			break;
205
		default:
206
			usage();
207
		}
208
427
	if (argc > optind)
209
		usage();
210
211
427
	if (pledge("stdio rpath getpw flock cpath wpath", NULL) == -1)
212
		err(1, "pledge");
213
214
427
	m = malloc(size = 1025);
215
427
	if (m == NULL)
216
		err(1, NULL);
217
427
	if (!freopen(tracefile, "r", stdin))
218
		err(1, "%s", tracefile);
219
220

854
	if (fread_tail(&ktr_header, sizeof(struct ktr_header), 1) == 0 ||
221
427
	    ktr_header.ktr_type != htobe32(KTR_START))
222
		errx(1, "%s: not a dump", tracefile);
223
6037386
	while (fread_tail(&ktr_header, sizeof(struct ktr_header), 1)) {
224
		silent = 0;
225

6036959
		if (pid_opt != -1 && pid_opt != ktr_header.ktr_pid)
226
			silent = 1;
227

12073918
		if (silent == 0 && trpoints & (1<<ktr_header.ktr_type))
228
6036959
			dumpheader(&ktr_header);
229
6036959
		ktrlen = ktr_header.ktr_len;
230
6036959
		if (ktrlen > size) {
231
			void *newm;
232
233
456
			if (ktrlen == SIZE_MAX)
234
				errx(1, "data too long");
235
456
			newm = realloc(m, ktrlen+1);
236
456
			if (newm == NULL)
237
				err(1, "realloc");
238
			m = newm;
239
			size = ktrlen;
240
456
		}
241

12073918
		if (ktrlen && fread_tail(m, ktrlen, 1) == 0)
242
			errx(1, "data too short");
243
6036959
		if (silent)
244
			continue;
245
6036959
		if ((trpoints & (1<<ktr_header.ktr_type)) == 0)
246
			continue;
247


6036959
		switch (ktr_header.ktr_type) {
248
		case KTR_SYSCALL:
249
2321224
			ktrsyscall((struct ktr_syscall *)m, ktrlen);
250
2321224
			break;
251
		case KTR_SYSRET:
252
2321242
			ktrsysret((struct ktr_sysret *)m, ktrlen);
253
2321242
			break;
254
		case KTR_NAMEI:
255
991915
			ktrnamei(m, ktrlen);
256
991915
			break;
257
		case KTR_GENIO:
258
233083
			ktrgenio((struct ktr_genio *)m, ktrlen);
259
233083
			break;
260
		case KTR_PSIG:
261
1575
			ktrpsig((struct ktr_psig *)m);
262
1575
			break;
263
		case KTR_STRUCT:
264
166557
			ktrstruct(m, ktrlen);
265
166557
			break;
266
		case KTR_USER:
267
			ktruser(m, ktrlen);
268
			break;
269
		case KTR_EXECARGS:
270
		case KTR_EXECENV:
271
1330
			ktrexec(m, ktrlen);
272
1330
			break;
273
		case KTR_PLEDGE:
274
33
			ktrpledge((struct ktr_pledge *)m, ktrlen);
275
33
			break;
276
		default:
277
			printf("\n");
278
			break;
279
		}
280
6036959
		if (tail)
281
			(void)fflush(stdout);
282
	}
283
	exit(0);
284
}
285
286
static int
287
fread_tail(void *buf, size_t size, size_t num)
288
{
289
	int i;
290
291
36224316
	while ((i = fread(buf, size, num, stdin)) == 0 && tail) {
292
		(void)sleep(1);
293
		clearerr(stdin);
294
	}
295
12074772
	return (i);
296
}
297
298
static void
299
dumpheader(struct ktr_header *kth)
300
{
301
	static struct timespec prevtime;
302
12073918
	char unknown[64], *type;
303
	struct timespec temp;
304
305


6036959
	switch (kth->ktr_type) {
306
	case KTR_SYSCALL:
307
		type = "CALL";
308
2321224
		break;
309
	case KTR_SYSRET:
310
		type = "RET ";
311
2321242
		break;
312
	case KTR_NAMEI:
313
		type = "NAMI";
314
991915
		break;
315
	case KTR_GENIO:
316
		type = "GIO ";
317
233083
		break;
318
	case KTR_PSIG:
319
		type = "PSIG";
320
1575
		break;
321
	case KTR_STRUCT:
322
		type = "STRU";
323
166557
		break;
324
	case KTR_USER:
325
		type = "USER";
326
		break;
327
	case KTR_EXECARGS:
328
		type = "ARGS";
329
1330
		break;
330
	case KTR_EXECENV:
331
		type = "ENV ";
332
		break;
333
	case KTR_PLEDGE:
334
		type = "PLDG";
335
33
		break;
336
	default:
337
		/* htobe32() not guaranteed to work as case label */
338
		if (kth->ktr_type == htobe32(KTR_START)) {
339
			type = "STRT";
340
			break;
341
		}
342
		(void)snprintf(unknown, sizeof unknown, "UNKNOWN(%u)",
343
		    kth->ktr_type);
344
		type = unknown;
345
	}
346
347
6036959
	basecol = printf("%6ld", (long)kth->ktr_pid);
348
6036959
	if (needtid)
349
		basecol += printf("/%-7ld", (long)kth->ktr_tid);
350
6036959
	basecol += printf(" %-8.*s ", MAXCOMLEN, kth->ktr_comm);
351
6036959
	if (timestamp) {
352
		if (timestamp == 3) {
353
			if (prevtime.tv_sec == 0)
354
				prevtime = kth->ktr_time;
355
			timespecsub(&kth->ktr_time, &prevtime, &temp);
356
		} else if (timestamp == 2) {
357
			timespecsub(&kth->ktr_time, &prevtime, &temp);
358
			prevtime = kth->ktr_time;
359
		} else
360
			temp = kth->ktr_time;
361
		basecol += printf("%lld.%06ld ", (long long)temp.tv_sec,
362
		    temp.tv_nsec / 1000);
363
	}
364
6036959
	basecol += printf("%s  ", type);
365
6036959
}
366
367
/*
368
 * Base Formatters
369
 */
370
371
/* some syscalls have padding that shouldn't be shown */
372
static int
373
pad(long arg)
374
{
375
	/* nothing printed */
376
480884
	return (1);
377
}
378
379
/* a formatter that just saves the argument for the next formatter */
380
int arg1;
381
static int
382
pass_two(long arg)
383
{
384
1120408
	arg1 = (int)arg;
385
386
	/* nothing printed */
387
560204
	return (1);
388
}
389
390
static int
391
pdeclong(long arg)
392
{
393
	(void)printf("%ld", arg);
394
	return (0);
395
}
396
397
static int
398
pdeculong(long arg)
399
{
400
359946
	(void)printf("%lu", arg);
401
179973
	return (0);
402
}
403
404
static int
405
phexlong(long arg)
406
{
407
5812344
	(void)printf("%#lx", arg);
408
2906172
	return (0);
409
}
410
411
static int
412
pnonfancy(long arg)
413
{
414
	if (decimal)
415
		(void)printf("%ld", arg);
416
	else
417
		(void)printf("%#lx", arg);
418
	return (0);
419
}
420
421
static void
422
pdecint(int arg)
423
{
424
1798894
	(void)printf("%d", arg);
425
899447
}
426
427
static void
428
pdecuint(int arg)
429
{
430
3208
	(void)printf("%u", arg);
431
1604
}
432
433
static void
434
phexint(int arg)
435
{
436
	(void)printf("%#x", arg);
437
}
438
439
static void
440
poctint(int arg)
441
{
442
	(void)printf("%#o", arg);
443
}
444
445
446
#ifdef __LP64__
447
448
/* on LP64, long long arguments are the same as long arguments */
449
#define Phexlonglong	Phexlong
450
#define phexll		NULL		/* not actually used on LP64 */
451
452
#else /* __LP64__ */
453
454
/* on ILP32, long long arguments are passed as two 32bit args */
455
#define Phexlonglong	PASS_LONGLONG, Phexll
456
457
static int
458
phexll(long arg2)
459
{
460
	long long val;
461
462
#if _BYTE_ORDER == _LITTLE_ENDIAN
463
	val = ((long long)arg2 << 32) | ((long long)arg1 & 0xffffffff);
464
#else
465
	val = ((long long)arg1 << 32) | ((long long)arg2 & 0xffffffff);
466
#endif
467
468
	if (fancy || !decimal)
469
		(void)printf("%#llx", val);
470
	else
471
		(void)printf("%lld", val);
472
	return (0);
473
}
474
475
#endif /* __LP64__ */
476
477
static int (*long_formatters[])(long) = {
478
	NULL,
479
	pdeclong,
480
	pdeculong,
481
	phexlong,
482
	pass_two,
483
	pass_two,
484
	phexll,
485
	pad,
486
	pnonfancy,
487
};
488
489
static void (*formatters[])(int) = {
490
	NULL,
491
	pdecint,
492
	phexint,
493
	poctint,
494
	pdecuint,
495
	ioctldecode,
496
	ptracedecode,
497
	atfd,
498
	polltimeout,
499
	wait4pid,
500
	signame,
501
	semctlname,
502
	shmctlname,
503
	semgetname,
504
	flagsandmodename,
505
	clockname,
506
	sockoptlevelname,
507
	ktraceopname,
508
	fcntlcmdname,
509
	modename,
510
	flagsname,
511
	openflagsname,
512
	atflagsname,
513
	accessmodename,
514
	mmapprotname,
515
	mmapflagsname,
516
	wait4optname,
517
	sendrecvflagsname,
518
	mountflagsname,
519
	rebootoptname,
520
	flockname,
521
	sockoptname,
522
	sockipprotoname,
523
	socktypename,
524
	sockflagsname,
525
	sockfamilyname,
526
	mlockallname,
527
	shmatname,
528
	whencename,
529
	pathconfname,
530
	rlimitname,
531
	shutdownhowname,
532
	prioname,
533
	madvisebehavname,
534
	msyncflagsname,
535
	clocktypename,
536
	rusagewho,
537
	sigactionflagname,
538
	sigprocmaskhowname,
539
	minheritname,
540
	quotactlname,
541
	sigill_name,
542
	sigtrap_name,
543
	sigemt_name,
544
	sigfpe_name,
545
	sigbus_name,
546
	sigsegv_name,
547
	sigchld_name,
548
	ktracefacname,
549
	itimername,
550
	sigset,
551
	uidname,
552
	gidname,
553
	syslogflagname,
554
	futexflagname,
555
};
556
557
enum {
558
	/* the end of the (known) arguments is recognized by the zero fill */
559
	end_of_args	=  0,
560
561
	/* negative are the negative of the index into long_formatters[] */
562
	Pdeclong	= -1,
563
	Pdeculong	= -2,
564
	Phexlong	= -3,
565
	PASS_TWO	= -4,
566
567
/* the remaining long formatters still get called when non-fancy (-n option) */
568
#define FMT_IS_NONFANCY(x)	((x) <= PASS_LONGLONG)
569
	PASS_LONGLONG	= -5,
570
	Phexll		= -6,
571
	PAD		= -7,
572
	Pnonfancy	= -8,
573
574
	/* positive values are the index into formatters[] */
575
	Pdecint		= 1,
576
	Phexint,
577
	Poctint,
578
	Pdecuint,
579
	Ioctldecode,
580
	Ptracedecode,
581
	Atfd,
582
	Polltimeout,
583
	Wait4pid,
584
	Signame,
585
	Semctlname,
586
	Shmctlname,
587
	Semgetname,
588
	Flagsandmodename,
589
	Clockname,
590
	Sockoptlevelname,
591
	Ktraceopname,
592
	Fcntlcmdname,
593
	Modename,
594
	Flagsname,
595
	Openflagsname,
596
	Atflagsname,
597
	Accessmodename,
598
	Mmapprotname,
599
	Mmapflagsname,
600
	Wait4optname,
601
	Sendrecvflagsname,
602
	Mountflagsname,
603
	Rebootoptname,
604
	Flockname,
605
	Sockoptname,
606
	Sockipprotoname,
607
	Socktypename,
608
	Sockflagsname,
609
	Sockfamilyname,
610
	Mlockallname,
611
	Shmatname,
612
	Whencename,
613
	Pathconfname,
614
	Rlimitname,
615
	Shutdownhowname,
616
	Prioname,
617
	Madvisebehavname,
618
	Msyncflagsname,
619
	Clocktypename,
620
	Rusagewho,
621
	Sigactionflagname,
622
	Sigprocmaskhowname,
623
	Minheritname,
624
	Quotactlname,
625
	Sigill_name,
626
	Sigtrap_name,
627
	Sigemt_name,
628
	Sigfpe_name,
629
	Sigbus_name,
630
	Sigsegv_name,
631
	Sigchld_name,
632
	Ktracefacname,
633
	Itimername,
634
	Sigset,
635
	Uidname,
636
	Gidname,
637
	Syslogflagname,
638
	Futexflagname,
639
};
640
641
#define Pptr		Phexlong
642
#define	Psize		Pdeculong	/* size_t for small buffers */
643
#define	Pbigsize	Phexlong	/* size_t for I/O buffers */
644
#define Pcount		Pdecint		/* int for a count of something */
645
#define Pfd		Pdecint
646
#define Ppath		Phexlong
647
#define Pdev_t		Pdecint
648
#define Ppid_t		Pdecint
649
#define Ppgid		Pdecint		/* pid or negative pgid */
650
#define Poff_t		Phexlonglong
651
#define Pmsqid		Pdecint
652
#define Pshmid		Pdecint
653
#define Psemid		Pdecint
654
#define Pkey_t		Pdecint
655
#define Pucount		Pdecuint
656
#define Chflagsname	Phexlong	/* to be added */
657
#define Sockprotoname	Phexlong	/* to be added */
658
#define Swapctlname	Phexlong	/* to be added */
659
#define Msgflgname	Phexlong	/* to be added */
660
661
662
typedef signed char formatter;
663
static const formatter scargs[][8] = {
664
    [SYS_exit]		= { Pdecint },
665
    [SYS_read]		= { Pfd, Pptr, Pbigsize },
666
    [SYS_write]		= { Pfd, Pptr, Pbigsize },
667
    [SYS_open]		= { Ppath, PASS_TWO, Flagsandmodename },
668
    [SYS_close]		= { Pfd },
669
    [SYS_getentropy]	= { Pptr, Psize },
670
    [SYS___tfork]	= { Pptr, Psize },
671
    [SYS_link]		= { Ppath, Ppath },
672
    [SYS_unlink]	= { Ppath },
673
    [SYS_wait4]		= { Wait4pid, Pptr, Wait4optname },
674
    [SYS_chdir]		= { Ppath },
675
    [SYS_fchdir]	= { Pfd },
676
    [SYS_mknod]		= { Ppath, Modename, Pdev_t },
677
    [SYS_chmod]		= { Ppath, Modename },
678
    [SYS_chown]		= { Ppath, Uidname, Gidname },
679
    [SYS_break]		= { Pptr },
680
    [SYS_getrusage]	= { Rusagewho, Pptr },
681
    [SYS_mount]		= { Pptr, Ppath, Mountflagsname, Pptr },
682
    [SYS_unmount]	= { Ppath, Mountflagsname },
683
    [SYS_setuid]	= { Uidname },
684
    [SYS_ptrace]	= { Ptracedecode, Ppid_t, Pptr, Pdecint },
685
    [SYS_recvmsg]	= { Pfd, Pptr, Sendrecvflagsname },
686
    [SYS_sendmsg]	= { Pfd, Pptr, Sendrecvflagsname },
687
    [SYS_recvfrom]	= { Pfd, Pptr, Pbigsize, Sendrecvflagsname },
688
    [SYS_accept]	= { Pfd, Pptr, Pptr },
689
    [SYS_getpeername]	= { Pfd, Pptr, Pptr },
690
    [SYS_getsockname]	= { Pfd, Pptr, Pptr },
691
    [SYS_access]	= { Ppath, Accessmodename },
692
    [SYS_chflags]	= { Ppath, Chflagsname },
693
    [SYS_fchflags]	= { Pfd, Chflagsname },
694
    [SYS_kill]		= { Ppgid, Signame },
695
    [SYS_stat]		= { Ppath, Pptr },
696
    [SYS_lstat]		= { Ppath, Pptr },
697
    [SYS_dup]		= { Pfd },
698
    [SYS_fstatat]	= { Atfd, Ppath, Pptr, Atflagsname },
699
    [SYS_profil]	= { Pptr, Pbigsize, Pbigsize, Pdecuint },
700
    [SYS_ktrace]	= { Ppath, Ktraceopname, Ktracefacname, Ppgid },
701
    [SYS_sigaction]	= { Signame, Pptr, Pptr },
702
    [SYS_sigprocmask]	= { Sigprocmaskhowname, Sigset },
703
    [SYS_getlogin_r]	= { Pptr, Psize },
704
    [SYS_setlogin]	= { Pptr },
705
    [SYS_acct]		= { Ppath },
706
    [SYS_fstat]		= { Pfd, Pptr },
707
    [SYS_ioctl]		= { Pfd, Ioctldecode, Pptr },
708
    [SYS_reboot]	= { Rebootoptname },
709
    [SYS_revoke]	= { Ppath },
710
    [SYS_symlink]	= { Ppath, Ppath },
711
    [SYS_readlink]	= { Ppath, Pptr, Psize },
712
    [SYS_execve]	= { Ppath, Pptr, Pptr },
713
    [SYS_umask]		= { Modename },
714
    [SYS_chroot]	= { Ppath },
715
    [SYS_getfsstat]	= { Pptr, Pbigsize, Mountflagsname },
716
    [SYS_statfs]	= { Ppath, Pptr },
717
    [SYS_fstatfs]	= { Pfd, Pptr },
718
    [SYS_fhstatfs]	= { Pptr, Pptr },
719
    [SYS_gettimeofday]	= { Pptr, Pptr },
720
    [SYS_settimeofday]	= { Pptr, Pptr },
721
    [SYS_setitimer]	= { Itimername, Pptr, Pptr },
722
    [SYS_getitimer]	= { Itimername, Pptr },
723
    [SYS_select]	= { Pcount, Pptr, Pptr, Pptr, Pptr },
724
    [SYS_kevent]	= { Pfd, Pptr, Pcount, Pptr, Pcount, Pptr },
725
    [SYS_munmap]	= { Pptr, Pbigsize },
726
    [SYS_mprotect]	= { Pptr, Pbigsize, Mmapprotname },
727
    [SYS_madvise]	= { Pptr, Pbigsize, Madvisebehavname },
728
    [SYS_utimes]	= { Ppath, Pptr },
729
    [SYS_futimes]	= { Pfd, Pptr },
730
    [SYS_kbind]		= { Pptr, Psize, Phexlonglong },
731
    [SYS_mincore]	= { Pptr, Pbigsize, Pptr },
732
    [SYS_getgroups]	= { Pcount, Pptr },
733
    [SYS_setgroups]	= { Pcount, Pptr },
734
    [SYS_setpgid]	= { Ppid_t, Ppid_t },
735
    [SYS_futex]		= { Pptr, Futexflagname, Pcount, Pptr, Pptr },
736
    [SYS_sendsyslog]	= { Pptr, Psize, Syslogflagname },
737
    [SYS_utimensat]	= { Atfd, Ppath, Pptr, Atflagsname },
738
    [SYS_futimens]	= { Pfd, Pptr },
739
    [SYS_clock_gettime]	= { Clockname, Pptr },
740
    [SYS_clock_settime]	= { Clockname, Pptr },
741
    [SYS_clock_getres]	= { Clockname, Pptr },
742
    [SYS_dup2]		= { Pfd, Pfd },
743
    [SYS_nanosleep]	= { Pptr, Pptr },
744
    [SYS_fcntl]		= { Pfd, PASS_TWO, Fcntlcmdname },
745
    [SYS_accept4]	= { Pfd, Pptr, Pptr, Sockflagsname },
746
    [SYS___thrsleep]	= { Pptr, Clockname, Pptr, Pptr, Pptr },
747
    [SYS_fsync]		= { Pfd },
748
    [SYS_setpriority]	= { Prioname, Ppid_t, Pdecint },
749
    [SYS_socket]	= { Sockfamilyname, Socktypename, Sockprotoname },
750
    [SYS_connect]	= { Pfd, Pptr, Pucount },
751
    [SYS_getdents]	= { Pfd, Pptr, Pbigsize },
752
    [SYS_getpriority]	= { Prioname, Ppid_t },
753
    [SYS_pipe2]		= { Pptr, Flagsname },
754
    [SYS_dup3]		= { Pfd, Pfd, Flagsname },
755
    [SYS_sigreturn]	= { Pptr },
756
    [SYS_bind]		= { Pfd, Pptr, Pucount },
757
    [SYS_setsockopt]	= { Pfd, PASS_TWO, Sockoptlevelname, Pptr, Pdecint },
758
    [SYS_listen]	= { Pfd, Pdecint },
759
    [SYS_chflagsat]	= { Atfd, Ppath, Chflagsname, Atflagsname },
760
    [SYS_ppoll]		= { Pptr, Pucount, Pptr, Pptr },
761
    [SYS_pselect]	= { Pcount, Pptr, Pptr, Pptr, Pptr, Pptr },
762
    [SYS_sigsuspend]	= { Sigset },
763
    [SYS_getsockopt]	= { Pfd, PASS_TWO, Sockoptlevelname, Pptr, Pptr },
764
    [SYS_thrkill]	= { Ppid_t, Signame, Pptr },
765
    [SYS_readv]		= { Pfd, Pptr, Pcount },
766
    [SYS_writev]	= { Pfd, Pptr, Pcount },
767
    [SYS_fchown]	= { Pfd, Uidname, Gidname },
768
    [SYS_fchmod]	= { Pfd, Modename },
769
    [SYS_setreuid]	= { Uidname, Uidname },
770
    [SYS_setregid]	= { Gidname, Gidname },
771
    [SYS_rename]	= { Ppath, Ppath },
772
    [SYS_flock]		= { Pfd, Flockname },
773
    [SYS_mkfifo]	= { Ppath, Modename },
774
    [SYS_sendto]	= { Pfd, Pptr, Pbigsize, Sendrecvflagsname },
775
    [SYS_shutdown]	= { Pfd, Shutdownhowname },
776
    [SYS_socketpair]	= { Sockfamilyname, Socktypename, Sockprotoname, Pptr },
777
    [SYS_mkdir]		= { Ppath, Modename },
778
    [SYS_rmdir]		= { Ppath },
779
    [SYS_adjtime]	= { Pptr, Pptr },
780
    [SYS_quotactl]	= { Ppath, Quotactlname, Uidname, Pptr },
781
    [SYS_nfssvc]	= { Phexint, Pptr },
782
    [SYS_getfh]		= { Ppath, Pptr },
783
    [SYS_sysarch]	= { Pdecint, Pptr },
784
    [SYS_pread]		= { Pfd, Pptr, Pbigsize, PAD, Poff_t },
785
    [SYS_pwrite]	= { Pfd, Pptr, Pbigsize, PAD, Poff_t },
786
    [SYS_setgid]	= { Gidname },
787
    [SYS_setegid]	= { Gidname },
788
    [SYS_seteuid]	= { Uidname },
789
    [SYS_pathconf]	= { Ppath, Pathconfname },
790
    [SYS_fpathconf]	= { Pfd, Pathconfname },
791
    [SYS_swapctl]	= { Swapctlname, Pptr, Pdecint },
792
    [SYS_getrlimit]	= { Rlimitname, Pptr },
793
    [SYS_setrlimit]	= { Rlimitname, Pptr },
794
    [SYS_mmap]		= { Pptr, Pbigsize, Mmapprotname, Mmapflagsname, Pfd, PAD, Poff_t },
795
    [SYS_lseek]		= { Pfd, PAD, Poff_t, Whencename },
796
    [SYS_truncate]	= { Ppath, PAD, Poff_t },
797
    [SYS_ftruncate]	= { Pfd, PAD, Poff_t },
798
    [SYS_sysctl]	= { Pptr, Pcount, Pptr, Pptr, Pptr, Psize },
799
    [SYS_mlock]		= { Pptr, Pbigsize },
800
    [SYS_munlock]	= { Pptr, Pbigsize },
801
    [SYS_getpgid]	= { Ppid_t },
802
    [SYS_utrace]	= { Pptr, Pptr, Psize },
803
    [SYS_semget]	= { Pkey_t, Pcount, Semgetname },
804
    [SYS_msgget]	= { Pkey_t, Msgflgname },
805
    [SYS_msgsnd]	= { Pmsqid, Pptr, Psize, Msgflgname },
806
    [SYS_msgrcv]	= { Pmsqid, Pptr, Psize, Pdeclong, Msgflgname },
807
    [SYS_shmat]		= { Pshmid, Pptr, Shmatname },
808
    [SYS_shmdt]		= { Pptr },
809
    [SYS_minherit]	= { Pptr, Pbigsize, Minheritname },
810
    [SYS_poll]		= { Pptr, Pucount, Polltimeout },
811
    [SYS_lchown]	= { Ppath, Uidname, Gidname },
812
    [SYS_getsid]	= { Ppid_t },
813
    [SYS_msync]		= { Pptr, Pbigsize, Msyncflagsname },
814
    [SYS_pipe]		= { Pptr },
815
    [SYS_fhopen]	= { Pptr, Openflagsname },
816
    [SYS_preadv]	= { Pfd, Pptr, Pcount, PAD, Poff_t },
817
    [SYS_pwritev]	= { Pfd, Pptr, Pcount, PAD, Poff_t },
818
    [SYS_mlockall]	= { Mlockallname },
819
    [SYS_getresuid]	= { Pptr, Pptr, Pptr },
820
    [SYS_setresuid]	= { Uidname, Uidname, Uidname },
821
    [SYS_getresgid]	= { Pptr, Pptr, Pptr },
822
    [SYS_setresgid]	= { Gidname, Gidname, Gidname },
823
    [SYS_mquery]	= { Pptr, Pbigsize, Mmapprotname, Mmapflagsname, Pfd, PAD, Poff_t },
824
    [SYS_closefrom]	= { Pfd },
825
    [SYS_sigaltstack]	= { Pptr, Pptr },
826
    [SYS_shmget]	= { Pkey_t, Pbigsize, Semgetname },
827
    [SYS_semop]		= { Psemid, Pptr, Psize },
828
    [SYS_fhstat]	= { Pptr, Pptr },
829
    [SYS___semctl]	= { Psemid, Pcount, Semctlname, Pptr },
830
    [SYS_shmctl]	= { Pshmid, Shmctlname, Pptr },
831
    [SYS_msgctl]	= { Pmsqid, Shmctlname, Pptr },
832
    [SYS___thrwakeup]	= { Pptr, Pcount },
833
    [SYS___threxit]	= { Pptr },
834
    [SYS___thrsigdivert] = { Sigset, Pptr, Pptr },
835
    [SYS___getcwd]	= { Pptr, Psize },
836
    [SYS_adjfreq]	= { Pptr, Pptr },
837
    [SYS_setrtable]	= { Pdecint },
838
    [SYS_faccessat]	= { Atfd, Ppath, Accessmodename, Atflagsname },
839
    [SYS_fchmodat]	= { Atfd, Ppath, Modename, Atflagsname },
840
    [SYS_fchownat]	= { Atfd, Ppath, Uidname, Gidname, Atflagsname },
841
    [SYS_linkat]	= { Atfd, Ppath, Atfd, Ppath, Atflagsname },
842
    [SYS_mkdirat]	= { Atfd, Ppath, Modename },
843
    [SYS_mkfifoat]	= { Atfd, Ppath, Modename },
844
    [SYS_mknodat]	= { Atfd, Ppath, Modename, Pdev_t },
845
    [SYS_openat]	= { Atfd, Ppath, PASS_TWO, Flagsandmodename },
846
    [SYS_readlinkat]	= { Atfd, Ppath, Pptr, Psize },
847
    [SYS_renameat]	= { Atfd, Ppath, Atfd, Ppath },
848
    [SYS_symlinkat]	= { Ppath, Atfd, Ppath },
849
    [SYS_unlinkat]	= { Atfd, Ppath, Atflagsname },
850
    [SYS___set_tcb]	= { Pptr },
851
};
852
853
854
static void
855
ktrsyscall(struct ktr_syscall *ktr, size_t ktrlen)
856
{
857
	register_t *ap;
858
	int narg;
859
	char sep;
860
861
4642448
	if (ktr->ktr_argsize > ktrlen)
862
		errx(1, "syscall argument length %d > ktr header length %zu",
863
		    ktr->ktr_argsize, ktrlen);
864
865
2321224
	narg = ktr->ktr_argsize / sizeof(register_t);
866
	sep = '\0';
867
868

4642448
	if (ktr->ktr_code >= SYS_MAXSYSCALL || ktr->ktr_code < 0)
869
		(void)printf("[%d]", ktr->ktr_code);
870
	else
871
2321224
		(void)printf("%s", syscallnames[ktr->ktr_code]);
872
2321224
	ap = (register_t *)((char *)ktr + sizeof(struct ktr_syscall));
873
4642448
	(void)putchar('(');
874
875
2321224
	if (ktr->ktr_code == SYS_sysctl && fancy) {
876
		const char *s;
877
		int n, i, *top;
878
879
2053
		n = ap[1];
880
2053
		if (n > CTL_MAXNAME)
881
			n = CTL_MAXNAME;
882
2053
		if (n < 0)
883
			errx(1, "invalid sysctl length %d", n);
884
2053
		if (n > 0) {
885
2053
			top = (int *)(ap + 6);
886
2053
			printf("%d", top[0]);
887
8212
			for (i = 1; i < n; i++)
888
2053
				printf(".%d", top[i]);
889
2053
			if ((s = kresolvsysctl(0, top)) != NULL) {
890
2053
				printf("<%s", s);
891
8212
				for (i = 1; i < n; i++) {
892
2053
					if ((s = kresolvsysctl(i, top)) != NULL)
893
2053
						printf(".%s", s);
894
					else
895
						printf(".%d", top[i]);
896
				}
897
4106
				putchar('>');
898
			}
899
		}
900
901
		sep = ',';
902
2053
		ap += 2;
903
2053
		narg -= 2;
904
2321224
	} else if (ktr->ktr_code < nitems(scargs)) {
905
2319171
		const formatter *fmts = scargs[ktr->ktr_code];
906
		int fmt;
907
908

24441283
		while (narg && (fmt = *fmts) != 0) {
909
6599395
			if (sep)
910
6990984
				putchar(sep);
911
			sep = ',';
912
6599395
			if (!fancy && !FMT_IS_NONFANCY(fmt))
913
				fmt = Pnonfancy;
914
6599395
			if (fmt > 0)
915
2712604
				formatters[fmt]((int)*ap);
916
3886791
			else if (long_formatters[-fmt](*ap))
917
800646
				sep = '\0';
918
6599395
			fmts++;
919
6599395
			ap++;
920
6599395
			narg--;
921
		}
922
2319171
	}
923
924
2353542
	while (narg > 0) {
925
16159
		if (sep)
926
29674
			putchar(sep);
927
16159
		if (decimal)
928
			(void)printf("%ld", (long)*ap);
929
		else
930
16159
			(void)printf("%#lx", (long)*ap);
931
		sep = ',';
932
16159
		ap++;
933
16159
		narg--;
934
	}
935
2321224
	(void)printf(")\n");
936
2321224
}
937
938
static struct ctlname topname[] = CTL_NAMES;
939
static struct ctlname kernname[] = CTL_KERN_NAMES;
940
static struct ctlname vmname[] = CTL_VM_NAMES;
941
static struct ctlname fsname[] = CTL_FS_NAMES;
942
static struct ctlname netname[] = CTL_NET_NAMES;
943
static struct ctlname hwname[] = CTL_HW_NAMES;
944
static struct ctlname debugname[CTL_DEBUG_MAXID];
945
static struct ctlname kernmallocname[] = CTL_KERN_MALLOC_NAMES;
946
static struct ctlname forkstatname[] = CTL_KERN_FORKSTAT_NAMES;
947
static struct ctlname nchstatsname[] = CTL_KERN_NCHSTATS_NAMES;
948
static struct ctlname kernprocname[] = {
949
	{ NULL },
950
	{ "all" },
951
	{ "pid" },
952
	{ "pgrp" },
953
	{ "session" },
954
	{ "tty" },
955
	{ "uid" },
956
	{ "ruid" },
957
	{ "kthread" },
958
};
959
static struct ctlname ttysname[] = CTL_KERN_TTY_NAMES;
960
static struct ctlname semname[] = CTL_KERN_SEMINFO_NAMES;
961
static struct ctlname shmname[] = CTL_KERN_SHMINFO_NAMES;
962
static struct ctlname watchdogname[] = CTL_KERN_WATCHDOG_NAMES;
963
static struct ctlname tcname[] = CTL_KERN_TIMECOUNTER_NAMES;
964
#ifdef CTL_MACHDEP_NAMES
965
static struct ctlname machdepname[] = CTL_MACHDEP_NAMES;
966
#endif
967
static struct ctlname ddbname[] = CTL_DDB_NAMES;
968
969
#ifndef nitems
970
#define nitems(_a)    (sizeof((_a)) / sizeof((_a)[0]))
971
#endif
972
973
#define SETNAME(name) do { names = (name); limit = nitems(name); } while (0)
974
975
static const char *
976
kresolvsysctl(int depth, const int *top)
977
{
978
	struct ctlname *names;
979
	size_t		limit;
980
10265
	int		idx = top[depth];
981
982
	names = NULL;
983
984

6159
	switch (depth) {
985
	case 0:
986
		SETNAME(topname);
987
2053
		break;
988
	case 1:
989


4106
		switch (top[0]) {
990
		case CTL_KERN:
991
			SETNAME(kernname);
992
1436
			break;
993
		case CTL_VM:
994
			SETNAME(vmname);
995
359
			break;
996
		case CTL_FS:
997
			SETNAME(fsname);
998
			break;
999
		case CTL_NET:
1000
			SETNAME(netname);
1001
			break;
1002
		case CTL_DEBUG:
1003
			SETNAME(debugname);
1004
			break;
1005
		case CTL_HW:
1006
			SETNAME(hwname);
1007
258
			break;
1008
#ifdef CTL_MACHDEP_NAMES
1009
		case CTL_MACHDEP:
1010
			SETNAME(machdepname);
1011
			break;
1012
#endif
1013
		case CTL_DDB:
1014
			SETNAME(ddbname);
1015
			break;
1016
		}
1017
		break;
1018
	case 2:
1019
		switch (top[0]) {
1020
		case CTL_KERN:
1021
			switch (top[1]) {
1022
			case KERN_MALLOCSTATS:
1023
				SETNAME(kernmallocname);
1024
				break;
1025
			case KERN_FORKSTAT:
1026
				SETNAME(forkstatname);
1027
				break;
1028
			case KERN_NCHSTATS:
1029
				SETNAME(nchstatsname);
1030
				break;
1031
			case KERN_TTY:
1032
				SETNAME(ttysname);
1033
				break;
1034
			case KERN_SEMINFO:
1035
				SETNAME(semname);
1036
				break;
1037
			case KERN_SHMINFO:
1038
				SETNAME(shmname);
1039
				break;
1040
			case KERN_WATCHDOG:
1041
				SETNAME(watchdogname);
1042
				break;
1043
			case KERN_PROC:
1044
				idx++;	/* zero is valid at this level */
1045
				SETNAME(kernprocname);
1046
				break;
1047
			case KERN_TIMECOUNTER:
1048
				SETNAME(tcname);
1049
				break;
1050
			}
1051
		}
1052
		break;
1053
	}
1054

8212
	if (names != NULL && idx > 0 && idx < limit)
1055
4106
		return (names[idx].ctl_name);
1056
	return (NULL);
1057
4106
}
1058
1059
static void
1060
ktrsysret(struct ktr_sysret *ktr, size_t ktrlen)
1061
{
1062
	register_t ret = 0;
1063
	long long retll;
1064
4642484
	int error = ktr->ktr_error;
1065
2321242
	int code = ktr->ktr_code;
1066
1067
2321242
	if (ktrlen < sizeof(*ktr))
1068
		errx(1, "sysret length %zu < ktr header length %zu",
1069
		    ktrlen, sizeof(*ktr));
1070
2321242
	ktrlen -= sizeof(*ktr);
1071
2321242
	if (error == 0) {
1072
1422905
		if (ktrlen == sizeof(ret)) {
1073
1422905
			memcpy(&ret, ktr+1, sizeof(ret));
1074
			retll = ret;
1075
1422905
		} else if (ktrlen == sizeof(retll))
1076
			memcpy(&retll, ktr+1, sizeof(retll));
1077
		else
1078
			errx(1, "sysret bogus length %zu", ktrlen);
1079
	}
1080
1081
2321242
	if (code >= SYS_MAXSYSCALL || code < 0)
1082
		(void)printf("[%d] ", code);
1083
	else
1084
2321242
		(void)printf("%s ", syscallnames[code]);
1085
1086
doerr:
1087
2321242
	if (error == 0) {
1088
1422905
		if (fancy) {
1089


1422905
			switch (code) {
1090
			case SYS_lseek:
1091
77048
				(void)printf("%lld", retll);
1092
77048
				if (retll < 0 || retll > 9)
1093
76818
					(void)printf("/%#llx", retll);
1094
				break;
1095
			case SYS_sigprocmask:
1096
			case SYS_sigpending:
1097
3307
				sigset(ret);
1098
3307
				break;
1099
			case SYS___thrsigdivert:
1100
				signame(ret);
1101
				break;
1102
			case SYS_getuid:
1103
			case SYS_geteuid:
1104
604
				uidname(ret);
1105
604
				break;
1106
			case SYS_getgid:
1107
			case SYS_getegid:
1108
604
				gidname(ret);
1109
604
				break;
1110
			/* syscalls that return errno values */
1111
			case SYS_getlogin_r:
1112
			case SYS___thrsleep:
1113
				if ((error = ret) != 0)
1114
					goto doerr;
1115
				/* FALLTHROUGH */
1116
			default:
1117
1341342
				(void)printf("%ld", (long)ret);
1118
1341342
				if (ret < 0 || ret > 9)
1119
344996
					(void)printf("/%#lx", (long)ret);
1120
			}
1121
		} else {
1122
			if (decimal)
1123
				(void)printf("%lld", retll);
1124
			else
1125
				(void)printf("%#llx", retll);
1126
		}
1127
898337
	} else if (error == ERESTART)
1128
731
		(void)printf("RESTART");
1129
897606
	else if (error == EJUSTRETURN)
1130
1532
		(void)printf("JUSTRETURN");
1131
	else {
1132
896074
		(void)printf("-1 errno %d", error);
1133
896074
		if (fancy)
1134
896074
			(void)printf(" %s", strerror(error));
1135
	}
1136
4642484
	(void)putchar('\n');
1137
2321242
}
1138
1139
static void
1140
ktrnamei(const char *cp, size_t len)
1141
{
1142
1983830
	showbufc(basecol, (unsigned char *)cp, len, VIS_DQ | VIS_TAB | VIS_NL);
1143
991915
}
1144
1145
void
1146
showbufc(int col, unsigned char *dp, size_t datalen, int flags)
1147
{
1148
	int width;
1149
2465820
	unsigned char visbuf[5], *cp;
1150
1151
1232910
	flags |= VIS_CSTYLE;
1152
2465820
	putchar('"');
1153
1232910
	col++;
1154
166684282
	for (; datalen > 0; datalen--, dp++) {
1155
82109231
		(void)vis(visbuf, *dp, flags, *(dp+1));
1156
		cp = visbuf;
1157
1158
		/*
1159
		 * Keep track of printables and
1160
		 * space chars (like fold(1)).
1161
		 */
1162
82109231
		if (col == 0) {
1163
527870
			(void)putchar('\t');
1164
			col = 8;
1165
263935
		}
1166
82109231
		switch (*cp) {
1167
		case '\n':
1168
			col = 0;
1169
840648
			(void)putchar('\n');
1170
			continue;
1171
		case '\t':
1172
695128
			width = 8 - (col&07);
1173
695128
			break;
1174
		default:
1175
80993779
			width = strlen(cp);
1176
80993779
		}
1177
81688907
		if (col + width > (screenwidth-2)) {
1178
880008
			(void)printf("\\\n\t");
1179
			col = 8;
1180
880008
		}
1181
81688907
		col += width;
1182
81688907
		do {
1183
268827062
			(void)putchar(*cp++);
1184
134413531
		} while (*cp);
1185
	}
1186
1232910
	if (col == 0)
1187
156389
		(void)printf("       ");
1188
1232910
	(void)printf("\"\n");
1189
1232910
}
1190
1191
static void
1192
showbuf(unsigned char *dp, size_t datalen)
1193
{
1194
	int i, j;
1195
	int col = 0, bpl;
1196
	unsigned char c;
1197
1198
466166
	if (iohex == 1) {
1199
		putchar('\t');
1200
		col = 8;
1201
		for (i = 0; i < datalen; i++) {
1202
			printf("%02x", dp[i]);
1203
			col += 3;
1204
			if (i < datalen - 1) {
1205
				if (col + 3 > screenwidth) {
1206
					printf("\n\t");
1207
					col = 8;
1208
				} else
1209
					putchar(' ');
1210
			}
1211
		}
1212
		putchar('\n');
1213
		return;
1214
	}
1215
233083
	if (iohex == 2) {
1216
		bpl = (screenwidth - 13)/4;
1217
		if (bpl <= 0)
1218
			bpl = 1;
1219
		for (i = 0; i < datalen; i += bpl) {
1220
			printf("   %04x:  ", i);
1221
			for (j = 0; j < bpl; j++) {
1222
				if (i+j >= datalen)
1223
					printf("   ");
1224
				else
1225
					printf("%02x ", dp[i+j]);
1226
			}
1227
			putchar(' ');
1228
			for (j = 0; j < bpl; j++) {
1229
				if (i+j >= datalen)
1230
					break;
1231
				c = dp[i+j];
1232
				if (!isprint(c))
1233
					c = '.';
1234
				putchar(c);
1235
			}
1236
			putchar('\n');
1237
		}
1238
		return;
1239
	}
1240
1241
233083
	(void)printf("       ");
1242
233083
	showbufc(7, dp, datalen, 0);
1243
466166
}
1244
1245
static void
1246
ktrgenio(struct ktr_genio *ktr, size_t len)
1247
{
1248
466166
	unsigned char *dp = (unsigned char *)ktr + sizeof(struct ktr_genio);
1249
	size_t datalen;
1250
1251
233083
	if (len < sizeof(struct ktr_genio))
1252
		errx(1, "invalid ktr genio length %zu", len);
1253
1254
233083
	datalen = len - sizeof(struct ktr_genio);
1255
1256
466166
	printf("fd %d %s %zu bytes\n", ktr->ktr_fd,
1257
233083
		ktr->ktr_rw == UIO_READ ? "read" : "wrote", datalen);
1258
233083
	if (maxdata == 0)
1259
		return;
1260
233083
	if (datalen > maxdata)
1261
		datalen = maxdata;
1262
233083
	if (iohex && !datalen)
1263
		return;
1264
233083
	showbuf(dp, datalen);
1265
466166
}
1266
1267
static void
1268
ktrpsig(struct ktr_psig *psig)
1269
{
1270
3150
	signame(psig->signo);
1271
1575
	printf(" ");
1272
1575
	if (psig->action == SIG_DFL)
1273
33
		(void)printf("SIG_DFL");
1274
	else {
1275
1542
		(void)printf("caught handler=0x%lx mask=",
1276
1542
		    (u_long)psig->action);
1277
1542
		sigset(psig->mask);
1278
	}
1279
1575
	if (psig->code) {
1280
16
		printf(" code ");
1281
16
		if (fancy) {
1282


16
			switch (psig->signo) {
1283
			case SIGILL:
1284
				sigill_name(psig->code);
1285
				break;
1286
			case SIGTRAP:
1287
				sigtrap_name(psig->code);
1288
				break;
1289
			case SIGEMT:
1290
				sigemt_name(psig->code);
1291
				break;
1292
			case SIGFPE:
1293
				sigfpe_name(psig->code);
1294
				break;
1295
			case SIGBUS:
1296
				sigbus_name(psig->code);
1297
				break;
1298
			case SIGSEGV:
1299
				sigsegv_name(psig->code);
1300
				break;
1301
			case SIGCHLD:
1302
				sigchld_name(psig->code);
1303
				break;
1304
			}
1305
		}
1306
16
		printf("<%d>", psig->code);
1307
16
	}
1308
1309

1575
	switch (psig->signo) {
1310
	case SIGSEGV:
1311
	case SIGILL:
1312
	case SIGBUS:
1313
	case SIGFPE:
1314
		printf(" addr=%p trapno=%d", psig->si.si_addr,
1315
		    psig->si.si_trapno);
1316
		break;
1317
	default:
1318
		break;
1319
	}
1320
1575
	printf("\n");
1321
1575
}
1322
1323
static void
1324
ktruser(struct ktr_user *usr, size_t len)
1325
{
1326
	if (len < sizeof(struct ktr_user))
1327
		errx(1, "invalid ktr user length %zu", len);
1328
	len -= sizeof(struct ktr_user);
1329
	printf("%.*s:", KTR_USER_MAXIDLEN, usr->ktr_id);
1330
	printf(" %zu bytes\n", len);
1331
	showbuf((unsigned char *)(usr + 1), len);
1332
}
1333
1334
static void
1335
ktrexec(const char *ptr, size_t len)
1336
{
1337
	int i, col;
1338
	size_t l;
1339
1340
3990
	putchar('\n');
1341
	i = 0;
1342
15840
	while (len > 0) {
1343
6590
		l = strnlen(ptr, len);
1344
6590
		col = printf("\t[%d] = ", i++);
1345
6590
		col += 7;	/* tab expands from 1 to 8 columns */
1346
6590
		showbufc(col, (unsigned char *)ptr, l, VIS_DQ|VIS_TAB|VIS_NL);
1347
6590
		if (l == len) {
1348
			printf("\tunterminated argument\n");
1349
			break;
1350
		}
1351
6590
		len -= l + 1;
1352
6590
		ptr += l + 1;
1353
	}
1354
1330
}
1355
1356
static void
1357
ktrpledge(struct ktr_pledge *pledge, size_t len)
1358
{
1359
	char *name = "";
1360
	int i;
1361
1362
66
	if (len < sizeof(struct ktr_pledge))
1363
		errx(1, "invalid ktr pledge length %zu", len);
1364
1365

66
	if (pledge->syscall >= SYS_MAXSYSCALL || pledge->syscall < 0)
1366
		(void)printf("[%d]", pledge->syscall);
1367
	else
1368
33
		(void)printf("%s", syscallnames[pledge->syscall]);
1369
33
	printf(", ");
1370

792
	for (i = 0; pledge->code && pledgenames[i].bits != 0; i++) {
1371
264
		if (pledgenames[i].bits & pledge->code) {
1372
33
			name = pledgenames[i].name;
1373
33
			break;
1374
		}
1375
	}
1376
33
	printf("\"%s\"", name);
1377
33
	(void)printf(", errno %d", pledge->error);
1378
33
	if (fancy)
1379
33
		(void)printf(" %s", strerror(pledge->error));
1380
33
	printf("\n");
1381
33
}
1382
1383
static void
1384
usage(void)
1385
{
1386
1387
	extern char *__progname;
1388
	fprintf(stderr, "usage: %s "
1389
	    "[-dHlnRTXx] [-f file] [-m maxdata] [-p pid]\n"
1390
	    "%*s[-t [cinpstuxX+]]\n",
1391
	    __progname, (int)(sizeof("usage: ") + strlen(__progname)), "");
1392
	exit(1);
1393
}
1394
1395
1396
/*
1397
 * FORMATTERS
1398
 */
1399
1400
static void
1401
ioctldecode(int cmd)
1402
{
1403
738
	char dirbuf[4], *dir = dirbuf;
1404
	const char *cp;
1405
1406
369
	if ((cp = ioctlname((unsigned)cmd)) != NULL) {
1407
369
		(void)printf("%s", cp);
1408
369
		return;
1409
	}
1410
1411
	if (cmd & IOC_IN)
1412
		*dir++ = 'W';
1413
	if (cmd & IOC_OUT)
1414
		*dir++ = 'R';
1415
	*dir = '\0';
1416
1417
	printf("_IO%s('%c',%d",
1418
	    dirbuf, (int)((cmd >> 8) & 0xff), cmd & 0xff);
1419
	if ((cmd & IOC_VOID) == 0)
1420
		printf(decimal ? ",%u)" : ",%#x)", (cmd >> 16) & 0xff);
1421
	else
1422
		printf(")");
1423
369
}
1424
1425
static void
1426
ptracedecode(int request)
1427
{
1428
	if (request >= 0 && request < nitems(ptrace_ops))
1429
		(void)printf("%s", ptrace_ops[request]);
1430
	else switch(request) {
1431
#ifdef PT_GETFPREGS
1432
	case PT_GETFPREGS:
1433
		(void)printf("PT_GETFPREGS");
1434
		break;
1435
#endif
1436
	case PT_GETREGS:
1437
		(void)printf("PT_GETREGS");
1438
		break;
1439
#ifdef PT_GETXMMREGS
1440
	case PT_GETXMMREGS:
1441
		(void)printf("PT_GETXMMREGS");
1442
		break;
1443
#endif
1444
#ifdef PT_SETFPREGS
1445
	case PT_SETFPREGS:
1446
		(void)printf("PT_SETFPREGS");
1447
		break;
1448
#endif
1449
	case PT_SETREGS:
1450
		(void)printf("PT_SETREGS");
1451
		break;
1452
#ifdef PT_SETXMMREGS
1453
	case PT_SETXMMREGS:
1454
		(void)printf("PT_SETXMMREGS");
1455
		break;
1456
#endif
1457
#ifdef PT_STEP
1458
	case PT_STEP:
1459
		(void)printf("PT_STEP");
1460
		break;
1461
#endif
1462
#ifdef PT_WCOOKIE
1463
	case PT_WCOOKIE:
1464
		(void)printf("PT_WCOOKIE");
1465
		break;
1466
#endif
1467
	default:
1468
		pdecint(request);
1469
	}
1470
}
1471
1472
1473
static void
1474
atfd(int fd)
1475
{
1476
	if (fd == AT_FDCWD)
1477
		(void)printf("AT_FDCWD");
1478
	else
1479
		pdecint(fd);
1480
}
1481
1482
static void
1483
polltimeout(int timeout)
1484
{
1485
30
	if (timeout == INFTIM)
1486
		(void)printf("INFTIM");
1487
	else
1488
15
		pdecint(timeout);
1489
15
}
1490
1491
static void
1492
wait4pid(int pid)
1493
{
1494
3130
	if (pid == WAIT_ANY)
1495
1540
		(void)printf("WAIT_ANY");
1496
25
	else if (pid == WAIT_MYPGRP)
1497
		(void)printf("WAIT_MYPGRP");
1498
	else
1499
25
		pdecint(pid);		/* ppgid */
1500
1565
}
1501
1502
static void
1503
signame(int sig)
1504
{
1505
54596
	if (sig > 0 && sig < NSIG)
1506
27298
		(void)printf("SIG%s", sys_signame[sig]);
1507
	else
1508
		(void)printf("SIG %d", sig);
1509
27298
}
1510
1511
void
1512
sigset(int ss)
1513
{
1514
	int	or = 0;
1515
	int	cnt = 0;
1516
	int	i;
1517
1518
2135760
	for (i = 1; i < NSIG; i++)
1519
1035520
		if (sigismember(&ss, i))
1520
45147
			cnt++;
1521
32360
	if (cnt > (NSIG-1)/2) {
1522
1338
		ss = ~ss;
1523
2676
		putchar('~');
1524
	}
1525
1526
32360
	if (ss == 0) {
1527
27353
		(void)printf("0<>");
1528
27353
		return;
1529
	}
1530
1531
5007
	printf("%#x<", ss);
1532
330462
	for (i = 1; i < NSIG; i++)
1533
160224
		if (sigismember(&ss, i)) {
1534

5007
			if (or) putchar('|'); else or=1;
1535
5007
			signame(i);
1536
5007
		}
1537
5007
	printf(">");
1538
37367
}
1539
1540
static void
1541
semctlname(int cmd)
1542
{
1543
	switch (cmd) {
1544
	case GETNCNT:
1545
		(void)printf("GETNCNT");
1546
		break;
1547
	case GETPID:
1548
		(void)printf("GETPID");
1549
		break;
1550
	case GETVAL:
1551
		(void)printf("GETVAL");
1552
		break;
1553
	case GETALL:
1554
		(void)printf("GETALL");
1555
		break;
1556
	case GETZCNT:
1557
		(void)printf("GETZCNT");
1558
		break;
1559
	case SETVAL:
1560
		(void)printf("SETVAL");
1561
		break;
1562
	case SETALL:
1563
		(void)printf("SETALL");
1564
		break;
1565
	case IPC_RMID:
1566
		(void)printf("IPC_RMID");
1567
		break;
1568
	case IPC_SET:
1569
		(void)printf("IPC_SET");
1570
		break;
1571
	case IPC_STAT:
1572
		(void)printf("IPC_STAT");
1573
		break;
1574
	default: /* Should not reach */
1575
		(void)printf("<invalid=%d>", cmd);
1576
	}
1577
}
1578
1579
static void
1580
shmctlname(int cmd)
1581
{
1582
	switch (cmd) {
1583
	case IPC_RMID:
1584
		(void)printf("IPC_RMID");
1585
		break;
1586
	case IPC_SET:
1587
		(void)printf("IPC_SET");
1588
		break;
1589
	case IPC_STAT:
1590
		(void)printf("IPC_STAT");
1591
		break;
1592
	default: /* Should not reach */
1593
		(void)printf("<invalid=%d>", cmd);
1594
	}
1595
}
1596
1597
1598
static void
1599
semgetname(int flag)
1600
{
1601
	int	or = 0;
1602
	if_print_or(flag, IPC_CREAT, or);
1603
	if_print_or(flag, IPC_EXCL, or);
1604
	if_print_or(flag, SEM_R, or);
1605
	if_print_or(flag, SEM_A, or);
1606
	if_print_or(flag, (SEM_R>>3), or);
1607
	if_print_or(flag, (SEM_A>>3), or);
1608
	if_print_or(flag, (SEM_R>>6), or);
1609
	if_print_or(flag, (SEM_A>>6), or);
1610
1611
	if (flag & ~(IPC_CREAT|IPC_EXCL|SEM_R|SEM_A|((SEM_R|SEM_A)>>3)|
1612
	    ((SEM_R|SEM_A)>>6)))
1613
		printf("<invalid=%#x>", flag);
1614
}
1615
1616
1617
/*
1618
 * Only used by SYS_open and SYS_openat. Unless O_CREAT is set in flags, the
1619
 * mode argument is unused (and often bogus and misleading).
1620
 */
1621
static void
1622
flagsandmodename(int mode)
1623
{
1624
943372
	openflagsname(arg1);
1625
471686
	if ((arg1 & O_CREAT) == O_CREAT) {
1626
509074
		(void)putchar(',');
1627
254537
		modename(mode);
1628
471686
	} else if (!fancy)
1629
		(void)printf(",<unused>%#o", mode);
1630
471686
}
1631
1632
static void
1633
clockname(int clockid)
1634
{
1635
13676
	clocktypename(__CLOCK_TYPE(clockid));
1636
6838
	if (__CLOCK_PTID(clockid) != 0)
1637
		printf("(%d)", __CLOCK_PTID(clockid));
1638
6838
}
1639
1640
/*
1641
 * [g|s]etsockopt's level argument can either be SOL_SOCKET or a value
1642
 * referring to a line in /etc/protocols.
1643
 */
1644
static void
1645
sockoptlevelname(int optname)
1646
{
1647
	struct protoent *pe;
1648
1649
14526
	if (arg1 == SOL_SOCKET) {
1650
7263
		(void)printf("SOL_SOCKET,");
1651
7263
		sockoptname(optname);
1652
7263
	} else {
1653
		pe = getprotobynumber(arg1);
1654
		(void)printf("%u<%s>,%d", arg1,
1655
		    pe != NULL ? pe->p_name : "unknown", optname);
1656
	}
1657
7263
}
1658
1659
static void
1660
ktraceopname(int ops)
1661
{
1662
	int invalid = 0;
1663
1664
	printf("%#x<", ops);
1665
	switch (KTROP(ops)) {
1666
	case KTROP_SET:
1667
		printf("KTROP_SET");
1668
		break;
1669
	case KTROP_CLEAR:
1670
		printf("KTROP_CLEAR");
1671
		break;
1672
	case KTROP_CLEARFILE:
1673
		printf("KTROP_CLEARFILE");
1674
		break;
1675
	default:
1676
		printf("KTROP(%d)", KTROP(ops));
1677
		invalid = 1;
1678
		break;
1679
	}
1680
	if (ops & KTRFLAG_DESCEND) printf("|KTRFLAG_DESCEND");
1681
	printf(">");
1682
	if (invalid || (ops & ~(KTROP((unsigned)-1) | KTRFLAG_DESCEND)))
1683
		(void)printf("<invalid>%d", ops);
1684
}