Bug 11063 - lack of GNU_STACK header doesn't result in rwx stack on i386
Summary: lack of GNU_STACK header doesn't result in rwx stack on i386
Status: CLOSED CODE_FIX
Alias: None
Product: Memory Management
Classification: Unclassified
Component: Other (show other bugs)
Hardware: All Linux
: P1 normal
Assignee: Andrew Morton
URL:
Keywords:
Depends on:
Blocks:
 
Reported: 2008-07-09 12:13 UTC by PaX Team
Modified: 2008-07-10 23:31 UTC (History)
1 user (show)

See Also:
Kernel Version:
Subsystem:
Regression: ---
Bisected commit-id:


Attachments

Description PaX Team 2008-07-09 12:13:05 UTC
Latest working kernel version: unknown, probably before the introduction of unlimited argv
Earliest failing kernel version: unknown, probably after the introduction of unlimited argv, 2.6.26-rc9 definitely fails
Distribution:
Hardware Environment:
Software Environment:
Problem Description:
ELF/i386 traditionally has an executable stack which in the PT_GNU_STACK world is provided two ways: if the ELF has a RWE PT_GNU_STACK program header or if it lacks that program header. due to this regression, the latter case results in a non-executable stack with corresponding breakage of (old) userland binaries that use nested function trampolines.

this bug was probably introduced when the unlimited argv feature was merged: in that system the stack vma (and its vm_flags) is initialized too early, before the incoming process' ELF header is consulted, which on i386 means that the personality used for determining the executable status of the stack is that of the old process, not the incoming one. later, in setup_arg_pages, only the explicit setting (disable/enable) of stack executability is honoured, EXSTACK_DEFAULT isn't consulted (i guess the assumption was that the initial ->vm_flags setting got it right).

Steps to reproduce: run any ELF that lacks a PT_GNU_STACK program header and check its stack vma, it'll be rw-, instead of rwx.
Comment 1 Anonymous Emailer 2008-07-09 15:33:11 UTC
Reply-To: akpm@linux-foundation.org


(switched to email.  Please respond via emailed reply-to-all, not via the
bugzilla web interface).

On Wed,  9 Jul 2008 12:13:05 -0700 (PDT) bugme-daemon@bugzilla.kernel.org wrote:

> http://bugzilla.kernel.org/show_bug.cgi?id=11063
> 
>            Summary: lack of GNU_STACK header doesn't result in rwx stack on
>                     i386
>            Product: Memory Management
>            Version: 2.5
>           Platform: All
>         OS/Version: Linux
>               Tree: Mainline
>             Status: NEW
>           Severity: normal
>           Priority: P1
>          Component: Other
>         AssignedTo: akpm@osdl.org
>         ReportedBy: pageexec@freemail.hu
> 
> 
> Latest working kernel version: unknown, probably before the introduction of
> unlimited argv
> Earliest failing kernel version: unknown, probably after the introduction of
> unlimited argv, 2.6.26-rc9 definitely fails
> Distribution:
> Hardware Environment:
> Software Environment:
> Problem Description:
> ELF/i386 traditionally has an executable stack which in the PT_GNU_STACK
> world
> is provided two ways: if the ELF has a RWE PT_GNU_STACK program header or if
> it
> lacks that program header. due to this regression, the latter case results in
> a
> non-executable stack with corresponding breakage of (old) userland binaries
> that use nested function trampolines.
> 
> this bug was probably introduced when the unlimited argv feature was merged:
> in
> that system the stack vma (and its vm_flags) is initialized too early, before
> the incoming process' ELF header is consulted, which on i386 means that the
> personality used for determining the executable status of the stack is that
> of
> the old process, not the incoming one. later, in setup_arg_pages, only the
> explicit setting (disable/enable) of stack executability is honoured,
> EXSTACK_DEFAULT isn't consulted (i guess the assumption was that the initial
> ->vm_flags setting got it right).
> 
> Steps to reproduce: run any ELF that lacks a PT_GNU_STACK program header and
> check its stack vma, it'll be rw-, instead of rwx.
> 
Comment 2 Anonymous Emailer 2008-07-09 15:34:06 UTC
Reply-To: akpm@linux-foundation.org

err, I missed the mailing list cc. Let me resend.

On Wed, 9 Jul 2008 15:27:16 -0700 Andrew Morton <akpm@linux-foundation.org> wrote:

> 
> (switched to email.  Please respond via emailed reply-to-all, not via the
> bugzilla web interface).
> 
> On Wed,  9 Jul 2008 12:13:05 -0700 (PDT) bugme-daemon@bugzilla.kernel.org
> wrote:
> 
> > http://bugzilla.kernel.org/show_bug.cgi?id=11063
> > 
> >            Summary: lack of GNU_STACK header doesn't result in rwx stack on
> >                     i386
> >            Product: Memory Management
> >            Version: 2.5
> >           Platform: All
> >         OS/Version: Linux
> >               Tree: Mainline
> >             Status: NEW
> >           Severity: normal
> >           Priority: P1
> >          Component: Other
> >         AssignedTo: akpm@osdl.org
> >         ReportedBy: pageexec@freemail.hu
> > 
> > 
> > Latest working kernel version: unknown, probably before the introduction of
> > unlimited argv
> > Earliest failing kernel version: unknown, probably after the introduction
> of
> > unlimited argv, 2.6.26-rc9 definitely fails
> > Distribution:
> > Hardware Environment:
> > Software Environment:
> > Problem Description:
> > ELF/i386 traditionally has an executable stack which in the PT_GNU_STACK
> world
> > is provided two ways: if the ELF has a RWE PT_GNU_STACK program header or
> if it
> > lacks that program header. due to this regression, the latter case results
> in a
> > non-executable stack with corresponding breakage of (old) userland binaries
> > that use nested function trampolines.
> > 
> > this bug was probably introduced when the unlimited argv feature was
> merged: in
> > that system the stack vma (and its vm_flags) is initialized too early,
> before
> > the incoming process' ELF header is consulted, which on i386 means that the
> > personality used for determining the executable status of the stack is that
> of
> > the old process, not the incoming one. later, in setup_arg_pages, only the
> > explicit setting (disable/enable) of stack executability is honoured,
> > EXSTACK_DEFAULT isn't consulted (i guess the assumption was that the
> initial
> > ->vm_flags setting got it right).
> > 
> > Steps to reproduce: run any ELF that lacks a PT_GNU_STACK program header
> and
> > check its stack vma, it'll be rw-, instead of rwx.
> > 
> 
Comment 3 Anonymous Emailer 2008-07-09 15:34:22 UTC
Reply-To: akpm@linux-foundation.org


(switched to email.  Please respond via emailed reply-to-all, not via the
bugzilla web interface).

On Wed,  9 Jul 2008 12:13:05 -0700 (PDT) bugme-daemon@bugzilla.kernel.org wrote:

> http://bugzilla.kernel.org/show_bug.cgi?id=11063
> 
>            Summary: lack of GNU_STACK header doesn't result in rwx stack on
>                     i386
>            Product: Memory Management
>            Version: 2.5
>           Platform: All
>         OS/Version: Linux
>               Tree: Mainline
>             Status: NEW
>           Severity: normal
>           Priority: P1
>          Component: Other
>         AssignedTo: akpm@osdl.org
>         ReportedBy: pageexec@freemail.hu
> 
> 
> Latest working kernel version: unknown, probably before the introduction of
> unlimited argv
> Earliest failing kernel version: unknown, probably after the introduction of
> unlimited argv, 2.6.26-rc9 definitely fails
> Distribution:
> Hardware Environment:
> Software Environment:
> Problem Description:
> ELF/i386 traditionally has an executable stack which in the PT_GNU_STACK
> world
> is provided two ways: if the ELF has a RWE PT_GNU_STACK program header or if
> it
> lacks that program header. due to this regression, the latter case results in
> a
> non-executable stack with corresponding breakage of (old) userland binaries
> that use nested function trampolines.
> 
> this bug was probably introduced when the unlimited argv feature was merged:
> in
> that system the stack vma (and its vm_flags) is initialized too early, before
> the incoming process' ELF header is consulted, which on i386 means that the
> personality used for determining the executable status of the stack is that
> of
> the old process, not the incoming one. later, in setup_arg_pages, only the
> explicit setting (disable/enable) of stack executability is honoured,
> EXSTACK_DEFAULT isn't consulted (i guess the assumption was that the initial
> ->vm_flags setting got it right).
> 
> Steps to reproduce: run any ELF that lacks a PT_GNU_STACK program header and
> check its stack vma, it'll be rw-, instead of rwx.
> 
Comment 4 Hugh Dickins 2008-07-10 13:18:56 UTC
Kernel Bugzilla #11063 points out that on some architectures (e.g. x86_32)
exec'ing an ELF without a PT_GNU_STACK program header should default to an
executable stack; but this got broken by the unlimited argv feature because
stack vma is now created before the right personality has been established:
so breaking old binaries using nested function trampolines.

Therefore re-evaluate VM_STACK_FLAGS in setup_arg_pages, where stack
vm_flags used to be set, before the mprotect_fixup.  Checking through
our existing VM_flags, none would have changed since insert_vm_struct:
so this seems safer than finding a way through the personality labyrinth.

Reported-by: pageexec@freemail.hu
Signed-off-by: Hugh Dickins <hugh@veritas.com>
Cc: stable@kernel.org
---

 fs/exec.c |    2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

--- 2.6.26-rc9/fs/exec.c	2008-06-21 08:41:19.000000000 +0100
+++ linux/fs/exec.c	2008-07-10 20:02:25.000000000 +0100
@@ -610,7 +610,7 @@ int setup_arg_pages(struct linux_binprm 
 	bprm->exec -= stack_shift;
 
 	down_write(&mm->mmap_sem);
-	vm_flags = vma->vm_flags;
+	vm_flags = VM_STACK_FLAGS;
 
 	/*
 	 * Adjust stack execute permissions; explicitly enable for
Comment 5 Adrian Bunk 2008-07-10 23:31:08 UTC
fixed by commit 96a8e13ed44e380fc2bb6c711d74d5ba698c00b2
Comment 6 PaX Team 2008-07-11 02:18:14 UTC
On 10 Jul 2008 at 21:19, Hugh Dickins wrote:

> Kernel Bugzilla #11063 points out that on some architectures (e.g. x86_32)
> exec'ing an ELF without a PT_GNU_STACK program header should default to an
> executable stack; but this got broken by the unlimited argv feature because
> stack vma is now created before the right personality has been established:
> so breaking old binaries using nested function trampolines.
> 
> Therefore re-evaluate VM_STACK_FLAGS in setup_arg_pages, where stack
> vm_flags used to be set, before the mprotect_fixup.  Checking through
> our existing VM_flags, none would have changed since insert_vm_struct:
> so this seems safer than finding a way through the personality labyrinth.

alternatively, if there's a concern of stack_vma->vm_flags manipulation
during execve (maybe not now, but in the future or in non-ELF formats
that also want to rely on personality bits), you could opt for a safer

	vm_flags = vma->vm_flags | (VM_STACK_FLAGS & (VM_EXEC | VM_MAYEXEC));

to just recompute the exec rights related bits.

> Reported-by: pageexec@freemail.hu
> Signed-off-by: Hugh Dickins <hugh@veritas.com>
> Cc: stable@kernel.org
> ---
> 
>  fs/exec.c |    2 +-
>  1 file changed, 1 insertion(+), 1 deletion(-)
> 
> --- 2.6.26-rc9/fs/exec.c      2008-06-21 08:41:19.000000000 +0100
> +++ linux/fs/exec.c   2008-07-10 20:02:25.000000000 +0100
> @@ -610,7 +610,7 @@ int setup_arg_pages(struct linux_binprm 
>       bprm->exec -= stack_shift;
>  
>       down_write(&mm->mmap_sem);
> -     vm_flags = vma->vm_flags;
> +     vm_flags = VM_STACK_FLAGS;
>  
>       /*
>        * Adjust stack execute permissions; explicitly enable for
> 
Comment 7 Hugh Dickins 2008-07-11 04:15:17 UTC
On Thu, 10 Jul 2008, pageexec@freemail.hu wrote:
> On 10 Jul 2008 at 21:19, Hugh Dickins wrote:
> 
> > Therefore re-evaluate VM_STACK_FLAGS in setup_arg_pages, where stack
> > vm_flags used to be set, before the mprotect_fixup.  Checking through
> > our existing VM_flags, none would have changed since insert_vm_struct:
> > so this seems safer than finding a way through the personality labyrinth.
> 
> alternatively, if there's a concern of stack_vma->vm_flags manipulation
> during execve (maybe not now, but in the future or in non-ELF formats
> that also want to rely on personality bits), you could opt for a safer
> 
>       vm_flags = vma->vm_flags | (VM_STACK_FLAGS & (VM_EXEC | VM_MAYEXEC));
> 
> to just recompute the exec rights related bits.

True.  It was a concern that crossed my mind (I was thinking particularly
of the VM_ACCOUNT flag, which gets added in once we deal with a writable
private mapping, but is set from the start here anyway), but I don't
think it's worth changing my

> > -   vm_flags = vma->vm_flags;
> > +   vm_flags = VM_STACK_FLAGS;

now that's already there in Linus' tree.  If a VM_flag gets added that
changes the picture, it might even need your line above to be changed.

Hugh

Note You need to log in before you can comment on or make changes to this bug.