Merge pull request #475 from dicej/static-synchronized

synchronize on Java class rather than VM class in static synchronized…
This commit is contained in:
Joshua Warner 2016-01-16 18:46:34 +00:00
commit ee7da77c70
4 changed files with 45 additions and 8 deletions

View File

@ -2146,7 +2146,7 @@ void releaseLock(MyThread* t, GcMethod* method, void* stack)
if (t->methodLockIsClean) {
object lock;
if (method->flags() & ACC_STATIC) {
lock = method->class_();
lock = getJClass(t, method->class_());
} else {
lock = *localObject(t,
stackForFrame(t, stack, method),
@ -2736,6 +2736,26 @@ void releaseMonitorForObject(MyThread* t, object o)
}
}
void acquireMonitorForClassOnEntrance(MyThread* t, GcClass* o)
{
if (LIKELY(o)) {
t->methodLockIsClean = false;
acquire(t, getJClass(t, o));
t->methodLockIsClean = true;
} else {
throwNew(t, GcNullPointerException::Type);
}
}
void releaseMonitorForClass(MyThread* t, GcClass* o)
{
if (LIKELY(o)) {
release(t, getJClass(t, o));
} else {
throwNew(t, GcNullPointerException::Type);
}
}
object makeMultidimensionalArray2(MyThread* t,
GcClass* class_,
uintptr_t* countStack,
@ -3406,13 +3426,22 @@ void handleEntrance(MyThread* t, Frame* frame)
frame->set(index, ir::Type::object());
}
handleMonitorEvent(
t, frame, getThunk(t, acquireMonitorForObjectOnEntranceThunk));
handleMonitorEvent(t,
frame,
getThunk(t,
method->flags() & ACC_STATIC
? acquireMonitorForClassOnEntranceThunk
: acquireMonitorForObjectOnEntranceThunk));
}
void handleExit(MyThread* t, Frame* frame)
{
handleMonitorEvent(t, frame, getThunk(t, releaseMonitorForObjectThunk));
handleMonitorEvent(t,
frame,
getThunk(t,
frame->context->method->flags() & ACC_STATIC
? releaseMonitorForClassThunk
: releaseMonitorForObjectThunk));
}
bool inTryBlock(MyThread* t UNUSED, GcCode* code, unsigned ip)
@ -7588,7 +7617,7 @@ uint64_t invokeNativeSlow(MyThread* t, GcMethod* method, void* function)
if (method->flags() & ACC_SYNCHRONIZED) {
if (method->flags() & ACC_STATIC) {
acquire(t, method->class_());
acquire(t, getJClass(t, method->class_()));
} else {
acquire(t, *reinterpret_cast<object*>(RUNTIME_ARRAY_BODY(args)[1]));
}
@ -7613,7 +7642,7 @@ uint64_t invokeNativeSlow(MyThread* t, GcMethod* method, void* function)
if (method->flags() & ACC_SYNCHRONIZED) {
if (method->flags() & ACC_STATIC) {
release(t, method->class_());
release(t, getJClass(t, method->class_()));
} else {
release(t, *reinterpret_cast<object*>(RUNTIME_ARRAY_BODY(args)[1]));
}

View File

@ -294,7 +294,7 @@ void pushFrame(Thread* t, GcMethod* method)
// to release a monitor we never successfully acquired when we try
// to pop the frame back off.
if (method->flags() & ACC_STATIC) {
acquire(t, method->class_());
acquire(t, getJClass(t, method->class_()));
} else {
acquire(t, peekObject(t, base));
}
@ -332,7 +332,7 @@ void popFrame(Thread* t)
if (method->flags() & ACC_SYNCHRONIZED) {
if (method->flags() & ACC_STATIC) {
release(t, method->class_());
release(t, getJClass(t, method->class_()));
} else {
release(t, peekObject(t, frameBase(t, t->frame)));
}

View File

@ -48,6 +48,8 @@ THUNK(setMaybeNull)
THUNK(acquireMonitorForObject)
THUNK(acquireMonitorForObjectOnEntrance)
THUNK(releaseMonitorForObject)
THUNK(acquireMonitorForClassOnEntrance)
THUNK(releaseMonitorForClass)
THUNK(makeMultidimensionalArray)
THUNK(makeMultidimensionalArrayFromReference)
THUNK(throw_)

View File

@ -145,6 +145,10 @@ public class Misc {
}
}
private static synchronized void testStaticNotify() {
Misc.class.notify();
}
public static void main(String[] args) throws Exception {
zam();
@ -165,6 +169,8 @@ public class Misc {
ClassLoader.getSystemClassLoader().toString();
testStaticNotify();
{ Misc m = new Misc();
m.toString();