New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
8275610: C2: Object field load floats above its null check resulting in a segfault #6701
Conversation
|
@chhagedorn The following label will be automatically applied to this pull request:
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. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I agree with bailout for now and proper fix it later.
@chhagedorn This change now passes all automated pre-integration checks. After integration, the commit message for the final commit will be:
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 279 new commits pushed to the
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.
|
Thanks Vladimir for your review! |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Looks good to me.
Thanks Roland for your review! |
/integrate |
Going to push as commit 7c6f57f.
Your commit was automatically rebased without conflicts. |
@chhagedorn Pushed as commit 7c6f57f. |
In the test case, a field load of an object floats above the object null check due to a
CastPP
that gets separated from its null checkIf
node. C2 then schedules the field load before the object null check which results in a segfault.The problem can be traced back to the elimination of identical back-to-back ifs (JDK-8143542). This is done in split-if where we detect identical back-to-back ifs in
PhaseIdealLoop::identical_backtoback_ifs()
. We then replace the boolean node of the dominatedIf
by a phi to use the split-if optimization to nicely fold away the dominatedIf
later in IGVN. This, however, does not update any data nodes that were dependent on the dominatedIf
projections.In the test case, we have the following graph right before splitting
313 If
(NC 2
) through190 Region
:313 If
is dominated by the identical (= both share308 Bool
)309 If
(NC 1
). The bool input for313 If
is replaced by a phi and the split-if optimization is applied. However, the data nodes dependent on the out projections of the dominated313 If
(261 CastPP
in this case) are not processed separately and just end up at the newly inserted regions in split-if. In the test case, we get the following graph where261 CastPP
ends up at the new334 Region
:Loopopts are applied and can remove the
325 CountedLoop
and we find that the171 RangeCheck
(RC 2
) is applied on a constant array index 1.Now at IGVN, the order in which the nodes are processed is important in order to trigger the segfault:
334 Region
with332 If
and333 If
are removed because of the special split-if setup we used to remove the identical313 If
. The control input of261 CastPP
is therefore updated to172 IfTrue
.RangeCheck::Ideal()
for171 RangeCheck
finds that305 RangeCheck
(RC 1
) already covers it and we remove171 RangeCheck
. In this process, we rewire261 CastPP
to the dominating305 RangeCheck
and we have the following graph:261 CastPP
- and also the field263 LoadI
- have now306 IfFalse
as early control. GCM is then scheduling263 LoadI
before the null check309 If
and we get a segfault.An easy fix is not straight forward. What we actually would want to do is rewiring
261 CastPP
from334 Region
to311 IfTrue
in the second graph after split-if to not separate it from the null check. But that's not possible because we would create a bad graph: The early control311 IfTrue
of261 CastPP
does not dominate its late control further down after334 Region
because of the not yet removed334 Region
. We would need to already clean the regions up and then do the rewiring. But then the question arises why to use the split-if optimization in the first place when we do not want to rely on IGVN to clean it up.I therefore suggest to go with an easy bailout fix for JDK 18 where we do not apply this identical back-to-back if removal optimization if there are data dependencies and rework this in an RFE for JDK 19. Roland already has some ideas how to do that.
I ran some standard benchmarks and did not see any performance regressions with this fix.
Thanks,
Christian
Progress
Issue
Reviewers
Reviewing
Using
git
Checkout this PR locally:
$ git fetch https://git.openjdk.java.net/jdk pull/6701/head:pull/6701
$ git checkout pull/6701
Update a local copy of the PR:
$ git checkout pull/6701
$ git pull https://git.openjdk.java.net/jdk pull/6701/head
Using Skara CLI tools
Checkout this PR locally:
$ git pr checkout 6701
View PR using the GUI difftool:
$ git pr show -t 6701
Using diff file
Download this PR as a diff file:
https://git.openjdk.java.net/jdk/pull/6701.diff