From: Antonio Huete Jimenez Date: Sun, 19 Sep 2010 00:44:12 +0000 (+0200) Subject: truss - Group some globals into a struct. X-Git-Tag: v2.9.0~128^2~1 X-Git-Url: https://gitweb.dragonflybsd.org/dragonfly.git/commitdiff_plain/283e0ddf5d60ab16a0eb7a22e5b2700dec074ae7 truss - Group some globals into a struct. Taken-from: FreeBSD --- diff --git a/usr.bin/truss/extern.h b/usr.bin/truss/extern.h index 98801f341a..1a0ded340d 100644 --- a/usr.bin/truss/extern.h +++ b/usr.bin/truss/extern.h @@ -44,8 +44,8 @@ extern int start_tracing(int, int); extern void restore_proc(int); extern const char *ioctlname(register_t val); #ifdef __i386__ -extern void i386_syscall_entry(int, int); -extern void i386_syscall_exit(int, int); -extern void i386_linux_syscall_entry(int, int); -extern void i386_linux_syscall_exit(int, int); +extern void i386_syscall_entry(struct trussinfo *, int); +extern int i386_syscall_exit(struct trussinfo *, int); +extern void i386_linux_syscall_entry(struct trussinfo *, int); +extern int i386_linux_syscall_exit(struct trussinfo *, int); #endif diff --git a/usr.bin/truss/i386-fbsd.c b/usr.bin/truss/i386-fbsd.c index c89e8772ac..081324f370 100644 --- a/usr.bin/truss/i386-fbsd.c +++ b/usr.bin/truss/i386-fbsd.c @@ -57,13 +57,13 @@ #include #include +#include "truss.h" #include "extern.h" #include "syscall.h" static int fd = -1; static int cpid = -1; -extern FILE *outfile; #include "syscalls.h" static int nsyscalls = sizeof(syscallnames) / sizeof(syscallnames[0]); @@ -110,7 +110,7 @@ clear_fsc(void) { */ void -i386_syscall_entry(int pid, int nargs) { +i386_syscall_entry(struct trussinfo *trussinfo, int nargs) { char *buf; struct reg regs = { .r_err = 0 }; int syscall_num; @@ -118,17 +118,17 @@ i386_syscall_entry(int pid, int nargs) { unsigned int parm_offset; struct syscall *sc; - if (fd == -1 || pid != cpid) { - asprintf(&buf, "%s/%d/regs", procfs_path, pid); + if (fd == -1 || trussinfo->pid != cpid) { + asprintf(&buf, "%s/%d/regs", procfs_path, trussinfo->pid); if (buf == NULL) err(1, "Out of memory"); fd = open(buf, O_RDWR); free(buf); if (fd == -1) { - fprintf(outfile, "-- CANNOT READ REGISTERS --\n"); + fprintf(trussinfo->outfile, "-- CANNOT READ REGISTERS --\n"); return; } - cpid = pid; + cpid = trussinfo->pid; } clear_fsc(); @@ -159,7 +159,7 @@ i386_syscall_entry(int pid, int nargs) { fsc.name = (syscall_num < 0 || syscall_num >= nsyscalls) ? NULL : syscallnames[syscall_num]; if (!fsc.name) { - fprintf(outfile, "-- UNKNOWN SYSCALL %d --\n", syscall_num); + fprintf(trussinfo->outfile, "-- UNKNOWN SYSCALL %d --\n", syscall_num); } if (nargs == 0) @@ -175,7 +175,7 @@ i386_syscall_entry(int pid, int nargs) { fsc.nargs = sc->nargs; } else { #if DEBUG - fprintf(outfile, "unknown syscall %s -- setting args to %d\n", + fprintf(trussinfo->trussinfo->outfile, "unknown syscall %s -- setting args to %d\n", fsc.name, nargs); #endif fsc.nargs = nargs; @@ -216,7 +216,7 @@ i386_syscall_entry(int pid, int nargs) { } #if DEBUG - fprintf(outfile, "\n"); + fprintf(trussinfo->trussinfo->outfile, "\n"); #endif /* @@ -228,7 +228,7 @@ i386_syscall_entry(int pid, int nargs) { if (fsc.name != NULL && (!strcmp(fsc.name, "execve") || !strcmp(fsc.name, "exit"))) { - print_syscall(outfile, fsc.name, fsc.nargs, fsc.s_args); + print_syscall(trussinfo, fsc.name, fsc.nargs, fsc.s_args); } return; @@ -241,8 +241,8 @@ i386_syscall_entry(int pid, int nargs) { * the sytem call number instead of, say, an error status). */ -void -i386_syscall_exit(int pid, int syscall_num __unused) { +int +i386_syscall_exit(struct trussinfo *trussinfo, int syscall_num __unused) { char *buf; struct reg regs; int retval; @@ -251,24 +251,26 @@ i386_syscall_exit(int pid, int syscall_num __unused) { struct syscall *sc; if (fsc.name == NULL) - return; + return 0; - if (fd == -1 || pid != cpid) { - asprintf(&buf, "%s/%d/regs", procfs_path, pid); + if (fd == -1 || trussinfo->pid != cpid) { + asprintf(&buf, "%s/%d/regs", procfs_path, trussinfo->pid); if (buf == NULL) err(1, "Out of memory"); fd = open(buf, O_RDONLY); free(buf); if (fd == -1) { - fprintf(outfile, "-- CANNOT READ REGISTERS --\n"); - return; + fprintf(trussinfo->outfile, "-- CANNOT READ REGISTERS --\n"); + return 0; } - cpid = pid; + cpid = trussinfo->pid; } lseek(fd, 0L, 0); - if (read(fd, ®s, sizeof(regs)) != sizeof(regs)) - return; + if (read(fd, ®s, sizeof(regs)) != sizeof(regs)) { + fprintf(trussinfo->outfile, "\n"); + return 0; + } retval = regs.r_eax; errorp = !!(regs.r_eflags & PSL_C); @@ -311,8 +313,8 @@ i386_syscall_exit(int pid, int syscall_num __unused) { * but that complicates things considerably. */ - print_syscall_ret(outfile, fsc.name, fsc.nargs, fsc.s_args, errorp, retval); + print_syscall_ret(trussinfo, fsc.name, fsc.nargs, fsc.s_args, errorp, retval); clear_fsc(); - return; + return (retval); } diff --git a/usr.bin/truss/i386-linux.c b/usr.bin/truss/i386-linux.c index 7336aa705f..535a29bbd9 100644 --- a/usr.bin/truss/i386-linux.c +++ b/usr.bin/truss/i386-linux.c @@ -54,13 +54,13 @@ #include #include +#include "truss.h" #include "extern.h" #include "syscall.h" static int fd = -1; static int cpid = -1; -extern FILE *outfile; #include "linux_syscalls.h" static int nsyscalls = @@ -89,24 +89,24 @@ clear_lsc(void) { } void -i386_linux_syscall_entry(int pid, int nargs) { +i386_linux_syscall_entry(struct trussinfo *trussinfo, int nargs) { char *buf; struct reg regs = { .r_err = 0 }; int syscall_num; int i; struct syscall *sc; - if (fd == -1 || pid != cpid) { - asprintf(&buf, "%s/%d/regs", procfs_path, pid); + if (fd == -1 || trussinfo->pid != cpid) { + asprintf(&buf, "%s/%d/regs", procfs_path, trussinfo->pid); if (buf == NULL) err(1, "Out of memory"); fd = open(buf, O_RDWR); free(buf); if (fd == -1) { - fprintf(outfile, "-- CANNOT READ REGISTERS --\n"); + fprintf(trussinfo->outfile, "-- CANNOT READ REGISTERS --\n"); return; } - cpid = pid; + cpid = trussinfo->pid; } clear_lsc(); @@ -118,7 +118,7 @@ i386_linux_syscall_entry(int pid, int nargs) { lsc.name = (syscall_num < 0 || syscall_num >= nsyscalls) ? NULL : linux_syscallnames[syscall_num]; if (!lsc.name) { - fprintf (outfile, "-- UNKNOWN SYSCALL %d\n", syscall_num); + fprintf (trussinfo->outfile, "-- UNKNOWN SYSCALL %d\n", syscall_num); } if (nargs == 0) @@ -143,7 +143,7 @@ i386_linux_syscall_entry(int pid, int nargs) { lsc.nargs = sc->nargs; } else { #ifdef DEBUG - fprintf(outfile, "unknown syscall %s -- setting args to %d\n", + fprintf(trussinfo->outfile, "unknown syscall %s -- setting args to %d\n", lsc.name, nargs); #endif lsc.nargs = nargs; @@ -176,7 +176,7 @@ i386_linux_syscall_entry(int pid, int nargs) { } if (!strcmp(lsc.name, "linux_execve") || !strcmp(lsc.name, "exit")) { - print_syscall(outfile, lsc.name, lsc.nargs, lsc.s_args); + print_syscall(trussinfo, lsc.name, lsc.nargs, lsc.s_args); } return; @@ -197,8 +197,8 @@ const int bsd_to_linux_errno[] = { -6, }; -void -i386_linux_syscall_exit(int pid, int syscall_num __unused) { +int +i386_linux_syscall_exit(struct trussinfo *trussinfo, int syscall_num __unused) { char *buf; struct reg regs; int retval; @@ -206,22 +206,24 @@ i386_linux_syscall_exit(int pid, int syscall_num __unused) { int errorp; struct syscall *sc; - if (fd == -1 || pid != cpid) { - asprintf(&buf, "%s/%d/regs", procfs_path, pid); + if (fd == -1 || trussinfo->pid != cpid) { + asprintf(&buf, "%s/%d/regs", procfs_path, trussinfo->pid); if (buf == NULL) err(1, "Out of memory"); fd = open(buf, O_RDONLY); free(buf); if (fd == -1) { - fprintf(outfile, "-- CANNOT READ REGISTERS --\n"); - return; + fprintf(trussinfo->outfile, "-- CANNOT READ REGISTERS --\n"); + return 0; } - cpid = pid; + cpid = trussinfo->pid; } lseek(fd, 0L, 0); - if (read(fd, ®s, sizeof(regs)) != sizeof(regs)) - return; + if (read(fd, ®s, sizeof(regs)) != sizeof(regs)) { + fprintf(trussinfo->outfile, "\n"); + return 0; + } retval = regs.r_eax; errorp = !!(regs.r_eflags & PSL_C); @@ -251,8 +253,8 @@ i386_linux_syscall_exit(int pid, int syscall_num __unused) { if (retval == bsd_to_linux_errno[i]) break; } - print_syscall_ret(outfile, lsc.name, lsc.nargs, lsc.s_args, errorp, + print_syscall_ret(trussinfo, lsc.name, lsc.nargs, lsc.s_args, errorp, errorp ? i : retval); clear_lsc(); - return; + return (retval); } diff --git a/usr.bin/truss/main.c b/usr.bin/truss/main.c index 158e82cd68..9efa056970 100644 --- a/usr.bin/truss/main.c +++ b/usr.bin/truss/main.c @@ -53,6 +53,7 @@ #include #include +#include "truss.h" #include "extern.h" /* @@ -60,9 +61,6 @@ * but this is the easiest way, right now, to deal with them. */ -int pid = 0; -int nosigs = 0; -FILE *outfile; int Procfd; static inline void @@ -80,8 +78,8 @@ usage(void) */ struct ex_types { const char *type; - void (*enter_syscall)(int, int); - void (*exit_syscall)(int, int); + void (*enter_syscall)(struct trussinfo *, int); + int (*exit_syscall)(struct trussinfo *, int); } ex_types[] = { #ifdef __i386__ { "FreeBSD a.out", i386_syscall_entry, i386_syscall_exit }, @@ -98,13 +96,13 @@ struct ex_types { */ static struct ex_types * -set_etype(void) { +set_etype(struct trussinfo *trussinfo) { struct ex_types *funcs; char *etype; char progt[32]; int fd; - asprintf(&etype, "%s/%d/etype", procfs_path, pid); + asprintf(&etype, "%s/%d/etype", procfs_path, trussinfo->pid); if (etype == NULL) err(1, "Out of memory"); if ((fd = open(etype, O_RDONLY)) == -1) { @@ -138,30 +136,37 @@ main(int ac, char **av) { int in_exec = 0; char *fname = NULL; int sigexit = 0; + struct trussinfo *trussinfo; - /* Check where procfs is mounted if it is mounted */ - if ((mntsize = getmntinfo(&mntbuf, MNT_NOWAIT)) == 0) - err(1, "getmntinfo"); - for (i = 0; i < mntsize; i++) { - if (strcasecmp(mntbuf[i].f_mntfromname, "procfs") == 0) { - strlcpy(procfs_path, mntbuf[i].f_mntonname, sizeof(procfs_path)); - have_procfs = 1; - break; - } - } - if (!have_procfs) { - errno = 2; - err(1, "You must have a mounted procfs to use truss"); - } + /* Initialize the trussinfo struct */ + trussinfo = (struct trussinfo *)malloc(sizeof(struct trussinfo)); + if (trussinfo == NULL) + errx(1, "malloc() failed"); + bzero(trussinfo, sizeof(struct trussinfo)); + trussinfo->outfile = stderr; + + /* Check where procfs is mounted if it is mounted */ + if ((mntsize = getmntinfo(&mntbuf, MNT_NOWAIT)) == 0) + err(1, "getmntinfo"); + for (i = 0; i < mntsize; i++) { + if (strcasecmp(mntbuf[i].f_mntfromname, "procfs") == 0) { + strlcpy(procfs_path, mntbuf[i].f_mntonname, sizeof(procfs_path)); + have_procfs = 1; + break; + } + } + if (!have_procfs) { + errno = 2; + err(1, "You must have a mounted procfs to use truss"); + } - outfile = stderr; while ((c = getopt(ac, av, "p:o:S")) != -1) { switch (c) { case 'p': /* specified pid */ - pid = atoi(optarg); - if (pid == getpid()) { + trussinfo->pid = atoi(optarg); + if (trussinfo->pid == getpid()) { /* make sure truss doesn't trace itself */ - fprintf(stderr, "truss: attempt to self trace: %d\n", pid); + fprintf(stderr, "truss: attempt to self trace: %d\n", trussinfo->pid); exit(2); } break; @@ -169,7 +174,7 @@ main(int ac, char **av) { fname = optarg; break; case 'S': /* Don't trace signals */ - nosigs = 1; + trussinfo->flags |= NOSIGS; break; default: usage(); @@ -177,11 +182,11 @@ main(int ac, char **av) { } ac -= optind; av += optind; - if ((pid == 0 && ac == 0) || (pid != 0 && ac != 0)) + if ((trussinfo->pid == 0 && ac == 0) || (trussinfo->pid != 0 && ac != 0)) usage(); if (fname != NULL) { /* Use output file */ - if ((outfile = fopen(fname, "w")) == NULL) + if ((trussinfo->outfile = fopen(fname, "w")) == NULL) errx(1, "cannot open %s", fname); } @@ -192,9 +197,9 @@ main(int ac, char **av) { * then we restore the event mask on these same signals. */ - if (pid == 0) { /* Start a command ourselves */ + if (trussinfo->pid == 0) { /* Start a command ourselves */ command = av; - pid = setup_and_wait(command); + trussinfo->pid = setup_and_wait(command); signal(SIGINT, SIG_IGN); signal(SIGTERM, SIG_IGN); signal(SIGQUIT, SIG_IGN); @@ -210,14 +215,15 @@ main(int ac, char **av) { * be woken up, either in exit() or in execve(). */ - Procfd = start_tracing(pid, S_EXEC | S_SCE | S_SCX | S_CORE | S_EXIT | - (nosigs ? 0 : S_SIG)); + Procfd = start_tracing( + trussinfo->pid, S_EXEC | S_SCE | S_SCX | S_CORE | S_EXIT | + ((trussinfo->flags & NOSIGS) ? 0 : S_SIG)); if (Procfd == -1) return 0; pfs.why = 0; - funcs = set_etype(); + funcs = set_etype(trussinfo); /* * At this point, it's a simple loop, waiting for the process to * stop, finding out why, printing out why, and then continuing it. @@ -232,7 +238,7 @@ main(int ac, char **av) { else { switch(i = pfs.why) { case S_SCE: - funcs->enter_syscall(pid, pfs.val); + funcs->enter_syscall(trussinfo, pfs.val); break; case S_SCX: /* @@ -246,32 +252,32 @@ main(int ac, char **av) { in_exec = 0; break; } - funcs->exit_syscall(pid, pfs.val); + funcs->exit_syscall(trussinfo, pfs.val); break; case S_SIG: - fprintf(outfile, "SIGNAL %lu\n", pfs.val); + fprintf(trussinfo->outfile, "SIGNAL %lu\n", pfs.val); sigexit = pfs.val; break; case S_EXIT: - fprintf (outfile, "process exit, rval = %lu\n", pfs.val); + fprintf (trussinfo->outfile, "process exit, rval = %lu\n", pfs.val); break; case S_EXEC: - funcs = set_etype(); + funcs = set_etype(trussinfo); in_exec = 1; break; default: - fprintf (outfile, "Process stopped because of: %d\n", i); + fprintf (trussinfo->outfile, "Process stopped because of: %d\n", i); break; } } if (ioctl(Procfd, PIOCCONT, val) == -1) { - if (kill(pid, 0) == -1 && errno == ESRCH) + if (kill(trussinfo->pid, 0) == -1 && errno == ESRCH) break; else warn("PIOCCONT"); } } while (pfs.why != S_EXIT); - fflush(outfile); + fflush(trussinfo->outfile); if (sigexit) { if (sigexit == SIGQUIT) exit(sigexit); diff --git a/usr.bin/truss/setup.c b/usr.bin/truss/setup.c index 3e0a4cf969..faff77f60b 100644 --- a/usr.bin/truss/setup.c +++ b/usr.bin/truss/setup.c @@ -51,6 +51,7 @@ #include #include +#include "truss.h" #include "extern.h" static int evflags = 0; diff --git a/usr.bin/truss/syscall.h b/usr.bin/truss/syscall.h index 3689d9eede..7c90a6d10a 100644 --- a/usr.bin/truss/syscall.h +++ b/usr.bin/truss/syscall.h @@ -45,5 +45,5 @@ struct syscall { struct syscall *get_syscall(const char*); char *get_string(int, void*, int); char *print_arg(int, struct syscall_args *, unsigned long*); -void print_syscall(FILE *, const char *, int, char **); -void print_syscall_ret(FILE *, const char *, int, char **, int, int); +void print_syscall(struct trussinfo *, const char *, int, char **); +void print_syscall_ret(struct trussinfo *, const char *, int, char **, int, int); diff --git a/usr.bin/truss/syscalls.c b/usr.bin/truss/syscalls.c index 910a540668..d2f3112bfb 100644 --- a/usr.bin/truss/syscalls.c +++ b/usr.bin/truss/syscalls.c @@ -51,6 +51,7 @@ #include #include +#include "truss.h" #include "extern.h" #include "syscall.h" @@ -346,34 +347,34 @@ print_arg(int fd, struct syscall_args *sc, unsigned long *args) { /* * print_syscall - * Print (to outfile) the system call and its arguments. Note that + * Print (to trussinfo->outfile) the system call and its arguments. Note that * nargs is the number of arguments (not the number of words; this is * potentially confusing, I know). */ void -print_syscall(FILE *outfile, const char *name, int nargs, char **s_args) { +print_syscall(struct trussinfo *trussinfo, const char *name, int nargs, char **s_args) { int i; int len = 0; - len += fprintf(outfile, "%s(", name); + len += fprintf(trussinfo->outfile, "%s(", name); for (i = 0; i < nargs; i++) { if (s_args[i]) - len += fprintf(outfile, "%s", s_args[i]); + len += fprintf(trussinfo->outfile, "%s", s_args[i]); else - len += fprintf(outfile, ""); - len += fprintf(outfile, "%s", i < (nargs - 1) ? "," : ""); + len += fprintf(trussinfo->outfile, ""); + len += fprintf(trussinfo->outfile, "%s", i < (nargs - 1) ? "," : ""); } - len += fprintf(outfile, ")"); + len += fprintf(trussinfo->outfile, ")"); for (i = 0; i < 6 - (len / 8); i++) - fprintf(outfile, "\t"); + fprintf(trussinfo->outfile, "\t"); } void -print_syscall_ret(FILE *outfile, const char *name, int nargs, char **s_args, int errorp, int retval) { - print_syscall(outfile, name, nargs, s_args); +print_syscall_ret(struct trussinfo *trussinfo, const char *name, int nargs, char **s_args, int errorp, int retval) { + print_syscall(trussinfo, name, nargs, s_args); if (errorp) { - fprintf(outfile, " ERR#%d '%s'\n", retval, strerror(retval)); + fprintf(trussinfo->outfile, " ERR#%d '%s'\n", retval, strerror(retval)); } else { - fprintf(outfile, " = %d (0x%x)\n", retval, retval); + fprintf(trussinfo->outfile, " = %d (0x%x)\n", retval, retval); } } diff --git a/usr.bin/truss/extern.h b/usr.bin/truss/truss.h similarity index 56% copy from usr.bin/truss/extern.h copy to usr.bin/truss/truss.h index 98801f341a..05659f922e 100644 --- a/usr.bin/truss/extern.h +++ b/usr.bin/truss/truss.h @@ -1,5 +1,5 @@ /* - * Copryight 1997 Sean Eric Fagan + * Copryight 2001 Jamey Wood * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -9,12 +9,6 @@ * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. - * 3. All advertising materials mentioning features or use of this software - * must display the following acknowledgement: - * This product includes software developed by Sean Eric Fagan - * 4. Neither the name of the author may be used to endorse or promote - * products derived from this software without specific prior written - * permission. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE @@ -28,24 +22,24 @@ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * - * $FreeBSD: src/usr.bin/truss/extern.h,v 1.1.2.1 2002/02/15 11:43:51 des Exp $ - * $DragonFly: src/usr.bin/truss/extern.h,v 1.4 2005/05/28 00:22:04 swildner Exp $ + * $FreeBSD: src/usr.bin/truss/truss.h,v 1.1 2002/08/04 00:46:48 mdodd Exp $ */ -#include +#define FOLLOWFORKS 0x00000001 +#define RELATIVETIMESTAMPS 0x00000002 +#define ABSOLUTETIMESTAMPS 0x00000004 +#define NOSIGS 0x00000008 +#define EXECVEARGS 0x00000010 +#define EXECVEENVS 0x00000020 -char procfs_path[FILENAME_MAX]; -int have_procfs; +struct trussinfo +{ + int pid; + int flags; + int in_fork; + FILE *outfile; -extern int Procfd; - -extern int setup_and_wait(char **); -extern int start_tracing(int, int); -extern void restore_proc(int); -extern const char *ioctlname(register_t val); -#ifdef __i386__ -extern void i386_syscall_entry(int, int); -extern void i386_syscall_exit(int, int); -extern void i386_linux_syscall_entry(int, int); -extern void i386_linux_syscall_exit(int, int); -#endif + struct timespec start_time; + struct timespec before; + struct timespec after; +};