OSDN Git Service

* mmap.cc (mprotect): When MAP_WRITE protection is requested, use
authorcorinna <corinna>
Thu, 15 Jul 2004 17:00:43 +0000 (17:00 +0000)
committercorinna <corinna>
Thu, 15 Jul 2004 17:00:43 +0000 (17:00 +0000)
READWRITE or WRITECOPY protection, whatever has been used when the
page has been allocated initially.

winsup/cygwin/ChangeLog
winsup/cygwin/mmap.cc

index 80e8af1..c217329 100644 (file)
@@ -1,5 +1,11 @@
 2004-07-15  Corinna Vinschen  <corinna@vinschen.de>
 
+       * mmap.cc (mprotect): When MAP_WRITE protection is requested, use
+       READWRITE or WRITECOPY protection, whatever has been used when the
+       page has been allocated initially.
+
+2004-07-15  Corinna Vinschen  <corinna@vinschen.de>
+
        * fhandler.h (class fhandler_dev_raw): Remove is_writing flag.
        Remove declaration of writebuf.
        (class fhandler_dev_floppy): Remove declaration of close.
index e2a25de..1661148 100644 (file)
@@ -786,15 +786,31 @@ mprotect (void *addr, size_t len, int prot)
       return 0;
     }
 
+  /* If write protection is requested, check if the page was
+     originally protected writecopy.  In this case call VirtualProtect
+     requesting PAGE_WRITECOPY, otherwise the VirtualProtect will fail
+     on NT version >= 5.0 */
+  bool writecopy = false;
+  if (prot & PROT_WRITE)
+    {
+      MEMORY_BASIC_INFORMATION mbi;
+      if (VirtualQuery (addr, &mbi, sizeof mbi))
+        {
+         if (mbi.AllocationProtect == PAGE_WRITECOPY
+             || mbi.AllocationProtect == PAGE_EXECUTE_WRITECOPY)
+           writecopy = true;
+       }
+    }
+
   switch (prot)
     {
       case PROT_READ | PROT_WRITE | PROT_EXEC:
       case PROT_WRITE | PROT_EXEC:
-       new_prot = PAGE_EXECUTE_READWRITE;
+       new_prot = writecopy ? PAGE_EXECUTE_WRITECOPY : PAGE_EXECUTE_READWRITE;
        break;
       case PROT_READ | PROT_WRITE:
       case PROT_WRITE:
-       new_prot = PAGE_READWRITE;
+       new_prot = writecopy ? PAGE_WRITECOPY : PAGE_READWRITE;
        break;
       case PROT_READ | PROT_EXEC:
        new_prot = PAGE_EXECUTE_READ;