* mmap.cc (mmap_record::access): Change argument type to caddr_t

for strictness.
	(mprotect): Protect against calling VirtualProtect() for shared
	pages on 9x/Me.
	(fixup_mmaps_after_fork): If ReadProcessMemory() fails, try to
	change protection of parent page to PAGE_READONLY, then try again.
	Revert protection afterwards.
This commit is contained in:
Corinna Vinschen 2003-01-14 20:40:09 +00:00
parent 9a47ce7f74
commit 857b65ddba
2 changed files with 61 additions and 6 deletions

View File

@ -1,3 +1,13 @@
2003-01-14 Corinna Vinschen <corinna@vinschen.de>
* mmap.cc (mmap_record::access): Change argument type to caddr_t
for strictness.
(mprotect): Protect against calling VirtualProtect() for shared
pages on 9x/Me.
(fixup_mmaps_after_fork): If ReadProcessMemory() fails, try to
change protection of parent page to PAGE_READONLY, then try again.
Revert protection afterwards.
2003-01-14 Thomas Pfaff <tpfaff@gmx.net> 2003-01-14 Thomas Pfaff <tpfaff@gmx.net>
* syscalls.cc (system): Add pthread_testcancel call. * syscalls.cc (system): Add pthread_testcancel call.

View File

@ -96,7 +96,7 @@ class mmap_record
__off64_t map_map (__off64_t off, DWORD len); __off64_t map_map (__off64_t off, DWORD len);
BOOL unmap_map (caddr_t addr, DWORD len); BOOL unmap_map (caddr_t addr, DWORD len);
void fixup_map (void); void fixup_map (void);
int access (char *address); int access (caddr_t address);
fhandler_base *alloc_fh (); fhandler_base *alloc_fh ();
void free_fh (fhandler_base *fh); void free_fh (fhandler_base *fh);
@ -226,7 +226,7 @@ mmap_record::fixup_map ()
} }
int int
mmap_record::access (char *address) mmap_record::access (caddr_t address)
{ {
if (address < base_address_ || address >= base_address_ + size_to_map_) if (address < base_address_ || address >= base_address_ + size_to_map_)
return 0; return 0;
@ -889,6 +889,13 @@ mprotect (caddr_t addr, size_t len, int prot)
syscall_printf ("mprotect (addr %x, len %d, prot %x)", addr, len, prot); syscall_printf ("mprotect (addr %x, len %d, prot %x)", addr, len, prot);
if (!wincap.virtual_protect_works_on_shared_pages ()
&& addr >= (caddr_t)0x80000000 && addr <= (caddr_t)0xBFFFFFFF)
{
syscall_printf ("0 = mprotect (9x: No VirtualProtect on shared memory)");
return 0;
}
if (prot == PROT_NONE) if (prot == PROT_NONE)
new_prot = PAGE_NOACCESS; new_prot = PAGE_NOACCESS;
else else
@ -948,7 +955,7 @@ fixup_mmaps_after_fork (HANDLE parent)
for (int it = 0; it < mmapped_areas->nlists; ++it) for (int it = 0; it < mmapped_areas->nlists; ++it)
{ {
list *l = mmapped_areas->lists[it]; list *l = mmapped_areas->lists[it];
if (l != 0) if (l)
{ {
int li; int li;
for (li = 0; li < l->nrecs; ++li) for (li = 0; li < l->nrecs; ++li)
@ -978,9 +985,47 @@ fixup_mmaps_after_fork (HANDLE parent)
&& !ReadProcessMemory (parent, address, address, && !ReadProcessMemory (parent, address, address,
getpagesize (), NULL)) getpagesize (), NULL))
{ {
system_printf ("ReadProcessMemory failed for MAP_PRIVATE address %p, %E", DWORD old_prot;
rec->get_address ());
return -1; if (GetLastError () != ERROR_PARTIAL_COPY ||
!wincap.virtual_protect_works_on_shared_pages ())
{
system_printf ("ReadProcessMemory failed for "
"MAP_PRIVATE address %p, %E",
rec->get_address ());
return -1;
}
if (!VirtualProtectEx (parent,
address, getpagesize (),
PAGE_READONLY, &old_prot))
{
system_printf ("VirtualProtectEx failed for "
"MAP_PRIVATE address %p, %E",
rec->get_address ());
return -1;
}
else
{
BOOL ret, ret2;
ret = ReadProcessMemory (parent, address, address,
getpagesize (), NULL);
ret2 = VirtualProtectEx(parent,
address, getpagesize (),
old_prot, &old_prot);
if (!ret2)
system_printf ("WARNING: VirtualProtectEx to"
"return to previous state "
"in parent failed for "
"MAP_PRIVATE address %p, %E",
rec->get_address ());
if (!ret)
{
system_printf ("ReadProcessMemory FAILED for "
"MAP_PRIVATE address %p, %E",
rec->get_address ());
return -1;
}
}
} }
} }
rec->fixup_map (); rec->fixup_map ();