-
-
Notifications
You must be signed in to change notification settings - Fork 808
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
Java 9 compatibility #295
Comments
After some small debug, seems that oracle blocked attach for this same VM by default.... and there need to be special flag to allow this. // class HotSpotVirtualMachine private static final boolean ALLOW_ATTACH_SELF;
// some code
static {
String s = VM.getSavedProperty("jdk.attach.allowAttachSelf");
ALLOW_ATTACH_SELF = (s != null) && !"false".equals(s);
}
// some code
// inside constructor
if (!ALLOW_ATTACH_SELF && (pid == 0 || pid == CURRENT_PID)) {
throw new IOException("Can not attach to current VM");
} With dirty hack this can be resolved using unsafe hack to access this saved properties object in static
{
Constructor<Unsafe> unsafeConstructor = Unsafe.class.getDeclaredConstructor();
unsafeConstructor.setAccessible(true);
unsafe = unsafeConstructor.newInstance();
constructorModifiers = Constructor.class.getDeclaredField("modifiers");
constructorModifiersOffset = unsafe.objectFieldOffset(constructorModifiers);
methodModifiers = Method.class.getDeclaredField("modifiers");
methodModifiersOffset = unsafe.objectFieldOffset(methodModifiers);
fieldModifiers = Field.class.getDeclaredField("modifiers");
fieldModifiersOffset = unsafe.objectFieldOffset(fieldModifiers);
setAccessible = AccessibleObject.class.getDeclaredMethod("setAccessible0", boolean.class);
setForceAccessible(setAccessible);
}
private static boolean setForceAccessible(AccessibleObject accessibleObject)
{
try
{
if (accessibleObject instanceof Constructor)
{
Constructor<?> object = (Constructor<?>) accessibleObject;
unsafe.getAndSetInt(object, constructorModifiersOffset, addPublicModifier(object.getModifiers()));
return true;
}
if (accessibleObject instanceof Method)
{
Method object = (Method) accessibleObject;
unsafe.getAndSetInt(object, methodModifiersOffset, addPublicModifier(object.getModifiers()));
return true;
}
if (accessibleObject instanceof Field)
{
Field object = (Field) accessibleObject;
unsafe.getAndSetInt(object, fieldModifiersOffset, addPublicModifier(object.getModifiers()));
return true;
}
return false;
}
catch (Exception e)
{
e.printStackTrace();
return false;
}
}
private static int addPublicModifier(int mod)
{
mod &= ~ (Modifier.PRIVATE);
mod &= ~ (Modifier.PROTECTED);
mod |= (Modifier.PUBLIC);
return mod;
} and setAccessible can be used to get access to any other place without access checks. But this is very dirty hack... so probably people will just need to use that flag. |
Hi, thanks for reporting this. Adding this flag was discussed on the mailing list but was discarded as a bad idea for Java 9 to be set to true by default. I expect this flag to not be set in future releases. Then again, this hack is not too bad to offer as an attempt to make the installation process work out of the box. For many users, this might just work at least for test environments where this is intended. I do however consider to just start a new VM process to attach the agent from there. Its a bit of a dirty hack but the whole self-attachment is a bit tricky to begin with, despite its usefulness. |
@raphw You might try to use other VM to attach agent and remove that check in |
I will check the source to see if there is a way around, therefore I but I think that I will go for the "secondary VM hack" without relying on Unsafe to ease the migration for test frameworks that rely on this feature. Long term, people will probably need to set the flag but there needs to be a short-time solution that is less disruptive. |
|
Seems that between build 153 and 166 of jdk 9 (jigsaw) something changed as byte-buddy (version
1.6.13
) fails to inject:(also package of Module class was changed, not sure if this is already updated, from
java.lang.reflect.Module
tojava.lang.Module
)The text was updated successfully, but these errors were encountered: