1 /* $NetBSD: opdump.c,v 1.35 2010/08/20 16:35:05 pooka Exp $ */
4 * Copyright (c) 2005, 2006 Antti Kantee. All Rights Reserved.
6 * Development of this software was supported by the
7 * Google Summer of Code program and the Ulla Tuominen Foundation.
8 * The Google SoC project was mentored by Bill Studenmund.
10 * Redistribution and use in source and binary forms, with or without
11 * modification, are permitted provided that the following conditions
13 * 1. Redistributions of source code must retain the above copyright
14 * notice, this list of conditions and the following disclaimer.
15 * 2. Redistributions in binary form must reproduce the above copyright
16 * notice, this list of conditions and the following disclaimer in the
17 * documentation and/or other materials provided with the distribution.
19 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
20 * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
21 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
22 * DISCLAIMED. IN NO EVENT SHALL THE AUTHOR 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 OR
25 * 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
32 /* Pretty-printing helper routines for VFS/VOP request contents */
34 /* yes, this is pretty much a mess */
36 #include <sys/types.h>
37 #include <sys/namei.h>
46 #include "puffsdump.h"
47 #include "puffs_priv.h"
50 #define __arraycount(__x) (sizeof(__x) / sizeof(__x[0]))
55 const char *puffsdump_vfsop_revmap[] = {
69 "PUFFS_VFS_EXTATTRCTL",
72 size_t puffsdump_vfsop_count = __arraycount(puffsdump_vfsop_revmap);
74 const char *puffsdump_vnop_revmap[] = {
116 "PUFFS_VN_GETEXTATTR",
117 "PUFFS_VN_LISTEXTATTR",
118 "PUFFS_VN_OPENEXTATTR",
119 "PUFFS_VN_DELETEEXTATTR",
120 "PUFFS_VN_SETEXTATTR",
121 "PUFFS_VN_CLOSEEXTATTR",
123 size_t puffsdump_vnop_count = __arraycount(puffsdump_vnop_revmap);
126 const char *puffsdump_cacheop_revmap[] = {
130 const char *puffsdump_errnot_revmap[] = {
132 "PUFFS_ERR_MAKENODE",
135 "PUFFS_ERR_READLINK",
139 "PUFFS_ERR_GETEXTATTR",
140 "PUFFS_ERR_LISTEXTATTR",
142 size_t puffsdump_errnot_count = __arraycount(puffsdump_errnot_revmap);
144 const char *puffsdump_flush_revmap[] = {
145 "PUFFS_INVAL_NAMECACHE_NODE",
146 "PUFFS_INVAL_NAMECACHE_DIR",
147 "PUFFS_INVAL_NAMECACHE_ALL",
148 "PUFFS_INVAL_PAGECACHE_NODE_RANGE",
149 "PUFFS_FLUSH_PAGECACHE_NODE_RANGE",
151 size_t puffsdump_flush_count = __arraycount(puffsdump_flush_revmap);
154 mydprintf(const char *fmt, ...)
159 vfprintf(stderr, fmt, ap);
164 puffsdump_req(struct puffs_req *preq)
167 static struct timeval tv_prev;
168 struct timeval tv_now, tv;
172 int opclass, isvn = 0;
174 mydprintf("reqid: %" PRIu64 ", ", preq->preq_id);
175 opclass = PUFFSOP_OPCLASS(preq->preq_opclass);
178 map = puffsdump_vfsop_revmap;
179 maxhandle = puffsdump_vfsop_count;
182 map = puffsdump_vnop_revmap;
183 maxhandle = puffsdump_vnop_count;
187 map = puffsdump_cacheop_revmap;
188 maxhandle = __arraycount(puffsdump_cacheop_revmap);
191 map = puffsdump_errnot_revmap;
192 maxhandle = puffsdump_errnot_count;
195 map = puffsdump_flush_revmap;
196 maxhandle = puffsdump_flush_count;
199 mydprintf("unhandled opclass %d\n", opclass);
203 if (preq->preq_optype < maxhandle) {
204 optype = map[preq->preq_optype];
206 snprintf(buf, sizeof(buf), "UNKNOWN (%d)", preq->preq_optype);
210 mydprintf("opclass %d%s, optype: %s, "
211 "cookie: %p,\n" DINT "aux: %p, auxlen: %zu, pid: %d, lwpid: %d\n",
212 opclass, PUFFSOP_WANTREPLY(preq->preq_opclass) ? "" : " (FAF)",
213 optype, preq->preq_cookie,
214 preq->preq_buf, preq->preq_buflen,
215 preq->preq_pid, preq->preq_lid);
218 switch (preq->preq_optype) {
219 case PUFFS_VN_LOOKUP:
220 puffsdump_lookup(preq);
224 puffsdump_readwrite(preq);
227 puffsdump_open(preq);
229 case PUFFS_VN_REMOVE:
232 puffsdump_targ(preq);
234 case PUFFS_VN_READDIR:
235 puffsdump_readdir(preq);
237 case PUFFS_VN_CREATE:
240 case PUFFS_VN_SYMLINK:
241 puffsdump_create(preq);
243 case PUFFS_VN_SETATTR:
244 puffsdump_attr(preq);
252 gettimeofday(&tv_now, NULL);
253 timersub(&tv_now, &tv_prev, &tv);
254 mydprintf(DINT "since previous call: %lld.%06ld\n",
255 (long long)tv.tv_sec, (long)tv.tv_usec);
256 gettimeofday(&tv_prev, NULL);
261 puffsdump_rv(struct puffs_req *preq)
264 if (PUFFSOP_OPCLASS(preq->preq_opclass) == PUFFSOP_VN) {
265 switch (preq->preq_optype) {
266 case PUFFS_VN_LOOKUP:
267 puffsdump_lookup_rv(preq);
269 case PUFFS_VN_CREATE:
272 case PUFFS_VN_SYMLINK:
273 puffsdump_create_rv(preq);
277 puffsdump_readwrite_rv(preq);
279 case PUFFS_VN_READDIR:
280 puffsdump_readdir_rv(preq);
282 case PUFFS_VN_GETATTR:
283 puffsdump_attr(preq);
290 mydprintf("RV reqid: %" PRIu64 ", result: %d %s\n",
291 preq->preq_id, preq->preq_rv,
292 preq->preq_rv ? strerror(preq->preq_rv) : "");
296 * Slightly tedious print-routine so that we get a nice NOVAL instead
297 * of some tedious output representations for -1, especially (uint64_t)-1
299 * We use typecasting to make this work beyond time_t/dev_t size changes.
302 dumpattr(struct vattr *vap)
306 /* XXX: better readability. and this is debug, so no cycle-sweat */
307 #define DEFAULTBUF() snprintf(buf, sizeof(buf), "NOVAL")
309 mydprintf(DINT "vattr:\n");
310 mydprintf(DINT DINT "type: %d, ", vap->va_type);
313 if (vap->va_mode != (mode_t)PUFFS_VNOVAL)
314 snprintf(buf, sizeof(buf), "0%o", vap->va_mode);
315 mydprintf("mode: %s, ", buf);
318 if (vap->va_nlink != (nlink_t)PUFFS_VNOVAL)
319 snprintf(buf, sizeof(buf), "%ju", (uintmax_t)vap->va_nlink);
320 mydprintf("nlink: %s, ", buf);
323 if (vap->va_uid != (uid_t)PUFFS_VNOVAL)
324 snprintf(buf, sizeof(buf), "%d", vap->va_uid);
325 mydprintf("uid: %s, ", buf);
328 if (vap->va_gid != (gid_t)PUFFS_VNOVAL)
329 snprintf(buf, sizeof(buf), "%d", vap->va_gid);
330 mydprintf("gid: %s\n", buf);
333 if ((unsigned long long)vap->va_fsid!=(unsigned long long)PUFFS_VNOVAL)
334 snprintf(buf, sizeof(buf), "0x%llx",
335 (unsigned long long)vap->va_fsid);
336 mydprintf(DINT DINT "fsid: %s, ", buf);
339 if (vap->va_fileid != (ino_t)PUFFS_VNOVAL)
340 snprintf(buf, sizeof(buf), "%" PRIu64, vap->va_fileid);
341 mydprintf("ino: %s, ", buf);
344 if (vap->va_size != (u_quad_t)PUFFS_VNOVAL)
345 snprintf(buf, sizeof(buf), "%" PRIu64, vap->va_size);
346 mydprintf("size: %s, ", buf);
349 if (vap->va_blocksize != (long)PUFFS_VNOVAL)
350 snprintf(buf, sizeof(buf), "%ld", vap->va_blocksize);
351 mydprintf("bsize: %s\n", buf);
354 if (vap->va_atime.tv_sec != (time_t)PUFFS_VNOVAL)
355 snprintf(buf, sizeof(buf), "%lld",
356 (long long)vap->va_atime.tv_sec);
357 mydprintf(DINT DINT "a.s: %s, ", buf);
360 if (vap->va_atime.tv_nsec != (long)PUFFS_VNOVAL)
361 snprintf(buf, sizeof(buf), "%ld", vap->va_atime.tv_nsec);
362 mydprintf("a.ns: %s, ", buf);
365 if (vap->va_mtime.tv_sec != (time_t)PUFFS_VNOVAL)
366 snprintf(buf, sizeof(buf), "%lld",
367 (long long)vap->va_mtime.tv_sec);
368 mydprintf("m.s: %s, ", buf);
371 if (vap->va_mtime.tv_nsec != (long)PUFFS_VNOVAL)
372 snprintf(buf, sizeof(buf), "%ld", vap->va_mtime.tv_nsec);
373 mydprintf("m.ns: %s\n", buf);
376 if (vap->va_ctime.tv_sec != (time_t)PUFFS_VNOVAL)
377 snprintf(buf, sizeof(buf), "%lld",
378 (long long)vap->va_ctime.tv_sec);
379 mydprintf(DINT DINT "c.s: %s, ", buf);
382 if (vap->va_ctime.tv_nsec != (long)PUFFS_VNOVAL)
383 snprintf(buf, sizeof(buf), "%ld", vap->va_ctime.tv_nsec);
384 mydprintf("c.ns: %s, ", buf);
387 if (vap->va_gen != (u_long)PUFFS_VNOVAL)
388 snprintf(buf, sizeof(buf), "%ju", (uintmax_t)vap->va_gen);
389 mydprintf(DINT DINT "gen: %s, ", buf);
392 if (vap->va_flags != (u_long)PUFFS_VNOVAL)
393 snprintf(buf, sizeof(buf), "0x%lx", vap->va_flags);
394 mydprintf("flags: %s, ", buf);
397 if (vap->va_bytes != (u_quad_t)PUFFS_VNOVAL)
398 snprintf(buf, sizeof(buf), "%" PRIu64, vap->va_bytes);
399 mydprintf(DINT DINT "bytes: %s, ", buf);
401 snprintf(buf, sizeof(buf), "%" PRIu64, vap->va_filerev);
402 mydprintf("filerev: %s, ", buf);
404 snprintf(buf, sizeof(buf), "0x%x", vap->va_vaflags);
405 mydprintf("vaflags: %s\n", buf);
409 puffsdump_cookie(puffs_cookie_t c, const char *cookiename)
412 mydprintf("%scookie: at %p\n", cookiename, c);
416 puffsdump_cn(struct puffs_kcn *pkcn)
419 mydprintf(DINT "puffs_cn: \"%s\", len %zu\n",
420 pkcn->pkcn_name, pkcn->pkcn_namelen);
424 puffsdump_lookup(struct puffs_req *preq)
426 struct puffs_vnmsg_lookup *lookup_msg = (void *)preq;
428 puffsdump_cn(&lookup_msg->pvnr_cn);
432 puffsdump_lookup_rv(struct puffs_req *preq)
434 struct puffs_vnmsg_lookup *lookup_msg = (void *)preq;
436 mydprintf(DINT "new %p, type 0x%x, size 0x%"PRIu64", dev 0x%llx\n",
437 lookup_msg->pvnr_newnode, lookup_msg->pvnr_vtype,
438 lookup_msg->pvnr_size, (unsigned long long)lookup_msg->pvnr_rdev);
442 puffsdump_create(struct puffs_req *preq)
444 /* XXX: wrong type, but we know it fits the slot */
445 struct puffs_vnmsg_create *create_msg = (void *)preq;
447 dumpattr(&create_msg->pvnr_va);
451 puffsdump_create_rv(struct puffs_req *preq)
453 /* XXX: wrong type, but we know it fits the slot */
454 struct puffs_vnmsg_create *create_msg = (void *)preq;
456 mydprintf(DINT "new %p\n", create_msg->pvnr_newnode);
460 puffsdump_readwrite(struct puffs_req *preq)
462 struct puffs_vnmsg_rw *rw_msg = (void *)preq;
464 mydprintf(DINT "offset: %" PRId64 ", resid %zu, ioflag 0x%x\n",
465 rw_msg->pvnr_offset, rw_msg->pvnr_resid, rw_msg->pvnr_ioflag);
469 puffsdump_readwrite_rv(struct puffs_req *preq)
471 struct puffs_vnmsg_rw *rw_msg = (void *)preq;
473 mydprintf(DINT "resid after op: %zu\n", rw_msg->pvnr_resid);
477 puffsdump_readdir_rv(struct puffs_req *preq)
479 struct puffs_vnmsg_readdir *readdir_msg = (void *)preq;
481 mydprintf(DINT "resid after op: %zu, eofflag %d\n",
482 readdir_msg->pvnr_resid, readdir_msg->pvnr_eofflag);
486 puffsdump_open(struct puffs_req *preq)
488 struct puffs_vnmsg_open *open_msg = (void *)preq;
490 mydprintf(DINT "mode: 0x%x\n", open_msg->pvnr_mode);
494 puffsdump_targ(struct puffs_req *preq)
496 struct puffs_vnmsg_remove *remove_msg = (void *)preq; /* XXX! */
498 mydprintf(DINT "target cookie: %p\n", remove_msg->pvnr_cookie_targ);
502 puffsdump_readdir(struct puffs_req *preq)
504 struct puffs_vnmsg_readdir *readdir_msg = (void *)preq;
506 mydprintf(DINT "read offset: %" PRId64 "\n", readdir_msg->pvnr_offset);
510 puffsdump_attr(struct puffs_req *preq)
512 struct puffs_vnmsg_setgetattr *attr_msg = (void *)preq;
514 dumpattr(&attr_msg->pvnr_va);