diff options
Diffstat (limited to 'fs/devpts/inode.c')
-rw-r--r-- | fs/devpts/inode.c | 76 |
1 files changed, 49 insertions, 27 deletions
diff --git a/fs/devpts/inode.c b/fs/devpts/inode.c index bfb8a230bac9..14c5620b5cab 100644 --- a/fs/devpts/inode.c +++ b/fs/devpts/inode.c | |||
@@ -18,6 +18,7 @@ | |||
18 | #include <linux/mount.h> | 18 | #include <linux/mount.h> |
19 | #include <linux/tty.h> | 19 | #include <linux/tty.h> |
20 | #include <linux/devpts_fs.h> | 20 | #include <linux/devpts_fs.h> |
21 | #include <linux/parser.h> | ||
21 | 22 | ||
22 | #define DEVPTS_SUPER_MAGIC 0x1cd1 | 23 | #define DEVPTS_SUPER_MAGIC 0x1cd1 |
23 | 24 | ||
@@ -32,39 +33,60 @@ static struct { | |||
32 | umode_t mode; | 33 | umode_t mode; |
33 | } config = {.mode = 0600}; | 34 | } config = {.mode = 0600}; |
34 | 35 | ||
36 | enum { | ||
37 | Opt_uid, Opt_gid, Opt_mode, | ||
38 | Opt_err | ||
39 | }; | ||
40 | |||
41 | static match_table_t tokens = { | ||
42 | {Opt_uid, "uid=%u"}, | ||
43 | {Opt_gid, "gid=%u"}, | ||
44 | {Opt_mode, "mode=%o"}, | ||
45 | {Opt_err, NULL} | ||
46 | }; | ||
47 | |||
35 | static int devpts_remount(struct super_block *sb, int *flags, char *data) | 48 | static int devpts_remount(struct super_block *sb, int *flags, char *data) |
36 | { | 49 | { |
37 | int setuid = 0; | 50 | char *p; |
38 | int setgid = 0; | 51 | |
39 | uid_t uid = 0; | 52 | config.setuid = 0; |
40 | gid_t gid = 0; | 53 | config.setgid = 0; |
41 | umode_t mode = 0600; | 54 | config.uid = 0; |
42 | char *this_char; | 55 | config.gid = 0; |
43 | 56 | config.mode = 0600; | |
44 | this_char = NULL; | 57 | |
45 | while ((this_char = strsep(&data, ",")) != NULL) { | 58 | while ((p = strsep(&data, ",")) != NULL) { |
46 | int n; | 59 | substring_t args[MAX_OPT_ARGS]; |
47 | char dummy; | 60 | int token; |
48 | if (!*this_char) | 61 | int option; |
62 | |||
63 | if (!*p) | ||
49 | continue; | 64 | continue; |
50 | if (sscanf(this_char, "uid=%i%c", &n, &dummy) == 1) { | 65 | |
51 | setuid = 1; | 66 | token = match_token(p, tokens, args); |
52 | uid = n; | 67 | switch (token) { |
53 | } else if (sscanf(this_char, "gid=%i%c", &n, &dummy) == 1) { | 68 | case Opt_uid: |
54 | setgid = 1; | 69 | if (match_int(&args[0], &option)) |
55 | gid = n; | 70 | return -EINVAL; |
56 | } else if (sscanf(this_char, "mode=%o%c", &n, &dummy) == 1) | 71 | config.uid = option; |
57 | mode = n & ~S_IFMT; | 72 | config.setuid = 1; |
58 | else { | 73 | break; |
59 | printk("devpts: called with bogus options\n"); | 74 | case Opt_gid: |
75 | if (match_int(&args[0], &option)) | ||
76 | return -EINVAL; | ||
77 | config.gid = option; | ||
78 | config.setgid = 1; | ||
79 | break; | ||
80 | case Opt_mode: | ||
81 | if (match_octal(&args[0], &option)) | ||
82 | return -EINVAL; | ||
83 | config.mode = option & ~S_IFMT; | ||
84 | break; | ||
85 | default: | ||
86 | printk(KERN_ERR "devpts: called with bogus options\n"); | ||
60 | return -EINVAL; | 87 | return -EINVAL; |
61 | } | 88 | } |
62 | } | 89 | } |
63 | config.setuid = setuid; | ||
64 | config.setgid = setgid; | ||
65 | config.uid = uid; | ||
66 | config.gid = gid; | ||
67 | config.mode = mode; | ||
68 | 90 | ||
69 | return 0; | 91 | return 0; |
70 | } | 92 | } |