1 /* Machine independent support for SVR4 /proc (process file system) for GDB.
2 Copyright 1999 Free Software Foundation, Inc.
3 Written by Michael Snyder at Cygnus Solutions.
4 Based on work by Fred Fish, Stu Grossman, Geoff Noer, and others.
6 This file is part of GDB.
8 This program is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 2 of the License, or
11 (at your option) any later version.
13 This program is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
18 You should have received a copy of the GNU General Public License
19 along with this program; if not, write to the Free Software Foundation,
20 Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
23 * Pretty-print trace of api calls to the /proc api
24 * (ioctl or read/write calls).
31 #if defined (NEW_PROC_API)
32 #define _STRUCTURED_PROC 1
36 #include <sys/types.h>
37 #include <sys/procfs.h>
38 #include <sys/proc.h> /* for struct proc */
39 #ifdef HAVE_SYS_USER_H
40 #include <sys/user.h> /* for struct user */
42 #include <fcntl.h> /* for O_RDWR etc. */
45 #include "proc-utils.h"
47 /* Much of the information used in the /proc interface, particularly for
48 printing status information, is kept as tables of structures of the
49 following form. These tables can be used to map numeric values to
50 their symbolic names and to a string that describes their specific use. */
53 long value; /* The numeric value */
54 char *name; /* The equivalent symbolic value */
55 char *desc; /* Short description of value */
58 static int procfs_trace = 0;
59 static FILE *procfs_file = NULL;
60 static char *procfs_filename = "procfs_trace";
63 prepare_to_trace (void)
65 if (procfs_trace) /* if procfs tracing turned on */
66 if (procfs_file == NULL) /* if output file not yet open */
67 if (procfs_filename != NULL) /* if output filename known */
68 procfs_file = fopen (procfs_filename, "a"); /* open output file */
72 set_procfs_trace_cmd (char *args, int from_tty, struct cmd_list_element *c)
74 #if 0 /* not sure what I might actually need to do here, if anything */
81 set_procfs_file_cmd (char *args, int from_tty, struct cmd_list_element *c)
83 /* Just changed the filename for procfs tracing.
84 If a file was already open, close it. */
93 static struct trans ioctl_table[] = {
94 #ifdef PIOCACINFO /* irix */
95 { PIOCACINFO, "PIOCACINFO", "get process account info" },
97 { PIOCACTION, "PIOCACTION", "get signal action structs" },
98 #ifdef PIOCARGUMENTS /* osf */
99 { PIOCARGUMENTS, "PIOCARGUMENTS", "command line args" },
101 #ifdef PIOCAUXV /* solaris aux vectors */
102 { PIOCAUXV, "PIOCAUXV", "get aux vector" },
103 { PIOCNAUXV, "PIOCNAUXV", "get number of aux vector entries" },
105 { PIOCCFAULT, "PIOCCFAULT", "clear current fault" },
106 { PIOCCRED, "PIOCCRED", "get process credentials" },
107 #ifdef PIOCENEVCTRS /* irix event counters */
108 { PIOCENEVCTRS, "PIOCENEVCTRS", "acquire and start event counters" },
109 { PIOCGETEVCTRL, "PIOCGETEVCTRL", "get control info of event counters" },
110 { PIOCGETEVCTRS, "PIOCGETEVCTRS", "dump event counters" },
111 { PIOCGETPREVCTRS, "PIOCGETPREVCTRS", "dump event counters & prusage info" },
112 { PIOCRELEVCTRS, "PIOCRELEVCTRS", "release/stop event counters" },
113 { PIOCSETEVCTRL, "PIOCSETEVCTRL", "set control info of event counters" },
114 { PIOCGETPTIMER, "PIOCGETPTIMER", "get process timers" },
115 #endif /* irix event counters */
116 { PIOCGENTRY, "PIOCGENTRY", "get traced syscall entry set" },
117 #if defined (PIOCGETPR)
118 { PIOCGETPR, "PIOCGETPR", "read struct proc" },
120 #if defined (PIOCGETU)
121 { PIOCGETU, "PIOCGETU", "read user area" },
123 #if defined (PIOCGETUTK) && (defined(KERNEL) || defined(SHOW_UTT)) /* osf */
124 { PIOCGETUTK, "PIOCGETUTK", "get the utask struct" },
126 { PIOCGEXIT, "PIOCGEXIT", "get traced syscall exit set" },
127 { PIOCGFAULT, "PIOCGFAULT", "get traced fault set" },
128 #ifdef PIOCGFPCR /* osf */
129 { PIOCGFPCR, "PIOCGFPCR", "get FP control register" },
130 { PIOCSFPCR, "PIOCSFPCR", "set FP conrtol register" },
132 { PIOCGFPREG, "PIOCGFPREG", "get floating point registers" },
133 { PIOCGHOLD, "PIOCGHOLD", "get held signal set" },
134 { PIOCGREG, "PIOCGREG", "get general registers" },
135 { PIOCGROUPS, "PIOCGROUPS", "get supplementary groups" },
136 #ifdef PIOCGSPCACT /* osf */
137 { PIOCGSPCACT, "PIOCGSPCACT", "get special action" },
138 { PIOCSSPCACT, "PIOCSSPCACT", "set special action" },
140 { PIOCGTRACE, "PIOCGTRACE", "get traced signal set" },
141 #ifdef PIOCGWATCH /* irix watchpoints */
142 { PIOCGWATCH, "PIOCGWATCH", "get watchpoint" },
143 { PIOCSWATCH, "PIOCSWATCH", "set watchpoint" },
144 { PIOCNWATCH, "PIOCNWATCH", "get number of watchpoints" },
145 #endif /* irix watchpoints */
146 #ifdef PIOCGWIN /* solaris sparc */
147 { PIOCGWIN, "PIOCGWIN", "get gwindows_t" },
149 #ifdef PIOCGXREG /* solaris sparc extra regs */
150 { PIOCGXREGSIZE, "PIOCXREGSIZE", "get extra register state size" },
151 { PIOCGXREG, "PIOCGXREG", "get extra register state" },
152 { PIOCSXREG, "PIOCSXREG", "set extra register state" },
154 { PIOCKILL, "PIOCKILL", "send signal" },
155 #ifdef PIOCLDT /* solaris i386 */
156 { PIOCLDT, "PIOCLDT", "get LDT" },
157 { PIOCNLDT, "PIOCNLDT", "get number of LDT entries" },
159 #ifdef PIOCLSTATUS /* solaris and unixware */
160 { PIOCLSTATUS, "PIOCLSTATUS", "get status of all lwps" },
161 { PIOCLUSAGE, "PIOCLUSAGE", "get resource usage of all lwps" },
162 { PIOCOPENLWP, "PIOCOPENLWP", "get lwp file descriptor" },
163 { PIOCLWPIDS, "PIOCLWPIDS", "get lwp identifiers" },
165 { PIOCMAP, "PIOCMAP", "get memory map information" },
166 { PIOCMAXSIG, "PIOCMAXSIG", "get max signal number" },
167 { PIOCNICE, "PIOCNICE", "set nice priority" },
168 { PIOCNMAP, "PIOCNMAP", "get number of memory mappings" },
169 { PIOCOPENM, "PIOCOPENM", "open mapped object for reading" },
170 #ifdef PIOCOPENMOBS /* osf */
171 { PIOCOPENMOBS, "PIOCOPENMOBS", "open mapped object" },
173 #ifdef PIOCOPENPD /* solaris */
174 { PIOCOPENPD, "PIOCOPENPD", "get page data file descriptor" },
176 { PIOCPSINFO, "PIOCPSINFO", "get ps(1) information" },
177 { PIOCRESET, "PIOCRESET", "reset process flags" },
178 { PIOCRFORK, "PIOCRFORK", "reset inherit-on-fork flag" },
179 { PIOCRRLC, "PIOCRRLC", "reset run-on-last-close flag" },
180 { PIOCRUN, "PIOCRUN", "make process runnable" },
181 #ifdef PIOCSAVECCNTRS /* irix */
182 { PIOCSAVECCNTRS, "PIOCSAVECCNTRS", "parent gets child cntrs" },
184 { PIOCSENTRY, "PIOCSENTRY", "set traced syscall entry set" },
185 { PIOCSET, "PIOCSET", "set process flags" },
186 { PIOCSEXIT, "PIOCSEXIT", "set traced syscall exit set" },
187 { PIOCSFAULT, "PIOCSFAULT", "set traced fault set" },
188 { PIOCSFORK, "PIOCSFORK", "set inherit-on-fork flag" },
189 { PIOCSFPREG, "PIOCSFPREG", "set floating point registers" },
190 { PIOCSHOLD, "PIOCSHOLD", "set held signal set" },
191 { PIOCSREG, "PIOCSREG", "set general registers" },
192 { PIOCSRLC, "PIOCSRLC", "set run-on-last-close flag" },
193 { PIOCSSIG, "PIOCSSIG", "set current signal" },
194 { PIOCSTATUS, "PIOCSTATUS", "get process status" },
195 { PIOCSTOP, "PIOCSTOP", "post stop request" },
196 { PIOCSTRACE, "PIOCSTRACE", "set traced signal set" },
197 { PIOCUNKILL, "PIOCUNKILL", "delete a signal" },
198 #ifdef PIOCUSAGE /* solaris */
199 { PIOCUSAGE, "PIOCUSAGE", "get resource usage" },
201 { PIOCWSTOP, "PIOCWSTOP", "wait for process to stop" },
203 #ifdef PIOCNTHR /* osf threads */
204 { PIOCNTHR, "PIOCNTHR", "get thread count" },
205 { PIOCRTINH, "PIOCRTINH", "reset inherit-on-thread-creation" },
206 { PIOCSTINH, "PIOCSTINH", "set inherit-on-thread-creation" },
207 { PIOCTLIST, "PIOCTLIST", "get thread ids" },
208 { PIOCXPTH, "PIOCXPTH", "translate port to thread handle" },
209 { PIOCTRUN, "PIOCTRUN", "make thread runnable" },
210 { PIOCTSTATUS, "PIOCTSTATUS", "get thread status" },
211 { PIOCTSTOP, "PIOCTSTOP", "stop a thread" },
212 /* ... TGTRACE TSTRACE TSSIG TKILL TUNKILL TCFAULT TGFAULT TSFAULT
213 TGFPREG TSFPREG TGREG TSREG TACTION TTERM TABRUN TGENTRY TSENTRY
214 TGEXIT TSEXIT TSHOLD ... thread functions */
215 #endif /* osf threads */
220 ioctl_with_trace (int fd, long opcode, void *ptr, char *file, int line)
228 for (i = 0; ioctl_table[i].name != NULL; i++)
229 if (ioctl_table[i].value == opcode)
233 fprintf (procfs_file ? procfs_file : stdout,
234 "%s:%d -- ", file, line);
237 arg1 = ptr ? *(long *) ptr : 0;
238 fprintf (procfs_file ? procfs_file : stdout,
239 "ioctl (PIOCSET, %s) %s\n",
240 arg1 == PR_FORK ? "PR_FORK" :
241 arg1 == PR_RLC ? "PR_RLC" :
243 arg1 == PR_ASYNC ? "PR_ASYNC" :
246 info_verbose ? ioctl_table[i].desc : "");
249 arg1 = ptr ? *(long *) ptr : 0;
250 fprintf (procfs_file ? procfs_file : stdout,
251 "ioctl (PIOCRESET, %s) %s\n",
252 arg1 == PR_FORK ? "PR_FORK" :
253 arg1 == PR_RLC ? "PR_RLC" :
255 arg1 == PR_ASYNC ? "PR_ASYNC" :
258 info_verbose ? ioctl_table[i].desc : "");
261 fprintf (procfs_file ? procfs_file : stdout,
262 "ioctl (PIOCSTRACE) ");
263 proc_prettyfprint_signalset (procfs_file ? procfs_file : stdout,
264 (sigset_t *) ptr, 0);
267 fprintf (procfs_file ? procfs_file : stdout,
269 opcode == PIOCSFAULT ? "PIOCSFAULT" : "PIOCGFAULT");
270 proc_prettyfprint_faultset (procfs_file ? procfs_file : stdout,
271 (fltset_t *) ptr, 0);
274 fprintf (procfs_file ? procfs_file : stdout,
276 opcode == PIOCSENTRY ? "PIOCSENTRY" : "PIOCGENTRY");
277 proc_prettyfprint_syscalls (procfs_file ? procfs_file : stdout,
278 (sysset_t *) ptr, 0);
281 fprintf (procfs_file ? procfs_file : stdout,
283 opcode == PIOCSEXIT ? "PIOCSEXIT" : "PIOCGEXIT");
284 proc_prettyfprint_syscalls (procfs_file ? procfs_file : stdout,
285 (sysset_t *) ptr, 0);
288 fprintf (procfs_file ? procfs_file : stdout,
290 opcode == PIOCSHOLD ? "PIOCSHOLD" : "PIOCGHOLD");
291 proc_prettyfprint_signalset (procfs_file ? procfs_file : stdout,
292 (sigset_t *) ptr, 0);
295 fprintf (procfs_file ? procfs_file : stdout,
296 "ioctl (PIOCSSIG) ");
297 proc_prettyfprint_signal (procfs_file ? procfs_file : stdout,
298 ptr ? ((siginfo_t *) ptr)->si_signo : 0,
300 fprintf (procfs_file ? procfs_file : stdout, "\n");
303 fprintf (procfs_file ? procfs_file : stdout,
306 arg1 = ptr ? *(long *) ptr : 0;
308 fprintf (procfs_file ? procfs_file : stdout, "clearSig ");
310 fprintf (procfs_file ? procfs_file : stdout, "clearFlt ");
312 fprintf (procfs_file ? procfs_file : stdout, "setTrace ");
314 fprintf (procfs_file ? procfs_file : stdout, "setHold ");
316 fprintf (procfs_file ? procfs_file : stdout, "setFlt ");
318 fprintf (procfs_file ? procfs_file : stdout, "setVaddr ");
320 fprintf (procfs_file ? procfs_file : stdout, "step ");
322 fprintf (procfs_file ? procfs_file : stdout, "syscallAbort ");
324 fprintf (procfs_file ? procfs_file : stdout, "stopReq ");
326 fprintf (procfs_file ? procfs_file : stdout, "\n");
329 fprintf (procfs_file ? procfs_file : stdout,
330 "ioctl (PIOCKILL) ");
331 proc_prettyfprint_signal (procfs_file ? procfs_file : stdout,
332 ptr ? *(long *) ptr : 0, 0);
333 fprintf (procfs_file ? procfs_file : stdout, "\n");
337 fprintf (procfs_file ? procfs_file : stdout,
338 "ioctl (PIOCSSPCACT) ");
339 arg1 = ptr ? *(long *) ptr : 0;
340 if (arg1 & PRFS_STOPFORK)
341 fprintf (procfs_file ? procfs_file : stdout, "stopFork ");
342 if (arg1 & PRFS_STOPEXEC)
343 fprintf (procfs_file ? procfs_file : stdout, "stopExec ");
344 if (arg1 & PRFS_STOPTERM)
345 fprintf (procfs_file ? procfs_file : stdout, "stopTerm ");
346 if (arg1 & PRFS_STOPTCR)
347 fprintf (procfs_file ? procfs_file : stdout, "stopThreadCreate ");
348 if (arg1 & PRFS_STOPTTERM)
349 fprintf (procfs_file ? procfs_file : stdout, "stopThreadTerm ");
350 if (arg1 & PRFS_KOLC)
351 fprintf (procfs_file ? procfs_file : stdout, "killOnLastClose ");
352 fprintf (procfs_file ? procfs_file : stdout, "\n");
354 #endif /* PIOCSSPCACT */
356 if (ioctl_table[i].name)
357 fprintf (procfs_file ? procfs_file : stdout,
360 info_verbose ? ioctl_table[i].desc : "");
362 fprintf (procfs_file ? procfs_file : stdout,
363 "ioctl (<unknown %ld (0x%lx)) \n", opcode, opcode);
367 fflush (procfs_file);
370 ret = ioctl (fd, opcode, ptr);
371 if (procfs_trace && ret < 0)
373 fprintf (procfs_file ? procfs_file : stdout,
374 "[ioctl (%s) FAILED! (%s)]\n",
375 ioctl_table[i].name != NULL ?
376 ioctl_table[i].name : "<unknown>",
377 safe_strerror (errno));
379 fflush (procfs_file);
385 #else /* NEW_PROC_API */
387 static struct trans rw_table[] = {
388 #ifdef PCAGENT /* solaris */
389 { PCAGENT, "PCAGENT", "create agent lwp with regs from argument" },
391 { PCCFAULT, "PCCFAULT", "clear current fault" },
392 #ifdef PCCSIG /* solaris */
393 { PCCSIG, "PCCSIG", "clear current signal" },
395 { PCDSTOP, "PCDSTOP", "post stop request" },
396 { PCKILL, "PCKILL", "post a signal" },
397 { PCNICE, "PCNICE", "set nice priority" },
398 #ifdef PCREAD /* solaris */
399 { PCREAD, "PCREAD", "read from the address space" },
400 { PCWRITE, "PCWRITE", "write to the address space" },
402 #ifdef PCRESET /* unixware */
403 { PCRESET, "PCRESET", "unset modes" },
405 { PCRUN, "PCRUN", "make process/lwp runnable" },
406 #ifdef PCSASRS /* solaris 2.7 only */
407 { PCSASRS, "PCSASRS", "set ancillary state registers" },
409 #ifdef PCSCRED /* solaris */
410 { PCSCRED, "PCSCRED", "set process credentials" },
412 { PCSENTRY, "PCSENTRY", "set traced syscall entry set" },
413 { PCSET, "PCSET", "set modes" },
414 { PCSEXIT, "PCSEXIT", "set traced syscall exit set" },
415 { PCSFAULT, "PCSFAULT", "set traced fault set" },
416 { PCSFPREG, "PCSFPREG", "set floating point registers" },
417 { PCSHOLD, "PCSHOLD", "set signal mask" },
418 { PCSREG, "PCSREG", "set general registers" },
419 { PCSSIG, "PCSSIG", "set current signal" },
420 { PCSTOP, "PCSTOP", "post stop request and wait" },
421 { PCSTRACE, "PCSTRACE", "set traced signal set" },
422 #ifdef PCSVADDR /* solaris */
423 { PCSVADDR, "PCSVADDR", "set pc virtual address" },
425 #ifdef PCSXREG /* solaris sparc only */
426 { PCSXREG, "PCSXREG", "set extra registers" },
428 #ifdef PCTWSTOP /* solaris */
429 { PCTWSTOP, "PCTWSTOP", "wait for stop, with timeout arg" },
431 { PCUNKILL, "PCUNKILL", "delete a pending signal" },
432 #ifdef PCUNSET /* solaris */
433 { PCUNSET, "PCUNSET", "unset modes" },
435 #ifdef PCWATCH /* solaris */
436 { PCWATCH, "PCWATCH", "set/unset watched memory area" },
438 { PCWSTOP, "PCWSTOP", "wait for process/lwp to stop, no timeout" },
442 static off_t lseek_offset;
445 write_with_trace (int fd, void *varg, size_t len, char *file, int line)
449 long *arg = (long *) varg;
454 long opcode = arg[0];
455 for (i = 0; rw_table[i].name != NULL; i++)
456 if (rw_table[i].value == opcode)
460 fprintf (procfs_file ? procfs_file : stdout,
461 "%s:%d -- ", file, line);
464 fprintf (procfs_file ? procfs_file : stdout,
465 "write (PCSET, %s) %s\n",
466 arg[1] == PR_FORK ? "PR_FORK" :
467 arg[1] == PR_RLC ? "PR_RLC" :
469 arg[1] == PR_ASYNC ? "PR_ASYNC" :
472 info_verbose ? rw_table[i].desc : "");
480 fprintf (procfs_file ? procfs_file : stdout,
481 "write (PCRESET, %s) %s\n",
482 arg[1] == PR_FORK ? "PR_FORK" :
483 arg[1] == PR_RLC ? "PR_RLC" :
485 arg[1] == PR_ASYNC ? "PR_ASYNC" :
488 info_verbose ? rw_table[i].desc : "");
491 fprintf (procfs_file ? procfs_file : stdout,
492 "write (PCSTRACE) ");
493 proc_prettyfprint_signalset (procfs_file ? procfs_file : stdout,
494 (sigset_t *) &arg[1], 0);
497 fprintf (procfs_file ? procfs_file : stdout,
498 "write (PCSFAULT) ");
499 proc_prettyfprint_faultset (procfs_file ? procfs_file : stdout,
500 (fltset_t *) &arg[1], 0);
503 fprintf (procfs_file ? procfs_file : stdout,
504 "write (PCSENTRY) ");
505 proc_prettyfprint_syscalls (procfs_file ? procfs_file : stdout,
506 (sysset_t *) &arg[1], 0);
509 fprintf (procfs_file ? procfs_file : stdout,
511 proc_prettyfprint_syscalls (procfs_file ? procfs_file : stdout,
512 (sysset_t *) &arg[1], 0);
515 fprintf (procfs_file ? procfs_file : stdout,
517 proc_prettyfprint_signalset (procfs_file ? procfs_file : stdout,
518 (sigset_t *) &arg[1], 0);
521 fprintf (procfs_file ? procfs_file : stdout,
523 proc_prettyfprint_signal (procfs_file ? procfs_file : stdout,
524 arg[1] ? ((siginfo_t *) &arg[1])->si_signo
527 fprintf (procfs_file ? procfs_file : stdout, "\n");
530 fprintf (procfs_file ? procfs_file : stdout,
533 fprintf (procfs_file ? procfs_file : stdout, "clearSig ");
534 if (arg[1] & PRCFAULT)
535 fprintf (procfs_file ? procfs_file : stdout, "clearFlt ");
537 fprintf (procfs_file ? procfs_file : stdout, "step ");
538 if (arg[1] & PRSABORT)
539 fprintf (procfs_file ? procfs_file : stdout, "syscallAbort ");
541 fprintf (procfs_file ? procfs_file : stdout, "stopReq ");
543 fprintf (procfs_file ? procfs_file : stdout, "\n");
546 fprintf (procfs_file ? procfs_file : stdout,
548 proc_prettyfprint_signal (procfs_file ? procfs_file : stdout,
550 fprintf (procfs_file ? procfs_file : stdout, "\n");
554 static unsigned char break_insn[] = BREAKPOINT;
556 if (len == sizeof (break_insn) &&
557 memcmp (arg, &break_insn, len) == 0)
558 fprintf (procfs_file ? procfs_file : stdout,
559 "write (<breakpoint at 0x%08lx>) \n",
560 (unsigned long) lseek_offset);
561 else if (rw_table[i].name)
562 fprintf (procfs_file ? procfs_file : stdout,
565 info_verbose ? rw_table[i].desc : "");
568 if (lseek_offset != -1)
569 fprintf (procfs_file ? procfs_file : stdout,
570 "write (<unknown>, %lud bytes at 0x%08lx) \n",
571 (unsigned long) len, (unsigned long) lseek_offset);
573 fprintf (procfs_file ? procfs_file : stdout,
574 "write (<unknown>, %lud bytes) \n",
575 (unsigned long) len);
581 fflush (procfs_file);
584 ret = write (fd, (void *) arg, len);
585 if (procfs_trace && ret != len)
587 fprintf (procfs_file ? procfs_file : stdout,
588 "[write (%s) FAILED! (%s)]\n",
589 rw_table[i].name != NULL ?
590 rw_table[i].name : "<unknown>",
591 safe_strerror (errno));
593 fflush (procfs_file);
601 lseek_with_trace (int fd, off_t offset, int whence, char *file, int line)
607 ret = lseek (fd, offset, whence);
609 if (procfs_trace && (ret == -1 || errno != 0))
611 fprintf (procfs_file ? procfs_file : stdout,
612 "[lseek (0x%08lx) FAILED! (%s)]\n",
613 (unsigned long) offset, safe_strerror (errno));
615 fflush (procfs_file);
621 #endif /* NEW_PROC_API */
624 open_with_trace (char *filename, int mode, char *file, int line)
630 ret = open (filename, mode);
634 fprintf (procfs_file ? procfs_file : stdout,
635 "%s:%d -- ", file, line);
639 fprintf (procfs_file ? procfs_file : stdout,
640 "[open FAILED! (%s) line %d]\\n",
641 safe_strerror (errno), line);
645 fprintf (procfs_file ? procfs_file : stdout,
646 "%d = open (%s, ", ret, filename);
647 if (mode == O_RDONLY)
648 fprintf (procfs_file ? procfs_file : stdout, "O_RDONLY) %d\n",
650 else if (mode == O_WRONLY)
651 fprintf (procfs_file ? procfs_file : stdout, "O_WRONLY) %d\n",
653 else if (mode == O_RDWR)
654 fprintf (procfs_file ? procfs_file : stdout, "O_RDWR) %d\n",
658 fflush (procfs_file);
665 close_with_trace (int fd, char *file, int line)
675 fprintf (procfs_file ? procfs_file : stdout,
676 "%s:%d -- ", file, line);
678 fprintf (procfs_file ? procfs_file : stdout,
679 "[close FAILED! (%s)]\n", safe_strerror (errno));
681 fprintf (procfs_file ? procfs_file : stdout,
682 "%d = close (%d)\n", ret, fd);
684 fflush (procfs_file);
691 wait_with_trace (int *wstat, char *file, int line)
699 fprintf (procfs_file ? procfs_file : stdout,
700 "%s:%d -- ", file, line);
701 fprintf (procfs_file ? procfs_file : stdout,
702 "wait (line %d) ", line);
704 fflush (procfs_file);
711 fprintf (procfs_file ? procfs_file : stdout,
712 "[wait FAILED! (%s)]\n", safe_strerror (errno));
714 fprintf (procfs_file ? procfs_file : stdout,
715 "returned pid %d, status 0x%x\n", ret, lstat);
717 fflush (procfs_file);
726 procfs_note (char *msg, char *file, int line)
732 fprintf (procfs_file ? procfs_file : stdout,
733 "%s:%d -- ", file, line);
734 fprintf (procfs_file ? procfs_file : stdout, msg);
736 fflush (procfs_file);
741 proc_prettyfprint_status (long flags, int why, int what, int thread)
747 fprintf (procfs_file ? procfs_file : stdout,
748 "Thread %d: ", thread);
750 proc_prettyfprint_flags (procfs_file ? procfs_file : stdout,
753 if (flags & (PR_STOPPED | PR_ISTOP))
754 proc_prettyfprint_why (procfs_file ? procfs_file : stdout,
757 fflush (procfs_file);
763 _initialize_proc_api (void)
765 struct cmd_list_element *c;
767 c = add_set_cmd ("procfs-trace", no_class,
768 var_boolean, (char *) &procfs_trace,
769 "Set tracing for /proc api calls.\n", &setlist);
771 add_show_from_set (c, &showlist);
772 c->function.sfunc = set_procfs_trace_cmd;
774 c = add_set_cmd ("procfs-file", no_class, var_filename,
775 (char *) &procfs_filename,
776 "Set filename for /proc tracefile.\n", &setlist);
778 add_show_from_set (c, &showlist);
779 c->function.sfunc = set_procfs_file_cmd;