Revision: linux-fs--kernel-read-vuln--0--patch-1 Archive: dilinger@voxel.net--2004-public Creator: Andres Salomon Date: Thu Dec 23 23:10:11 EST 2004 Standard-date: 2004-12-24 04:10:11 GMT Modified-files: binfmt_em86.c binfmt_misc.c binfmt_script.c compat.c exec.c New-patches: dilinger@voxel.net--2004-public/linux-fs--kernel-read-vuln--0--patch-1 Summary: fix bugs mentioned in advisory Keywords: http://seclists.org/lists/bugtraq/2004/Dec/0214.html This fixes all 6 places mentioned in the advisory. Most are in binfmt_loader callbacks, called from exec::do_execve; they fail w/ -EIO if the kernel_read succeeded, but for some reason a short read was done. Revision: linux-fs--kernel-read-vuln--0--patch-2 Archive: dilinger@voxel.net--2004-public Creator: Andres Salomon Date: Thu Dec 23 23:33:01 EST 2004 Standard-date: 2004-12-24 04:33:01 GMT Modified-files: binfmt_flat.c New-patches: dilinger@voxel.net--2004-public/linux-fs--kernel-read-vuln--0--patch-2 Summary: fix another place where kernel_read isn't sufficiently checked Keywords: I don't know what was up w/ this original check (checking for a res between -4096 and 0, non-inclusive), but it seems.. off. Better to check specifically for BINPRM_BUF_SIZE. --- orig/fs/binfmt_em86.c +++ mod/fs/binfmt_em86.c @@ -89,8 +89,11 @@ bprm->file = file; retval = prepare_binprm(bprm); - if (retval < 0) + if (retval != BINPRM_BUF_SIZE) { + if (retval >= 0) + retval = -EIO; return retval; + } return search_binary_handler(bprm, regs); } --- orig/fs/binfmt_flat.c +++ mod/fs/binfmt_flat.c @@ -780,9 +780,11 @@ return res; res = prepare_binprm(&bprm); - - if (res <= (unsigned long)-4096) + if (res == BINPRM_BUF_SIZE) res = load_flat_file(&bprm, libs, id, NULL); + else if (res >= 0) + res = -EIO; + if (bprm.file) { allow_write_access(bprm.file); fput(bprm.file); --- orig/fs/binfmt_misc.c +++ mod/fs/binfmt_misc.c @@ -195,8 +195,11 @@ } else retval = prepare_binprm (bprm); - if (retval < 0) + if (retval != BINPRM_BUF_SIZE) { + if (retval >= 0) + retval = -EIO; goto _error; + } retval = search_binary_handler (bprm, regs); if (retval < 0) --- orig/fs/binfmt_script.c +++ mod/fs/binfmt_script.c @@ -91,8 +91,11 @@ bprm->file = file; retval = prepare_binprm(bprm); - if (retval < 0) + if (retval != BINPRM_BUF_SIZE) { + if (retval >= 0) + retval = -EIO; return retval; + } return search_binary_handler(bprm,regs); } --- orig/fs/compat.c +++ mod/fs/compat.c @@ -1426,8 +1426,11 @@ goto out; retval = prepare_binprm(bprm); - if (retval < 0) + if (retval != BINPRM_BUF_SIZE) { + if (retval >= 0) + retval = -EIO; goto out; + } retval = copy_strings_kernel(1, &bprm->filename, bprm); if (retval < 0) --- orig/fs/exec.c +++ mod/fs/exec.c @@ -1024,8 +1024,11 @@ bprm->file = file; bprm->loader = loader; retval = prepare_binprm(bprm); - if (retval<0) + if (retval != BINPRM_BUF_SIZE) { + if (retval >= 0) + retval = -EIO; return retval; + } /* should call search_binary_handler recursively here, but it does not matter */ } @@ -1139,8 +1142,11 @@ goto out; retval = prepare_binprm(bprm); - if (retval < 0) + if (retval != BINPRM_BUF_SIZE) { + if (retval >= 0) + retval = -EIO; goto out; + } retval = copy_strings_kernel(1, &bprm->filename, bprm); if (retval < 0)