mirror of
https://github.com/openjdk/jdk.git
synced 2025-08-28 15:24:43 +02:00
8266349: Pass down requested page size to reserve_memory_special
Reviewed-by: stuefe, mgkwill
This commit is contained in:
parent
e0c86884e5
commit
2798b0d98a
10 changed files with 38 additions and 34 deletions
|
@ -2141,7 +2141,7 @@ void os::large_page_init() {
|
|||
return; // Nothing to do. See query_multipage_support and friends.
|
||||
}
|
||||
|
||||
char* os::pd_reserve_memory_special(size_t bytes, size_t alignment, char* req_addr, bool exec) {
|
||||
char* os::pd_reserve_memory_special(size_t bytes, size_t alignment, size_t page_size, char* req_addr, bool exec) {
|
||||
fatal("os::reserve_memory_special should not be called on AIX.");
|
||||
return NULL;
|
||||
}
|
||||
|
|
|
@ -1776,7 +1776,7 @@ void os::large_page_init() {
|
|||
}
|
||||
|
||||
|
||||
char* os::pd_reserve_memory_special(size_t bytes, size_t alignment, char* req_addr, bool exec) {
|
||||
char* os::pd_reserve_memory_special(size_t bytes, size_t alignment, size_t page_size, char* req_addr, bool exec) {
|
||||
fatal("os::reserve_memory_special should not be called on BSD.");
|
||||
return NULL;
|
||||
}
|
||||
|
|
|
@ -3957,14 +3957,15 @@ bool os::Linux::commit_memory_special(size_t bytes,
|
|||
|
||||
char* os::Linux::reserve_memory_special_huge_tlbfs(size_t bytes,
|
||||
size_t alignment,
|
||||
size_t page_size,
|
||||
char* req_addr,
|
||||
bool exec) {
|
||||
assert(UseLargePages && UseHugeTLBFS, "only for Huge TLBFS large pages");
|
||||
assert(is_aligned(req_addr, alignment), "Must be");
|
||||
assert(is_aligned(req_addr, os::large_page_size()), "Must be");
|
||||
assert(is_aligned(req_addr, page_size), "Must be");
|
||||
assert(is_aligned(alignment, os::vm_allocation_granularity()), "Must be");
|
||||
assert(is_power_of_2(os::large_page_size()), "Must be");
|
||||
assert(bytes >= os::large_page_size(), "Shouldn't allocate large pages for small sizes");
|
||||
assert(_page_sizes.contains(page_size), "Must be a valid page size");
|
||||
assert(bytes >= page_size, "Shouldn't allocate large pages for small sizes");
|
||||
|
||||
// We only end up here when at least 1 large page can be used.
|
||||
// If the size is not a multiple of the large page size, we
|
||||
|
@ -3974,15 +3975,15 @@ char* os::Linux::reserve_memory_special_huge_tlbfs(size_t bytes,
|
|||
// a requested address is given it will be used and it must be
|
||||
// aligned to both the large page size and the given alignment.
|
||||
// The larger of the two will be used.
|
||||
size_t required_alignment = MAX(os::large_page_size(), alignment);
|
||||
size_t required_alignment = MAX(page_size, alignment);
|
||||
char* const aligned_start = anon_mmap_aligned(req_addr, bytes, required_alignment);
|
||||
if (aligned_start == NULL) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
// First commit using large pages.
|
||||
size_t large_bytes = align_down(bytes, os::large_page_size());
|
||||
bool large_committed = commit_memory_special(large_bytes, os::large_page_size(), aligned_start, exec);
|
||||
size_t large_bytes = align_down(bytes, page_size);
|
||||
bool large_committed = commit_memory_special(large_bytes, page_size, aligned_start, exec);
|
||||
|
||||
if (large_committed && bytes == large_bytes) {
|
||||
// The size was large page aligned so no additional work is
|
||||
|
@ -4011,16 +4012,17 @@ char* os::Linux::reserve_memory_special_huge_tlbfs(size_t bytes,
|
|||
return aligned_start;
|
||||
}
|
||||
|
||||
char* os::pd_reserve_memory_special(size_t bytes, size_t alignment,
|
||||
char* os::pd_reserve_memory_special(size_t bytes, size_t alignment, size_t page_size,
|
||||
char* req_addr, bool exec) {
|
||||
assert(UseLargePages, "only for large pages");
|
||||
|
||||
char* addr;
|
||||
if (UseSHM) {
|
||||
// No support for using specific page sizes with SHM.
|
||||
addr = os::Linux::reserve_memory_special_shm(bytes, alignment, req_addr, exec);
|
||||
} else {
|
||||
assert(UseHugeTLBFS, "must be");
|
||||
addr = os::Linux::reserve_memory_special_huge_tlbfs(bytes, alignment, req_addr, exec);
|
||||
addr = os::Linux::reserve_memory_special_huge_tlbfs(bytes, alignment, page_size, req_addr, exec);
|
||||
}
|
||||
|
||||
if (addr != NULL) {
|
||||
|
|
|
@ -90,7 +90,7 @@ class Linux {
|
|||
static int hugetlbfs_page_size_flag(size_t page_size);
|
||||
|
||||
static char* reserve_memory_special_shm(size_t bytes, size_t alignment, char* req_addr, bool exec);
|
||||
static char* reserve_memory_special_huge_tlbfs(size_t bytes, size_t alignment, char* req_addr, bool exec);
|
||||
static char* reserve_memory_special_huge_tlbfs(size_t bytes, size_t alignment, size_t page_size, char* req_addr, bool exec);
|
||||
static bool commit_memory_special(size_t bytes, size_t page_size, char* req_addr, bool exec);
|
||||
|
||||
static bool release_memory_special_impl(char* base, size_t bytes);
|
||||
|
|
|
@ -3274,11 +3274,12 @@ bool os::can_execute_large_page_memory() {
|
|||
return true;
|
||||
}
|
||||
|
||||
char* os::pd_reserve_memory_special(size_t bytes, size_t alignment, char* addr,
|
||||
char* os::pd_reserve_memory_special(size_t bytes, size_t alignment, size_t page_size, char* addr,
|
||||
bool exec) {
|
||||
assert(UseLargePages, "only for large pages");
|
||||
assert(page_size == os::large_page_size(), "Currently only support one large page size on Windows");
|
||||
|
||||
if (!is_aligned(bytes, os::large_page_size()) || alignment > os::large_page_size()) {
|
||||
if (!is_aligned(bytes, page_size) || alignment > page_size) {
|
||||
return NULL; // Fallback to small pages.
|
||||
}
|
||||
|
||||
|
|
|
@ -169,14 +169,14 @@ static char* reserve_memory(char* requested_address, const size_t size,
|
|||
}
|
||||
|
||||
static char* reserve_memory_special(char* requested_address, const size_t size,
|
||||
const size_t alignment, bool exec) {
|
||||
const size_t alignment, const size_t page_size, bool exec) {
|
||||
|
||||
log_trace(pagesize)("Attempt special mapping: size: " SIZE_FORMAT "%s, "
|
||||
"alignment: " SIZE_FORMAT "%s",
|
||||
byte_size_in_exact_unit(size), exact_unit_for_byte_size(size),
|
||||
byte_size_in_exact_unit(alignment), exact_unit_for_byte_size(alignment));
|
||||
|
||||
char* base = os::reserve_memory_special(size, alignment, requested_address, exec);
|
||||
char* base = os::reserve_memory_special(size, alignment, page_size, requested_address, exec);
|
||||
if (base != NULL) {
|
||||
// Check alignment constraints.
|
||||
assert(is_aligned(base, alignment),
|
||||
|
@ -236,7 +236,7 @@ void ReservedSpace::reserve(size_t size,
|
|||
// explicit large pages and these have to be committed up front to ensure
|
||||
// no reservations are lost.
|
||||
|
||||
char* base = reserve_memory_special(requested_address, size, alignment, executable);
|
||||
char* base = reserve_memory_special(requested_address, size, alignment, page_size, executable);
|
||||
if (base != NULL) {
|
||||
// Successful reservation using large pages.
|
||||
initialize_members(base, size, alignment, page_size, true, executable);
|
||||
|
|
|
@ -1890,12 +1890,12 @@ void os::realign_memory(char *addr, size_t bytes, size_t alignment_hint) {
|
|||
pd_realign_memory(addr, bytes, alignment_hint);
|
||||
}
|
||||
|
||||
char* os::reserve_memory_special(size_t size, size_t alignment,
|
||||
char* os::reserve_memory_special(size_t size, size_t alignment, size_t page_size,
|
||||
char* addr, bool executable) {
|
||||
|
||||
assert(is_aligned(addr, alignment), "Unaligned request address");
|
||||
|
||||
char* result = pd_reserve_memory_special(size, alignment, addr, executable);
|
||||
char* result = pd_reserve_memory_special(size, alignment, page_size, addr, executable);
|
||||
if (result != NULL) {
|
||||
// The memory is committed
|
||||
MemTracker::record_virtual_memory_reserve_and_commit((address)result, size, CALLER_PC);
|
||||
|
|
|
@ -159,7 +159,8 @@ class os: AllStatic {
|
|||
static void pd_free_memory(char *addr, size_t bytes, size_t alignment_hint);
|
||||
static void pd_realign_memory(char *addr, size_t bytes, size_t alignment_hint);
|
||||
|
||||
static char* pd_reserve_memory_special(size_t size, size_t alignment,
|
||||
static char* pd_reserve_memory_special(size_t size, size_t alignment, size_t page_size,
|
||||
|
||||
char* addr, bool executable);
|
||||
static bool pd_release_memory_special(char* addr, size_t bytes);
|
||||
|
||||
|
@ -428,7 +429,7 @@ class os: AllStatic {
|
|||
|
||||
static char* non_memory_address_word();
|
||||
// reserve, commit and pin the entire memory region
|
||||
static char* reserve_memory_special(size_t size, size_t alignment,
|
||||
static char* reserve_memory_special(size_t size, size_t alignment, size_t page_size,
|
||||
char* addr, bool executable);
|
||||
static bool release_memory_special(char* addr, size_t bytes);
|
||||
static void large_page_init();
|
||||
|
|
|
@ -47,8 +47,8 @@ namespace {
|
|||
char* const _ptr;
|
||||
const size_t _size;
|
||||
public:
|
||||
static char* reserve_memory_special_huge_tlbfs(size_t bytes, size_t alignment, char* req_addr, bool exec) {
|
||||
return os::Linux::reserve_memory_special_huge_tlbfs(bytes, alignment, req_addr, exec);
|
||||
static char* reserve_memory_special_huge_tlbfs(size_t bytes, size_t alignment, size_t page_size, char* req_addr, bool exec) {
|
||||
return os::Linux::reserve_memory_special_huge_tlbfs(bytes, alignment, page_size, req_addr, exec);
|
||||
}
|
||||
HugeTlbfsMemory(char* const ptr, size_t size) : _ptr(ptr), _size(size) { }
|
||||
~HugeTlbfsMemory() {
|
||||
|
@ -100,7 +100,7 @@ TEST_VM(os_linux, reserve_memory_special_huge_tlbfs_size_aligned) {
|
|||
size_t lp = os::large_page_size();
|
||||
|
||||
for (size_t size = lp; size <= lp * 10; size += lp) {
|
||||
char* addr = HugeTlbfsMemory::reserve_memory_special_huge_tlbfs(size, lp, NULL, false);
|
||||
char* addr = HugeTlbfsMemory::reserve_memory_special_huge_tlbfs(size, lp, lp, NULL, false);
|
||||
|
||||
if (addr != NULL) {
|
||||
HugeTlbfsMemory mr(addr, size);
|
||||
|
@ -126,7 +126,7 @@ TEST_VM(os_linux, reserve_memory_special_huge_tlbfs_size_not_aligned_without_add
|
|||
for (int i = 0; i < num_sizes; i++) {
|
||||
const size_t size = sizes[i];
|
||||
for (size_t alignment = ag; is_size_aligned(size, alignment); alignment *= 2) {
|
||||
char* p = HugeTlbfsMemory::reserve_memory_special_huge_tlbfs(size, alignment, NULL, false);
|
||||
char* p = HugeTlbfsMemory::reserve_memory_special_huge_tlbfs(size, alignment, lp, NULL, false);
|
||||
if (p != NULL) {
|
||||
HugeTlbfsMemory mr(p, size);
|
||||
EXPECT_PRED2(is_ptr_aligned, p, alignment) << " size = " << size;
|
||||
|
@ -166,7 +166,7 @@ TEST_VM(os_linux, reserve_memory_special_huge_tlbfs_size_not_aligned_with_good_r
|
|||
for (size_t alignment = ag; is_size_aligned(size, alignment); alignment *= 2) {
|
||||
// req_addr must be at least large page aligned.
|
||||
char* const req_addr = align_up(mapping, MAX2(alignment, lp));
|
||||
char* p = HugeTlbfsMemory::reserve_memory_special_huge_tlbfs(size, alignment, req_addr, false);
|
||||
char* p = HugeTlbfsMemory::reserve_memory_special_huge_tlbfs(size, alignment, lp, req_addr, false);
|
||||
if (p != NULL) {
|
||||
HugeTlbfsMemory mr(p, size);
|
||||
ASSERT_EQ(req_addr, p) << " size = " << size << ", alignment = " << alignment;
|
||||
|
@ -216,7 +216,7 @@ TEST_VM(os_linux, reserve_memory_special_huge_tlbfs_size_not_aligned_with_bad_re
|
|||
for (size_t alignment = ag; is_size_aligned(size, alignment); alignment *= 2) {
|
||||
// req_addr must be at least large page aligned.
|
||||
char* const req_addr = align_up(mapping, MAX2(alignment, lp));
|
||||
char* p = HugeTlbfsMemory::reserve_memory_special_huge_tlbfs(size, alignment, req_addr, false);
|
||||
char* p = HugeTlbfsMemory::reserve_memory_special_huge_tlbfs(size, alignment, lp, req_addr, false);
|
||||
HugeTlbfsMemory mr(p, size);
|
||||
// as the area around req_addr contains already existing mappings, the API should always
|
||||
// return NULL (as per contract, it cannot return another address)
|
||||
|
@ -253,12 +253,12 @@ class TestReserveMemorySpecial : AllStatic {
|
|||
}
|
||||
}
|
||||
|
||||
static void test_reserve_memory_special_huge_tlbfs_size_aligned(size_t size, size_t alignment) {
|
||||
static void test_reserve_memory_special_huge_tlbfs_size_aligned(size_t size, size_t alignment, size_t page_size) {
|
||||
if (!UseHugeTLBFS) {
|
||||
return;
|
||||
}
|
||||
|
||||
char* addr = os::Linux::reserve_memory_special_huge_tlbfs(size, alignment, NULL, false);
|
||||
char* addr = os::Linux::reserve_memory_special_huge_tlbfs(size, alignment, page_size, NULL, false);
|
||||
|
||||
if (addr != NULL) {
|
||||
small_page_write(addr, size);
|
||||
|
@ -275,7 +275,7 @@ class TestReserveMemorySpecial : AllStatic {
|
|||
size_t lp = os::large_page_size();
|
||||
|
||||
for (size_t size = lp; size <= lp * 10; size += lp) {
|
||||
test_reserve_memory_special_huge_tlbfs_size_aligned(size, lp);
|
||||
test_reserve_memory_special_huge_tlbfs_size_aligned(size, lp, lp);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -319,7 +319,7 @@ class TestReserveMemorySpecial : AllStatic {
|
|||
for (int i = 0; i < num_sizes; i++) {
|
||||
const size_t size = sizes[i];
|
||||
for (size_t alignment = ag; is_aligned(size, alignment); alignment *= 2) {
|
||||
char* p = os::Linux::reserve_memory_special_huge_tlbfs(size, alignment, NULL, false);
|
||||
char* p = os::Linux::reserve_memory_special_huge_tlbfs(size, alignment, lp, NULL, false);
|
||||
if (p != NULL) {
|
||||
EXPECT_TRUE(is_aligned(p, alignment));
|
||||
small_page_write(p, size);
|
||||
|
@ -334,7 +334,7 @@ class TestReserveMemorySpecial : AllStatic {
|
|||
for (size_t alignment = ag; is_aligned(size, alignment); alignment *= 2) {
|
||||
// req_addr must be at least large page aligned.
|
||||
char* const req_addr = align_up(mapping1, MAX2(alignment, lp));
|
||||
char* p = os::Linux::reserve_memory_special_huge_tlbfs(size, alignment, req_addr, false);
|
||||
char* p = os::Linux::reserve_memory_special_huge_tlbfs(size, alignment, lp, req_addr, false);
|
||||
if (p != NULL) {
|
||||
EXPECT_EQ(p, req_addr);
|
||||
small_page_write(p, size);
|
||||
|
@ -349,7 +349,7 @@ class TestReserveMemorySpecial : AllStatic {
|
|||
for (size_t alignment = ag; is_aligned(size, alignment); alignment *= 2) {
|
||||
// req_addr must be at least large page aligned.
|
||||
char* const req_addr = align_up(mapping2, MAX2(alignment, lp));
|
||||
char* p = os::Linux::reserve_memory_special_huge_tlbfs(size, alignment, req_addr, false);
|
||||
char* p = os::Linux::reserve_memory_special_huge_tlbfs(size, alignment, lp, req_addr, false);
|
||||
// as the area around req_addr contains already existing mappings, the API should always
|
||||
// return NULL (as per contract, it cannot return another address)
|
||||
EXPECT_TRUE(p == NULL);
|
||||
|
|
|
@ -64,7 +64,7 @@ void TestReserveMemorySpecial_test() {
|
|||
FLAG_SET_CMDLINE(UseNUMAInterleaving, false);
|
||||
|
||||
const size_t large_allocation_size = os::large_page_size() * 4;
|
||||
char* result = os::reserve_memory_special(large_allocation_size, os::large_page_size(), NULL, false);
|
||||
char* result = os::reserve_memory_special(large_allocation_size, os::large_page_size(), os::large_page_size(), NULL, false);
|
||||
if (result != NULL) {
|
||||
// failed to allocate memory, skipping the test
|
||||
return;
|
||||
|
@ -75,7 +75,7 @@ void TestReserveMemorySpecial_test() {
|
|||
// we managed to get it once.
|
||||
const size_t expected_allocation_size = os::large_page_size();
|
||||
char* expected_location = result + os::large_page_size();
|
||||
char* actual_location = os::reserve_memory_special(expected_allocation_size, os::large_page_size(), expected_location, false);
|
||||
char* actual_location = os::reserve_memory_special(expected_allocation_size, os::large_page_size(), os::large_page_size(), expected_location, false);
|
||||
if (actual_location != NULL) {
|
||||
// failed to allocate memory, skipping the test
|
||||
return;
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue