]> Zhao Yanbai Git Server - minix.git/commitdiff
VFS: add debug dump for select 43/3343/1
authorDavid van Moolenbroek <david@minix3.org>
Thu, 4 Aug 2016 16:12:54 +0000 (16:12 +0000)
committerDavid van Moolenbroek <david@minix3.org>
Fri, 5 Aug 2016 11:14:09 +0000 (11:14 +0000)
By now it has become clear that the VFS select code has an unusually
high concentration of bugs, and there is no indication that any form
of convergence to a bug-free state is in sight.  Thus, for now, it
may be helpful to be able to dump the contents of the select tables
in order to track down any bugs in the future.  Hopefully that will
allow the next bugs to be resolved slightly after than before.

The debug dump can be triggered with "svrctl vfs get print_select".

Change-Id: Ia826746dce0f065d7f3b46aa9047945067b8263d

minix/servers/vfs/misc.c
minix/servers/vfs/proto.h
minix/servers/vfs/select.c

index b47bbd0d77a3f4db0de8a08de0a1a8d02e965717..d02b9953437a2880b0aa505575bde74b812222c2 100644 (file)
@@ -862,6 +862,11 @@ int do_svrctl(void)
                                sysgetenv.val = 0;
                                sysgetenv.vallen = 0;
                                r = OK;
+                       } else if (!strcmp(search_key, "print_select")) {
+                               select_dump();
+                               sysgetenv.val = 0;
+                               sysgetenv.vallen = 0;
+                               r = OK;
                        } else if (!strcmp(search_key, "active_threads")) {
                                int active = NR_WTHREADS - worker_available();
                                snprintf(small_buf, sizeof(small_buf) - 1,
index 37763a6552864a9652703a2cdb9115c30e30eaf5..d031282d4e6c93a4ea8bd02b6a807e6da858087e 100644 (file)
@@ -352,6 +352,7 @@ void select_forget(void);
 void select_reply1(endpoint_t driver_e, devminor_t minor, int status);
 void select_reply2(endpoint_t driver_e, devminor_t minor, int status);
 void select_unsuspend_by_endpt(endpoint_t proc);
+void select_dump(void);
 
 /* worker.c */
 void worker_init(void);
index ac6e34044de3630a3f09467456717a139acb839d..92b852b543993b5027ea152576545f8c24e5e706 100644 (file)
@@ -1113,3 +1113,54 @@ static void select_lock_filp(struct filp *f, int ops)
 
   lock_filp(f, locktype);
 }
+
+/*
+ * Dump the state of the entire select table, for debugging purposes.
+ */
+void
+select_dump(void)
+{
+       struct selectentry *se;
+       struct filp *f;
+       struct dmap *dp;
+       dev_t dev;
+       int s, fd;
+
+       for (s = 0; s < MAXSELECTS; s++) {
+               se = &selecttab[s];
+               if (se->requestor == NULL)
+                       continue;
+
+               printf("select %d: endpt %d nfds %d nreadyfds %d error %d "
+                   "block %d starting %d expiry %u is_deferred %d\n",
+                   s, se->req_endpt, se->nfds, se->nreadyfds, se->error,
+                   se->block, se->starting, se->expiry, is_deferred(se));
+
+               for (fd = 0; !se->starting && fd < se->nfds; fd++) {
+                       /* Save on output: do not print NULL filps at all. */
+                       if ((f = se->filps[fd]) == NULL)
+                               continue;
+
+                       printf("- [%d] filp %p flags %x type ", fd, f,
+                           f->filp_select_flags);
+                       if (is_regular_file(f))
+                               printf("regular\n");
+                       else if (is_pipe(f))
+                               printf("pipe\n");
+                       else if (is_char_device(f)) {
+                               dev = cdev_map(f->filp_vno->v_sdev,
+                                   se->requestor);
+                               printf("char (dev <%d,%d>, dmap ",
+                                   major(dev), minor(dev));
+                               if (dev != NO_DEV) {
+                                       dp = &dmap[major(dev)];
+                                       printf("busy %d filp %p)\n",
+                                           dp->dmap_sel_busy,
+                                           dp->dmap_sel_filp);
+                               } else
+                                       printf("unknown)\n");
+                       } else
+                               printf("unknown\n");
+               }
+       }
+}