8315321: [aix] os::attempt_reserve_memory_at must map at the requested address or fail

Reviewed-by: mdoerr
This commit is contained in:
Thomas Stuefe 2023-09-01 11:05:34 +00:00
parent 42f5b9e7aa
commit c32e340d94
2 changed files with 20 additions and 4 deletions

View File

@ -1590,10 +1590,13 @@ static char* reserve_shmated_memory (size_t bytes, char* requested_addr) {
}
// Now attach the shared segment.
// Note that I attach with SHM_RND - which means that the requested address is rounded down, if
// needed, to the next lowest segment boundary. Otherwise the attach would fail if the address
// were not a segment boundary.
char* const addr = (char*) shmat(shmid, requested_addr, SHM_RND);
// Note that we deliberately *don't* pass SHM_RND. The contract of os::attempt_reserve_memory_at() -
// which invokes this function with a request address != NULL - is to map at the specified address
// excactly, or to fail. If the caller passed us an address that is not usable (aka not a valid segment
// boundary), shmat should not round down the address, or think up a completely new one.
// (In places where this matters, e.g. when reserving the heap, we take care of passing segment-aligned
// addresses on Aix. See, e.g., ReservedHeapSpace.
char* const addr = (char*) shmat(shmid, requested_addr, 0);
const int errno_shmat = errno;
// (A) Right after shmat and before handing shmat errors delete the shm segment.

View File

@ -25,6 +25,7 @@
#include "memory/allocation.hpp"
#include "memory/resourceArea.hpp"
#include "runtime/frame.inline.hpp"
#include "runtime/globals.hpp"
#include "runtime/os.inline.hpp"
#include "runtime/thread.hpp"
#include "runtime/threads.hpp"
@ -948,6 +949,18 @@ TEST_VM(os, reserve_at_wish_address_shall_not_replace_mappings_largepages) {
}
}
#ifdef AIX
// On Aix, we should fail attach attempts not aligned to segment boundaries (256m)
TEST_VM(os, aix_reserve_at_non_shmlba_aligned_address) {
if (Use64KPages && Use64KPagesThreshold == 0) {
char* p = os::attempt_reserve_memory_at((char*)0x1f00000, M);
ASSERT_EQ(p, nullptr); // should have failed
p = os::attempt_reserve_memory_at((char*)((64 * G) + M), M);
ASSERT_EQ(p, nullptr); // should have failed
}
}
#endif // AIX
TEST_VM(os, vm_min_address) {
size_t s = os::vm_min_address();
ASSERT_GE(s, M);