aboutsummaryrefslogtreecommitdiffstats
path: root/kernel/params.c
diff options
context:
space:
mode:
authorYi Yang <yi.y.yang@intel.com>2008-02-08 07:21:57 -0500
committerLinus Torvalds <torvalds@woody.linux-foundation.org>2008-02-08 12:22:41 -0500
commit06b2a76d25d3cfbd14680021c1d356c91be6904e (patch)
treed7bc9d65fc7cfa9b30a9e3c731fd7a3e8d8c0100 /kernel/params.c
parent10e6f32bdf02448f787d78647e75cf98a02f19a4 (diff)
Add new string functions strict_strto* and convert kernel params to use them
Currently, for every sysfs node, the callers will be responsible for implementing store operation, so many many callers are doing duplicate things to validate input, they have the same mistakes because they are calling simple_strtol/ul/ll/uul, especially for module params, they are just numeric, but you can echo such values as 0x1234xxx, 07777888 and 1234aaa, for these cases, module params store operation just ignores succesive invalid char and converts prefix part to a numeric although input is acctually invalid. This patch tries to fix the aforementioned issues and implements strict_strtox serial functions, kernel/params.c uses them to strictly validate input, so module params will reject such values as 0x1234xxxx and returns an error: write error: Invalid argument Any modules which export numeric sysfs node can use strict_strtox instead of simple_strtox to reject any invalid input. Here are some test results: Before applying this patch: [root@yangyi-dev /]# cat /sys/module/e1000/parameters/copybreak 4096 [root@yangyi-dev /]# echo 0x1000 > /sys/module/e1000/parameters/copybreak [root@yangyi-dev /]# cat /sys/module/e1000/parameters/copybreak 4096 [root@yangyi-dev /]# echo 0x1000g > /sys/module/e1000/parameters/copybreak [root@yangyi-dev /]# cat /sys/module/e1000/parameters/copybreak 4096 [root@yangyi-dev /]# echo 0x1000gggggggg > /sys/module/e1000/parameters/copybreak [root@yangyi-dev /]# cat /sys/module/e1000/parameters/copybreak 4096 [root@yangyi-dev /]# echo 010000 > /sys/module/e1000/parameters/copybreak [root@yangyi-dev /]# cat /sys/module/e1000/parameters/copybreak 4096 [root@yangyi-dev /]# echo 0100008 > /sys/module/e1000/parameters/copybreak [root@yangyi-dev /]# cat /sys/module/e1000/parameters/copybreak 4096 [root@yangyi-dev /]# echo 010000aaaaa > /sys/module/e1000/parameters/copybreak [root@yangyi-dev /]# cat /sys/module/e1000/parameters/copybreak 4096 [root@yangyi-dev /]# After applying this patch: [root@yangyi-dev /]# cat /sys/module/e1000/parameters/copybreak 4096 [root@yangyi-dev /]# echo 0x1000 > /sys/module/e1000/parameters/copybreak [root@yangyi-dev /]# cat /sys/module/e1000/parameters/copybreak 4096 [root@yangyi-dev /]# echo 0x1000g > /sys/module/e1000/parameters/copybreak -bash: echo: write error: Invalid argument [root@yangyi-dev /]# cat /sys/module/e1000/parameters/copybreak 4096 [root@yangyi-dev /]# echo 0x1000gggggggg > /sys/module/e1000/parameters/copybreak -bash: echo: write error: Invalid argument [root@yangyi-dev /]# echo 010000 > /sys/module/e1000/parameters/copybreak [root@yangyi-dev /]# echo 0100008 > /sys/module/e1000/parameters/copybreak -bash: echo: write error: Invalid argument [root@yangyi-dev /]# echo 010000aaaaa > /sys/module/e1000/parameters/copybreak -bash: echo: write error: Invalid argument [root@yangyi-dev /]# cat /sys/module/e1000/parameters/copybreak 4096 [root@yangyi-dev /]# echo -n 4096 > /sys/module/e1000/parameters/copybreak [root@yangyi-dev /]# cat /sys/module/e1000/parameters/copybreak 4096 [root@yangyi-dev /]# [akpm@linux-foundation.org: fix compiler warnings] [akpm@linux-foundation.org: fix off-by-one found by tiwai@suse.de] Signed-off-by: Yi Yang <yi.y.yang@intel.com> Cc: Greg KH <greg@kroah.com> Cc: "Randy.Dunlap" <rdunlap@xenotime.net> Cc: Takashi Iwai <tiwai@suse.de> Cc: Hugh Dickins <hugh@veritas.com> Signed-off-by: Andrew Morton <akpm@linux-foundation.org> Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Diffstat (limited to 'kernel/params.c')
-rw-r--r--kernel/params.c20
1 files changed, 10 insertions, 10 deletions
diff --git a/kernel/params.c b/kernel/params.c
index e28c70628bb7..afc46a23eb6d 100644
--- a/kernel/params.c
+++ b/kernel/params.c
@@ -180,12 +180,12 @@ int parse_args(const char *name,
180#define STANDARD_PARAM_DEF(name, type, format, tmptype, strtolfn) \ 180#define STANDARD_PARAM_DEF(name, type, format, tmptype, strtolfn) \
181 int param_set_##name(const char *val, struct kernel_param *kp) \ 181 int param_set_##name(const char *val, struct kernel_param *kp) \
182 { \ 182 { \
183 char *endp; \
184 tmptype l; \ 183 tmptype l; \
184 int ret; \
185 \ 185 \
186 if (!val) return -EINVAL; \ 186 if (!val) return -EINVAL; \
187 l = strtolfn(val, &endp, 0); \ 187 ret = strtolfn(val, 0, &l); \
188 if (endp == val || ((type)l != l)) \ 188 if (ret == -EINVAL || ((type)l != l)) \
189 return -EINVAL; \ 189 return -EINVAL; \
190 *((type *)kp->arg) = l; \ 190 *((type *)kp->arg) = l; \
191 return 0; \ 191 return 0; \
@@ -195,13 +195,13 @@ int parse_args(const char *name,
195 return sprintf(buffer, format, *((type *)kp->arg)); \ 195 return sprintf(buffer, format, *((type *)kp->arg)); \
196 } 196 }
197 197
198STANDARD_PARAM_DEF(byte, unsigned char, "%c", unsigned long, simple_strtoul); 198STANDARD_PARAM_DEF(byte, unsigned char, "%c", unsigned long, strict_strtoul);
199STANDARD_PARAM_DEF(short, short, "%hi", long, simple_strtol); 199STANDARD_PARAM_DEF(short, short, "%hi", long, strict_strtol);
200STANDARD_PARAM_DEF(ushort, unsigned short, "%hu", unsigned long, simple_strtoul); 200STANDARD_PARAM_DEF(ushort, unsigned short, "%hu", unsigned long, strict_strtoul);
201STANDARD_PARAM_DEF(int, int, "%i", long, simple_strtol); 201STANDARD_PARAM_DEF(int, int, "%i", long, strict_strtol);
202STANDARD_PARAM_DEF(uint, unsigned int, "%u", unsigned long, simple_strtoul); 202STANDARD_PARAM_DEF(uint, unsigned int, "%u", unsigned long, strict_strtoul);
203STANDARD_PARAM_DEF(long, long, "%li", long, simple_strtol); 203STANDARD_PARAM_DEF(long, long, "%li", long, strict_strtol);
204STANDARD_PARAM_DEF(ulong, unsigned long, "%lu", unsigned long, simple_strtoul); 204STANDARD_PARAM_DEF(ulong, unsigned long, "%lu", unsigned long, strict_strtoul);
205 205
206int param_set_charp(const char *val, struct kernel_param *kp) 206int param_set_charp(const char *val, struct kernel_param *kp)
207{ 207{