Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

fuse: add simple request tracepoints

I've been timing various fuse operations and it's quite annoying to do
with kprobes. Add two tracepoints for sending and ending fuse requests
to make it easier to debug and time various operations.

Signed-off-by: Josef Bacik <josef@toxicpanda.com>
Reviewed-by: Bernd Schubert <bschubert@ddn.com>
Signed-off-by: Miklos Szeredi <mszeredi@redhat.com>

authored by

Josef Bacik and committed by
Miklos Szeredi
396b209e 0acad928

+140
+3
fs/fuse/Makefile
··· 3 3 # Makefile for the FUSE filesystem. 4 4 # 5 5 6 + # Needed for trace events 7 + ccflags-y = -I$(src) 8 + 6 9 obj-$(CONFIG_FUSE_FS) += fuse.o 7 10 obj-$(CONFIG_CUSE) += cuse.o 8 11 obj-$(CONFIG_VIRTIO_FS) += virtiofs.o
+5
fs/fuse/dev.c
··· 22 22 #include <linux/splice.h> 23 23 #include <linux/sched.h> 24 24 25 + #define CREATE_TRACE_POINTS 26 + #include "fuse_trace.h" 27 + 25 28 MODULE_ALIAS_MISCDEV(FUSE_MINOR); 26 29 MODULE_ALIAS("devname:fuse"); 27 30 ··· 292 289 req->in.h.len = sizeof(struct fuse_in_header) + 293 290 fuse_len_args(req->args->in_numargs, 294 291 (struct fuse_arg *) req->args->in_args); 292 + trace_fuse_request_send(req); 295 293 fiq->ops->send_req(fiq, req); 296 294 } 297 295 ··· 339 335 if (test_and_set_bit(FR_FINISHED, &req->flags)) 340 336 goto put_request; 341 337 338 + trace_fuse_request_end(req); 342 339 /* 343 340 * test_and_set_bit() implies smp_mb() between bit 344 341 * changing and below FR_INTERRUPTED check. Pairs with
+132
fs/fuse/fuse_trace.h
··· 1 + /* SPDX-License-Identifier: GPL-2.0 */ 2 + #undef TRACE_SYSTEM 3 + #define TRACE_SYSTEM fuse 4 + 5 + #if !defined(_TRACE_FUSE_H) || defined(TRACE_HEADER_MULTI_READ) 6 + #define _TRACE_FUSE_H 7 + 8 + #include <linux/tracepoint.h> 9 + 10 + #define OPCODES \ 11 + EM( FUSE_LOOKUP, "FUSE_LOOKUP") \ 12 + EM( FUSE_FORGET, "FUSE_FORGET") \ 13 + EM( FUSE_GETATTR, "FUSE_GETATTR") \ 14 + EM( FUSE_SETATTR, "FUSE_SETATTR") \ 15 + EM( FUSE_READLINK, "FUSE_READLINK") \ 16 + EM( FUSE_SYMLINK, "FUSE_SYMLINK") \ 17 + EM( FUSE_MKNOD, "FUSE_MKNOD") \ 18 + EM( FUSE_MKDIR, "FUSE_MKDIR") \ 19 + EM( FUSE_UNLINK, "FUSE_UNLINK") \ 20 + EM( FUSE_RMDIR, "FUSE_RMDIR") \ 21 + EM( FUSE_RENAME, "FUSE_RENAME") \ 22 + EM( FUSE_LINK, "FUSE_LINK") \ 23 + EM( FUSE_OPEN, "FUSE_OPEN") \ 24 + EM( FUSE_READ, "FUSE_READ") \ 25 + EM( FUSE_WRITE, "FUSE_WRITE") \ 26 + EM( FUSE_STATFS, "FUSE_STATFS") \ 27 + EM( FUSE_RELEASE, "FUSE_RELEASE") \ 28 + EM( FUSE_FSYNC, "FUSE_FSYNC") \ 29 + EM( FUSE_SETXATTR, "FUSE_SETXATTR") \ 30 + EM( FUSE_GETXATTR, "FUSE_GETXATTR") \ 31 + EM( FUSE_LISTXATTR, "FUSE_LISTXATTR") \ 32 + EM( FUSE_REMOVEXATTR, "FUSE_REMOVEXATTR") \ 33 + EM( FUSE_FLUSH, "FUSE_FLUSH") \ 34 + EM( FUSE_INIT, "FUSE_INIT") \ 35 + EM( FUSE_OPENDIR, "FUSE_OPENDIR") \ 36 + EM( FUSE_READDIR, "FUSE_READDIR") \ 37 + EM( FUSE_RELEASEDIR, "FUSE_RELEASEDIR") \ 38 + EM( FUSE_FSYNCDIR, "FUSE_FSYNCDIR") \ 39 + EM( FUSE_GETLK, "FUSE_GETLK") \ 40 + EM( FUSE_SETLK, "FUSE_SETLK") \ 41 + EM( FUSE_SETLKW, "FUSE_SETLKW") \ 42 + EM( FUSE_ACCESS, "FUSE_ACCESS") \ 43 + EM( FUSE_CREATE, "FUSE_CREATE") \ 44 + EM( FUSE_INTERRUPT, "FUSE_INTERRUPT") \ 45 + EM( FUSE_BMAP, "FUSE_BMAP") \ 46 + EM( FUSE_DESTROY, "FUSE_DESTROY") \ 47 + EM( FUSE_IOCTL, "FUSE_IOCTL") \ 48 + EM( FUSE_POLL, "FUSE_POLL") \ 49 + EM( FUSE_NOTIFY_REPLY, "FUSE_NOTIFY_REPLY") \ 50 + EM( FUSE_BATCH_FORGET, "FUSE_BATCH_FORGET") \ 51 + EM( FUSE_FALLOCATE, "FUSE_FALLOCATE") \ 52 + EM( FUSE_READDIRPLUS, "FUSE_READDIRPLUS") \ 53 + EM( FUSE_RENAME2, "FUSE_RENAME2") \ 54 + EM( FUSE_LSEEK, "FUSE_LSEEK") \ 55 + EM( FUSE_COPY_FILE_RANGE, "FUSE_COPY_FILE_RANGE") \ 56 + EM( FUSE_SETUPMAPPING, "FUSE_SETUPMAPPING") \ 57 + EM( FUSE_REMOVEMAPPING, "FUSE_REMOVEMAPPING") \ 58 + EM( FUSE_SYNCFS, "FUSE_SYNCFS") \ 59 + EM( FUSE_TMPFILE, "FUSE_TMPFILE") \ 60 + EM( FUSE_STATX, "FUSE_STATX") \ 61 + EMe(CUSE_INIT, "CUSE_INIT") 62 + 63 + /* 64 + * This will turn the above table into TRACE_DEFINE_ENUM() for each of the 65 + * entries. 66 + */ 67 + #undef EM 68 + #undef EMe 69 + #define EM(a, b) TRACE_DEFINE_ENUM(a); 70 + #define EMe(a, b) TRACE_DEFINE_ENUM(a); 71 + 72 + OPCODES 73 + 74 + /* Now we redfine it with the table that __print_symbolic needs. */ 75 + #undef EM 76 + #undef EMe 77 + #define EM(a, b) {a, b}, 78 + #define EMe(a, b) {a, b} 79 + 80 + TRACE_EVENT(fuse_request_send, 81 + TP_PROTO(const struct fuse_req *req), 82 + 83 + TP_ARGS(req), 84 + 85 + TP_STRUCT__entry( 86 + __field(dev_t, connection) 87 + __field(uint64_t, unique) 88 + __field(enum fuse_opcode, opcode) 89 + __field(uint32_t, len) 90 + ), 91 + 92 + TP_fast_assign( 93 + __entry->connection = req->fm->fc->dev; 94 + __entry->unique = req->in.h.unique; 95 + __entry->opcode = req->in.h.opcode; 96 + __entry->len = req->in.h.len; 97 + ), 98 + 99 + TP_printk("connection %u req %llu opcode %u (%s) len %u ", 100 + __entry->connection, __entry->unique, __entry->opcode, 101 + __print_symbolic(__entry->opcode, OPCODES), __entry->len) 102 + ); 103 + 104 + TRACE_EVENT(fuse_request_end, 105 + TP_PROTO(const struct fuse_req *req), 106 + 107 + TP_ARGS(req), 108 + 109 + TP_STRUCT__entry( 110 + __field(dev_t, connection) 111 + __field(uint64_t, unique) 112 + __field(uint32_t, len) 113 + __field(int32_t, error) 114 + ), 115 + 116 + TP_fast_assign( 117 + __entry->connection = req->fm->fc->dev; 118 + __entry->unique = req->in.h.unique; 119 + __entry->len = req->out.h.len; 120 + __entry->error = req->out.h.error; 121 + ), 122 + 123 + TP_printk("connection %u req %llu len %u error %d", __entry->connection, 124 + __entry->unique, __entry->len, __entry->error) 125 + ); 126 + 127 + #endif /* _TRACE_FUSE_H */ 128 + 129 + #undef TRACE_INCLUDE_PATH 130 + #define TRACE_INCLUDE_PATH . 131 + #define TRACE_INCLUDE_FILE fuse_trace 132 + #include <trace/define_trace.h>