[project @ 1998-11-26 09:17:22 by sof]
[ghc-hetmet.git] / ghc / runtime / storage / mprotect.lc
index a27199f..1cef887 100644 (file)
@@ -7,10 +7,9 @@
 %*                                                                     *
 %************************************************************************
 
-Is @mprotect@ POSIX now?
+Is @mprotect@ POSIX now? [Yup, POSIX.4 -- sof]
 
 \begin{code}
-
 #if STACK_CHECK_BY_PAGE_FAULT
 
 /* #define STK_CHK_DEBUG */
@@ -36,23 +35,45 @@ Is @mprotect@ POSIX now?
 #  if defined(HAVE_GETPAGESIZE)
 #   define GETPAGESIZE()    getpagesize()
 #  else
-#   error getpagesize
+#   if defined(linux_TARGET_OS) || defined(linuxaout_TARGET_OS)
+#    /* it has it, but it is in BSD land; easier to just say so */
+#    define GETPAGESIZE()   getpagesize()
+#   else 
+#    error getpagesize
+#   endif
 #  endif
 # endif
 
 #if defined(sunos4_TARGET_OS)
-extern int getpagesize PROTO((void));
-extern int mprotect PROTO((caddr_t, size_t, int));
+int getpagesize PROTO((void));
+int mprotect PROTO((caddr_t, size_t, int));
+#endif
+
+#if defined(aix_TARGET_OS)
+/* PROT_NONE doesn't work on aix, PROT_READ works and should suit the job */
+#define PROT_NONE PROT_READ
+#endif
+/* Needed for FreeBSD (SDM, 96/03) */
+#ifndef PROT_NONE
+#define PROT_NONE 0
+#endif
+
+/* For VirtualProtect() and its flags */
+#if defined(cygwin32_TARGET_OS)
+#include <windows.h>
 #endif
 
 void 
-unmapMiddleStackPage(addr_, size)
-char * /*caddr_t*/ addr_;
+unmapMiddleStackPage(addr, size)
+char * /*caddr_t*/ addr;
 int size;
 {
     int pagesize = GETPAGESIZE();
-    caddr_t addr = addr_;
-    caddr_t middle = (caddr_t) (((W_) (addr + size / 2)) / pagesize * pagesize);
+    char * middle = (char *) (((W_) (addr + size / 2)) / pagesize * pagesize);
+#if defined(cygwin32_TARGET_OS)
+    unsigned int old_prot;
+#endif
 
 # ifdef STK_CHK_DEBUG
     fprintf(stderr, "pagesize: %x\nstack start: %08lx\nstack size: %08lx\nstack middle: %08lx\n",
@@ -63,7 +84,14 @@ int size;
        fprintf(stderr, "Stack too small; stack overflow trap disabled.\n");
        return;
     }
+/* mprotect() is broken in beta18, so we use the native Win32
+   call instead
+*/
+#if defined(cygwin32_TARGET_OS)
+    if (VirtualProtect(middle, pagesize, PAGE_NOACCESS, &old_prot) == 0) {
+#else
     if (mprotect(middle, pagesize, PROT_NONE) == -1) {
+#endif
        perror("mprotect");
        EXIT(EXIT_FAILURE);
     }
@@ -74,5 +102,4 @@ int size;
 }
 
 #endif /* STACK_CHECK_BY_PAGE_FAULT */
-
 \end{code}