Skip to content
Browse files

code rearrangment to improve state of Android libcore tests

This mainly moves several sun.misc.Unsafe method implementations from
classpath-openjdk.cpp to builtin.cpp so that the Avian and Android
builds can use them.

It also replaces FinalizerReference.finalizeAllEnqueued with a no-op,
since the real implementations assumes too much about how the VM
handles (or delegates) finalization.
  • Loading branch information...
1 parent dfdd1f6 commit 4e12847858b7ddaaecdfd5e1ef2696b44a5d735e @dicej dicej committed
View
35 classpath/avian/Classes.java
@@ -406,6 +406,41 @@ public static int findMethod(VMClass vmClass, String name,
return -1;
}
+ public static int countMethods(VMClass vmClass, boolean publicOnly) {
+ int count = 0;
+ if (vmClass.methodTable != null) {
+ for (int i = 0; i < vmClass.methodTable.length; ++i) {
+ if (((! publicOnly)
+ || ((vmClass.methodTable[i].flags & Modifier.PUBLIC))
+ != 0)
+ && (! toString(vmClass.methodTable[i].name).startsWith("<")))
+ {
+ ++ count;
+ }
+ }
+ }
+ return count;
+ }
+
+ public static Method[] getMethods(VMClass vmClass, boolean publicOnly) {
+ Method[] array = new Method[countMethods(vmClass, publicOnly)];
+ if (vmClass.methodTable != null) {
+ Classes.link(vmClass);
+
+ int ai = 0;
+ for (int i = 0; i < vmClass.methodTable.length; ++i) {
+ if ((((vmClass.methodTable[i].flags & Modifier.PUBLIC) != 0)
+ || (! publicOnly))
+ && ! toString(vmClass.methodTable[i].name).startsWith("<"))
+ {
+ array[ai++] = makeMethod(SystemClassLoader.getClass(vmClass), i);
+ }
+ }
+ }
+
+ return array;
+ }
+
public static Annotation getAnnotation(ClassLoader loader, Object[] a) {
if (a[0] == null) {
a[0] = Proxy.newProxyInstance
View
48 classpath/java/lang/Class.java
@@ -366,54 +366,12 @@ private static void getAllFields(VMClass vmClass, ArrayList<Field> fields) {
return fields.toArray(new Field[fields.size()]);
}
- private int countMethods(boolean publicOnly) {
- int count = 0;
- if (vmClass.methodTable != null) {
- for (int i = 0; i < vmClass.methodTable.length; ++i) {
- if (((! publicOnly)
- || ((vmClass.methodTable[i].flags & Modifier.PUBLIC))
- != 0)
- && (! Method.getName(vmClass.methodTable[i]).startsWith("<")))
- {
- ++ count;
- }
- }
- }
- return count;
- }
-
public Method[] getDeclaredMethods() {
- Method[] array = new Method[countMethods(false)];
- if (vmClass.methodTable != null) {
- Classes.link(vmClass);
-
- int ai = 0;
- for (int i = 0; i < vmClass.methodTable.length; ++i) {
- if (! Method.getName(vmClass.methodTable[i]).startsWith("<")) {
- array[ai++] = new Method(vmClass.methodTable[i]);
- }
- }
- }
-
- return array;
+ return Classes.getMethods(vmClass, false);
}
public Method[] getMethods() {
- Method[] array = new Method[countMethods(true)];
- if (vmClass.methodTable != null) {
- Classes.link(vmClass);
-
- int index = 0;
- for (int i = 0; i < vmClass.methodTable.length; ++i) {
- if (((vmClass.methodTable[i].flags & Modifier.PUBLIC) != 0)
- && (! Method.getName(vmClass.methodTable[i]).startsWith("<")))
- {
- array[index++] = new Method(vmClass.methodTable[i]);
- }
- }
- }
-
- return array;
+ return Classes.getMethods(vmClass, true);
}
public Class[] getInterfaces() {
@@ -591,7 +549,7 @@ private int countAnnotations() {
}
public Annotation[] getAnnotations() {
- Annotation[] array = new Annotation[countMethods(true)];
+ Annotation[] array = new Annotation[countAnnotations()];
int i = 0;
for (VMClass c = vmClass; c != null; c = c.super_) {
if (c.addendum != null && c.addendum.annotationTable != null) {
View
15 classpath/sun/misc/Unsafe.java
@@ -46,6 +46,14 @@ public static Unsafe getUnsafe() {
public native void putDouble(long address, double x);
+ public native void putIntVolatile(Object o, long offset, int x);
+
+ public native void putOrderedInt(Object o, long offset, int x);
+
+ public native Object getObject(Object o, long offset);
+
+ public native void putObject(Object o, long offset, Object x);
+
public native long getAddress(long address);
public native void putAddress(long address, long x);
@@ -54,6 +62,10 @@ public static Unsafe getUnsafe() {
public native long objectFieldOffset(Field field);
+ public native void park(boolean absolute, long time);
+
+ public native void unpark(Object target);
+
public native void copyMemory(Object srcBase, long srcOffset,
Object destBase, long destOffset,
long count);
@@ -61,6 +73,9 @@ public native void copyMemory(Object srcBase, long srcOffset,
public native boolean compareAndSwapInt(Object o, long offset, int old,
int new_);
+ public native boolean compareAndSwapObject(Object o, long offset, Object old,
+ Object new_);
+
public void copyMemory(long src, long dst, long count) {
copyMemory(null, src, null, dst, count);
}
View
12 src/avian/machine.h
@@ -3942,6 +3942,18 @@ lineNumberLine(uint64_t ln)
return ln & 0xFFFFFFFF;
}
+object
+interruptLock(Thread* t, object thread);
+
+void
+clearInterrupted(Thread* t);
+
+void
+threadInterrupt(Thread* t, object thread);
+
+bool
+threadIsInterrupted(Thread* t, object thread, bool clear);
+
inline FILE*
errorLog(Thread* t)
{
View
111 src/builtin.cpp
@@ -605,6 +605,46 @@ Avian_java_nio_FixedArrayByteBuffer_allocateFixed
}
extern "C" JNIEXPORT int64_t JNICALL
+Avian_sun_misc_Unsafe_getObject
+(Thread*, object, uintptr_t* arguments)
+{
+ object o = reinterpret_cast<object>(arguments[1]);
+ int64_t offset; memcpy(&offset, arguments + 2, 8);
+
+ return fieldAtOffset<uintptr_t>(o, offset);
+}
+
+extern "C" JNIEXPORT void JNICALL
+Avian_sun_misc_Unsafe_putObject
+(Thread* t, object, uintptr_t* arguments)
+{
+ object o = reinterpret_cast<object>(arguments[1]);
+ int64_t offset; memcpy(&offset, arguments + 2, 8);
+ uintptr_t value = arguments[4];
+
+ set(t, o, offset, reinterpret_cast<object>(value));
+}
+
+extern "C" JNIEXPORT int64_t JNICALL
+Avian_sun_misc_Unsafe_compareAndSwapObject
+(Thread* t, object, uintptr_t* arguments)
+{
+ object target = reinterpret_cast<object>(arguments[1]);
+ int64_t offset; memcpy(&offset, arguments + 2, 8);
+ uintptr_t expect = arguments[4];
+ uintptr_t update = arguments[5];
+
+ bool success = atomicCompareAndSwap
+ (&fieldAtOffset<uintptr_t>(target, offset), expect, update);
+
+ if (success) {
+ mark(t, target, offset);
+ }
+
+ return success;
+}
+
+extern "C" JNIEXPORT int64_t JNICALL
Avian_sun_misc_Unsafe_compareAndSwapInt
(Thread*, object, uintptr_t* arguments)
{
@@ -617,6 +657,77 @@ Avian_sun_misc_Unsafe_compareAndSwapInt
(&fieldAtOffset<uint32_t>(target, offset), expect, update);
}
+extern "C" JNIEXPORT void JNICALL
+Avian_sun_misc_Unsafe_unpark
+(Thread* t, object, uintptr_t* arguments)
+{
+ object thread = reinterpret_cast<object>(arguments[1]);
+
+ monitorAcquire(t, interruptLock(t, thread));
+ threadUnparked(t, thread) = true;
+ monitorNotify(t, interruptLock(t, thread));
+ monitorRelease(t, interruptLock(t, thread));
+}
+
+extern "C" JNIEXPORT void JNICALL
+Avian_sun_misc_Unsafe_park
+(Thread* t, object, uintptr_t* arguments)
+{
+ bool absolute = arguments[1];
+ int64_t time; memcpy(&time, arguments + 2, 8);
+
+ int64_t then = t->m->system->now();
+
+ if (absolute) {
+ time -= then;
+ if (time <= 0) {
+ return;
+ }
+ } else if (time) {
+ // if not absolute, interpret time as nanoseconds, but make sure
+ // it doesn't become zero when we convert to milliseconds, since
+ // zero is interpreted as infinity below
+ time = (time / (1000 * 1000)) + 1;
+ }
+
+ monitorAcquire(t, interruptLock(t, t->javaThread));
+ while (time >= 0
+ and (not (threadUnparked(t, t->javaThread)
+ or monitorWait
+ (t, interruptLock(t, t->javaThread), time))))
+ {
+ int64_t now = t->m->system->now();
+ time -= now - then;
+ then = now;
+
+ if (time == 0) {
+ break;
+ }
+ }
+ threadUnparked(t, t->javaThread) = false;
+ monitorRelease(t, interruptLock(t, t->javaThread));
+}
+
+extern "C" JNIEXPORT void JNICALL
+Avian_sun_misc_Unsafe_putIntVolatile
+(Thread*, object, uintptr_t* arguments)
+{
+ object o = reinterpret_cast<object>(arguments[1]);
+ int64_t offset; memcpy(&offset, arguments + 2, 8);
+ int32_t value = arguments[4];
+
+ storeStoreMemoryBarrier();
+ fieldAtOffset<int32_t>(o, offset) = value;
+ storeLoadMemoryBarrier();
+}
+
+extern "C" JNIEXPORT void JNICALL
+Avian_sun_misc_Unsafe_putOrderedInt
+(Thread* t, object method, uintptr_t* arguments)
+{
+ Avian_sun_misc_Unsafe_putIntVolatile(t, method, arguments);
+}
+
extern "C" JNIEXPORT int64_t JNICALL
Avian_avian_Classes_primitiveClass
(Thread* t, object, uintptr_t* arguments)
View
42 src/classpath-android.cpp
@@ -48,6 +48,12 @@ loadLibrary(Thread* t, object, uintptr_t* arguments)
loadLibrary(t, "", RUNTIME_ARRAY_BODY(n), true, true);
}
+void JNICALL
+finalizeAllEnqueued(Thread*, object, uintptr_t*)
+{
+ // ignore
+}
+
int64_t JNICALL
appLoader(Thread* t, object, uintptr_t*)
{
@@ -150,6 +156,11 @@ initVmThread(Thread* t, object thread)
set(t, thread, fieldOffset(t, field), instance);
}
+
+ if (threadGroup(t, thread) == 0) {
+ set(t, thread, ThreadGroup, threadGroup(t, t->javaThread));
+ expect(t, threadGroup(t, thread));
+ }
}
object
@@ -353,6 +364,18 @@ class MyClasspath : public Classpath {
}
{ object c = resolveClass
+ (t, root(t, Machine::BootLoader), "java/lang/ref/FinalizerReference",
+ false);
+
+ if (c) {
+ PROTECT(t, c);
+
+ intercept(t, c, "finalizeAllEnqueued", "()V",
+ voidPointer(finalizeAllEnqueued), updateRuntimeData);
+ }
+ }
+
+ { object c = resolveClass
(t, root(t, Machine::BootLoader), "java/lang/ClassLoader", false);
if (c) {
@@ -1071,7 +1094,7 @@ Avian_java_lang_VMThread_getStatus
(Thread*, object, uintptr_t*)
{
// todo
- return -1;
+ return 1;
}
extern "C" JNIEXPORT int64_t JNICALL
@@ -1382,6 +1405,23 @@ Avian_java_lang_Class_isInstance
}
extern "C" JNIEXPORT int64_t JNICALL
+Avian_java_lang_Class_getDeclaredMethods
+(Thread* t, object, uintptr_t* arguments)
+{
+ object c = reinterpret_cast<object>(arguments[0]);
+ PROTECT(t, c);
+
+ bool publicOnly = arguments[1];
+
+ object get = resolveMethod
+ (t, root(t, Machine::BootLoader), "avian/Classes", "getMethods",
+ "(Lavian/VMClass;Z)[Ljava/lang/reflect/Method;");
+
+ return reinterpret_cast<uintptr_t>
+ (t->m->processor->invoke(t, get, 0, jclassVmClass(t, c), publicOnly));
+}
+
+extern "C" JNIEXPORT int64_t JNICALL
Avian_java_lang_reflect_Method_invokeNative
(Thread* t, object, uintptr_t* arguments)
{
View
5 src/classpath-avian.cpp
@@ -661,7 +661,7 @@ Avian_java_lang_Thread_interrupt
{
int64_t peer; memcpy(&peer, arguments, 8);
- interrupt(t, reinterpret_cast<Thread*>(peer));
+ threadInterrupt(t, reinterpret_cast<Thread*>(peer)->javaThread);
}
extern "C" JNIEXPORT int64_t JNICALL
@@ -670,7 +670,8 @@ Avian_java_lang_Thread_interrupted
{
int64_t peer; memcpy(&peer, arguments, 8);
- return getAndClearInterrupted(t, reinterpret_cast<Thread*>(peer));
+ return threadIsInterrupted
+ (t, reinterpret_cast<Thread*>(peer)->javaThread, true);
}
extern "C" JNIEXPORT int64_t JNICALL
View
142 src/classpath-openjdk.cpp
@@ -2461,38 +2461,6 @@ setProperty(Thread* t, object method, object properties,
t->m->processor->invoke(t, method, properties, n, v);
}
-object
-interruptLock(Thread* t, object thread)
-{
- object lock = threadInterruptLock(t, thread);
-
- loadMemoryBarrier();
-
- if (lock == 0) {
- PROTECT(t, thread);
- ACQUIRE(t, t->m->referenceLock);
-
- if (threadInterruptLock(t, thread) == 0) {
- object head = makeMonitorNode(t, 0, 0);
- object lock = makeMonitor(t, 0, 0, 0, head, head, 0);
-
- storeStoreMemoryBarrier();
-
- set(t, thread, ThreadInterruptLock, lock);
- }
- }
-
- return threadInterruptLock(t, thread);
-}
-
-void
-clearInterrupted(Thread* t)
-{
- monitorAcquire(t, local::interruptLock(t, t->javaThread));
- threadInterrupted(t, t->javaThread) = false;
- monitorRelease(t, local::interruptLock(t, t->javaThread));
-}
-
bool
pipeAvailable(int fd, int* available)
{
@@ -2725,27 +2693,6 @@ Avian_sun_misc_Unsafe_objectFieldOffset
}
extern "C" JNIEXPORT int64_t JNICALL
-Avian_sun_misc_Unsafe_getObject
-(Thread*, object, uintptr_t* arguments)
-{
- object o = reinterpret_cast<object>(arguments[1]);
- int64_t offset; memcpy(&offset, arguments + 2, 8);
-
- return fieldAtOffset<uintptr_t>(o, offset);
-}
-
-extern "C" JNIEXPORT void JNICALL
-Avian_sun_misc_Unsafe_putObject
-(Thread* t, object, uintptr_t* arguments)
-{
- object o = reinterpret_cast<object>(arguments[1]);
- int64_t offset; memcpy(&offset, arguments + 2, 8);
- uintptr_t value = arguments[4];
-
- set(t, o, offset, reinterpret_cast<object>(value));
-}
-
-extern "C" JNIEXPORT int64_t JNICALL
Avian_sun_misc_Unsafe_getShort__Ljava_lang_Object_2J
(Thread*, object, uintptr_t* arguments)
{
@@ -2960,25 +2907,6 @@ Avian_sun_misc_Unsafe_putOrderedObject
}
extern "C" JNIEXPORT int64_t JNICALL
-Avian_sun_misc_Unsafe_compareAndSwapObject
-(Thread* t, object, uintptr_t* arguments)
-{
- object target = reinterpret_cast<object>(arguments[1]);
- int64_t offset; memcpy(&offset, arguments + 2, 8);
- uintptr_t expect = arguments[4];
- uintptr_t update = arguments[5];
-
- bool success = atomicCompareAndSwap
- (&fieldAtOffset<uintptr_t>(target, offset), expect, update);
-
- if (success) {
- mark(t, target, offset);
- }
-
- return success;
-}
-
-extern "C" JNIEXPORT int64_t JNICALL
Avian_sun_misc_Unsafe_compareAndSwapLong
(Thread* t UNUSED, object, uintptr_t* arguments)
{
@@ -3016,57 +2944,6 @@ Avian_sun_misc_Unsafe_ensureClassInitialized
}
extern "C" JNIEXPORT void JNICALL
-Avian_sun_misc_Unsafe_unpark
-(Thread* t, object, uintptr_t* arguments)
-{
- object thread = reinterpret_cast<object>(arguments[1]);
-
- monitorAcquire(t, local::interruptLock(t, thread));
- threadUnparked(t, thread) = true;
- monitorNotify(t, local::interruptLock(t, thread));
- monitorRelease(t, local::interruptLock(t, thread));
-}
-
-extern "C" JNIEXPORT void JNICALL
-Avian_sun_misc_Unsafe_park
-(Thread* t, object, uintptr_t* arguments)
-{
- bool absolute = arguments[1];
- int64_t time; memcpy(&time, arguments + 2, 8);
-
- int64_t then = t->m->system->now();
-
- if (absolute) {
- time -= then;
- if (time <= 0) {
- return;
- }
- } else if (time) {
- // if not absolute, interpret time as nanoseconds, but make sure
- // it doesn't become zero when we convert to milliseconds, since
- // zero is interpreted as infinity below
- time = (time / (1000 * 1000)) + 1;
- }
-
- monitorAcquire(t, local::interruptLock(t, t->javaThread));
- while (time >= 0
- and (not (threadUnparked(t, t->javaThread)
- or monitorWait
- (t, local::interruptLock(t, t->javaThread), time))))
- {
- int64_t now = t->m->system->now();
- time -= now - then;
- then = now;
-
- if (time == 0) {
- break;
- }
- }
- threadUnparked(t, t->javaThread) = false;
- monitorRelease(t, local::interruptLock(t, t->javaThread));
-}
-
-extern "C" JNIEXPORT void JNICALL
Avian_sun_misc_Unsafe_monitorEnter
(Thread* t, object, uintptr_t* arguments)
{
@@ -3635,15 +3512,7 @@ EXPORT(JVM_CountStackFrames)(Thread*, jobject) { abort(); }
uint64_t
jvmInterrupt(Thread* t, uintptr_t* arguments)
{
- jobject thread = reinterpret_cast<jobject>(arguments[0]);
-
- monitorAcquire(t, local::interruptLock(t, *thread));
- Thread* p = reinterpret_cast<Thread*>(threadPeer(t, *thread));
- if (p) {
- interrupt(t, p);
- }
- threadInterrupted(t, *thread) = true;
- monitorRelease(t, local::interruptLock(t, *thread));
+ threadInterrupt(t, *reinterpret_cast<jobject>(arguments[0]));
return 1;
}
@@ -3662,14 +3531,7 @@ jvmIsInterrupted(Thread* t, uintptr_t* arguments)
jobject thread = reinterpret_cast<jobject>(arguments[0]);
jboolean clear = arguments[1];
- monitorAcquire(t, local::interruptLock(t, *thread));
- bool v = threadInterrupted(t, *thread);
- if (clear) {
- threadInterrupted(t, *thread) = false;
- }
- monitorRelease(t, local::interruptLock(t, *thread));
-
- return v;
+ return threadIsInterrupted(t, *thread, clear);
}
extern "C" JNIEXPORT jboolean JNICALL
View
61 src/machine.cpp
@@ -5186,6 +5186,67 @@ populateMultiArray(Thread* t, object array, int32_t* counts,
}
}
+object
+interruptLock(Thread* t, object thread)
+{
+ object lock = threadInterruptLock(t, thread);
+
+ loadMemoryBarrier();
+
+ if (lock == 0) {
+ PROTECT(t, thread);
+ ACQUIRE(t, t->m->referenceLock);
+
+ if (threadInterruptLock(t, thread) == 0) {
+ object head = makeMonitorNode(t, 0, 0);
+ object lock = makeMonitor(t, 0, 0, 0, head, head, 0);
+
+ storeStoreMemoryBarrier();
+
+ set(t, thread, ThreadInterruptLock, lock);
+ }
+ }
+
+ return threadInterruptLock(t, thread);
+}
+
+void
+clearInterrupted(Thread* t)
+{
+ monitorAcquire(t, interruptLock(t, t->javaThread));
+ threadInterrupted(t, t->javaThread) = false;
+ monitorRelease(t, interruptLock(t, t->javaThread));
+}
+
+void
+threadInterrupt(Thread* t, object thread)
+{
+ PROTECT(t, thread);
+
+ monitorAcquire(t, interruptLock(t, thread));
+ Thread* p = reinterpret_cast<Thread*>(threadPeer(t, thread));
+ if (p) {
+ interrupt(t, p);
+ }
+ threadInterrupted(t, thread) = true;
+ monitorRelease(t, interruptLock(t, thread));
+}
+
+bool
+threadIsInterrupted(Thread* t, object thread, bool clear)
+{
+ PROTECT(t, thread);
+
+ monitorAcquire(t, interruptLock(t, thread));
+ bool v = threadInterrupted(t, thread);
+ if (clear) {
+ threadInterrupted(t, thread) = false;
+ }
+ monitorRelease(t, interruptLock(t, thread));
+
+ return v;
+}
+
void
noop()
{ }

0 comments on commit 4e12847

Please sign in to comment.
Something went wrong with that request. Please try again.