* fhandler.h (class fhandler_base): Declare fixup_mmap_after_fork
with additional flags parameter. Change offset parameter to _off64_t. (class fhandler_disk_file): Ditto. (class fhandler_dev_mem): Ditto. * fhandler_mem.cc (fhandler_dev_mem::fixup_mmap_after_fork): Accomodate new parameters. * mmap.cc: Include ntdll.h. (class mmap_record): Add flags member. (mmap_record::mmap_record): Add flags parameter. (mmap_record::get_flags): New method. (class map): Add next_anon_addr member to store next anonymous mapping address suggestion. (map::get_next_anon_addr): New method. (map::set_next_anon_addr): New method. (mmap64): Don't align offset and length to granularity in case of MAP_ANONYMOUS on NT. Check for already existing mapping only on 9x. Call mmap_record::mmap_record with additional flags argument. (fhandler_base::fixup_mmap_after_fork): Accomodate new parameters. (fhandler_disk_file::mmap): Use NtMapViewOfSection with AT_ROUND_TO_PAGE flag for anonymous mappings on NT. If addr is NULL, try to map adjacent to previous mapping. (fhandler_disk_file::fixup_mmap_after_fork): Add flags argument. Change offset parameter to _off64_t. Use NtMapViewOfSection to re-create anonymous mappings on NT. (fixup_mmaps_after_fork): Accomodate new parameters when calling fhandler's fixup_mmaps_after_fork function. * ntdll.h (AT_ROUND_TO_PAGE): New define.
This commit is contained in:
parent
99e281eb19
commit
6d11044c63
|
@ -1,3 +1,33 @@
|
||||||
|
2005-02-25 Corinna Vinschen <corinna@vinschen.de>
|
||||||
|
|
||||||
|
* fhandler.h (class fhandler_base): Declare fixup_mmap_after_fork
|
||||||
|
with additional flags parameter. Change offset parameter to _off64_t.
|
||||||
|
(class fhandler_disk_file): Ditto.
|
||||||
|
(class fhandler_dev_mem): Ditto.
|
||||||
|
* fhandler_mem.cc (fhandler_dev_mem::fixup_mmap_after_fork):
|
||||||
|
Accomodate new parameters.
|
||||||
|
* mmap.cc: Include ntdll.h.
|
||||||
|
(class mmap_record): Add flags member.
|
||||||
|
(mmap_record::mmap_record): Add flags parameter.
|
||||||
|
(mmap_record::get_flags): New method.
|
||||||
|
(class map): Add next_anon_addr member to store next anonymous mapping
|
||||||
|
address suggestion.
|
||||||
|
(map::get_next_anon_addr): New method.
|
||||||
|
(map::set_next_anon_addr): New method.
|
||||||
|
(mmap64): Don't align offset and length to granularity in case of
|
||||||
|
MAP_ANONYMOUS on NT. Check for already existing mapping only on 9x.
|
||||||
|
Call mmap_record::mmap_record with additional flags argument.
|
||||||
|
(fhandler_base::fixup_mmap_after_fork): Accomodate new parameters.
|
||||||
|
(fhandler_disk_file::mmap): Use NtMapViewOfSection with
|
||||||
|
AT_ROUND_TO_PAGE flag for anonymous mappings on NT. If addr is NULL,
|
||||||
|
try to map adjacent to previous mapping.
|
||||||
|
(fhandler_disk_file::fixup_mmap_after_fork): Add flags argument.
|
||||||
|
Change offset parameter to _off64_t. Use NtMapViewOfSection to
|
||||||
|
re-create anonymous mappings on NT.
|
||||||
|
(fixup_mmaps_after_fork): Accomodate new parameters when calling
|
||||||
|
fhandler's fixup_mmaps_after_fork function.
|
||||||
|
* ntdll.h (AT_ROUND_TO_PAGE): New define.
|
||||||
|
|
||||||
2005-02-25 Corinna Vinschen <corinna@vinschen.de>
|
2005-02-25 Corinna Vinschen <corinna@vinschen.de>
|
||||||
|
|
||||||
* mmap.cc (mmap64): Handle anonymous MAP_FIXED request on
|
* mmap.cc (mmap64): Handle anonymous MAP_FIXED request on
|
||||||
|
|
|
@ -285,8 +285,9 @@ class fhandler_base
|
||||||
int flags, _off64_t off);
|
int flags, _off64_t off);
|
||||||
virtual int munmap (HANDLE h, caddr_t addr, size_t len);
|
virtual int munmap (HANDLE h, caddr_t addr, size_t len);
|
||||||
virtual int msync (HANDLE h, caddr_t addr, size_t len, int flags);
|
virtual int msync (HANDLE h, caddr_t addr, size_t len, int flags);
|
||||||
virtual bool fixup_mmap_after_fork (HANDLE h, DWORD access, DWORD offset,
|
virtual bool fixup_mmap_after_fork (HANDLE h, DWORD access, int flags,
|
||||||
DWORD size, void *address);
|
_off64_t offset, DWORD size,
|
||||||
|
void *address);
|
||||||
|
|
||||||
void *operator new (size_t, void *p) {return p;}
|
void *operator new (size_t, void *p) {return p;}
|
||||||
|
|
||||||
|
@ -633,8 +634,8 @@ class fhandler_disk_file: public fhandler_base
|
||||||
HANDLE mmap (caddr_t *addr, size_t len, DWORD access, int flags, _off64_t off);
|
HANDLE mmap (caddr_t *addr, size_t len, DWORD access, int flags, _off64_t off);
|
||||||
int munmap (HANDLE h, caddr_t addr, size_t len);
|
int munmap (HANDLE h, caddr_t addr, size_t len);
|
||||||
int msync (HANDLE h, caddr_t addr, size_t len, int flags);
|
int msync (HANDLE h, caddr_t addr, size_t len, int flags);
|
||||||
bool fixup_mmap_after_fork (HANDLE h, DWORD access, DWORD offset,
|
bool fixup_mmap_after_fork (HANDLE h, DWORD access, int flags,
|
||||||
DWORD size, void *address);
|
_off64_t offset, DWORD size, void *address);
|
||||||
DIR *opendir ();
|
DIR *opendir ();
|
||||||
struct dirent *readdir (DIR *);
|
struct dirent *readdir (DIR *);
|
||||||
_off64_t telldir (DIR *);
|
_off64_t telldir (DIR *);
|
||||||
|
@ -1055,8 +1056,8 @@ class fhandler_dev_mem: public fhandler_base
|
||||||
HANDLE mmap (caddr_t *addr, size_t len, DWORD access, int flags, _off64_t off);
|
HANDLE mmap (caddr_t *addr, size_t len, DWORD access, int flags, _off64_t off);
|
||||||
int munmap (HANDLE h, caddr_t addr, size_t len);
|
int munmap (HANDLE h, caddr_t addr, size_t len);
|
||||||
int msync (HANDLE h, caddr_t addr, size_t len, int flags);
|
int msync (HANDLE h, caddr_t addr, size_t len, int flags);
|
||||||
bool fixup_mmap_after_fork (HANDLE h, DWORD access, DWORD offset,
|
bool fixup_mmap_after_fork (HANDLE h, DWORD access, int flags,
|
||||||
DWORD size, void *address);
|
_off64_t offset, DWORD size, void *address);
|
||||||
|
|
||||||
void dump ();
|
void dump ();
|
||||||
} ;
|
} ;
|
||||||
|
|
|
@ -361,8 +361,9 @@ fhandler_dev_mem::msync (HANDLE h, caddr_t addr, size_t len, int flags)
|
||||||
}
|
}
|
||||||
|
|
||||||
bool
|
bool
|
||||||
fhandler_dev_mem::fixup_mmap_after_fork (HANDLE h, DWORD access, DWORD offset,
|
fhandler_dev_mem::fixup_mmap_after_fork (HANDLE h, DWORD access, int flags,
|
||||||
DWORD size, void *address)
|
_off64_t offset, DWORD size,
|
||||||
|
void *address)
|
||||||
{
|
{
|
||||||
DWORD ret;
|
DWORD ret;
|
||||||
PHYSICAL_ADDRESS phys;
|
PHYSICAL_ADDRESS phys;
|
||||||
|
|
|
@ -22,6 +22,7 @@ details. */
|
||||||
#include "cygheap.h"
|
#include "cygheap.h"
|
||||||
#include "pinfo.h"
|
#include "pinfo.h"
|
||||||
#include "sys/cygwin.h"
|
#include "sys/cygwin.h"
|
||||||
|
#include "ntdll.h"
|
||||||
|
|
||||||
#define PAGE_CNT(bytes) howmany((bytes),getpagesize())
|
#define PAGE_CNT(bytes) howmany((bytes),getpagesize())
|
||||||
|
|
||||||
|
@ -58,6 +59,7 @@ class mmap_record
|
||||||
int fdesc_;
|
int fdesc_;
|
||||||
HANDLE mapping_handle_;
|
HANDLE mapping_handle_;
|
||||||
DWORD access_mode_;
|
DWORD access_mode_;
|
||||||
|
int flags_;
|
||||||
_off64_t offset_;
|
_off64_t offset_;
|
||||||
DWORD size_to_map_;
|
DWORD size_to_map_;
|
||||||
caddr_t base_address_;
|
caddr_t base_address_;
|
||||||
|
@ -65,10 +67,12 @@ class mmap_record
|
||||||
device dev;
|
device dev;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
mmap_record (int fd, HANDLE h, DWORD ac, _off64_t o, DWORD s, caddr_t b) :
|
mmap_record (int fd, HANDLE h, DWORD ac, int f, _off64_t o, DWORD s,
|
||||||
|
caddr_t b) :
|
||||||
fdesc_ (fd),
|
fdesc_ (fd),
|
||||||
mapping_handle_ (h),
|
mapping_handle_ (h),
|
||||||
access_mode_ (ac),
|
access_mode_ (ac),
|
||||||
|
flags_ (f),
|
||||||
offset_ (o),
|
offset_ (o),
|
||||||
size_to_map_ (s),
|
size_to_map_ (s),
|
||||||
base_address_ (b),
|
base_address_ (b),
|
||||||
|
@ -83,6 +87,7 @@ class mmap_record
|
||||||
HANDLE get_handle () const { return mapping_handle_; }
|
HANDLE get_handle () const { return mapping_handle_; }
|
||||||
device& get_device () { return dev; }
|
device& get_device () { return dev; }
|
||||||
DWORD get_access () const { return access_mode_; }
|
DWORD get_access () const { return access_mode_; }
|
||||||
|
DWORD get_flags () const { return flags_; }
|
||||||
_off64_t get_offset () const { return offset_; }
|
_off64_t get_offset () const { return offset_; }
|
||||||
DWORD get_size () const { return size_to_map_; }
|
DWORD get_size () const { return size_to_map_; }
|
||||||
caddr_t get_address () const { return base_address_; }
|
caddr_t get_address () const { return base_address_; }
|
||||||
|
@ -128,12 +133,15 @@ class map
|
||||||
private:
|
private:
|
||||||
list *lists;
|
list *lists;
|
||||||
int nlists, maxlists;
|
int nlists, maxlists;
|
||||||
|
caddr_t next_anon_addr;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
list *get_list (int i) { return i >= nlists ? NULL : lists + i; }
|
list *get_list (int i) { return i >= nlists ? NULL : lists + i; }
|
||||||
list *get_list_by_fd (int fd);
|
list *get_list_by_fd (int fd);
|
||||||
list *add_list (int fd);
|
list *add_list (int fd);
|
||||||
void del_list (int i);
|
void del_list (int i);
|
||||||
|
caddr_t get_next_anon_addr () { return next_anon_addr; }
|
||||||
|
void set_next_anon_addr (caddr_t addr) { next_anon_addr = addr; }
|
||||||
};
|
};
|
||||||
|
|
||||||
/* This is the global map structure pointer. It's allocated once on the
|
/* This is the global map structure pointer. It's allocated once on the
|
||||||
|
@ -530,13 +538,21 @@ mmap64 (void *addr, size_t len, int prot, int flags, int fd, _off64_t off)
|
||||||
if (flags & MAP_ANONYMOUS)
|
if (flags & MAP_ANONYMOUS)
|
||||||
fd = -1;
|
fd = -1;
|
||||||
|
|
||||||
/* If MAP_FIXED is requested on a non-granularity boundary, change request
|
/* 9x only: If MAP_FIXED is requested on a non-granularity boundary,
|
||||||
so that this looks like a request with offset addr % granularity. */
|
change request so that this looks like a request with offset
|
||||||
if (fd == -1 && (flags & MAP_FIXED) && ((DWORD)addr % granularity) && !off)
|
addr % granularity. */
|
||||||
|
if (wincap.share_mmaps_only_by_name () && fd == -1 && (flags & MAP_FIXED)
|
||||||
|
&& ((DWORD)addr % granularity) && !off)
|
||||||
off = (DWORD)addr % granularity;
|
off = (DWORD)addr % granularity;
|
||||||
/* Map always in multipliers of `granularity'-sized chunks. */
|
/* Map always in multipliers of `granularity'-sized chunks.
|
||||||
_off64_t gran_off = off & ~(granularity - 1);
|
Not necessary for anonymous maps on NT. */
|
||||||
DWORD gran_len = howmany (off + len, granularity) * granularity - gran_off;
|
_off64_t gran_off = off;
|
||||||
|
DWORD gran_len = len;
|
||||||
|
if (wincap.share_mmaps_only_by_name () || fd != -1)
|
||||||
|
{
|
||||||
|
gran_off = off & ~(granularity - 1);
|
||||||
|
gran_len = howmany (off + len, granularity) * granularity - gran_off;
|
||||||
|
}
|
||||||
|
|
||||||
fhandler_base *fh;
|
fhandler_base *fh;
|
||||||
|
|
||||||
|
@ -571,8 +587,11 @@ mmap64 (void *addr, size_t len, int prot, int flags, int fd, _off64_t off)
|
||||||
gran_len = fsiz;
|
gran_len = fsiz;
|
||||||
}
|
}
|
||||||
else if (fh->get_device () == FH_ZERO)
|
else if (fh->get_device () == FH_ZERO)
|
||||||
/* mmap /dev/zero is like MAP_ANONYMOUS. */
|
{
|
||||||
fd = -1;
|
/* mmap /dev/zero is like MAP_ANONYMOUS. */
|
||||||
|
fd = -1;
|
||||||
|
flags |= MAP_ANONYMOUS;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
if (fd == -1)
|
if (fd == -1)
|
||||||
{
|
{
|
||||||
|
@ -597,60 +616,67 @@ mmap64 (void *addr, size_t len, int prot, int flags, int fd, _off64_t off)
|
||||||
|
|
||||||
list *map_list = mmapped_areas->get_list_by_fd (fd);
|
list *map_list = mmapped_areas->get_list_by_fd (fd);
|
||||||
|
|
||||||
/* First check if this mapping matches into the chunk of another
|
/* A bit of memory munging on 9x. */
|
||||||
already performed mapping. Only valid for MAP_ANON in a special
|
if (map_list && fd == -1 && wincap.share_mmaps_only_by_name ())
|
||||||
case of MAP_PRIVATE. */
|
|
||||||
if (map_list && fd == -1 && off == 0 && !(flags & MAP_FIXED))
|
|
||||||
{
|
{
|
||||||
mmap_record *rec;
|
/* First check if this mapping matches into the chunk of another
|
||||||
if ((rec = map_list->search_record (off, len)) != NULL
|
already performed mapping. Only valid for MAP_ANON in a special
|
||||||
&& rec->get_access () == access)
|
case of MAP_PRIVATE. */
|
||||||
|
if (off == 0 && !(flags & MAP_FIXED))
|
||||||
{
|
{
|
||||||
if ((off = rec->map_pages (off, len)) == (_off64_t)-1)
|
mmap_record *rec;
|
||||||
|
if ((rec = map_list->search_record (off, len)) != NULL
|
||||||
|
&& rec->get_access () == access)
|
||||||
{
|
{
|
||||||
syscall_printf ("-1 = mmap()");
|
if ((off = rec->map_pages (off, len)) == (_off64_t)-1)
|
||||||
ReleaseResourceLock (LOCK_MMAP_LIST, READ_LOCK|WRITE_LOCK,
|
{
|
||||||
"mmap");
|
syscall_printf ("-1 = mmap()");
|
||||||
return MAP_FAILED;
|
ReleaseResourceLock (LOCK_MMAP_LIST, READ_LOCK|WRITE_LOCK,
|
||||||
|
"mmap");
|
||||||
|
return MAP_FAILED;
|
||||||
|
}
|
||||||
|
caddr_t ret = rec->get_address () + off;
|
||||||
|
syscall_printf ("%x = mmap() succeeded", ret);
|
||||||
|
ReleaseResourceLock (LOCK_MMAP_LIST, READ_LOCK | WRITE_LOCK,
|
||||||
|
"mmap");
|
||||||
|
return ret;
|
||||||
}
|
}
|
||||||
caddr_t ret = rec->get_address () + off;
|
|
||||||
syscall_printf ("%x = mmap() succeeded", ret);
|
|
||||||
ReleaseResourceLock (LOCK_MMAP_LIST, READ_LOCK | WRITE_LOCK, "mmap");
|
|
||||||
return ret;
|
|
||||||
}
|
}
|
||||||
}
|
if ((flags & MAP_FIXED))
|
||||||
if (map_list && fd == -1 && (flags & MAP_FIXED))
|
|
||||||
{
|
|
||||||
caddr_t u_addr;
|
|
||||||
DWORD u_len;
|
|
||||||
long record_idx = -1;
|
|
||||||
if ((record_idx = map_list->search_record ((caddr_t)addr, len, u_addr,
|
|
||||||
u_len, record_idx)) >= 0)
|
|
||||||
{
|
{
|
||||||
mmap_record *rec = map_list->get_record (record_idx);
|
caddr_t u_addr;
|
||||||
if (u_addr > (caddr_t)addr || u_addr + len < (caddr_t)addr + len
|
DWORD u_len;
|
||||||
|| rec->get_access () != access)
|
long record_idx = -1;
|
||||||
|
if ((record_idx = map_list->search_record ((caddr_t)addr, len,
|
||||||
|
u_addr, u_len,
|
||||||
|
record_idx)) >= 0)
|
||||||
{
|
{
|
||||||
/* Partial match only, or access mode doesn't match. */
|
mmap_record *rec = map_list->get_record (record_idx);
|
||||||
/* FIXME: Handle partial mappings gracefully if adjacent
|
if (u_addr > (caddr_t)addr || u_addr + len < (caddr_t)addr + len
|
||||||
memory is available. */
|
|| rec->get_access () != access)
|
||||||
set_errno (EINVAL);
|
{
|
||||||
syscall_printf ("-1 = mmap()");
|
/* Partial match only, or access mode doesn't match. */
|
||||||
|
/* FIXME: Handle partial mappings gracefully if adjacent
|
||||||
|
memory is available. */
|
||||||
|
set_errno (EINVAL);
|
||||||
|
syscall_printf ("-1 = mmap()");
|
||||||
|
ReleaseResourceLock (LOCK_MMAP_LIST, READ_LOCK | WRITE_LOCK,
|
||||||
|
"mmap");
|
||||||
|
return MAP_FAILED;
|
||||||
|
}
|
||||||
|
if (!rec->map_pages ((caddr_t)addr, len))
|
||||||
|
{
|
||||||
|
syscall_printf ("-1 = mmap()");
|
||||||
|
ReleaseResourceLock (LOCK_MMAP_LIST, READ_LOCK | WRITE_LOCK,
|
||||||
|
"mmap");
|
||||||
|
return MAP_FAILED;
|
||||||
|
}
|
||||||
|
caddr_t ret = (caddr_t)addr;
|
||||||
|
syscall_printf ("%x = mmap() succeeded", ret);
|
||||||
ReleaseResourceLock (LOCK_MMAP_LIST, READ_LOCK | WRITE_LOCK,
|
ReleaseResourceLock (LOCK_MMAP_LIST, READ_LOCK | WRITE_LOCK,
|
||||||
"mmap");
|
"mmap");
|
||||||
return MAP_FAILED;
|
return ret;
|
||||||
}
|
}
|
||||||
if (!rec->map_pages ((caddr_t)addr, len))
|
|
||||||
{
|
|
||||||
syscall_printf ("-1 = mmap()");
|
|
||||||
ReleaseResourceLock (LOCK_MMAP_LIST, READ_LOCK | WRITE_LOCK,
|
|
||||||
"mmap");
|
|
||||||
return MAP_FAILED;
|
|
||||||
}
|
|
||||||
caddr_t ret = (caddr_t)addr;
|
|
||||||
syscall_printf ("%x = mmap() succeeded", ret);
|
|
||||||
ReleaseResourceLock (LOCK_MMAP_LIST, READ_LOCK | WRITE_LOCK, "mmap");
|
|
||||||
return ret;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -672,7 +698,7 @@ mmap64 (void *addr, size_t len, int prot, int flags, int fd, _off64_t off)
|
||||||
Now it's time for bookkeeping stuff. */
|
Now it's time for bookkeeping stuff. */
|
||||||
if (fd == -1)
|
if (fd == -1)
|
||||||
gran_len = PAGE_CNT (gran_len) * getpagesize ();
|
gran_len = PAGE_CNT (gran_len) * getpagesize ();
|
||||||
mmap_record mmap_rec (fd, h, access, gran_off, gran_len, base);
|
mmap_record mmap_rec (fd, h, access, flags, gran_off, gran_len, base);
|
||||||
|
|
||||||
/* Get list of mmapped areas for this fd, create a new one if
|
/* Get list of mmapped areas for this fd, create a new one if
|
||||||
one does not exist yet.
|
one does not exist yet.
|
||||||
|
@ -959,8 +985,9 @@ fhandler_base::msync (HANDLE h, caddr_t addr, size_t len, int flags)
|
||||||
}
|
}
|
||||||
|
|
||||||
bool
|
bool
|
||||||
fhandler_base::fixup_mmap_after_fork (HANDLE h, DWORD access, DWORD offset,
|
fhandler_base::fixup_mmap_after_fork (HANDLE h, DWORD access, int flags,
|
||||||
DWORD size, void *address)
|
_off64_t offset, DWORD size,
|
||||||
|
void *address)
|
||||||
{
|
{
|
||||||
set_errno (ENODEV);
|
set_errno (ENODEV);
|
||||||
return -1;
|
return -1;
|
||||||
|
@ -1022,7 +1049,25 @@ fhandler_disk_file::mmap (caddr_t *addr, size_t len, DWORD access,
|
||||||
void *base = NULL;
|
void *base = NULL;
|
||||||
/* If a non-zero address is given, try mapping using the given address first.
|
/* If a non-zero address is given, try mapping using the given address first.
|
||||||
If it fails and flags is not MAP_FIXED, try again with NULL address. */
|
If it fails and flags is not MAP_FIXED, try again with NULL address. */
|
||||||
if (*addr)
|
if (!wincap.share_mmaps_only_by_name ()
|
||||||
|
&& get_handle () == INVALID_HANDLE_VALUE)
|
||||||
|
{
|
||||||
|
PHYSICAL_ADDRESS phys;
|
||||||
|
phys.QuadPart = (ULONGLONG) off;
|
||||||
|
ULONG ulen = len;
|
||||||
|
base = *addr ?: (void *) mmapped_areas->get_next_anon_addr ();
|
||||||
|
NTSTATUS ret = NtMapViewOfSection (h, INVALID_HANDLE_VALUE, &base, 0L,
|
||||||
|
ulen, &phys, &ulen, ViewShare,
|
||||||
|
base ? AT_ROUND_TO_PAGE : 0, protect);
|
||||||
|
if (ret != STATUS_SUCCESS)
|
||||||
|
{
|
||||||
|
__seterrno_from_win_error (RtlNtStatusToDosError (ret));
|
||||||
|
base = NULL;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
mmapped_areas->set_next_anon_addr ((caddr_t) base + len);
|
||||||
|
}
|
||||||
|
else if (*addr)
|
||||||
base = MapViewOfFileEx (h, access, high, low, len, *addr);
|
base = MapViewOfFileEx (h, access, high, low, len, *addr);
|
||||||
if (!base && !(flags & MAP_FIXED))
|
if (!base && !(flags & MAP_FIXED))
|
||||||
base = MapViewOfFileEx (h, access, high, low, len, NULL);
|
base = MapViewOfFileEx (h, access, high, low, len, NULL);
|
||||||
|
@ -1068,11 +1113,39 @@ fhandler_disk_file::msync (HANDLE h, caddr_t addr, size_t len, int flags)
|
||||||
}
|
}
|
||||||
|
|
||||||
bool
|
bool
|
||||||
fhandler_disk_file::fixup_mmap_after_fork (HANDLE h, DWORD access, DWORD offset,
|
fhandler_disk_file::fixup_mmap_after_fork (HANDLE h, DWORD access, int flags,
|
||||||
DWORD size, void *address)
|
_off64_t offset, DWORD size,
|
||||||
|
void *address)
|
||||||
{
|
{
|
||||||
/* Re-create the MapViewOfFileEx call */
|
/* Re-create the MapViewOfFileEx call */
|
||||||
void *base = MapViewOfFileEx (h, access, 0, offset, size, address);
|
void *base;
|
||||||
|
if (!wincap.share_mmaps_only_by_name () && (flags & MAP_ANONYMOUS))
|
||||||
|
{
|
||||||
|
PHYSICAL_ADDRESS phys;
|
||||||
|
phys.QuadPart = (ULONGLONG) offset;
|
||||||
|
ULONG ulen = size;
|
||||||
|
base = address;
|
||||||
|
DWORD protect;
|
||||||
|
switch (access)
|
||||||
|
{
|
||||||
|
case FILE_MAP_WRITE:
|
||||||
|
protect = PAGE_READWRITE;
|
||||||
|
break;
|
||||||
|
case FILE_MAP_READ:
|
||||||
|
protect = PAGE_READONLY;
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
protect = PAGE_WRITECOPY;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
NTSTATUS ret = NtMapViewOfSection (h, INVALID_HANDLE_VALUE, &base, 0L,
|
||||||
|
ulen, &phys, &ulen, ViewShare,
|
||||||
|
AT_ROUND_TO_PAGE, protect);
|
||||||
|
if (ret != STATUS_SUCCESS)
|
||||||
|
__seterrno_from_win_error (RtlNtStatusToDosError (ret));
|
||||||
|
}
|
||||||
|
else
|
||||||
|
base = MapViewOfFileEx (h, access, 0, offset, size, address);
|
||||||
if (base != address)
|
if (base != address)
|
||||||
{
|
{
|
||||||
MEMORY_BASIC_INFORMATION m;
|
MEMORY_BASIC_INFORMATION m;
|
||||||
|
@ -1121,6 +1194,7 @@ fixup_mmaps_after_fork (HANDLE parent)
|
||||||
fhandler_base *fh = rec->alloc_fh ();
|
fhandler_base *fh = rec->alloc_fh ();
|
||||||
bool ret = fh->fixup_mmap_after_fork (rec->get_handle (),
|
bool ret = fh->fixup_mmap_after_fork (rec->get_handle (),
|
||||||
rec->get_access (),
|
rec->get_access (),
|
||||||
|
rec->get_flags (),
|
||||||
rec->get_offset (),
|
rec->get_offset (),
|
||||||
rec->get_size (),
|
rec->get_size (),
|
||||||
rec->get_address ());
|
rec->get_address ());
|
||||||
|
|
|
@ -23,6 +23,8 @@
|
||||||
#define WSLE_PAGE_SHARE_COUNT_MASK 0x0E0
|
#define WSLE_PAGE_SHARE_COUNT_MASK 0x0E0
|
||||||
#define WSLE_PAGE_SHAREABLE 0x100
|
#define WSLE_PAGE_SHAREABLE 0x100
|
||||||
|
|
||||||
|
#define AT_ROUND_TO_PAGE 0x40000000
|
||||||
|
|
||||||
typedef ULONG KAFFINITY;
|
typedef ULONG KAFFINITY;
|
||||||
|
|
||||||
typedef enum _SYSTEM_INFORMATION_CLASS
|
typedef enum _SYSTEM_INFORMATION_CLASS
|
||||||
|
|
Loading…
Reference in New Issue