Commit bcb23e3c authored by Trond Myklebust's avatar Trond Myklebust

NFSROOT: clean up the parser routines (patch by Fabian Frederic)

parent 15820773
...@@ -66,7 +66,8 @@ ...@@ -66,7 +66,8 @@
* is NOT for the length of the hostname. * is NOT for the length of the hostname.
* Hua Qin : Support for mounting root file system via * Hua Qin : Support for mounting root file system via
* NFS over TCP. * NFS over TCP.
*/ * Fabian Frederick: Option parser rebuilt (using parser lib)
*/
#include <linux/config.h> #include <linux/config.h>
#include <linux/types.h> #include <linux/types.h>
...@@ -85,6 +86,7 @@ ...@@ -85,6 +86,7 @@
#include <linux/inet.h> #include <linux/inet.h>
#include <linux/root_dev.h> #include <linux/root_dev.h>
#include <net/ipconfig.h> #include <net/ipconfig.h>
#include <linux/parser.h>
/* Define this to allow debugging output */ /* Define this to allow debugging output */
#undef NFSROOT_DEBUG #undef NFSROOT_DEBUG
...@@ -114,92 +116,158 @@ static int mount_port __initdata = 0; /* Mount daemon port number */ ...@@ -114,92 +116,158 @@ static int mount_port __initdata = 0; /* Mount daemon port number */
***************************************************************************/ ***************************************************************************/
/* enum {
* The following integer options are recognized Opt_port, Opt_rsize, Opt_wsize, Opt_timeo, Opt_retrans, Opt_acregmin,
*/ Opt_acregmax, Opt_acdirmin, Opt_acdirmax, Opt_soft, Opt_hard, Opt_intr,
static struct nfs_int_opts { Opt_nointr, Opt_posix, Opt_noposix, Opt_cto, Opt_nocto, Opt_ac,
char *name; Opt_noac, Opt_lock, Opt_nolock, Opt_v2, Opt_v3, Opt_udp, Opt_tcp,
int *val; Opt_broken_suid, Opt_err,
} root_int_opts[] __initdata = {
{ "port", &nfs_port },
{ "rsize", &nfs_data.rsize },
{ "wsize", &nfs_data.wsize },
{ "timeo", &nfs_data.timeo },
{ "retrans", &nfs_data.retrans },
{ "acregmin", &nfs_data.acregmin },
{ "acregmax", &nfs_data.acregmax },
{ "acdirmin", &nfs_data.acdirmin },
{ "acdirmax", &nfs_data.acdirmax },
{ NULL, NULL }
}; };
static match_table_t tokens = {
/* {Opt_port, "port=%u"},
* And now the flag options {Opt_rsize, "rsize=%u"},
*/ {Opt_wsize, "wsize=%u"},
static struct nfs_bool_opts { {Opt_timeo, "timeo=%u"},
char *name; {Opt_retrans, "retrans=%u"},
int and_mask; {Opt_acregmin, "acregmin=%u"},
int or_mask; {Opt_acregmax, "acregmax=%u"},
} root_bool_opts[] __initdata = { {Opt_acdirmin, "acdirmin=%u"},
{ "soft", ~NFS_MOUNT_SOFT, NFS_MOUNT_SOFT }, {Opt_acdirmax, "acdirmax=%u"},
{ "hard", ~NFS_MOUNT_SOFT, 0 }, {Opt_soft, "soft"},
{ "intr", ~NFS_MOUNT_INTR, NFS_MOUNT_INTR }, {Opt_hard, "hard"},
{ "nointr", ~NFS_MOUNT_INTR, 0 }, {Opt_intr, "intr"},
{ "posix", ~NFS_MOUNT_POSIX, NFS_MOUNT_POSIX }, {Opt_nointr, "nointr"},
{ "noposix", ~NFS_MOUNT_POSIX, 0 }, {Opt_posix, "posix"},
{ "cto", ~NFS_MOUNT_NOCTO, 0 }, {Opt_noposix, "noposix"},
{ "nocto", ~NFS_MOUNT_NOCTO, NFS_MOUNT_NOCTO }, {Opt_cto, "cto"},
{ "ac", ~NFS_MOUNT_NOAC, 0 }, {Opt_nocto, "nocto"},
{ "noac", ~NFS_MOUNT_NOAC, NFS_MOUNT_NOAC }, {Opt_ac, "ac"},
{ "lock", ~NFS_MOUNT_NONLM, 0 }, {Opt_noac, "noac"},
{ "nolock", ~NFS_MOUNT_NONLM, NFS_MOUNT_NONLM }, {Opt_lock, "lock"},
#ifdef CONFIG_NFS_V3 {Opt_nolock, "nolock"},
{ "v2", ~NFS_MOUNT_VER3, 0 }, {Opt_v2, "v2"},
{ "v3", ~NFS_MOUNT_VER3, NFS_MOUNT_VER3 }, {Opt_v3, "v3"},
#endif {Opt_udp, "udp"},
{ "udp", ~NFS_MOUNT_TCP, 0 }, {Opt_tcp, "tcp"},
{ "tcp", ~NFS_MOUNT_TCP, NFS_MOUNT_TCP }, {Opt_broken_suid, "broken_suid"},
{ "broken_suid",~NFS_MOUNT_BROKEN_SUID, NFS_MOUNT_BROKEN_SUID }, {Opt_err, NULL}
{ NULL, 0, 0 }
}; };
/* /*
* Parse option string. * Parse option string.
*/ */
static void __init root_nfs_parse(char *name, char *buf)
static int __init root_nfs_parse(char *name, char *buf)
{ {
char *options, *val, *cp;
char *p;
if ((options = strchr(name, ','))) { substring_t args[MAX_OPT_ARGS];
*options++ = 0; int option;
while ((cp = strsep(&options, ",")) != NULL) {
if (!*cp) if (!name)
continue; return 1;
if ((val = strchr(cp, '='))) {
struct nfs_int_opts *opts = root_int_opts; if (name[0] && strcmp(name, "default")){
*val++ = '\0'; strlcpy(buf, name, NFS_MAXPATHLEN);
while (opts->name && strcmp(opts->name, cp)) return 1;
opts++; }
if (opts->name) while ((p = strsep (&name, ",")) != NULL) {
*(opts->val) = (int) simple_strtoul(val, NULL, 10); int token;
} else { if (!*p)
struct nfs_bool_opts *opts = root_bool_opts; continue;
while (opts->name && strcmp(opts->name, cp)) token = match_token(p, tokens, args);
opts++;
if (opts->name) { /* %u tokens only */
nfs_data.flags &= opts->and_mask; if (match_int(&args[0], &option))
nfs_data.flags |= opts->or_mask; return 0;
} switch (token) {
} case Opt_port:
nfs_port = option;
break;
case Opt_rsize:
nfs_data.rsize = option;
break;
case Opt_wsize:
nfs_data.wsize = option;
break;
case Opt_timeo:
nfs_data.timeo = option;
break;
case Opt_retrans:
nfs_data.retrans = option;
break;
case Opt_acregmin:
nfs_data.acregmin = option;
break;
case Opt_acregmax:
nfs_data.acregmax = option;
break;
case Opt_acdirmin:
nfs_data.acdirmin = option;
break;
case Opt_acdirmax:
nfs_data.acdirmax = option;
break;
case Opt_soft:
nfs_data.flags |= NFS_MOUNT_SOFT;
break;
case Opt_hard:
nfs_data.flags &= ~NFS_MOUNT_SOFT;
break;
case Opt_intr:
nfs_data.flags |= NFS_MOUNT_INTR;
break;
case Opt_nointr:
nfs_data.flags &= ~NFS_MOUNT_INTR;
break;
case Opt_posix:
nfs_data.flags |= NFS_MOUNT_POSIX;
break;
case Opt_noposix:
nfs_data.flags &= ~NFS_MOUNT_POSIX;
break;
case Opt_cto:
nfs_data.flags &= ~NFS_MOUNT_NOCTO;
break;
case Opt_nocto:
nfs_data.flags |= NFS_MOUNT_NOCTO;
break;
case Opt_ac:
nfs_data.flags &= ~NFS_MOUNT_NOAC;
break;
case Opt_noac:
nfs_data.flags |= NFS_MOUNT_NOAC;
break;
case Opt_lock:
nfs_data.flags &= ~NFS_MOUNT_NONLM;
break;
case Opt_nolock:
nfs_data.flags |= NFS_MOUNT_NONLM;
break;
case Opt_v2:
nfs_data.flags &= ~NFS_MOUNT_VER3;
break;
case Opt_v3:
nfs_data.flags |= NFS_MOUNT_VER3;
break;
case Opt_udp:
nfs_data.flags &= ~NFS_MOUNT_TCP;
break;
case Opt_tcp:
nfs_data.flags |= NFS_MOUNT_TCP;
break;
case Opt_broken_suid:
nfs_data.flags |= NFS_MOUNT_BROKEN_SUID;
break;
default :
return 0;
} }
} }
if (name[0] && strcmp(name, "default")) return 1;
strlcpy(buf, name, NFS_MAXPATHLEN);
} }
/* /*
* Prepare the NFS data structure and parse all options. * Prepare the NFS data structure and parse all options.
*/ */
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment