https://sourceware.org/git/gitweb.cgi?p=newlib-cygwin.git;h=c2c1b843092768bd922f587bba9107c97f2a7ade

commit c2c1b843092768bd922f587bba9107c97f2a7ade
Author: Corinna Vinschen <[email protected]>
Date:   Sat Jun 27 12:08:07 2015 +0200

    Handle ss_flags value longjmp safe.
    
        * exceptions.cc (_cygtls::call_signal_handler): Drop manipulating
        thread's ss_flags here.  It's not safe against longjmp.
        * signal.cc (sigaltstack): Check if we're running on the alternate
        stack and set ss_flags returned in oss to SS_ONSTACK.
    
    Signed-off-by: Corinna Vinschen <[email protected]>

Diff:
---
 winsup/cygwin/ChangeLog     |  7 +++++++
 winsup/cygwin/exceptions.cc |  4 ----
 winsup/cygwin/signal.cc     | 12 +++++++++++-
 3 files changed, 18 insertions(+), 5 deletions(-)

diff --git a/winsup/cygwin/ChangeLog b/winsup/cygwin/ChangeLog
index 7f33687..31b429b 100644
--- a/winsup/cygwin/ChangeLog
+++ b/winsup/cygwin/ChangeLog
@@ -1,3 +1,10 @@
+2015-06-27  Corinna Vinschen  <[email protected]>
+
+       * exceptions.cc (_cygtls::call_signal_handler): Drop manipulating
+       thread's ss_flags here.  It's not safe against longjmp.
+       * signal.cc (sigaltstack): Check if we're running on the alternate
+       stack and set ss_flags returned in oss to SS_ONSTACK.
+
 2015-06-26  Corinna Vinschen  <[email protected]>
 
        * include/cygwin/signal.h: Revert to define MINSIGSTKSZ and SIGSTKSZ
diff --git a/winsup/cygwin/exceptions.cc b/winsup/cygwin/exceptions.cc
index d493abb..90a8ff2 100644
--- a/winsup/cygwin/exceptions.cc
+++ b/winsup/cygwin/exceptions.cc
@@ -1599,8 +1599,6 @@ _cygtls::call_signal_handler ()
          uintptr_t new_sp = (uintptr_t) _my_tls.altstack.ss_sp
                             + _my_tls.altstack.ss_size;
          new_sp &= ~0xf;
-         /* Mark alternate stack as used. */
-         _my_tls.altstack.ss_flags = SS_ONSTACK;
          /* In assembler: Save regs on new stack, move to alternate stack,
             call thisfunc, revert stack regs. */
 #ifdef __x86_64__
@@ -1671,8 +1669,6 @@ _cygtls::call_signal_handler ()
                       [FUNC]   "o" (thisfunc)
                   : "memory");
 #endif
-         /* Revert alternate stack to unused. */
-         _my_tls.altstack.ss_flags = 0;
        }
       else
        /* No alternate signal stack requested or available, just call
diff --git a/winsup/cygwin/signal.cc b/winsup/cygwin/signal.cc
index 94faaf3..467c919 100644
--- a/winsup/cygwin/signal.cc
+++ b/winsup/cygwin/signal.cc
@@ -667,7 +667,17 @@ sigaltstack (const stack_t *ss, stack_t *oss)
            }
        }
       if (oss)
-       memcpy (oss, &me.altstack, sizeof *oss);
+       {
+         char stack_marker;
+         memcpy (oss, &me.altstack, sizeof *oss);
+         if (!me.altstack.ss_flags && me.altstack.ss_sp)
+           {
+             if (&stack_marker >= (char *) me.altstack.ss_sp
+                 && &stack_marker < (char *) me.altstack.ss_sp
+                                    + me.altstack.ss_size)
+               oss->ss_flags = SS_ONSTACK;
+           }
+       }
     }
   __except (EFAULT)
     {

Reply via email to