Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/trunk]: src/usr.bin/pmap Make error messages a little more informative. ...



details:   https://anonhg.NetBSD.org/src/rev/9584b4bcdd03
branches:  trunk
changeset: 536512:9584b4bcdd03
user:      atatat <atatat%NetBSD.org@localhost>
date:      Tue Sep 17 19:54:28 2002 +0000

description:
Make error messages a little more informative.  Add -R option to
recurse into submaps (a kernel thing) as suggested by Chuck Cranor,
with the output from these entries indented.  Clean up and rework code
slightly, to make the recursion task much easier.  Also, add a note to
the BUGS section in the man page thats mentions that stuff "just won't
work right" unless pmap is reading from the proper kernel.

diffstat:

 usr.bin/pmap/pmap.1 |   16 ++-
 usr.bin/pmap/pmap.c |  306 ++++++++++++++++++++++++++++++---------------------
 2 files changed, 194 insertions(+), 128 deletions(-)

diffs (truncated from 542 to 300 lines):

diff -r 6e7b94e728b1 -r 9584b4bcdd03 usr.bin/pmap/pmap.1
--- a/usr.bin/pmap/pmap.1       Tue Sep 17 19:50:48 2002 +0000
+++ b/usr.bin/pmap/pmap.1       Tue Sep 17 19:54:28 2002 +0000
@@ -1,4 +1,4 @@
-.\"    $NetBSD: pmap.1,v 1.2 2002/09/13 15:32:49 atatat Exp $
+.\"    $NetBSD: pmap.1,v 1.3 2002/09/17 19:54:28 atatat Exp $
 .\"
 .\" Copyright (c) 2002 The NetBSD Foundation, Inc.
 .\" All rights reserved.
@@ -42,7 +42,7 @@
 .Nd display process memory map
 .Sh SYNOPSIS
 .Nm
-.Op Fl adlmPsv
+.Op Fl adlmPRsv
 .Op Fl D Ar number
 .Op Fl M Ar core
 .Op Fl N Ar system
@@ -136,6 +136,13 @@
 occurs last on the command line, the
 .Fl p
 is optional.
+.It Fl R
+Recurse into submaps.  In some cases, a vm_map_entry in the kernel
+will point to a submap.  Using this flag tells
+.Nm
+to print the entries of the submap as well.  The submap output is
+indented, and does not affect any total printed at the bottom of the
+output.
 .It Fl s
 The Solaris style output format, modeled after the Solaris command of
 the same name.  This is the default output style.
@@ -327,6 +334,11 @@
 utility and documentation was written by Andrew Brown
 .Aq atatat%netbsd.org@localhost .
 .Sh BUGS
+Very little will work unless
+.Nm
+is reading from the correct kernel in order to retrieve the
+proper symbol information.
+.Pp
 Since processes can change state while
 .Nm
 is running, some of the information printed may be inaccurate.  This
diff -r 6e7b94e728b1 -r 9584b4bcdd03 usr.bin/pmap/pmap.c
--- a/usr.bin/pmap/pmap.c       Tue Sep 17 19:50:48 2002 +0000
+++ b/usr.bin/pmap/pmap.c       Tue Sep 17 19:54:28 2002 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: pmap.c,v 1.3 2002/09/13 15:32:49 atatat Exp $ */
+/*     $NetBSD: pmap.c,v 1.4 2002/09/17 19:54:28 atatat Exp $ */
 
 /*
  * Copyright (c) 2002 The NetBSD Foundation, Inc.
@@ -38,7 +38,7 @@
 
 #include <sys/cdefs.h>
 #ifndef lint
-__RCSID("$NetBSD: pmap.c,v 1.3 2002/09/13 15:32:49 atatat Exp $");
+__RCSID("$NetBSD: pmap.c,v 1.4 2002/09/17 19:54:28 atatat Exp $");
 #endif
 
 #include <sys/types.h>
@@ -105,7 +105,7 @@
 void *uvm_vnodeops, *uvm_deviceops, *aobj_pager, *ubc_pager;
 void *kernel_floor;
 u_long nchash_addr, nchashtbl_addr, kernel_map_addr;
-int debug, verbose;
+int debug, verbose, recurse;
 int print_all, print_map, print_maps, print_solaris, print_ddb;
 int rwx = VM_PROT_READ | VM_PROT_WRITE | VM_PROT_EXECUTE, heapfound;
 rlim_t maxssiz;
@@ -155,13 +155,16 @@
        ssize_t len; \
        len = kvm_read((kd), (addr), (dst), (sz)); \
        if (len != (sz)) \
-               errx(1, "%s == %ld vs. %lu @ %lx", \
-                   kvm_geterr(kd), (long)len, (unsigned long)(sz), (addr)); \
+               errx(1, "trying to read %lu bytes from %lx: %s", \
+                   (unsigned long)(sz), (addr), kvm_geterr(kd)); \
 } while (0/*CONSTCOND*/)
 
 /* suck the data using the structure */
 #define KDEREF(kd, item) _KDEREF((kd), A(item), D(item, data), S(item))
 
+/* when recursing, output is indented */
+#define indent(n) ((n) * (recurse > 1 ? recurse - 1 : 0))
+
 struct nlist nl[] = {
        { "_maxsmap" },
 #define NL_MAXSSIZ             0
@@ -186,12 +189,13 @@
 
 void load_symbols(kvm_t *);
 void process_map(kvm_t *, pid_t, struct kinfo_proc2 *);
+void dump_vm_map(kvm_t *, struct kbit *, struct kbit *, char *);
 size_t dump_vm_map_entry(kvm_t *, struct kbit *, struct kbit *, int);
 char *findname(kvm_t *, struct kbit *, struct kbit *, struct kbit *,
               struct kbit *, struct kbit *);
 int search_cache(kvm_t *, struct kbit *, char **, char *, size_t);
 void load_name_cache(kvm_t *);
-void cache_enter(struct namecache *);
+void cache_enter(int, struct namecache *);
 
 int
 main(int argc, char *argv[])
@@ -200,17 +204,16 @@
        pid_t pid;
        int many, ch, rc;
        char errbuf[_POSIX2_LINE_MAX + 1];
-       /* u_long addr, next; */
        struct kinfo_proc2 *kproc;
-       /* struct proc proc; */
        char *kmem, *kernel;
 
        pid = -1;
        verbose = debug = 0;
        print_all = print_map = print_maps = print_solaris = print_ddb = 0;
+       recurse = 0;
        kmem = kernel = NULL;
 
-       while ((ch = getopt(argc, argv, "aD:dlmM:N:p:Prsvx")) != -1) {
+       while ((ch = getopt(argc, argv, "aD:dlmM:N:p:PRrsvx")) != -1) {
                switch (ch) {
                case 'a':
                        print_all = 1;
@@ -239,6 +242,9 @@
                case 'P':
                        pid = getpid();
                        break;
+               case 'R':
+                       recurse = 1;
+                       break;
                case 's':
                        print_solaris = 1;
                        break;
@@ -325,22 +331,14 @@
 void
 process_map(kvm_t *kd, pid_t pid, struct kinfo_proc2 *proc)
 {
-       struct kbit kbit[4];
-       struct kbit *vmspace, *vm_map, *header, *vm_map_entry;
-       struct vm_map_entry *last;
-       size_t total;
-       u_long addr, next;
+       struct kbit kbit[2], *vmspace, *vm_map;
        char *thing;
 
        vmspace = &kbit[0];
        vm_map = &kbit[1];
-       header = &kbit[2];
-       vm_map_entry = &kbit[3];
 
        A(vmspace) = 0;
        A(vm_map) = 0;
-       A(header) = 0;
-       A(vm_map_entry) = 0;
 
        if (pid > 0) {
                heapfound = 0;
@@ -381,94 +379,8 @@
                A(vm_map) = kernel_map_addr;
                KDEREF(kd, vm_map);
        }
-       if (debug & PRINT_VM_MAP) {
-               printf("%s %p = {", thing, P(vm_map));
 
-               printf(" pmap = %p,\n", D(vm_map, vm_map)->pmap);
-               printf("    lock = <struct lock>,");
-               printf(" header = <struct vm_map_entry>,");
-               printf(" nentries = %d,\n", D(vm_map, vm_map)->nentries);
-               printf("    size = %lx,", D(vm_map, vm_map)->size);
-               printf(" ref_count = %d,", D(vm_map, vm_map)->ref_count);
-               printf(" ref_lock = <struct simplelock>,\n");
-               printf("    hint = %p,", D(vm_map, vm_map)->hint);
-               printf(" hint_lock = <struct simplelock>,\n");
-               printf("    first_free = %p,", D(vm_map, vm_map)->first_free);
-               printf(" flags = %x <%s%s%s%s%s%s >,\n", D(vm_map, vm_map)->flags,
-                      D(vm_map, vm_map)->flags & VM_MAP_PAGEABLE ? " PAGEABLE" : "",
-                      D(vm_map, vm_map)->flags & VM_MAP_INTRSAFE ? " INTRSAFE" : "",
-                      D(vm_map, vm_map)->flags & VM_MAP_WIREFUTURE ? " WIREFUTURE" : "",
-                      D(vm_map, vm_map)->flags & VM_MAP_BUSY ? " BUSY" : "",
-                      D(vm_map, vm_map)->flags & VM_MAP_WANTLOCK ? " WANTLOCK" : "",
-#if VM_MAP_TOPDOWN > 0
-                      D(vm_map, vm_map)->flags & VM_MAP_TOPDOWN ? " TOPDOWN" :
-#endif
-                      "");
-               printf("    flags_lock = <struct simplelock>,");
-               printf(" timestamp = %u }\n", D(vm_map, vm_map)->timestamp);
-       }
-       if (print_ddb) {
-               printf("MAP %p: [0x%lx->0x%lx]\n", P(vm_map),
-                      D(vm_map, vm_map)->min_offset, D(vm_map, vm_map)->max_offset);
-               printf("\t#ent=%d, sz=%ld, ref=%d, version=%d, flags=0x%x\n",
-                      D(vm_map, vm_map)->nentries, D(vm_map, vm_map)->size,
-                      D(vm_map, vm_map)->ref_count, D(vm_map, vm_map)->timestamp,
-                      D(vm_map, vm_map)->flags);
-               printf("\tpmap=%p(resident=<unknown>)\n", D(vm_map, vm_map)->pmap);
-       }
-
-       A(header) = A(vm_map) + offsetof(struct vm_map, header);
-       S(header) = sizeof(struct vm_map_entry);
-       memcpy(D(header, vm_map_entry), &D(vm_map, vm_map)->header, S(header));
-       dump_vm_map_entry(kd, vmspace, header, 1);
-
-       /* headers */
-#ifdef DISABLED_HEADERS
-       if (print_map)
-               printf("%-*s %-*s rwx RWX CPY NCP I W A\n",
-                      (int)sizeof(long) * 2 + 2, "Start",
-                      (int)sizeof(long) * 2 + 2, "End");
-       if (print_maps)
-               printf("%-*s %-*s rwxp %-*s Dev   Inode      File\n",
-                      (int)sizeof(long) * 2 + 0, "Start",
-                      (int)sizeof(long) * 2 + 0, "End",
-                      (int)sizeof(long) * 2 + 0, "Offset");
-       if (print_solaris)
-               printf("%-*s %*s Protection        File\n",
-                      (int)sizeof(long) * 2 + 0, "Start",
-                      (int)sizeof(int) * 2 - 1,  "Size ");
-#endif
-       if (print_all)
-               printf("%-*s %-*s %*s %-*s rwxpc  RWX  I/W/A Dev  %*s - File\n",
-                      (int)sizeof(long) * 2, "Start",
-                      (int)sizeof(long) * 2, "End",
-                      (int)sizeof(int)  * 2, "Size ",
-                      (int)sizeof(long) * 2, "Offset",
-                      (int)sizeof(int)  * 2, "Inode");
-
-       /* these are the "sub entries" */
-       total = 0;
-       next = (u_long)D(header, vm_map_entry)->next;
-       D(vm_map_entry, vm_map_entry)->next =
-               D(header, vm_map_entry)->next + 1;
-       last = P(header);
-
-       while (next != 0 && D(vm_map_entry, vm_map_entry)->next != last) {
-               addr = next;
-               A(vm_map_entry) = addr;
-               S(vm_map_entry) = sizeof(struct vm_map_entry);
-               KDEREF(kd, vm_map_entry);
-               total += dump_vm_map_entry(kd, vmspace, vm_map_entry, 0);
-               next = (u_long)D(vm_map_entry, vm_map_entry)->next;
-       }
-       if (print_solaris)
-               printf("%-*s %8luK\n",
-                      (int)sizeof(void *) * 2 - 2, " total",
-                      (unsigned long)total);
-       if (print_all)
-               printf("%-*s %9luk\n",
-                      (int)sizeof(void *) * 4 - 1, " total",
-                      (unsigned long)total);
+       dump_vm_map(kd, vmspace, vm_map, thing);
 }
 
 void
@@ -496,6 +408,125 @@
                sizeof(kernel_map_addr));
 }
 
+void
+dump_vm_map(kvm_t *kd, struct kbit *vmspace, struct kbit *vm_map,
+           char *name)
+{
+       struct kbit kbit[2], *header, *vm_map_entry;
+       struct vm_map_entry *last, *next;
+       size_t total;
+       u_long addr;
+
+       header = &kbit[0];
+       vm_map_entry = &kbit[1];
+       A(header) = 0;
+       A(vm_map_entry) = 0;
+
+       if (debug & PRINT_VM_MAP) {
+               printf("%*s%s %p = {", indent(2), "", name, P(vm_map));
+               printf(" pmap = %p,\n", D(vm_map, vm_map)->pmap);
+               printf("%*s    lock = <struct lock>,", indent(2), "");
+               printf(" header = <struct vm_map_entry>,");
+               printf(" nentries = %d,\n", D(vm_map, vm_map)->nentries);
+               printf("%*s    size = %lx,", indent(2), "",
+                      D(vm_map, vm_map)->size);
+               printf(" ref_count = %d,", D(vm_map, vm_map)->ref_count);
+               printf(" ref_lock = <struct simplelock>,\n");
+               printf("%*s    hint = %p,", indent(2), "",
+                      D(vm_map, vm_map)->hint);
+               printf(" hint_lock = <struct simplelock>,\n");
+               printf("%*s    first_free = %p,", indent(2), "",
+                      D(vm_map, vm_map)->first_free);
+               printf(" flags = %x <%s%s%s%s%s%s >,\n", D(vm_map, vm_map)->flags,
+                      D(vm_map, vm_map)->flags & VM_MAP_PAGEABLE ? " PAGEABLE" : "",
+                      D(vm_map, vm_map)->flags & VM_MAP_INTRSAFE ? " INTRSAFE" : "",
+                      D(vm_map, vm_map)->flags & VM_MAP_WIREFUTURE ? " WIREFUTURE" : "",
+                      D(vm_map, vm_map)->flags & VM_MAP_BUSY ? " BUSY" : "",
+                      D(vm_map, vm_map)->flags & VM_MAP_WANTLOCK ? " WANTLOCK" : "",
+#if VM_MAP_TOPDOWN > 0
+                      D(vm_map, vm_map)->flags & VM_MAP_TOPDOWN ? " TOPDOWN" :
+#endif
+                      "");
+               printf("%*s    flags_lock = <struct simplelock>,", indent(2), "");
+               printf(" timestamp = %u }\n", D(vm_map, vm_map)->timestamp);



Home | Main Index | Thread Index | Old Index