Simplify fork code setting up child stack info

* fork.cc (frok::parent): Simplify code propagating stack setup to
        child process.  Tweak comments.

Signed-off-by: Corinna Vinschen <corinna@vinschen.de>
This commit is contained in:
Corinna Vinschen 2015-07-07 17:05:20 +02:00
parent c9b3716279
commit 606013bcf1
2 changed files with 26 additions and 30 deletions

View File

@ -1,3 +1,8 @@
2015-07-07 Corinna Vinschen <corinna@vinschen.de>
* fork.cc (frok::parent): Simplify code propagating stack setup to
child process. Tweak comments.
2015-07-06 Yaakov Selkowitz <yselkowi@redhat.com> 2015-07-06 Yaakov Selkowitz <yselkowi@redhat.com>
* path.cc: Rework basename redefinition handling. Explain why. * path.cc: Rework basename redefinition handling. Explain why.

View File

@ -307,39 +307,30 @@ frok::parent (volatile char * volatile stack_here)
ch.forker_finished = forker_finished; ch.forker_finished = forker_finished;
PTEB teb = NtCurrentTeb ();
ch.stackaddr = teb->DeallocationStack;
ch.stackbottom = _tlsbase; ch.stackbottom = _tlsbase;
/* If DeallocationStack is NULL, we're running on an application-provided ch.stackaddr = NtCurrentTeb ()->DeallocationStack;
stack. If so, the entire stack is committed anyway and StackLimit points
to the allocation address of the stack. Otherwise we're running on a
system-allocated stack and using StackLimit is dangerous, in case the
application encountered a stack overflow and recovered from it via
a signal handler running on an alternate stack. Since stack_here is
the address of the stack pointer we start the child with anyway, we
can set ch.stacktop to this value rounded down to page size. The
child will not need the rest of the stack anyway. */
if (!ch.stackaddr) if (!ch.stackaddr)
ch.stacktop = _tlstop;
else
ch.stacktop = (void *) ((uintptr_t) stack_here & ~wincap.page_size ());
ch.guardsize = 0;
if (&_my_tls != _main_tls)
{ {
/* We have not been started from the main thread. Fetch the /* If DeallocationStack is NULL, we're running on an application-provided
information required to set up the thread stack identically stack. If so, the entire stack is committed anyway and StackLimit
in the child. */ points to the allocation address of the stack. Mark in guardsize that
if (!ch.stackaddr) we must not set up guard pages. */
{ ch.stackaddr = ch.stacktop = _tlstop;
/* Pthread with application-provided stack. Don't set up a ch.guardsize = (size_t) -1;
PAGE_GUARD page. guardsize == -1 is used in alloc_stack_hard_way }
to recognize this type of stack. */ else
ch.stackaddr = _my_tls.tid->attr.stackaddr; {
ch.guardsize = (size_t) -1; /* Otherwise we're running on a system-allocated stack. Since stack_here
} is the address of the stack pointer we start the child with anyway, we
else if (_my_tls.tid) can set ch.stacktop to this value rounded down to page size. The
/* If it's a pthread, fetch guardsize from thread attributes. */ child will not need the rest of the stack anyway. Guardsize depends
ch.guardsize = _my_tls.tid->attr.guardsize; on whether we're running on a pthread or not. If pthread, we fetch
the guardpage size from the pthread attribs, otherwise we use the
system default. */
ch.stacktop = (void *) ((uintptr_t) stack_here & ~wincap.page_size ());
ch.guardsize = (&_my_tls != _main_tls && _my_tls.tid)
? _my_tls.tid->attr.guardsize
: wincap.def_guard_page_size ();
} }
debug_printf ("stack - bottom %p, top %p, addr %p, guardsize %ly", debug_printf ("stack - bottom %p, top %p, addr %p, guardsize %ly",
ch.stackbottom, ch.stacktop, ch.stackaddr, ch.guardsize); ch.stackbottom, ch.stacktop, ch.stackaddr, ch.guardsize);