7190310: Inlining WeakReference.get(), and hoisting $referent may lead to non-terminating loops

In C2 add software membar after load from Reference.referent field to prevent commoning of loads across safepoint since GC can change its value. In C1 always generate Reference.get() intrinsic.

Reviewed-by: roland, twisti, dholmes, johnc
This commit is contained in:
Vladimir Kozlov 2012-08-20 09:58:58 -07:00
parent e3c3c8527e
commit 04c6a7ce10
9 changed files with 333 additions and 300 deletions

View file

@ -3058,7 +3058,7 @@ GraphBuilder::GraphBuilder(Compilation* compilation, IRScope* scope)
case vmIntrinsics::_Reference_get:
{
if (UseG1GC) {
{
// With java.lang.ref.reference.get() we must go through the
// intrinsic - when G1 is enabled - even when get() is the root
// method of the compile so that, if necessary, the value in
@ -3070,6 +3070,9 @@ GraphBuilder::GraphBuilder(Compilation* compilation, IRScope* scope)
// object removed from the list of discovered references during
// reference processing.
// Also we need intrinsic to prevent commoning reads from this field
// across safepoint since GC can change its value.
// Set up a stream so that appending instructions works properly.
ciBytecodeStream s(scope->method());
s.reset_to_bci(0);
@ -3226,7 +3229,6 @@ const char* GraphBuilder::should_not_inline(ciMethod* callee) const {
bool GraphBuilder::try_inline_intrinsics(ciMethod* callee) {
if (!InlineNatives ) INLINE_BAILOUT("intrinsic method inlining disabled");
if (callee->is_synchronized()) {
// We don't currently support any synchronized intrinsics
return false;
@ -3234,9 +3236,13 @@ bool GraphBuilder::try_inline_intrinsics(ciMethod* callee) {
// callee seems like a good candidate
// determine id
vmIntrinsics::ID id = callee->intrinsic_id();
if (!InlineNatives && id != vmIntrinsics::_Reference_get) {
// InlineNatives does not control Reference.get
INLINE_BAILOUT("intrinsic method inlining disabled");
}
bool preserves_state = false;
bool cantrap = true;
vmIntrinsics::ID id = callee->intrinsic_id();
switch (id) {
case vmIntrinsics::_arraycopy:
if (!InlineArrayCopy) return false;
@ -3376,11 +3382,10 @@ bool GraphBuilder::try_inline_intrinsics(ciMethod* callee) {
return true;
case vmIntrinsics::_Reference_get:
// It is only when G1 is enabled that we absolutely
// need to use the intrinsic version of Reference.get()
// so that the value in the referent field, if necessary,
// can be registered by the pre-barrier code.
if (!UseG1GC) return false;
// Use the intrinsic version of Reference.get() so that the value in
// the referent field can be registered by the G1 pre-barrier code.
// Also to prevent commoning reads from this field across safepoint
// since GC can change its value.
preserves_state = true;
break;