This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC 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]

Re: Give a better error for PCH with exec-shield-randomize


Eric Botcazou <ebotcazou@libertysurf.fr> writes:

> > So: could somebody with access to a Solaris system please compile and
> > run the appended little program, and please tell me the exit status?
> > I am hoping that the exit status will be 0.  On Linux, the exit status
> > is 1.
> 
> 0 on Solaris 2.5.1, 2.6, 7, 8 and 9, so the page is correctly detected as 
> mapped.

Thanks for checking.  Would you mind trying out the appended patch, to
confirm that with this patch PCH still works on Solaris?  This patch
avoids using the mincore workaround for an mmap failure on Linux.  I
included the diffs for the generated files for convenience.

Ian

Index: config.in
===================================================================
RCS file: /cvs/gcc/gcc/gcc/config.in,v
retrieving revision 1.181
diff -u -r1.181 config.in
--- config.in	9 Jan 2004 01:18:34 -0000	1.181
+++ config.in	5 Mar 2004 14:13:55 -0000
@@ -455,6 +455,9 @@
    NULL. */
 #undef HAVE_WORKING_MBSTOWCS
 
+/* Define this macro if mincore detects private anonymous mappings. */
+#undef HAVE_WORKING_MINCORE
+
 /* Define to 1 if `vfork' works. */
 #undef HAVE_WORKING_VFORK
 
Index: configure
===================================================================
RCS file: /cvs/gcc/gcc/gcc/configure,v
retrieving revision 1.807
diff -u -r1.807 configure
--- configure	5 Mar 2004 14:11:58 -0000	1.807
+++ configure	5 Mar 2004 14:13:59 -0000
@@ -6596,6 +6596,89 @@
   fi
 fi
 
+if test x$ac_cv_func_mincore = xyes; then
+  echo "$as_me:$LINENO: checking whether mincore detects anonymous mappings" >&5
+echo $ECHO_N "checking whether mincore detects anonymous mappings... $ECHO_C" >&6
+if test "${gcc_cv_func_mincore_works+set}" = set; then
+  echo $ECHO_N "(cached) $ECHO_C" >&6
+else
+      if test "$cross_compiling" = yes; then
+  case "${host}" in
+     *-*-linux*) gcc_cv_func_mincore_works=no ;;
+     *) gcc_cv_func_mincore_works=yes ;;
+     esac
+
+else
+  cat >conftest.$ac_ext <<_ACEOF
+#line $LINENO "configure"
+/* confdefs.h.  */
+_ACEOF
+cat confdefs.h >>conftest.$ac_ext
+cat >>conftest.$ac_ext <<_ACEOF
+/* end confdefs.h.  */
+
+#include <stdlib.h>
+#include <errno.h>
+#include <unistd.h>
+#include <sys/types.h>
+#include <sys/mman.h>
+
+#ifndef MAP_FAILED
+#define MAP_FAILED ((void *) -1)
+#endif
+
+int
+main ()
+{
+#ifndef MAP_ANONYMOUS
+  exit (0);
+#else
+  size_t pagesize = getpagesize ();
+  void *p = mmap (0, pagesize, PROT_READ | PROT_WRITE,
+		  MAP_PRIVATE | MAP_ANONYMOUS, -1, 0);
+  char c;
+  if (p == MAP_FAILED)
+    exit (0);
+  errno = 0;
+  exit (mincore (p, pagesize, &c) == -1 && errno == ENOMEM);
+#endif
+}
+
+_ACEOF
+rm -f conftest$ac_exeext
+if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5
+  (eval $ac_link) 2>&5
+  ac_status=$?
+  echo "$as_me:$LINENO: \$? = $ac_status" >&5
+  (exit $ac_status); } && { ac_try='./conftest$ac_exeext'
+  { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5
+  (eval $ac_try) 2>&5
+  ac_status=$?
+  echo "$as_me:$LINENO: \$? = $ac_status" >&5
+  (exit $ac_status); }; }; then
+  gcc_cv_func_mincore_works=yes
+else
+  echo "$as_me: program exited with status $ac_status" >&5
+echo "$as_me: failed program was:" >&5
+sed 's/^/| /' conftest.$ac_ext >&5
+
+( exit $ac_status )
+gcc_cv_func_mincore_works=no
+fi
+rm -f core core.* *.core gmon.out bb.out conftest$ac_exeext conftest.$ac_objext conftest.$ac_ext
+fi
+fi
+echo "$as_me:$LINENO: result: $gcc_cv_func_mincore_works" >&5
+echo "${ECHO_T}$gcc_cv_func_mincore_works" >&6
+  if test x$gcc_cv_func_mincore_works = xyes; then
+
+cat >>confdefs.h <<\_ACEOF
+#define HAVE_WORKING_MINCORE 1
+_ACEOF
+
+  fi
+fi
+
 echo "$as_me:$LINENO: checking for ssize_t" >&5
 echo $ECHO_N "checking for ssize_t... $ECHO_C" >&6
 if test "${ac_cv_type_ssize_t+set}" = set; then
Index: configure.ac
===================================================================
RCS file: /cvs/gcc/gcc/gcc/configure.ac,v
retrieving revision 2.20
diff -u -r2.20 configure.ac
--- configure.ac	5 Mar 2004 14:11:58 -0000	2.20
+++ configure.ac	5 Mar 2004 14:14:00 -0000
@@ -833,6 +833,50 @@
   fi
 fi
 
+if test x$ac_cv_func_mincore = xyes; then
+  AC_CACHE_CHECK(whether mincore detects anonymous mappings,
+		 gcc_cv_func_mincore_works,
+[    AC_TRY_RUN([
+#include <stdlib.h>
+#include <errno.h>
+#include <unistd.h>
+#include <sys/types.h>
+#include <sys/mman.h>
+
+#ifndef MAP_FAILED
+#define MAP_FAILED ((void *) -1)
+#endif
+
+int
+main ()
+{
+#ifndef MAP_ANONYMOUS
+  exit (0);
+#else
+  size_t pagesize = getpagesize ();
+  void *p = mmap (0, pagesize, PROT_READ | PROT_WRITE,
+		  MAP_PRIVATE | MAP_ANONYMOUS, -1, 0);
+  char c;
+  if (p == MAP_FAILED)
+    exit (0);
+  errno = 0;
+  exit (mincore (p, pagesize, &c) == -1 && errno == ENOMEM);
+#endif
+}
+],
+    gcc_cv_func_mincore_works=yes,
+    gcc_cv_func_mincore_works=no,
+    [case "${host}" in
+     *-*-linux*) gcc_cv_func_mincore_works=no ;;
+     *) gcc_cv_func_mincore_works=yes ;;
+     esac
+    ])])
+  if test x$gcc_cv_func_mincore_works = xyes; then
+    AC_DEFINE(HAVE_WORKING_MINCORE, 1,
+  [Define this macro if mincore detects private anonymous mappings.])
+  fi
+fi
+
 AC_CHECK_TYPE(ssize_t, int)
 
 # Try to determine the array type of the second argument of getgroups
Index: ggc-common.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/ggc-common.c,v
retrieving revision 1.84
diff -u -r1.84 ggc-common.c
--- ggc-common.c	5 Mar 2004 01:22:58 -0000	1.84
+++ ggc-common.c	5 Mar 2004 14:14:05 -0000
@@ -608,17 +608,23 @@
 		   PROT_READ | PROT_WRITE, MAP_PRIVATE,
 		   fileno (f), mmi.offset);
 
-#if HAVE_MINCORE
+#if defined (HAVE_MINCORE) && defined (HAVE_WORKING_MINCORE)
       if (addr != mmi.preferred_base)
 	{
 	  size_t page_size = getpagesize();
 	  char one_byte;
 
-	  /* We really want to be mapped at mmi.preferred_base
-	     so we're going to resort to MAP_FIXED.  But before,
-	     make sure that we can do so without destroying a
-	     previously mapped area, by looping over all pages
-	     that would be affected by the fixed mapping.  */
+	  /* We didn't get the mapping we want.  On Solaris, this can
+	     happen even though the mapping we want is available.  Use
+	     mincore to see if the mapping could succeed.  If it
+	     could, then force it using MAP_FIXED.  */
+
+	  if (addr != (void *) MAP_FAILED)
+	    {
+	      munmap (addr, mmi.size);
+	      addr = (void *) MAP_FAILED;
+	    }
+
 	  errno = 0;
 
 	  for (i = 0; i < mmi.size; i+= page_size)
@@ -630,16 +636,11 @@
 	      break;
 
 	  if (i >= mmi.size)
-	    {
-	      if (addr != (void *) MAP_FAILED)
-		munmap (addr, mmi.size);
-
-	      addr = mmap (mmi.preferred_base, mmi.size, 
-			   PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_FIXED,
-			   fileno (f), mmi.offset);
-	    }
+	    addr = mmap (mmi.preferred_base, mmi.size, 
+			 PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_FIXED,
+			 fileno (f), mmi.offset);
 	}
-#endif /* HAVE_MINCORE */
+#endif /* defined (HAVE_MINCORE) && defined (HAVE_WORKING_MINCORE) */
 
       needs_read = addr == (void *) MAP_FAILED;
 


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