8237199: ZGC: Rename ZBackingFile to ZPhysicalMemoryBacking
Reviewed-by: stefank, eosterlund, smonteith
This commit is contained in:
parent
c6dc3308a1
commit
74f0ef5050
@ -22,11 +22,11 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
#include "precompiled.hpp"
|
#include "precompiled.hpp"
|
||||||
#include "gc/z/zBackingFile_bsd.hpp"
|
|
||||||
#include "gc/z/zErrno.hpp"
|
#include "gc/z/zErrno.hpp"
|
||||||
#include "gc/z/zGlobals.hpp"
|
#include "gc/z/zGlobals.hpp"
|
||||||
#include "gc/z/zLargePages.inline.hpp"
|
#include "gc/z/zLargePages.inline.hpp"
|
||||||
#include "gc/z/zPhysicalMemory.inline.hpp"
|
#include "gc/z/zPhysicalMemory.inline.hpp"
|
||||||
|
#include "gc/z/zPhysicalMemoryBacking_bsd.hpp"
|
||||||
#include "logging/log.hpp"
|
#include "logging/log.hpp"
|
||||||
#include "runtime/globals.hpp"
|
#include "runtime/globals.hpp"
|
||||||
#include "runtime/os.hpp"
|
#include "runtime/os.hpp"
|
||||||
@ -38,6 +38,10 @@
|
|||||||
#include <sys/mman.h>
|
#include <sys/mman.h>
|
||||||
#include <sys/types.h>
|
#include <sys/types.h>
|
||||||
|
|
||||||
|
// The backing is represented by a reserved virtual address space, in which
|
||||||
|
// we commit and uncommit physical memory. Multi-mapping the different heap
|
||||||
|
// views is done by simply remapping the backing memory using mach_vm_remap().
|
||||||
|
|
||||||
static int vm_flags_superpage() {
|
static int vm_flags_superpage() {
|
||||||
if (!ZLargePages::is_explicit()) {
|
if (!ZLargePages::is_explicit()) {
|
||||||
return 0;
|
return 0;
|
||||||
@ -68,16 +72,16 @@ static ZErrno mremap(uintptr_t from_addr, uintptr_t to_addr, size_t size) {
|
|||||||
return (res == KERN_SUCCESS) ? ZErrno(0) : ZErrno(EINVAL);
|
return (res == KERN_SUCCESS) ? ZErrno(0) : ZErrno(EINVAL);
|
||||||
}
|
}
|
||||||
|
|
||||||
ZBackingFile::ZBackingFile() :
|
ZPhysicalMemoryBacking::ZPhysicalMemoryBacking() :
|
||||||
_base(0),
|
_base(0),
|
||||||
_size(0),
|
_size(0),
|
||||||
_initialized(false) {
|
_initialized(false) {
|
||||||
|
|
||||||
// Reserve address space for virtual backing file
|
// Reserve address space for backing memory
|
||||||
_base = (uintptr_t)os::reserve_memory(MaxHeapSize);
|
_base = (uintptr_t)os::reserve_memory(MaxHeapSize);
|
||||||
if (_base == 0) {
|
if (_base == 0) {
|
||||||
// Failed
|
// Failed
|
||||||
log_error(gc)("Failed to reserve address space for virtual backing file");
|
log_error(gc)("Failed to reserve address space for backing memory");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -85,19 +89,19 @@ ZBackingFile::ZBackingFile() :
|
|||||||
_initialized = true;
|
_initialized = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool ZBackingFile::is_initialized() const {
|
bool ZPhysicalMemoryBacking::is_initialized() const {
|
||||||
return _initialized;
|
return _initialized;
|
||||||
}
|
}
|
||||||
|
|
||||||
void ZBackingFile::warn_commit_limits(size_t max) const {
|
void ZPhysicalMemoryBacking::warn_commit_limits(size_t max) const {
|
||||||
// Does nothing
|
// Does nothing
|
||||||
}
|
}
|
||||||
|
|
||||||
size_t ZBackingFile::size() const {
|
size_t ZPhysicalMemoryBacking::size() const {
|
||||||
return _size;
|
return _size;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool ZBackingFile::commit_inner(size_t offset, size_t length) {
|
bool ZPhysicalMemoryBacking::commit_inner(size_t offset, size_t length) {
|
||||||
assert(is_aligned(offset, os::vm_page_size()), "Invalid offset");
|
assert(is_aligned(offset, os::vm_page_size()), "Invalid offset");
|
||||||
assert(is_aligned(length, os::vm_page_size()), "Invalid length");
|
assert(is_aligned(length, os::vm_page_size()), "Invalid length");
|
||||||
|
|
||||||
@ -114,7 +118,7 @@ bool ZBackingFile::commit_inner(size_t offset, size_t length) {
|
|||||||
|
|
||||||
const size_t end = offset + length;
|
const size_t end = offset + length;
|
||||||
if (end > _size) {
|
if (end > _size) {
|
||||||
// Record new virtual file size
|
// Record new size
|
||||||
_size = end;
|
_size = end;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -122,7 +126,7 @@ bool ZBackingFile::commit_inner(size_t offset, size_t length) {
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
size_t ZBackingFile::commit(size_t offset, size_t length) {
|
size_t ZPhysicalMemoryBacking::commit(size_t offset, size_t length) {
|
||||||
// Try to commit the whole region
|
// Try to commit the whole region
|
||||||
if (commit_inner(offset, length)) {
|
if (commit_inner(offset, length)) {
|
||||||
// Success
|
// Success
|
||||||
@ -150,7 +154,7 @@ size_t ZBackingFile::commit(size_t offset, size_t length) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
size_t ZBackingFile::uncommit(size_t offset, size_t length) {
|
size_t ZPhysicalMemoryBacking::uncommit(size_t offset, size_t length) {
|
||||||
assert(is_aligned(offset, os::vm_page_size()), "Invalid offset");
|
assert(is_aligned(offset, os::vm_page_size()), "Invalid offset");
|
||||||
assert(is_aligned(length, os::vm_page_size()), "Invalid length");
|
assert(is_aligned(length, os::vm_page_size()), "Invalid length");
|
||||||
|
|
||||||
@ -168,14 +172,14 @@ size_t ZBackingFile::uncommit(size_t offset, size_t length) {
|
|||||||
return length;
|
return length;
|
||||||
}
|
}
|
||||||
|
|
||||||
void ZBackingFile::map(uintptr_t addr, size_t size, uintptr_t offset) const {
|
void ZPhysicalMemoryBacking::map(uintptr_t addr, size_t size, uintptr_t offset) const {
|
||||||
const ZErrno err = mremap(_base + offset, addr, size);
|
const ZErrno err = mremap(_base + offset, addr, size);
|
||||||
if (err) {
|
if (err) {
|
||||||
fatal("Failed to remap memory (%s)", err.to_string());
|
fatal("Failed to remap memory (%s)", err.to_string());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void ZBackingFile::unmap(uintptr_t addr, size_t size) const {
|
void ZPhysicalMemoryBacking::unmap(uintptr_t addr, size_t size) const {
|
||||||
// Note that we must keep the address space reservation intact and just detach
|
// Note that we must keep the address space reservation intact and just detach
|
||||||
// the backing memory. For this reason we map a new anonymous, non-accessible
|
// the backing memory. For this reason we map a new anonymous, non-accessible
|
||||||
// and non-reserved page over the mapping instead of actually unmapping.
|
// and non-reserved page over the mapping instead of actually unmapping.
|
@ -21,20 +21,10 @@
|
|||||||
* questions.
|
* questions.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef OS_BSD_GC_Z_ZBACKINGFILE_BSD_HPP
|
#ifndef OS_BSD_GC_Z_ZPHYSICALMEMORYBACKING_BSD_HPP
|
||||||
#define OS_BSD_GC_Z_ZBACKINGFILE_BSD_HPP
|
#define OS_BSD_GC_Z_ZPHYSICALMEMORYBACKING_BSD_HPP
|
||||||
|
|
||||||
#include "memory/allocation.hpp"
|
class ZPhysicalMemoryBacking {
|
||||||
|
|
||||||
class ZPhysicalMemory;
|
|
||||||
|
|
||||||
// On macOS, we use a virtual backing file. It is represented by a reserved virtual
|
|
||||||
// address space, in which we commit physical memory using the mach_vm_map() API.
|
|
||||||
// The multi-mapping API simply remaps these addresses using mach_vm_remap() into
|
|
||||||
// the different heap views. This works as-if there was a backing file, it's just
|
|
||||||
// that the file is represented with memory mappings instead.
|
|
||||||
|
|
||||||
class ZBackingFile {
|
|
||||||
private:
|
private:
|
||||||
uintptr_t _base;
|
uintptr_t _base;
|
||||||
size_t _size;
|
size_t _size;
|
||||||
@ -43,7 +33,7 @@ private:
|
|||||||
bool commit_inner(size_t offset, size_t length);
|
bool commit_inner(size_t offset, size_t length);
|
||||||
|
|
||||||
public:
|
public:
|
||||||
ZBackingFile();
|
ZPhysicalMemoryBacking();
|
||||||
|
|
||||||
bool is_initialized() const;
|
bool is_initialized() const;
|
||||||
|
|
||||||
@ -58,4 +48,4 @@ public:
|
|||||||
void unmap(uintptr_t addr, size_t size) const;
|
void unmap(uintptr_t addr, size_t size) const;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // OS_BSD_GC_Z_ZBACKINGFILE_BSD_HPP
|
#endif // OS_BSD_GC_Z_ZPHYSICALMEMORYBACKING_BSD_HPP
|
@ -23,11 +23,11 @@
|
|||||||
|
|
||||||
#include "precompiled.hpp"
|
#include "precompiled.hpp"
|
||||||
#include "gc/z/zArray.inline.hpp"
|
#include "gc/z/zArray.inline.hpp"
|
||||||
#include "gc/z/zBackingFile_linux.hpp"
|
|
||||||
#include "gc/z/zBackingPath_linux.hpp"
|
#include "gc/z/zBackingPath_linux.hpp"
|
||||||
#include "gc/z/zErrno.hpp"
|
#include "gc/z/zErrno.hpp"
|
||||||
#include "gc/z/zGlobals.hpp"
|
#include "gc/z/zGlobals.hpp"
|
||||||
#include "gc/z/zLargePages.inline.hpp"
|
#include "gc/z/zLargePages.inline.hpp"
|
||||||
|
#include "gc/z/zPhysicalMemoryBacking_linux.hpp"
|
||||||
#include "gc/z/zSyscall_linux.hpp"
|
#include "gc/z/zSyscall_linux.hpp"
|
||||||
#include "logging/log.hpp"
|
#include "logging/log.hpp"
|
||||||
#include "runtime/init.hpp"
|
#include "runtime/init.hpp"
|
||||||
@ -109,7 +109,7 @@ static const char* z_preferred_hugetlbfs_mountpoints[] = {
|
|||||||
static int z_fallocate_hugetlbfs_attempts = 3;
|
static int z_fallocate_hugetlbfs_attempts = 3;
|
||||||
static bool z_fallocate_supported = true;
|
static bool z_fallocate_supported = true;
|
||||||
|
|
||||||
ZBackingFile::ZBackingFile() :
|
ZPhysicalMemoryBacking::ZPhysicalMemoryBacking() :
|
||||||
_fd(-1),
|
_fd(-1),
|
||||||
_size(0),
|
_size(0),
|
||||||
_filesystem(0),
|
_filesystem(0),
|
||||||
@ -178,7 +178,7 @@ ZBackingFile::ZBackingFile() :
|
|||||||
_initialized = true;
|
_initialized = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
int ZBackingFile::create_mem_fd(const char* name) const {
|
int ZPhysicalMemoryBacking::create_mem_fd(const char* name) const {
|
||||||
// Create file name
|
// Create file name
|
||||||
char filename[PATH_MAX];
|
char filename[PATH_MAX];
|
||||||
snprintf(filename, sizeof(filename), "%s%s", name, ZLargePages::is_explicit() ? ".hugetlb" : "");
|
snprintf(filename, sizeof(filename), "%s%s", name, ZLargePages::is_explicit() ? ".hugetlb" : "");
|
||||||
@ -198,7 +198,7 @@ int ZBackingFile::create_mem_fd(const char* name) const {
|
|||||||
return fd;
|
return fd;
|
||||||
}
|
}
|
||||||
|
|
||||||
int ZBackingFile::create_file_fd(const char* name) const {
|
int ZPhysicalMemoryBacking::create_file_fd(const char* name) const {
|
||||||
const char* const filesystem = ZLargePages::is_explicit()
|
const char* const filesystem = ZLargePages::is_explicit()
|
||||||
? ZFILESYSTEM_HUGETLBFS
|
? ZFILESYSTEM_HUGETLBFS
|
||||||
: ZFILESYSTEM_TMPFS;
|
: ZFILESYSTEM_TMPFS;
|
||||||
@ -260,7 +260,7 @@ int ZBackingFile::create_file_fd(const char* name) const {
|
|||||||
return fd;
|
return fd;
|
||||||
}
|
}
|
||||||
|
|
||||||
int ZBackingFile::create_fd(const char* name) const {
|
int ZPhysicalMemoryBacking::create_fd(const char* name) const {
|
||||||
if (ZPath == NULL) {
|
if (ZPath == NULL) {
|
||||||
// If the path is not explicitly specified, then we first try to create a memfd file
|
// If the path is not explicitly specified, then we first try to create a memfd file
|
||||||
// instead of looking for a tmpfd/hugetlbfs mount point. Note that memfd_create() might
|
// instead of looking for a tmpfd/hugetlbfs mount point. Note that memfd_create() might
|
||||||
@ -278,11 +278,11 @@ int ZBackingFile::create_fd(const char* name) const {
|
|||||||
return create_file_fd(name);
|
return create_file_fd(name);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool ZBackingFile::is_initialized() const {
|
bool ZPhysicalMemoryBacking::is_initialized() const {
|
||||||
return _initialized;
|
return _initialized;
|
||||||
}
|
}
|
||||||
|
|
||||||
void ZBackingFile::warn_available_space(size_t max) const {
|
void ZPhysicalMemoryBacking::warn_available_space(size_t max) const {
|
||||||
// Note that the available space on a tmpfs or a hugetlbfs filesystem
|
// Note that the available space on a tmpfs or a hugetlbfs filesystem
|
||||||
// will be zero if no size limit was specified when it was mounted.
|
// will be zero if no size limit was specified when it was mounted.
|
||||||
if (_available == 0) {
|
if (_available == 0) {
|
||||||
@ -307,7 +307,7 @@ void ZBackingFile::warn_available_space(size_t max) const {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void ZBackingFile::warn_max_map_count(size_t max) const {
|
void ZPhysicalMemoryBacking::warn_max_map_count(size_t max) const {
|
||||||
const char* const filename = ZFILENAME_PROC_MAX_MAP_COUNT;
|
const char* const filename = ZFILENAME_PROC_MAX_MAP_COUNT;
|
||||||
FILE* const file = fopen(filename, "r");
|
FILE* const file = fopen(filename, "r");
|
||||||
if (file == NULL) {
|
if (file == NULL) {
|
||||||
@ -342,7 +342,7 @@ void ZBackingFile::warn_max_map_count(size_t max) const {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void ZBackingFile::warn_commit_limits(size_t max) const {
|
void ZPhysicalMemoryBacking::warn_commit_limits(size_t max) const {
|
||||||
// Warn if available space is too low
|
// Warn if available space is too low
|
||||||
warn_available_space(max);
|
warn_available_space(max);
|
||||||
|
|
||||||
@ -350,25 +350,25 @@ void ZBackingFile::warn_commit_limits(size_t max) const {
|
|||||||
warn_max_map_count(max);
|
warn_max_map_count(max);
|
||||||
}
|
}
|
||||||
|
|
||||||
size_t ZBackingFile::size() const {
|
size_t ZPhysicalMemoryBacking::size() const {
|
||||||
return _size;
|
return _size;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool ZBackingFile::is_tmpfs() const {
|
bool ZPhysicalMemoryBacking::is_tmpfs() const {
|
||||||
return _filesystem == TMPFS_MAGIC;
|
return _filesystem == TMPFS_MAGIC;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool ZBackingFile::is_hugetlbfs() const {
|
bool ZPhysicalMemoryBacking::is_hugetlbfs() const {
|
||||||
return _filesystem == HUGETLBFS_MAGIC;
|
return _filesystem == HUGETLBFS_MAGIC;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool ZBackingFile::tmpfs_supports_transparent_huge_pages() const {
|
bool ZPhysicalMemoryBacking::tmpfs_supports_transparent_huge_pages() const {
|
||||||
// If the shmem_enabled file exists and is readable then we
|
// If the shmem_enabled file exists and is readable then we
|
||||||
// know the kernel supports transparent huge pages for tmpfs.
|
// know the kernel supports transparent huge pages for tmpfs.
|
||||||
return access(ZFILENAME_SHMEM_ENABLED, R_OK) == 0;
|
return access(ZFILENAME_SHMEM_ENABLED, R_OK) == 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
ZErrno ZBackingFile::fallocate_compat_ftruncate(size_t size) const {
|
ZErrno ZPhysicalMemoryBacking::fallocate_compat_ftruncate(size_t size) const {
|
||||||
while (ftruncate(_fd, size) == -1) {
|
while (ftruncate(_fd, size) == -1) {
|
||||||
if (errno != EINTR) {
|
if (errno != EINTR) {
|
||||||
// Failed
|
// Failed
|
||||||
@ -380,7 +380,7 @@ ZErrno ZBackingFile::fallocate_compat_ftruncate(size_t size) const {
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
ZErrno ZBackingFile::fallocate_compat_mmap(size_t offset, size_t length, bool touch) const {
|
ZErrno ZPhysicalMemoryBacking::fallocate_compat_mmap(size_t offset, size_t length, bool touch) const {
|
||||||
// On hugetlbfs, mapping a file segment will fail immediately, without
|
// On hugetlbfs, mapping a file segment will fail immediately, without
|
||||||
// the need to touch the mapped pages first, if there aren't enough huge
|
// the need to touch the mapped pages first, if there aren't enough huge
|
||||||
// pages available to back the mapping.
|
// pages available to back the mapping.
|
||||||
@ -410,7 +410,7 @@ ZErrno ZBackingFile::fallocate_compat_mmap(size_t offset, size_t length, bool to
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
ZErrno ZBackingFile::fallocate_compat_pwrite(size_t offset, size_t length) const {
|
ZErrno ZPhysicalMemoryBacking::fallocate_compat_pwrite(size_t offset, size_t length) const {
|
||||||
uint8_t data = 0;
|
uint8_t data = 0;
|
||||||
|
|
||||||
// Allocate backing memory by writing to each block
|
// Allocate backing memory by writing to each block
|
||||||
@ -425,7 +425,7 @@ ZErrno ZBackingFile::fallocate_compat_pwrite(size_t offset, size_t length) const
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
ZErrno ZBackingFile::fallocate_fill_hole_compat(size_t offset, size_t length) {
|
ZErrno ZPhysicalMemoryBacking::fallocate_fill_hole_compat(size_t offset, size_t length) {
|
||||||
// fallocate(2) is only supported by tmpfs since Linux 3.5, and by hugetlbfs
|
// fallocate(2) is only supported by tmpfs since Linux 3.5, and by hugetlbfs
|
||||||
// since Linux 4.3. When fallocate(2) is not supported we emulate it using
|
// since Linux 4.3. When fallocate(2) is not supported we emulate it using
|
||||||
// ftruncate/pwrite (for tmpfs) or ftruncate/mmap/munmap (for hugetlbfs).
|
// ftruncate/pwrite (for tmpfs) or ftruncate/mmap/munmap (for hugetlbfs).
|
||||||
@ -462,7 +462,7 @@ ZErrno ZBackingFile::fallocate_fill_hole_compat(size_t offset, size_t length) {
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
ZErrno ZBackingFile::fallocate_fill_hole_syscall(size_t offset, size_t length) {
|
ZErrno ZPhysicalMemoryBacking::fallocate_fill_hole_syscall(size_t offset, size_t length) {
|
||||||
const int mode = 0; // Allocate
|
const int mode = 0; // Allocate
|
||||||
const int res = ZSyscall::fallocate(_fd, mode, offset, length);
|
const int res = ZSyscall::fallocate(_fd, mode, offset, length);
|
||||||
if (res == -1) {
|
if (res == -1) {
|
||||||
@ -480,7 +480,7 @@ ZErrno ZBackingFile::fallocate_fill_hole_syscall(size_t offset, size_t length) {
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
ZErrno ZBackingFile::fallocate_fill_hole(size_t offset, size_t length) {
|
ZErrno ZPhysicalMemoryBacking::fallocate_fill_hole(size_t offset, size_t length) {
|
||||||
// Using compat mode is more efficient when allocating space on hugetlbfs.
|
// Using compat mode is more efficient when allocating space on hugetlbfs.
|
||||||
// Note that allocating huge pages this way will only reserve them, and not
|
// Note that allocating huge pages this way will only reserve them, and not
|
||||||
// associate them with segments of the file. We must guarantee that we at
|
// associate them with segments of the file. We must guarantee that we at
|
||||||
@ -505,7 +505,7 @@ ZErrno ZBackingFile::fallocate_fill_hole(size_t offset, size_t length) {
|
|||||||
return fallocate_fill_hole_compat(offset, length);
|
return fallocate_fill_hole_compat(offset, length);
|
||||||
}
|
}
|
||||||
|
|
||||||
ZErrno ZBackingFile::fallocate_punch_hole(size_t offset, size_t length) {
|
ZErrno ZPhysicalMemoryBacking::fallocate_punch_hole(size_t offset, size_t length) {
|
||||||
if (is_hugetlbfs()) {
|
if (is_hugetlbfs()) {
|
||||||
// We can only punch hole in pages that have been touched. Non-touched
|
// We can only punch hole in pages that have been touched. Non-touched
|
||||||
// pages are only reserved, and not associated with any specific file
|
// pages are only reserved, and not associated with any specific file
|
||||||
@ -528,7 +528,7 @@ ZErrno ZBackingFile::fallocate_punch_hole(size_t offset, size_t length) {
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
ZErrno ZBackingFile::split_and_fallocate(bool punch_hole, size_t offset, size_t length) {
|
ZErrno ZPhysicalMemoryBacking::split_and_fallocate(bool punch_hole, size_t offset, size_t length) {
|
||||||
// Try first half
|
// Try first half
|
||||||
const size_t offset0 = offset;
|
const size_t offset0 = offset;
|
||||||
const size_t length0 = align_up(length / 2, _block_size);
|
const size_t length0 = align_up(length / 2, _block_size);
|
||||||
@ -549,7 +549,7 @@ ZErrno ZBackingFile::split_and_fallocate(bool punch_hole, size_t offset, size_t
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
ZErrno ZBackingFile::fallocate(bool punch_hole, size_t offset, size_t length) {
|
ZErrno ZPhysicalMemoryBacking::fallocate(bool punch_hole, size_t offset, size_t length) {
|
||||||
assert(is_aligned(offset, _block_size), "Invalid offset");
|
assert(is_aligned(offset, _block_size), "Invalid offset");
|
||||||
assert(is_aligned(length, _block_size), "Invalid length");
|
assert(is_aligned(length, _block_size), "Invalid length");
|
||||||
|
|
||||||
@ -565,7 +565,7 @@ ZErrno ZBackingFile::fallocate(bool punch_hole, size_t offset, size_t length) {
|
|||||||
return err;
|
return err;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool ZBackingFile::commit_inner(size_t offset, size_t length) {
|
bool ZPhysicalMemoryBacking::commit_inner(size_t offset, size_t length) {
|
||||||
log_trace(gc, heap)("Committing memory: " SIZE_FORMAT "M-" SIZE_FORMAT "M (" SIZE_FORMAT "M)",
|
log_trace(gc, heap)("Committing memory: " SIZE_FORMAT "M-" SIZE_FORMAT "M (" SIZE_FORMAT "M)",
|
||||||
offset / M, (offset + length) / M, length / M);
|
offset / M, (offset + length) / M, length / M);
|
||||||
|
|
||||||
@ -596,7 +596,7 @@ retry:
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
size_t ZBackingFile::commit(size_t offset, size_t length) {
|
size_t ZPhysicalMemoryBacking::commit(size_t offset, size_t length) {
|
||||||
// Try to commit the whole region
|
// Try to commit the whole region
|
||||||
if (commit_inner(offset, length)) {
|
if (commit_inner(offset, length)) {
|
||||||
// Success
|
// Success
|
||||||
@ -624,7 +624,7 @@ size_t ZBackingFile::commit(size_t offset, size_t length) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
size_t ZBackingFile::uncommit(size_t offset, size_t length) {
|
size_t ZPhysicalMemoryBacking::uncommit(size_t offset, size_t length) {
|
||||||
log_trace(gc, heap)("Uncommitting memory: " SIZE_FORMAT "M-" SIZE_FORMAT "M (" SIZE_FORMAT "M)",
|
log_trace(gc, heap)("Uncommitting memory: " SIZE_FORMAT "M-" SIZE_FORMAT "M (" SIZE_FORMAT "M)",
|
||||||
offset / M, (offset + length) / M, length / M);
|
offset / M, (offset + length) / M, length / M);
|
||||||
|
|
||||||
@ -637,7 +637,7 @@ size_t ZBackingFile::uncommit(size_t offset, size_t length) {
|
|||||||
return length;
|
return length;
|
||||||
}
|
}
|
||||||
|
|
||||||
void ZBackingFile::map(uintptr_t addr, size_t size, uintptr_t offset) const {
|
void ZPhysicalMemoryBacking::map(uintptr_t addr, size_t size, uintptr_t offset) const {
|
||||||
const void* const res = mmap((void*)addr, size, PROT_READ|PROT_WRITE, MAP_FIXED|MAP_SHARED, _fd, offset);
|
const void* const res = mmap((void*)addr, size, PROT_READ|PROT_WRITE, MAP_FIXED|MAP_SHARED, _fd, offset);
|
||||||
if (res == MAP_FAILED) {
|
if (res == MAP_FAILED) {
|
||||||
ZErrno err;
|
ZErrno err;
|
||||||
@ -645,7 +645,7 @@ void ZBackingFile::map(uintptr_t addr, size_t size, uintptr_t offset) const {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void ZBackingFile::unmap(uintptr_t addr, size_t size) const {
|
void ZPhysicalMemoryBacking::unmap(uintptr_t addr, size_t size) const {
|
||||||
// Note that we must keep the address space reservation intact and just detach
|
// Note that we must keep the address space reservation intact and just detach
|
||||||
// the backing memory. For this reason we map a new anonymous, non-accessible
|
// the backing memory. For this reason we map a new anonymous, non-accessible
|
||||||
// and non-reserved page over the mapping instead of actually unmapping.
|
// and non-reserved page over the mapping instead of actually unmapping.
|
@ -21,14 +21,12 @@
|
|||||||
* questions.
|
* questions.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef OS_LINUX_GC_Z_ZBACKINGFILE_LINUX_HPP
|
#ifndef OS_LINUX_GC_Z_ZPHYSICALMEMORYBACKING_LINUX_HPP
|
||||||
#define OS_LINUX_GC_Z_ZBACKINGFILE_LINUX_HPP
|
#define OS_LINUX_GC_Z_ZPHYSICALMEMORYBACKING_LINUX_HPP
|
||||||
|
|
||||||
#include "memory/allocation.hpp"
|
|
||||||
|
|
||||||
class ZErrno;
|
class ZErrno;
|
||||||
|
|
||||||
class ZBackingFile {
|
class ZPhysicalMemoryBacking {
|
||||||
private:
|
private:
|
||||||
int _fd;
|
int _fd;
|
||||||
size_t _size;
|
size_t _size;
|
||||||
@ -61,7 +59,7 @@ private:
|
|||||||
bool commit_inner(size_t offset, size_t length);
|
bool commit_inner(size_t offset, size_t length);
|
||||||
|
|
||||||
public:
|
public:
|
||||||
ZBackingFile();
|
ZPhysicalMemoryBacking();
|
||||||
|
|
||||||
bool is_initialized() const;
|
bool is_initialized() const;
|
||||||
|
|
||||||
@ -76,4 +74,4 @@ public:
|
|||||||
void unmap(uintptr_t addr, size_t size) const;
|
void unmap(uintptr_t addr, size_t size) const;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // OS_LINUX_GC_Z_ZBACKINGFILE_LINUX_HPP
|
#endif // OS_LINUX_GC_Z_ZPHYSICALMEMORYBACKING_LINUX_HPP
|
@ -22,53 +22,53 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
#include "precompiled.hpp"
|
#include "precompiled.hpp"
|
||||||
#include "gc/z/zBackingFile_windows.hpp"
|
|
||||||
#include "gc/z/zGlobals.hpp"
|
#include "gc/z/zGlobals.hpp"
|
||||||
#include "gc/z/zGranuleMap.inline.hpp"
|
#include "gc/z/zGranuleMap.inline.hpp"
|
||||||
#include "gc/z/zMapper_windows.hpp"
|
#include "gc/z/zMapper_windows.hpp"
|
||||||
|
#include "gc/z/zPhysicalMemoryBacking_windows.hpp"
|
||||||
#include "logging/log.hpp"
|
#include "logging/log.hpp"
|
||||||
#include "runtime/globals.hpp"
|
#include "runtime/globals.hpp"
|
||||||
#include "utilities/debug.hpp"
|
#include "utilities/debug.hpp"
|
||||||
|
|
||||||
// The backing file commits and uncommits physical memory, that can be
|
// The backing commits and uncommits physical memory, that can be
|
||||||
// multi-mapped into the virtual address space. To support fine-graned
|
// multi-mapped into the virtual address space. To support fine-graned
|
||||||
// committing and uncommitting, each ZGranuleSize chunked is mapped to
|
// committing and uncommitting, each ZGranuleSize'd chunk is mapped to
|
||||||
// a separate paging file mapping.
|
// a separate paging file mapping.
|
||||||
|
|
||||||
ZBackingFile::ZBackingFile() :
|
ZPhysicalMemoryBacking::ZPhysicalMemoryBacking() :
|
||||||
_handles(MaxHeapSize),
|
_handles(MaxHeapSize),
|
||||||
_size(0) {}
|
_size(0) {}
|
||||||
|
|
||||||
bool ZBackingFile::is_initialized() const {
|
bool ZPhysicalMemoryBacking::is_initialized() const {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
void ZBackingFile::warn_commit_limits(size_t max) const {
|
void ZPhysicalMemoryBacking::warn_commit_limits(size_t max) const {
|
||||||
// Does nothing
|
// Does nothing
|
||||||
}
|
}
|
||||||
|
|
||||||
size_t ZBackingFile::size() const {
|
size_t ZPhysicalMemoryBacking::size() const {
|
||||||
return _size;
|
return _size;
|
||||||
}
|
}
|
||||||
|
|
||||||
HANDLE ZBackingFile::get_handle(uintptr_t offset) const {
|
HANDLE ZPhysicalMemoryBacking::get_handle(uintptr_t offset) const {
|
||||||
HANDLE const handle = _handles.get(offset);
|
HANDLE const handle = _handles.get(offset);
|
||||||
assert(handle != 0, "Should be set");
|
assert(handle != 0, "Should be set");
|
||||||
return handle;
|
return handle;
|
||||||
}
|
}
|
||||||
|
|
||||||
void ZBackingFile::put_handle(uintptr_t offset, HANDLE handle) {
|
void ZPhysicalMemoryBacking::put_handle(uintptr_t offset, HANDLE handle) {
|
||||||
assert(handle != INVALID_HANDLE_VALUE, "Invalid handle");
|
assert(handle != INVALID_HANDLE_VALUE, "Invalid handle");
|
||||||
assert(_handles.get(offset) == 0, "Should be cleared");
|
assert(_handles.get(offset) == 0, "Should be cleared");
|
||||||
_handles.put(offset, handle);
|
_handles.put(offset, handle);
|
||||||
}
|
}
|
||||||
|
|
||||||
void ZBackingFile::clear_handle(uintptr_t offset) {
|
void ZPhysicalMemoryBacking::clear_handle(uintptr_t offset) {
|
||||||
assert(_handles.get(offset) != 0, "Should be set");
|
assert(_handles.get(offset) != 0, "Should be set");
|
||||||
_handles.put(offset, 0);
|
_handles.put(offset, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
size_t ZBackingFile::commit_from_paging_file(size_t offset, size_t size) {
|
size_t ZPhysicalMemoryBacking::commit_from_paging_file(size_t offset, size_t size) {
|
||||||
for (size_t i = 0; i < size; i += ZGranuleSize) {
|
for (size_t i = 0; i < size; i += ZGranuleSize) {
|
||||||
HANDLE const handle = ZMapper::create_and_commit_paging_file_mapping(ZGranuleSize);
|
HANDLE const handle = ZMapper::create_and_commit_paging_file_mapping(ZGranuleSize);
|
||||||
if (handle == 0) {
|
if (handle == 0) {
|
||||||
@ -81,7 +81,7 @@ size_t ZBackingFile::commit_from_paging_file(size_t offset, size_t size) {
|
|||||||
return size;
|
return size;
|
||||||
}
|
}
|
||||||
|
|
||||||
size_t ZBackingFile::uncommit_from_paging_file(size_t offset, size_t size) {
|
size_t ZPhysicalMemoryBacking::uncommit_from_paging_file(size_t offset, size_t size) {
|
||||||
for (size_t i = 0; i < size; i += ZGranuleSize) {
|
for (size_t i = 0; i < size; i += ZGranuleSize) {
|
||||||
HANDLE const handle = get_handle(offset + i);
|
HANDLE const handle = get_handle(offset + i);
|
||||||
clear_handle(offset + i);
|
clear_handle(offset + i);
|
||||||
@ -91,7 +91,7 @@ size_t ZBackingFile::uncommit_from_paging_file(size_t offset, size_t size) {
|
|||||||
return size;
|
return size;
|
||||||
}
|
}
|
||||||
|
|
||||||
size_t ZBackingFile::commit(size_t offset, size_t length) {
|
size_t ZPhysicalMemoryBacking::commit(size_t offset, size_t length) {
|
||||||
log_trace(gc, heap)("Committing memory: " SIZE_FORMAT "M-" SIZE_FORMAT "M (" SIZE_FORMAT "M)",
|
log_trace(gc, heap)("Committing memory: " SIZE_FORMAT "M-" SIZE_FORMAT "M (" SIZE_FORMAT "M)",
|
||||||
offset / M, (offset + length) / M, length / M);
|
offset / M, (offset + length) / M, length / M);
|
||||||
|
|
||||||
@ -106,14 +106,14 @@ size_t ZBackingFile::commit(size_t offset, size_t length) {
|
|||||||
return committed;
|
return committed;
|
||||||
}
|
}
|
||||||
|
|
||||||
size_t ZBackingFile::uncommit(size_t offset, size_t length) {
|
size_t ZPhysicalMemoryBacking::uncommit(size_t offset, size_t length) {
|
||||||
log_trace(gc, heap)("Uncommitting memory: " SIZE_FORMAT "M-" SIZE_FORMAT "M (" SIZE_FORMAT "M)",
|
log_trace(gc, heap)("Uncommitting memory: " SIZE_FORMAT "M-" SIZE_FORMAT "M (" SIZE_FORMAT "M)",
|
||||||
offset / M, (offset + length) / M, length / M);
|
offset / M, (offset + length) / M, length / M);
|
||||||
|
|
||||||
return uncommit_from_paging_file(offset, length);
|
return uncommit_from_paging_file(offset, length);
|
||||||
}
|
}
|
||||||
|
|
||||||
void ZBackingFile::map(uintptr_t addr, size_t size, size_t offset) const {
|
void ZPhysicalMemoryBacking::map(uintptr_t addr, size_t size, size_t offset) const {
|
||||||
assert(is_aligned(offset, ZGranuleSize), "Misaligned");
|
assert(is_aligned(offset, ZGranuleSize), "Misaligned");
|
||||||
assert(is_aligned(addr, ZGranuleSize), "Misaligned");
|
assert(is_aligned(addr, ZGranuleSize), "Misaligned");
|
||||||
assert(is_aligned(size, ZGranuleSize), "Misaligned");
|
assert(is_aligned(size, ZGranuleSize), "Misaligned");
|
||||||
@ -124,7 +124,7 @@ void ZBackingFile::map(uintptr_t addr, size_t size, size_t offset) const {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void ZBackingFile::unmap(uintptr_t addr, size_t size) const {
|
void ZPhysicalMemoryBacking::unmap(uintptr_t addr, size_t size) const {
|
||||||
assert(is_aligned(addr, ZGranuleSize), "Misaligned");
|
assert(is_aligned(addr, ZGranuleSize), "Misaligned");
|
||||||
assert(is_aligned(size, ZGranuleSize), "Misaligned");
|
assert(is_aligned(size, ZGranuleSize), "Misaligned");
|
||||||
|
|
@ -21,15 +21,14 @@
|
|||||||
* questions.
|
* questions.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef OS_WINDOWS_GC_Z_ZBACKINGFILE_WINDOWS_HPP
|
#ifndef OS_WINDOWS_GC_Z_ZPHYSICALMEMORYBACKING_WINDOWS_HPP
|
||||||
#define OS_WINDOWS_GC_Z_ZBACKINGFILE_WINDOWS_HPP
|
#define OS_WINDOWS_GC_Z_ZPHYSICALMEMORYBACKING_WINDOWS_HPP
|
||||||
|
|
||||||
#include "gc/z/zGranuleMap.hpp"
|
#include "gc/z/zGranuleMap.hpp"
|
||||||
#include "memory/allocation.hpp"
|
|
||||||
|
|
||||||
#include <Windows.h>
|
#include <Windows.h>
|
||||||
|
|
||||||
class ZBackingFile {
|
class ZPhysicalMemoryBacking {
|
||||||
private:
|
private:
|
||||||
ZGranuleMap<HANDLE> _handles;
|
ZGranuleMap<HANDLE> _handles;
|
||||||
size_t _size;
|
size_t _size;
|
||||||
@ -42,7 +41,7 @@ private:
|
|||||||
size_t uncommit_from_paging_file(size_t offset, size_t size);
|
size_t uncommit_from_paging_file(size_t offset, size_t size);
|
||||||
|
|
||||||
public:
|
public:
|
||||||
ZBackingFile();
|
ZPhysicalMemoryBacking();
|
||||||
|
|
||||||
bool is_initialized() const;
|
bool is_initialized() const;
|
||||||
|
|
||||||
@ -57,4 +56,4 @@ public:
|
|||||||
void unmap(uintptr_t addr, size_t size) const;
|
void unmap(uintptr_t addr, size_t size) const;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // OS_WINDOWS_GC_Z_ZBACKINGFILE_WINDOWS_HPP
|
#endif // OS_WINDOWS_GC_Z_ZPHYSICALMEMORYBACKING_WINDOWS_HPP
|
@ -26,7 +26,7 @@
|
|||||||
|
|
||||||
#include "gc/z/zMemory.hpp"
|
#include "gc/z/zMemory.hpp"
|
||||||
#include "memory/allocation.hpp"
|
#include "memory/allocation.hpp"
|
||||||
#include OS_HEADER(gc/z/zBackingFile)
|
#include OS_HEADER(gc/z/zPhysicalMemoryBacking)
|
||||||
|
|
||||||
class ZPhysicalMemorySegment : public CHeapObj<mtGC> {
|
class ZPhysicalMemorySegment : public CHeapObj<mtGC> {
|
||||||
private:
|
private:
|
||||||
@ -66,9 +66,9 @@ public:
|
|||||||
|
|
||||||
class ZPhysicalMemoryManager {
|
class ZPhysicalMemoryManager {
|
||||||
private:
|
private:
|
||||||
ZBackingFile _backing;
|
ZPhysicalMemoryBacking _backing;
|
||||||
ZMemoryManager _committed;
|
ZMemoryManager _committed;
|
||||||
ZMemoryManager _uncommitted;
|
ZMemoryManager _uncommitted;
|
||||||
|
|
||||||
void nmt_commit(const ZPhysicalMemory& pmem, uintptr_t offset) const;
|
void nmt_commit(const ZPhysicalMemory& pmem, uintptr_t offset) const;
|
||||||
void nmt_uncommit(const ZPhysicalMemory& pmem, uintptr_t offset) const;
|
void nmt_uncommit(const ZPhysicalMemory& pmem, uintptr_t offset) const;
|
||||||
|
Loading…
x
Reference in New Issue
Block a user