import of ftp.dlink.com/GPL/DSMG-600_reB/ppclinux.tar.gz
[linux-2.4.21-pre4.git] / net / sunrpc / sysctl.c
1 /*
2  * linux/net/sunrpc/sysctl.c
3  *
4  * Sysctl interface to sunrpc module. This is for debugging only now.
5  *
6  * I would prefer to register the sunrpc table below sys/net, but that's
7  * impossible at the moment.
8  */
9
10 #include <linux/config.h>
11 #include <linux/version.h>
12 #include <linux/types.h>
13 #include <linux/linkage.h>
14 #include <linux/ctype.h>
15 #include <linux/fs.h>
16 #include <linux/sysctl.h>
17 #define __NO_VERSION__
18 #include <linux/module.h>
19
20 #include <asm/uaccess.h>
21 #include <linux/sunrpc/types.h>
22 #include <linux/sunrpc/sched.h>
23 #include <linux/sunrpc/stats.h>
24
25 /*
26  * Declare the debug flags here
27  */
28 unsigned int    rpc_debug;
29 unsigned int    nfs_debug;
30 unsigned int    nfsd_debug;
31 unsigned int    nlm_debug;
32
33 #ifdef RPC_DEBUG
34
35 static struct ctl_table_header *sunrpc_table_header;
36 static ctl_table                sunrpc_table[];
37
38 void
39 rpc_register_sysctl(void)
40 {
41         if (!sunrpc_table_header) {
42                 sunrpc_table_header = register_sysctl_table(sunrpc_table, 1);
43 #ifdef CONFIG_PROC_FS
44                 if (sunrpc_table[0].de)
45                         sunrpc_table[0].de->owner = THIS_MODULE;
46 #endif
47         }
48                         
49 }
50
51 void
52 rpc_unregister_sysctl(void)
53 {
54         if (sunrpc_table_header) {
55                 unregister_sysctl_table(sunrpc_table_header);
56                 sunrpc_table_header = NULL;
57         }
58 }
59
60 static int
61 proc_dodebug(ctl_table *table, int write, struct file *file,
62                                 void *buffer, size_t *lenp)
63 {
64         char            tmpbuf[20], *p, c;
65         unsigned int    value;
66         size_t          left, len;
67
68         if ((file->f_pos && !write) || !*lenp) {
69                 *lenp = 0;
70                 return 0;
71         }
72
73         left = *lenp;
74
75         if (write) {
76                 if (!access_ok(VERIFY_READ, buffer, left))
77                         return -EFAULT;
78                 p = (char *) buffer;
79                 while (left && __get_user(c, p) >= 0 && isspace(c))
80                         left--, p++;
81                 if (!left)
82                         goto done;
83
84                 if (left > sizeof(tmpbuf) - 1)
85                         return -EINVAL;
86                 copy_from_user(tmpbuf, p, left);
87                 tmpbuf[left] = '\0';
88
89                 for (p = tmpbuf, value = 0; '0' <= *p && *p <= '9'; p++, left--)
90                         value = 10 * value + (*p - '0');
91                 if (*p && !isspace(*p))
92                         return -EINVAL;
93                 while (left && isspace(*p))
94                         left--, p++;
95                 *(unsigned int *) table->data = value;
96                 /* Display the RPC tasks on writing to rpc_debug */
97                 if (table->ctl_name == CTL_RPCDEBUG) {
98                         rpc_show_tasks();
99                 }
100         } else {
101                 if (!access_ok(VERIFY_WRITE, buffer, left))
102                         return -EFAULT;
103                 len = sprintf(tmpbuf, "%d", *(unsigned int *) table->data);
104                 if (len > left)
105                         len = left;
106                 copy_to_user(buffer, tmpbuf, len);
107                 if ((left -= len) > 0) {
108                         put_user('\n', (char *)buffer + len);
109                         left--;
110                 }
111         }
112
113 done:
114         *lenp -= left;
115         file->f_pos += *lenp;
116         return 0;
117 }
118
119 #define DIRENTRY(nam1, nam2, child)     \
120         {CTL_##nam1, #nam2, NULL, 0, 0555, child }
121 #define DBGENTRY(nam1, nam2)    \
122         {CTL_##nam1##DEBUG, #nam2 "_debug", &nam2##_debug, sizeof(int),\
123          0644, NULL, &proc_dodebug}
124
125 static ctl_table                debug_table[] = {
126         DBGENTRY(RPC,  rpc),
127         DBGENTRY(NFS,  nfs),
128         DBGENTRY(NFSD, nfsd),
129         DBGENTRY(NLM,  nlm),
130         {0}
131 };
132
133 static ctl_table                sunrpc_table[] = {
134         DIRENTRY(SUNRPC, sunrpc, debug_table),
135         {0}
136 };
137
138 #endif