[PATCH] Fix keyctl usage of strnlen_user()
authorDavi Arnaut <davi.arnaut@gmail.com>
Fri, 3 Feb 2006 11:04:46 +0000 (03:04 -0800)
committerChris Wright <chrisw@sous-sol.org>
Fri, 10 Feb 2006 07:20:11 +0000 (23:20 -0800)
In the small window between strnlen_user() and copy_from_user() userspace
could alter the terminating `\0' character.

Signed-off-by: Davi Arnaut <davi.arnaut@gmail.com>
Cc: David Howells <dhowells@redhat.com>
Cc: <stable@kernel.org>
Signed-off-by: Andrew Morton <akpm@osdl.org>
Signed-off-by: Chris Wright <chrisw@sous-sol.org>
Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
security/keys/keyctl.c

index b7a468fabdf9a22e4ca1eecfc6da96f055512a58..337bc123923dde99081a35066fc7bb89e95dc865 100644 (file)
@@ -66,9 +66,10 @@ asmlinkage long sys_add_key(const char __user *_type,
        description = kmalloc(dlen + 1, GFP_KERNEL);
        if (!description)
                goto error;
+       description[dlen] = '\0';
 
        ret = -EFAULT;
-       if (copy_from_user(description, _description, dlen + 1) != 0)
+       if (copy_from_user(description, _description, dlen) != 0)
                goto error2;
 
        /* pull the payload in if one was supplied */
@@ -160,9 +161,10 @@ asmlinkage long sys_request_key(const char __user *_type,
        description = kmalloc(dlen + 1, GFP_KERNEL);
        if (!description)
                goto error;
+       description[dlen] = '\0';
 
        ret = -EFAULT;
-       if (copy_from_user(description, _description, dlen + 1) != 0)
+       if (copy_from_user(description, _description, dlen) != 0)
                goto error2;
 
        /* pull the callout info into kernel space */
@@ -181,9 +183,10 @@ asmlinkage long sys_request_key(const char __user *_type,
                callout_info = kmalloc(dlen + 1, GFP_KERNEL);
                if (!callout_info)
                        goto error2;
+               callout_info[dlen] = '\0';
 
                ret = -EFAULT;
-               if (copy_from_user(callout_info, _callout_info, dlen + 1) != 0)
+               if (copy_from_user(callout_info, _callout_info, dlen) != 0)
                        goto error3;
        }
 
@@ -278,9 +281,10 @@ long keyctl_join_session_keyring(const char __user *_name)
                name = kmalloc(nlen + 1, GFP_KERNEL);
                if (!name)
                        goto error;
+               name[nlen] = '\0';
 
                ret = -EFAULT;
-               if (copy_from_user(name, _name, nlen + 1) != 0)
+               if (copy_from_user(name, _name, nlen) != 0)
                        goto error2;
        }
 
@@ -582,9 +586,10 @@ long keyctl_keyring_search(key_serial_t ringid,
        description = kmalloc(dlen + 1, GFP_KERNEL);
        if (!description)
                goto error;
+       description[dlen] = '\0';
 
        ret = -EFAULT;
-       if (copy_from_user(description, _description, dlen + 1) != 0)
+       if (copy_from_user(description, _description, dlen) != 0)
                goto error2;
 
        /* get the keyring at which to begin the search */