You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@openwebbeans.apache.org by rm...@apache.org on 2019/12/12 06:44:08 UTC
[openwebbeans] branch master updated: OWB-1306 better support of
java versions for our unsafe usage
This is an automated email from the ASF dual-hosted git repository.
rmannibucau pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/openwebbeans.git
The following commit(s) were added to refs/heads/master by this push:
new 26aaec0 OWB-1306 better support of java versions for our unsafe usage
26aaec0 is described below
commit 26aaec0274c994336f9bca30b4609065ec323864
Author: Romain Manni-Bucau <rm...@apache.org>
AuthorDate: Thu Dec 12 07:43:52 2019 +0100
OWB-1306 better support of java versions for our unsafe usage
---
.../java/org/apache/webbeans/proxy/Unsafe.java | 53 ++++++++++++++++++++--
1 file changed, 48 insertions(+), 5 deletions(-)
diff --git a/webbeans-impl/src/main/java/org/apache/webbeans/proxy/Unsafe.java b/webbeans-impl/src/main/java/org/apache/webbeans/proxy/Unsafe.java
index 09f9fce..8df2a12 100644
--- a/webbeans-impl/src/main/java/org/apache/webbeans/proxy/Unsafe.java
+++ b/webbeans-impl/src/main/java/org/apache/webbeans/proxy/Unsafe.java
@@ -18,6 +18,7 @@
*/
package org.apache.webbeans.proxy;
+import java.lang.reflect.AccessibleObject;
import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
@@ -37,6 +38,7 @@ public class Unsafe
* initializing the class.
*/
private Object unsafe;
+ private Object internalUnsafe;
private Method unsafeAllocateInstance;
private final AtomicReference<Method> unsafeDefineClass = new AtomicReference<>();
@@ -58,13 +60,25 @@ public class Unsafe
return null;
}
});
+ this.internalUnsafe = AccessController.doPrivileged((PrivilegedAction<Object>) () -> {
+ try // j11, unwrap unsafe, it owns defineClass now and no more theUnsafe
+ {
+ final Field theInternalUnsafe = unsafeClass.getDeclaredField("theInternalUnsafe");
+ theInternalUnsafe.setAccessible(true);
+ return theInternalUnsafe.get(null).getClass();
+ }
+ catch (final Exception notJ11OrMore)
+ {
+ return unsafe;
+ }
+ });
if (unsafe != null)
{
unsafeAllocateInstance = AccessController.doPrivileged((PrivilegedAction<Method>) () -> {
try
{
- Method mtd = unsafeClass.getDeclaredMethod("allocateInstance", Class.class);
+ Method mtd = unsafe.getClass().getDeclaredMethod("allocateInstance", Class.class);
mtd.setAccessible(true);
return mtd;
}
@@ -73,6 +87,37 @@ public class Unsafe
return null; // use newInstance()
}
});
+
+ try
+ {
+ final Class<?> rootLoaderClass = Class.forName("java.lang.ClassLoader");
+ rootLoaderClass.getDeclaredMethod(
+ "defineClass", new Class[] { String.class, byte[].class, int.class, int.class })
+ .setAccessible(true);
+ rootLoaderClass.getDeclaredMethod(
+ "defineClass", new Class[] {
+ String.class, byte[].class, int.class, int.class, ProtectionDomain.class })
+ .setAccessible(true);
+ }
+ catch (final Exception e)
+ {
+ try // some j>8, since we have unsafe let's use it
+ {
+ final Class<?> rootLoaderClass = Class.forName("java.lang.ClassLoader");
+ final sun.misc.Unsafe un = sun.misc.Unsafe.class.cast(unsafe);
+ final long accOffset = un.objectFieldOffset(AccessibleObject.class.getDeclaredField("override"));
+
+ un.putBoolean(rootLoaderClass.getDeclaredMethod("defineClass",
+ new Class[]{String.class, byte[].class, int.class, int.class}), accOffset, true);
+ un.putBoolean(rootLoaderClass.getDeclaredMethod("defineClass",
+ new Class[]{String.class, byte[].class, int.class, int.class, ProtectionDomain.class}),
+ accOffset, true);
+ }
+ catch (final Exception ex)
+ {
+ // no-op
+ }
+ }
}
}
@@ -156,7 +201,7 @@ public class Unsafe
{
synchronized (this)
{
- final Class<?> unsafeClass = getUnsafeClass();
+ final Class<?> unsafeClass = internalUnsafe.getClass();
value = AccessController.doPrivileged((PrivilegedAction<Method>) () -> {
try
{
@@ -208,10 +253,9 @@ public class Unsafe
private Class<?> getUnsafeClass()
{
- Class<?> unsafeClass;
try
{
- unsafeClass = AccessController.doPrivileged((PrivilegedAction<Class<?>>) () -> {
+ return AccessController.doPrivileged((PrivilegedAction<Class<?>>) () -> {
try
{
return Thread.currentThread().getContextClassLoader().loadClass("sun.misc.Unsafe");
@@ -233,6 +277,5 @@ public class Unsafe
{
throw new IllegalStateException("Cannot get sun.misc.Unsafe class", e);
}
- return unsafeClass;
}
}