About auto suspendableScanner

81 views
Skip to first unread message

Gary Wu

unread,
May 23, 2016, 5:27:28 AM5/23/16
to quasar-pulsar-user
Hi,

I would like to know if there is any critical issue for auto suspendableScanner. As the doc said it is experimental, do we have any open issues for this component?
Anything I need to pay special attention if I would like to use it so that I could know where to start if I met problem.

Manual annotation is easy to have miss instrument issue. An auto instrument module will really helpful.

BR
Gary

Fabio Tudone

unread,
May 24, 2016, 8:48:00 PM5/24/16
to quasar-pulsar-user
Hi,

it looks like there aren't open suspendableScanner issues at all at present. It is still marked experimental just because we're not receiving a lot of feedback about it, possibly because most users prefer manual instrumentation with the help of verification and that may mean it's still to be considered a "young" module.
I can't think of major issues or problems, the only disadvantage is that it could end up instrumenting more than necessary (for example think of all call sites to Runnable.run being instrumented only because there's one suspendable implementation out of 20 that are not).

Fully automatic runtime instrumentation is expected to land with (and for) Java9+ as it requires StackWalker.

-- Fabio

yun qin

unread,
May 27, 2016, 4:14:43 PM5/27/16
to quasar-pulsar-user
Hi Fabio,

The issue I saw during my experiment with automatic instrumentation is that it tends to instrument more methods than necessary.
This can lead to trying to instrument special methods (constructors) and synchronized methods.
In both cases the instrumentation fails with UnableToInstrumentException, like the following:

[quasar] ERROR: Unable to instrument Foo
co.paralleluniverse.fibers.instrument.UnableToInstrumentException: Unable to instrument Foo#bar()V because of synchronized method
        at co.paralleluniverse.fibers.instrument.CheckInstrumentationVisitor.visitMethod(CheckInstrumentationVisitor.java:136)
        at co.paralleluniverse.asm.ClassReader.b(Unknown Source)
        at co.paralleluniverse.asm.ClassReader.accept(Unknown Source)
        at co.paralleluniverse.asm.ClassReader.accept(Unknown Source)
        at co.paralleluniverse.fibers.instrument.MethodDatabase.checkFileAndClose(MethodDatabase.java:388)
        at co.paralleluniverse.fibers.instrument.MethodDatabase.checkClass(MethodDatabase.java:365)
        at co.paralleluniverse.fibers.instrument.MethodDatabase.getOrLoadClassEntry(MethodDatabase.java:222)
        at co.paralleluniverse.fibers.instrument.MethodDatabase.isMethodSuspendable0(MethodDatabase.java:233)
        at co.paralleluniverse.fibers.instrument.MethodDatabase.isMethodSuspendable(MethodDatabase.java:200)
        at co.paralleluniverse.fibers.instrument.InstrumentMethod.isSuspendableCall(InstrumentMethod.java:195)
        at co.paralleluniverse.fibers.instrument.InstrumentMethod.callsSuspendables(InstrumentMethod.java:161)
        at co.paralleluniverse.fibers.instrument.InstrumentClass.visitEnd(InstrumentClass.java:261)
        at co.paralleluniverse.asm.ClassReader.accept(Unknown Source)
        at co.paralleluniverse.asm.ClassReader.accept(Unknown Source)
        at co.paralleluniverse.fibers.instrument.QuasarInstrumentor.instrumentClass(QuasarInstrumentor.java:120)
        at co.paralleluniverse.fibers.instrument.QuasarInstrumentor.instrumentClass(QuasarInstrumentor.java:88)
        at co.paralleluniverse.fibers.instrument.JavaAgent$Transformer.transform(JavaAgent.java:187)
        at sun.instrument.TransformerManager.transform(TransformerManager.java:188)
        at sun.instrument.InstrumentationImpl.transform(InstrumentationImpl.java:428)

[quasar] ERROR: Unable to instrument class Foo
co.paralleluniverse.fibers.instrument.UnableToInstrumentException: Unable to instrument Foo#<init>()V because of special method
        at co.paralleluniverse.fibers.instrument.InstrumentClass.visitEnd(InstrumentClass.java:263)
        at co.paralleluniverse.asm.ClassReader.accept(Unknown Source)
        at co.paralleluniverse.asm.ClassReader.accept(Unknown Source)
        at co.paralleluniverse.fibers.instrument.QuasarInstrumentor.instrumentClass(QuasarInstrumentor.java:120)
        at co.paralleluniverse.fibers.instrument.QuasarInstrumentor.instrumentClass(QuasarInstrumentor.java:88)
        at co.paralleluniverse.fibers.instrument.JavaAgent$Transformer.transform(JavaAgent.java:187)
        at sun.instrument.TransformerManager.transform(TransformerManager.java:188)
        at sun.instrument.InstrumentationImpl.transform(InstrumentationImpl.java:428)
        at java.lang.ClassLoader.defineClass1(Native Method)
        at java.lang.ClassLoader.defineClass(ClassLoader.java:760)
        at java.security.SecureClassLoader.defineClass(SecureClassLoader.java:142)
        at java.net.URLClassLoader.defineClass(URLClassLoader.java:467)
        at java.net.URLClassLoader.access$100(URLClassLoader.java:73)
        at java.net.URLClassLoader$1.run(URLClassLoader.java:368)
        at java.net.URLClassLoader$1.run(URLClassLoader.java:362)
        at java.security.AccessController.doPrivileged(Native Method)
        at java.net.URLClassLoader.findClass(URLClassLoader.java:361)
        at java.lang.ClassLoader.loadClass(ClassLoader.java:424)
        at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:331)
        at java.lang.ClassLoader.loadClass(ClassLoader.java:357)
        at java.lang.ClassLoader.defineClass1(Native Method)
        at java.lang.ClassLoader.defineClass(ClassLoader.java:760)
        at java.security.SecureClassLoader.defineClass(SecureClassLoader.java:142)
        at java.net.URLClassLoader.defineClass(URLClassLoader.java:467)
        at java.net.URLClassLoader.access$100(URLClassLoader.java:73)
        at java.net.URLClassLoader$1.run(URLClassLoader.java:368)
        at java.net.URLClassLoader$1.run(URLClassLoader.java:362)
        at java.security.AccessController.doPrivileged(Native Method)
        at java.net.URLClassLoader.findClass(URLClassLoader.java:361)
        at java.lang.ClassLoader.loadClass(ClassLoader.java:424)
        at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:331)
        at java.lang.ClassLoader.loadClass(ClassLoader.java:357)
        at java.lang.Class.getDeclaredMethods0(Native Method)
        at java.lang.Class.privateGetDeclaredMethods(Class.java:2701)
        at java.lang.Class.getDeclaredMethods(Class.java:1975)

My questions are:
1. Is there a way to manually "terminate" the instrumentation vistors in the aforementioned cases with auto instrumentation enabled.
2. If not, is there any best practices to workaround the instrumentation errors. Or are they benign in nature?

BTW, we are using quasar-core 0.7.5.

Many thanks!

在 2016年5月24日星期二 UTC-4下午8:48:00,Fabio Tudone写道:

Fabio Tudone

unread,
May 30, 2016, 8:01:46 AM5/30/16
to quasar-pulsar-user
Hi Gary,

2. Instrumentation errors about methods that are not really suspendable (because they have just been conservatively detected are such by some instrumentation type but they're not really suspending at runtime) are benign and you can just ignore them. Also, they're printed on stderr so they shouldn't interfer with your application logs. Anyways, as for "<init>" methods see f.e. here. As for sync methods I think this is related to this ticket.

1. The current automatic instrumentation Ant task will simply generate "suspendables" and "suspendable-supers": you could run it just once, edit the files by removing the calls that you know are not really suspendable and then move them to your "META-INF" classpath resources folder. Then you could maintain them manually (if needed) or redo the process. At present there's no support for an exclusion list but you could use the classifier system to build one very easily if that's what you need it (see f.e. here for more info).

-- Fabio
Reply all
Reply to author
Forward
0 new messages