add match_strlcpy() us it to make v9fs make uname and remotename parsing more robust

match_strcpy() is a somewhat creepy function: the caller needs to make sure
that the destination buffer is big enough, and when he screws up or
forgets, match_strcpy() happily overruns the buffer.

There's exactly one customer: v9fs_parse_options().  I believe it currently
can't overflow its buffer, but that's not exactly obvious.

The source string is a substing of the mount options.  The kernel silently
truncates those to PAGE_SIZE bytes, including the terminating zero.  See
compat_sys_mount() and do_mount().

The destination buffer is obtained from __getname(), which allocates from
name_cachep, which is initialized by vfs_caches_init() for size PATH_MAX.

We're safe as long as PATH_MAX <= PAGE_SIZE.  PATH_MAX is 4096.  As far as
I know, the smallest PAGE_SIZE is also 4096.

Here's a patch that makes the code a bit more obviously correct.  It
doesn't depend on PATH_MAX <= PAGE_SIZE.

Signed-off-by: Markus Armbruster <[email protected]>
Cc: Latchesar Ionkov <[email protected]>
Cc: Jim Meyering <[email protected]>
Cc: "Randy.Dunlap" <[email protected]>
Signed-off-by: Andrew Morton <[email protected]>
Signed-off-by: Eric Van Hensbergen <[email protected]>
This commit is contained in:
Markus Armbruster 2008-02-26 09:57:11 -06:00 • committed by Eric Van Hensbergen
commit b32a09db4f
3 changed files with 23 additions and 15 deletions

View file

@ -125,10 +125,10 @@ static void v9fs_parse_options(struct v9fs_session_info *v9ses)
v9ses->afid = option;
break;
case Opt_uname:
match_strcpy(v9ses->uname, &args[0]);
match_strlcpy(v9ses->uname, &args[0], PATH_MAX);
break;
case Opt_remotename:
match_strcpy(v9ses->aname, &args[0]);
match_strlcpy(v9ses->aname, &args[0], PATH_MAX);
break;
case Opt_nodevmap:
v9ses->nodev = 1;