+static int
+proc_call_handler(void *data, int write,
+ loff_t *ppos, void *buffer, size_t *lenp,
+ int (*handler)(void *data, int write,
+ loff_t pos, void *buffer, int len))
+{
+ int rc = handler(data, write, *ppos, buffer, *lenp);
+
+ if (rc < 0)
+ return rc;
+
+ if (write) {
+ *ppos += *lenp;
+ } else {
+ *lenp = rc;
+ *ppos += rc;
+ }
+ return 0;
+}
+
+#define DECLARE_PROC_HANDLER(name) \
+static int \
+LL_PROC_PROTO(name) \
+{ \
+ DECLARE_LL_PROC_PPOS; \
+ \
+ return proc_call_handler(table->data, write, \
+ ppos, buffer, lenp, \
+ __##name); \
+}
+
+static int __proc_dobitmasks(void *data, int write,
+ loff_t pos, void *buffer, int nob)
+{
+ const int tmpstrlen = 512;
+ char *tmpstr;
+ int rc;
+ unsigned int *mask = data;
+ int is_subsys = (mask == &libcfs_subsystem_debug) ? 1 : 0;
+
+ rc = trace_allocate_string_buffer(&tmpstr, tmpstrlen);
+ if (rc < 0)
+ return rc;
+
+ if (!write) {
+ libcfs_debug_mask2str(tmpstr, tmpstrlen, *mask, is_subsys);
+ rc = strlen(tmpstr);
+
+ if (pos >= rc) {
+ rc = 0;
+ } else {
+ rc = trace_copyout_string(buffer, nob,
+ tmpstr + pos, "\n");
+ }
+ } else {
+ rc = trace_copyin_string(tmpstr, tmpstrlen, buffer, nob);
+ if (rc < 0)
+ return rc;
+
+ rc = libcfs_debug_str2mask(mask, tmpstr, is_subsys);
+ }
+
+ trace_free_string_buffer(tmpstr, tmpstrlen);
+ return rc;
+}
+
+DECLARE_PROC_HANDLER(proc_dobitmasks)
+
+static int __proc_dump_kernel(void *data, int write,
+ loff_t pos, void *buffer, int nob)
+{
+ if (!write)
+ return 0;
+
+ return trace_dump_debug_buffer_usrstr(buffer, nob);
+}
+
+DECLARE_PROC_HANDLER(proc_dump_kernel)
+
+static int __proc_daemon_file(void *data, int write,
+ loff_t pos, void *buffer, int nob)
+{
+ if (!write) {
+ int len = strlen(tracefile);
+
+ if (pos >= len)
+ return 0;
+
+ return trace_copyout_string(buffer, nob,
+ tracefile + pos, "\n");
+ }
+
+ return trace_daemon_command_usrstr(buffer, nob);
+}
+
+DECLARE_PROC_HANDLER(proc_daemon_file)
+
+static int __proc_debug_mb(void *data, int write,
+ loff_t pos, void *buffer, int nob)
+{
+ if (!write) {
+ char tmpstr[32];
+ int len = snprintf(tmpstr, sizeof(tmpstr), "%d",
+ trace_get_debug_mb());
+
+ if (pos >= len)
+ return 0;
+
+ return trace_copyout_string(buffer, nob, tmpstr + pos, "\n");
+ }
+
+ return trace_set_debug_mb_usrstr(buffer, nob);
+}
+
+DECLARE_PROC_HANDLER(proc_debug_mb)