Skip to content

Conversation

MBaesken
Copy link
Member

@MBaesken MBaesken commented Jul 9, 2025

When running HS test
gtest/GTestWrapper.java
with ubsan-enabled binaries on macOS aarch64, the following error is reported (did not see this so far on Linux but there we use gcc and it seems the gcc/ubsan checks are a bit more limited).

test/hotspot/gtest/gc/g1/test_freeRegionList.cpp:37: Failure
Death test: child_G1FreeRegionList_length_()
Result: died but not with expected exit code:
Terminated by signal 6 (core dumped)
Actual msg:

[  DEATH   ] /jdk/src/hotspot/share/memory/memRegion.hpp:66:43: runtime error: applying non-zero offset 8388608 to null pointer
[  DEATH   ]     #0 0x108afd6f4 in MemRegion::end() const+0x84 (libjvm.dylib:arm64+0x16556f4)
[  DEATH   ]     #1 0x1075c68a0 in G1FreeRegionList_length_other_vm_Test::TestBody()+0x380 (libjvm.dylib:arm64+0x11e8a0)
[  DEATH   ]     #2 0x1090f3bb0 in testing::Test::Run()+0xc0 (libjvm.dylib:arm64+0x1c4bbb0)
[  DEATH   ]     #3 0x1090f4d94 in testing::TestInfo::Run()+0x1e4 (libjvm.dylib:arm64+0x1c4cd94)
[  DEATH   ]     #4 0x1090f6754 in testing::TestSuite::Run()+0x43c (libjvm.dylib:arm64+0x1c4e754)
[  DEATH   ]     #5 0x109103ca0 in testing::internal::UnitTestImpl::RunAllTests()+0x48c (libjvm.dylib:arm64+0x1c5bca0)
[  DEATH   ]     #6 0x109103588 in testing::UnitTest::Run()+0x78 (libjvm.dylib:arm64+0x1c5b588)
[  DEATH   ]     #7 0x1074a9ac0 in runUnitTestsInner(int, char**)+0x724 (libjvm.dylib:arm64+0x1ac0)
[  DEATH   ]     #8 0x102dc3f18 in main+0x2c (gtestLauncher:arm64+0x100003f18)
[  DEATH   ]     #9 0x196fea0dc  (<unknown module>)
[  DEATH   ] 
[  DEATH   ] SUMMARY: UndefinedBehaviorSanitizer: undefined-behavior /jdk/src/hotspot/share/memory/memRegion.hpp:66:43 in 
[  DEATH   ] 

Seems the test_freeRegionList.cpp uses a special MemRegion starting at nullptr ; but this causes a bit of trouble when adding to start == nullptr .
So far I see this issue just in the gtest, seems other MemRegion objects do not start at nullptr .


Progress

  • Change must be properly reviewed (1 review required, with at least 1 Reviewer)
  • Change must not contain extraneous whitespace
  • Commit message must refer to an issue

Issue

  • JDK-8360941: [ubsan] MemRegion::end() shows runtime error: applying non-zero offset 8388608 to null pointer (Bug - P4)

Reviewers

Contributors

Reviewing

Using git

Checkout this PR locally:
$ git fetch https://git.openjdk.org/jdk.git pull/26216/head:pull/26216
$ git checkout pull/26216

Update a local copy of the PR:
$ git checkout pull/26216
$ git pull https://git.openjdk.org/jdk.git pull/26216/head

Using Skara CLI tools

Checkout this PR locally:
$ git pr checkout 26216

View PR using the GUI difftool:
$ git pr show -t 26216

Using diff file

Download this PR as a diff file:
https://git.openjdk.org/jdk/pull/26216.diff

Using Webrev

Link to Webrev Comment

@bridgekeeper
Copy link

bridgekeeper bot commented Jul 9, 2025

👋 Welcome back mbaesken! A progress list of the required criteria for merging this PR into master will be added to the body of your pull request. There are additional pull request commands available for use with this pull request.

@openjdk
Copy link

openjdk bot commented Jul 9, 2025

@MBaesken This change now passes all automated pre-integration checks.

ℹ️ This project also has non-automated pre-integration requirements. Please see the file CONTRIBUTING.md for details.

After integration, the commit message for the final commit will be:

8360941: [ubsan] MemRegion::end() shows runtime error: applying non-zero offset 8388608 to null pointer

Co-authored-by: Kim Barrett <[email protected]>
Co-authored-by: Thomas Stuefe <[email protected]>
Reviewed-by: kbarrett, lucy

You can use pull request commands such as /summary, /contributor and /issue to adjust it as needed.

At the time when this comment was updated there had been 181 new commits pushed to the master branch:

As there are no conflicts, your changes will automatically be rebased on top of these commits when integrating. If you prefer to avoid this automatic rebasing, please check the documentation for the /integrate command for further details.

➡️ To integrate this PR with the above commit message to the master branch, type /integrate in a new comment.

@openjdk openjdk bot changed the title JDK-8360941: [ubsan] MemRegion::end() shows runtime error: applying non-zero offset 8388608 to null pointer 8360941: [ubsan] MemRegion::end() shows runtime error: applying non-zero offset 8388608 to null pointer Jul 9, 2025
@openjdk openjdk bot added the rfr Pull request is ready for review label Jul 9, 2025
@openjdk
Copy link

openjdk bot commented Jul 9, 2025

@MBaesken The following label will be automatically applied to this pull request:

  • hotspot-runtime

When this pull request is ready to be reviewed, an "RFR" email will be sent to the corresponding mailing list. If you would like to change these labels, use the /label pull request command.

@mlbridge
Copy link

mlbridge bot commented Jul 9, 2025

Copy link
Contributor

@RealLucy RealLucy left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks awful to me. But anyway - approved.

This is a perfect example where we destroy the clean look of hotspot code to accommodate odd usage. Wouldn't it be better to code the ugly stuff in the test?

@openjdk openjdk bot added the ready Pull request is ready to be integrated label Jul 11, 2025
@openjdk openjdk bot removed the ready Pull request is ready to be integrated label Jul 16, 2025
@MBaesken
Copy link
Member Author

I adjusted the test and took 'some other address than null' .

And removed the cast from the header.

@MBaesken
Copy link
Member Author

Taking 'some other address' than nullptr / 0 as suggested just fails (I worked yesterday with opt build where no failure was seen).
But fastdebug leads to this assert , any ideas ?
Or suggestions for a 'better' address (!= 0) that works ?

#  Internal Error (/openjdk-jdk-dev-linux_aarch64-dbg/jdk/src/hotspot/share/gc/g1/g1HeapRegion.cpp:254), pid=1541642, tid=1541642
#  assert(Universe::on_page_boundary(mr.start()) && Universe::on_page_boundary(mr.end())) failed: invalid space boundaries
#
# Problematic frame:
# V  [libjvm.so+0x110d75c]  G1HeapRegion::G1HeapRegion(unsigned int, G1BlockOffsetTable*, MemRegion, G1CardSetConfiguration*)+0x158
#

---------------  T H R E A D  ---------------

Current thread (0x0000c8cccb63ed40):  JavaThread "main"             [_thread_in_native, id=1541642, stack(0x0000ffffeb8e0000,0x0000ffffebade000) (2040K)]

Stack: [0x0000ffffeb8e0000,0x0000ffffebade000],  sp=0x0000ffffebadc6c0,  free space=2033k
Native frames: (J=compiled Java code, j=interpreted, Vv=VM code, C=native code)
V  [libjvm.so+0x110d75c]  G1HeapRegion::G1HeapRegion(unsigned int, G1BlockOffsetTable*, MemRegion, G1CardSetConfiguration*)+0x158  (g1HeapRegion.cpp:254)
V  [libjvm.so+0x5a235c]  test_G1FreeRegionList_length_()+0x20c  (test_freeRegionList.cpp:75)
V  [libjvm.so+0x5a29cc]  G1FreeRegionList_length_other_vm_Test::TestBody()+0x32c  (test_freeRegionList.cpp:37)
V  [libjvm.so+0x2075298]  testing::Test::Run()+0xe4  (gtest.cc:2670)
V  [libjvm.so+0x2075424]  testing::TestInfo::Run()+0x170  (gtest.cc:2836)
V  [libjvm.so+0x2075710]  testing::TestSuite::Run()+0x2d0  (gtest.cc:3015)
V  [libjvm.so+0x2081774]  testing::internal::UnitTestImpl::RunAllTests()+0x360  (gtest.cc:5920)
V  [libjvm.so+0x207506c]  testing::UnitTest::Run()+0x7c  (gtest.cc:2670)
V  [libjvm.so+0x45c31c]  runUnitTestsInner(int, char**)+0x3fc  (gtest.h:2317)
C  [gtestLauncher+0x7c0]  main+0x1c  (gtestLauncher.cpp:40)
C  [libc.so.6+0x284c4]
C  [libc.so.6+0x28598]  __libc_start_main+0x98

@MBaesken
Copy link
Member Author

@tschatzl , maybe you have a good suggestion for an address ?
Using 0 / nullptr
MemRegion heap(nullptr, num_regions_in_test * G1HeapRegion::GrainWords);
leads to undefined behaviour because we add to address 0 (and adjusting the HS coding for this is a bit ugly and was not liked).
But the new address used by me in the current commit triggers the assert above .

@kimbarrett
Copy link

kimbarrett commented Jul 17, 2025

Taking 'some other address' than nullptr / 0 as suggested just fails (I worked yesterday with opt build where no failure was seen). But fastdebug leads to this assert , any ideas ? Or suggestions for a 'better' address (!= 0) that works ?

It needs to be at least page-aligned. I'm not finding any other alignment requirement just now, but there might
be a minimum region alignment that is more restrictive than page-aligned that I'm forgetting and haven't found.

So align_up(addr, os::vm_page_size()) may work.

The other likely alignment possibility is G1HeapRegion::GrainWord * BytesPerWord.

I still think allocating the space might be safer. So os::malloc space for one more region than the test calls for, and
align the result up to GrainWord alignment.

// does not access it.
MemRegion heap(nullptr, num_regions_in_test * G1HeapRegion::GrainWords);
int val = 1;
HeapWord* ptr = reinterpret_cast<HeapWord*>(&val);

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The initial value for val doesn't matter, since we're using its address rather than value.
And the cast could be removed by changing the type of val, leading to something like this:

HeapWord val{};
HeapWord* ptr = align_up(&val, os::vm_page_size());

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I adjusted the coding .

@MBaesken
Copy link
Member Author

Hi Kim, should I add you as contributor ?

const size_t szw = num_regions_in_test * G1HeapRegion::GrainWords;
const size_t sz = szw * BytesPerWord;
char* addr = os::reserve_memory(sz, mtTest);
MemRegion heap((HeapWord*)addr, szw);

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So far as I can tell, there's no guarantee that os::reserve_memory will return an address with any
particular alignment. Since the earlier attempt with unaligned storage failed, it may only be by accident
that this isn't failing as well. We have os::reserve_memory_aligned, or could add an extra region to
the desired size and align up the result.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

os::reserve_memory addresses are always regular-page-aligned. But os::reserve_memory_aligned may be better here since I guess the addresses would better have been region-size-aligned, so aligned to G1HeapRegion::GrainWords. That could be larger than system page size.

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Too bad the only way to find out about that alignment behavior is to dig into the sources for all ports
and read the documentation for the underlying OS function. :(


bot_storage->uncommit_regions(0, num_regions_in_test);
delete bot_storage;
os::release_memory(addr, szw);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Wrong size; release_memory takes bytes, not words. Use sz.

This explains also the crash on Windows you told me about in your mail. Was this patch also in the testing queue?

const size_t szw = num_regions_in_test * G1HeapRegion::GrainWords;
const size_t sz = szw * BytesPerWord;
const size_t lpsz = os::large_page_size();
char* addr = os::reserve_memory_aligned(sz, lpsz, mtTest);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
char* addr = os::reserve_memory_aligned(sz, lpsz, mtTest);
char* addr = os::reserve_memory_aligned(sz, G1HeapRegion::GrainBytes, mtTest);

@MBaesken you want to align the start address at region size; not sure the G1 code we call in this test cares, but it might.

Copy link

@kimbarrett kimbarrett left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks good.

const size_t szw = num_regions_in_test * G1HeapRegion::GrainWords;
const size_t sz = szw * BytesPerWord;
char* addr = os::reserve_memory(sz, mtTest);
MemRegion heap((HeapWord*)addr, szw);

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Too bad the only way to find out about that alignment behavior is to dig into the sources for all ports
and read the documentation for the underlying OS function. :(

@openjdk openjdk bot added the ready Pull request is ready to be integrated label Jul 22, 2025
@MBaesken
Copy link
Member Author

/contributor add kimbarrett

@openjdk
Copy link

openjdk bot commented Jul 23, 2025

@MBaesken kimbarrett was not found in the census.

Syntax: /contributor (add|remove) [@user | openjdk-user | Full Name <email@address>]. For example:

  • /contributor add @openjdk-bot
  • /contributor add duke
  • /contributor add J. Duke <[email protected]>

User names can only be used for users in the census associated with this repository. For other contributors you need to supply the full name and email address.

@MBaesken
Copy link
Member Author

/contributor add kbarrett

@openjdk
Copy link

openjdk bot commented Jul 23, 2025

@MBaesken
Contributor Kim Barrett <[email protected]> successfully added.

@MBaesken
Copy link
Member Author

/contributor add stuefe

@openjdk
Copy link

openjdk bot commented Jul 23, 2025

@MBaesken
Contributor Thomas Stuefe <[email protected]> successfully added.

@MBaesken
Copy link
Member Author

Thanks for the reviews !

/integrate

@openjdk
Copy link

openjdk bot commented Jul 23, 2025

Going to push as commit ceb0c0f.
Since your change was applied there have been 181 commits pushed to the master branch:

Your commit was automatically rebased without conflicts.

@openjdk openjdk bot added the integrated Pull request has been integrated label Jul 23, 2025
@openjdk openjdk bot closed this Jul 23, 2025
@openjdk openjdk bot removed ready Pull request is ready to be integrated rfr Pull request is ready for review labels Jul 23, 2025
@openjdk
Copy link

openjdk bot commented Jul 23, 2025

@MBaesken Pushed as commit ceb0c0f.

💡 You may see a message that your pull request was closed with unmerged commits. This can be safely ignored.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
hotspot-runtime [email protected] integrated Pull request has been integrated
Development

Successfully merging this pull request may close these issues.

4 participants