This is the mail archive of the glibc-cvs@sourceware.org mailing list for the glibc project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

GNU C Library master sources branch master updated. glibc-2.25-714-ged421fc


This is an automated email from the git hooks/post-receive script. It was
generated because a ref change was pushed to the repository containing
the project "GNU C Library master sources".

The branch, master has been updated
       via  ed421fca42fd9b4cab7c66e77894b8dd7ca57ed0 (commit)
      from  94070f86c0c849c71ed2e7e2189bb4d1f7411a17 (commit)

Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.

- Log -----------------------------------------------------------------
http://sourceware.org/git/gitweb.cgi?p=glibc.git;a=commitdiff;h=ed421fca42fd9b4cab7c66e77894b8dd7ca57ed0

commit ed421fca42fd9b4cab7c66e77894b8dd7ca57ed0
Author: H.J. Lu <hjl.tools@gmail.com>
Date:   Tue Jul 11 07:44:01 2017 -0700

    Avoid backtrace from __stack_chk_fail [BZ #12189]
    
    __stack_chk_fail is called on corrupted stack.  Stack backtrace is very
    unreliable against corrupted stack.  __libc_message is changed to accept
    enum __libc_message_action and call BEFORE_ABORT only if action includes
    do_backtrace.  __fortify_fail_abort is added to avoid backtrace from
    __stack_chk_fail.
    
    	[BZ #12189]
    	* debug/Makefile (CFLAGS-tst-ssp-1.c): New.
    	(tests): Add tst-ssp-1 if -fstack-protector works.
    	* debug/fortify_fail.c: Include <stdbool.h>.
    	(_fortify_fail_abort): New function.
    	(__fortify_fail): Call _fortify_fail_abort.
    	(__fortify_fail_abort): Add a hidden definition.
    	* debug/stack_chk_fail.c: Include <stdbool.h>.
    	(__stack_chk_fail): Call __fortify_fail_abort, instead of
    	__fortify_fail.
    	* debug/tst-ssp-1.c: New file.
    	* include/stdio.h (__libc_message_action): New enum.
    	(__libc_message): Replace int with enum __libc_message_action.
    	(__fortify_fail_abort): New hidden prototype.
    	* malloc/malloc.c (malloc_printerr): Update __libc_message calls.
    	* sysdeps/posix/libc_fatal.c (__libc_message): Replace int
    	with enum __libc_message_action.  Call BEFORE_ABORT only if
    	action includes do_backtrace.
    	(__libc_fatal): Update __libc_message call.

diff --git a/ChangeLog b/ChangeLog
index 7ee4f2d..081551f 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,25 @@
+2017-07-11  H.J. Lu  <hongjiu.lu@intel.com>
+
+	[BZ #12189]
+	* debug/Makefile (CFLAGS-tst-ssp-1.c): New.
+	(tests): Add tst-ssp-1 if -fstack-protector works.
+	* debug/fortify_fail.c: Include <stdbool.h>.
+	(_fortify_fail_abort): New function.
+	(__fortify_fail): Call _fortify_fail_abort.
+	(__fortify_fail_abort): Add a hidden definition.
+	* debug/stack_chk_fail.c: Include <stdbool.h>.
+	(__stack_chk_fail): Call __fortify_fail_abort, instead of
+	__fortify_fail.
+	* debug/tst-ssp-1.c: New file.
+	* include/stdio.h (__libc_message_action): New enum.
+	(__libc_message): Replace int with enum __libc_message_action.
+	(__fortify_fail_abort): New hidden prototype.
+	* malloc/malloc.c (malloc_printerr): Update __libc_message calls.
+	* sysdeps/posix/libc_fatal.c (__libc_message): Replace int
+	with enum __libc_message_action.  Call BEFORE_ABORT only if
+	action includes do_backtrace.
+	(__libc_fatal): Update __libc_message call.
+
 2017-07-11  Adhemerval Zanella  <adhemerval.zanella@linaro.org>
 
 	[BZ #21738]
diff --git a/debug/Makefile b/debug/Makefile
index cd4975c..c6d7872 100644
--- a/debug/Makefile
+++ b/debug/Makefile
@@ -139,12 +139,18 @@ LDFLAGS-tst-backtrace4 = -rdynamic
 LDFLAGS-tst-backtrace5 = -rdynamic
 LDFLAGS-tst-backtrace6 = -rdynamic
 
+CFLAGS-tst-ssp-1.c = -fstack-protector
+
 tests = backtrace-tst tst-longjmp_chk tst-chk1 tst-chk2 tst-chk3 \
 	tst-lfschk1 tst-lfschk2 tst-lfschk3 test-strcpy_chk test-stpcpy_chk \
 	tst-chk4 tst-chk5 tst-chk6 tst-lfschk4 tst-lfschk5 tst-lfschk6 \
 	tst-longjmp_chk2 tst-backtrace2 tst-backtrace3 tst-backtrace4 \
 	tst-backtrace5 tst-backtrace6
 
+ifeq ($(have-ssp),yes)
+tests += tst-ssp-1
+endif
+
 ifeq (,$(CXX))
 tests-unsupported = tst-chk4 tst-chk5 tst-chk6 \
 		    tst-lfschk4 tst-lfschk5 tst-lfschk6
diff --git a/debug/fortify_fail.c b/debug/fortify_fail.c
index a31977a..c90d384 100644
--- a/debug/fortify_fail.c
+++ b/debug/fortify_fail.c
@@ -17,17 +17,28 @@
 
 #include <stdio.h>
 #include <stdlib.h>
+#include <stdbool.h>
 
 
 extern char **__libc_argv attribute_hidden;
 
 void
 __attribute__ ((noreturn)) internal_function
-__fortify_fail (const char *msg)
+__fortify_fail_abort (_Bool do_backtrace, const char *msg)
 {
   /* The loop is added only to keep gcc happy.  */
   while (1)
-    __libc_message (2, "*** %s ***: %s terminated\n",
+    __libc_message (do_backtrace ? (do_abort | do_backtrace) : do_abort,
+		    "*** %s ***: %s terminated\n",
 		    msg, __libc_argv[0] ?: "<unknown>");
 }
+
+void
+__attribute__ ((noreturn)) internal_function
+__fortify_fail (const char *msg)
+{
+  __fortify_fail_abort (true, msg);
+}
+
 libc_hidden_def (__fortify_fail)
+libc_hidden_def (__fortify_fail_abort)
diff --git a/debug/stack_chk_fail.c b/debug/stack_chk_fail.c
index 4f73464..9ab9bc7 100644
--- a/debug/stack_chk_fail.c
+++ b/debug/stack_chk_fail.c
@@ -17,6 +17,7 @@
 
 #include <stdio.h>
 #include <stdlib.h>
+#include <stdbool.h>
 
 
 extern char **__libc_argv attribute_hidden;
@@ -25,7 +26,7 @@ void
 __attribute__ ((noreturn))
 __stack_chk_fail (void)
 {
-  __fortify_fail ("stack smashing detected");
+  __fortify_fail_abort (false, "stack smashing detected");
 }
 
 strong_alias (__stack_chk_fail, __stack_chk_fail_local)
diff --git a/debug/stack_chk_fail.c b/debug/tst-ssp-1.c
similarity index 61%
copy from debug/stack_chk_fail.c
copy to debug/tst-ssp-1.c
index 4f73464..52c67e2 100644
--- a/debug/stack_chk_fail.c
+++ b/debug/tst-ssp-1.c
@@ -1,4 +1,5 @@
-/* Copyright (C) 2005-2017 Free Software Foundation, Inc.
+/* Verify that __stack_chk_fail won't segfault.
+   Copyright (C) 2017 Free Software Foundation, Inc.
    This file is part of the GNU C Library.
 
    The GNU C Library is free software; you can redistribute it and/or
@@ -15,17 +16,30 @@
    License along with the GNU C Library; if not, see
    <http://www.gnu.org/licenses/>.  */
 
-#include <stdio.h>
-#include <stdlib.h>
+/* Based on gcc.dg/ssp-1.c from GCC testsuite.  */
 
+#include <signal.h>
 
-extern char **__libc_argv attribute_hidden;
+static void
+__attribute__ ((noinline, noclone))
+test (char *foo)
+{
+  int i;
+
+  /* smash stack */
+  for (i = 0; i <= 400; i++)
+    foo[i] = 42;
+}
 
-void
-__attribute__ ((noreturn))
-__stack_chk_fail (void)
+static int
+do_test (void)
 {
-  __fortify_fail ("stack smashing detected");
+  char foo[30];
+
+  test (foo);
+
+  return 1; /* fail */
 }
 
-strong_alias (__stack_chk_fail, __stack_chk_fail_local)
+#define EXPECTED_SIGNAL SIGABRT
+#include <support/test-driver.c>
diff --git a/include/stdio.h b/include/stdio.h
index f68f633..215f919 100644
--- a/include/stdio.h
+++ b/include/stdio.h
@@ -86,13 +86,24 @@ extern int __gen_tempname (char *__tmpl, int __suffixlen, int __flags,
 #  define __GT_DIR	1	/* create a directory */
 #  define __GT_NOCREATE	2	/* just find a name not currently in use */
 
+enum __libc_message_action
+{
+  do_message	= 0,		/* Print message.  */
+  do_abort	= 1 << 0,	/* Abort.  */
+  do_backtrace	= 1 << 1	/* Backtrace.  */
+};
+
 /* Print out MESSAGE on the error output and abort.  */
 extern void __libc_fatal (const char *__message)
      __attribute__ ((__noreturn__));
-extern void __libc_message (int do_abort, const char *__fnt, ...);
+extern void __libc_message (enum __libc_message_action action,
+			    const char *__fnt, ...);
 extern void __fortify_fail (const char *msg)
      __attribute__ ((__noreturn__)) internal_function;
+extern void __fortify_fail_abort (_Bool, const char *msg)
+     __attribute__ ((__noreturn__)) internal_function;
 libc_hidden_proto (__fortify_fail)
+libc_hidden_proto (__fortify_fail_abort)
 
 /* Acquire ownership of STREAM.  */
 extern void __flockfile (FILE *__stream);
diff --git a/malloc/malloc.c b/malloc/malloc.c
index 2527e25..54e406b 100644
--- a/malloc/malloc.c
+++ b/malloc/malloc.c
@@ -5397,7 +5397,8 @@ malloc_printerr (int action, const char *str, void *ptr, mstate ar_ptr)
     set_arena_corrupt (ar_ptr);
 
   if ((action & 5) == 5)
-    __libc_message (action & 2, "%s\n", str);
+    __libc_message ((action & 2) ? (do_abort | do_backtrace) : do_message,
+		    "%s\n", str);
   else if (action & 1)
     {
       char buf[2 * sizeof (uintptr_t) + 1];
@@ -5407,7 +5408,8 @@ malloc_printerr (int action, const char *str, void *ptr, mstate ar_ptr)
       while (cp > buf)
         *--cp = '0';
 
-      __libc_message (action & 2, "*** Error in `%s': %s: 0x%s ***\n",
+      __libc_message ((action & 2) ? (do_abort | do_backtrace) : do_message,
+		      "*** Error in `%s': %s: 0x%s ***\n",
                       __libc_argv[0] ? : "<unknown>", str, cp);
     }
   else if (action & 2)
diff --git a/sysdeps/posix/libc_fatal.c b/sysdeps/posix/libc_fatal.c
index b261963..25af8bd 100644
--- a/sysdeps/posix/libc_fatal.c
+++ b/sysdeps/posix/libc_fatal.c
@@ -64,7 +64,7 @@ struct str_list
 
 /* Abort with an error message.  */
 void
-__libc_message (int do_abort, const char *fmt, ...)
+__libc_message (enum __libc_message_action action, const char *fmt, ...)
 {
   va_list ap;
   int fd = -1;
@@ -140,7 +140,7 @@ __libc_message (int do_abort, const char *fmt, ...)
 
       written = WRITEV_FOR_FATAL (fd, iov, nlist, total);
 
-      if (do_abort)
+      if ((action & do_abort))
 	{
 	  total = ((total + 1 + GLRO(dl_pagesize) - 1)
 		   & ~(GLRO(dl_pagesize) - 1));
@@ -167,9 +167,10 @@ __libc_message (int do_abort, const char *fmt, ...)
 
   va_end (ap);
 
-  if (do_abort)
+  if ((action & do_abort))
     {
-      BEFORE_ABORT (do_abort, written, fd);
+      if ((action & do_backtrace))
+	BEFORE_ABORT (do_abort, written, fd);
 
       /* Kill the application.  */
       abort ();
@@ -182,6 +183,6 @@ __libc_fatal (const char *message)
 {
   /* The loop is added only to keep gcc happy.  */
   while (1)
-    __libc_message (1, "%s", message);
+    __libc_message (do_abort | do_backtrace, "%s", message);
 }
 libc_hidden_def (__libc_fatal)

-----------------------------------------------------------------------

Summary of changes:
 ChangeLog                                   |   22 ++++++++++++++++
 debug/Makefile                              |    6 ++++
 debug/fortify_fail.c                        |   15 +++++++++-
 debug/stack_chk_fail.c                      |    3 +-
 inet/test-hnto-types.c => debug/tst-ssp-1.c |   36 +++++++++++++++-----------
 include/stdio.h                             |   13 +++++++++-
 malloc/malloc.c                             |    6 +++-
 sysdeps/posix/libc_fatal.c                  |   11 ++++---
 8 files changed, 86 insertions(+), 26 deletions(-)
 copy inet/test-hnto-types.c => debug/tst-ssp-1.c (68%)


hooks/post-receive
-- 
GNU C Library master sources


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]