Trying to work newer indy into JRuby

John Rose John.Rose at Sun.COM
Mon May 18 12:01:35 PDT 2009


On May 18, 2009, at 5:33 AM, Charles Oliver Nutter wrote:

> Ok! I have managed to dispatch single-arg method calls using the new
> invokedynamic!

That's a good night's work!  I'm sorry--well, not--that I slept  
through it.

> The logic is fairly primitive right now: http://gist.github.com/113440

I like that file; it reads well.

The first two lines of GuardedRubyMethodHandle.invoke are your fast  
path; that's where we need to get the maximum amount of inlining.  The  
JVM interpreter gets to those lines very quickly (without intervening  
bytecodes) when it executes an invokedynamic instruction.  Christian  
Thalinger and I are working on making this true also in the compiled  
code.

The call to entry.typeOk looks like it might be megamorphic; if so  
that's a potential performance problem. There might be a way to  
refactor this with method handles to avoid the megamorphism; that's  
what guardWithTest is supposed to do.  We'll get a better idea of what  
to work on when we look at the disassemblies of compiled code, but  
we'll need another round of compiler support to get this far.

The expression entry.method.call might also have a megamorphism (your  
nemesis, of course).  I think it wants to be entry.mh.invoke, or even  
((MethodHandle)entry).invoke, where entry is a JMH.

Minor nits: I suggest making bootstrap in registerBootstrap be a  
private static final like DEFAULT.  And you might consider naming  
those statics after their methods (modulo Java naming conventions):   
BOOTSTRAP, INVOKE.

> Rather than try to introduce method handles throughout the system,  
> this
> current design simply replaces my existing CallSite logic with
> invokedynamic. The dynamic call from Ruby code passes threadcontext,
> caller object, target object, and arguments through invokedynamic,  
> which
> is then bootstrapped with a new dyn.CallSite instance and my
> GuardedMethodHandle. GMH simply asks the cached CacheEntry tuple if  
> it's
> still valid for the incoming type, and then either dispatches  
> through to
> the JRuby DynamicMethod object or re-looks-up the method and  
> reinstalls
> in the dyn.CallSite.
>
> So far it appears to be at least no slower doing it this way, but I'm
> hoping we'll be able to coax more performance out of this.

That's because you haven't run into the deoptimization the compiler  
does on invokedynamic.

> It's also pretty crashy right now; several tests I tried simply blew  
> up.
> I can provide dumps and reproduction cases on demand.

There are a number of crashes I know about.  (Remi has been good at  
producing them!)  Please do some triage, and pick me a crash to work  
on that seems most in your way (sans workaround).  Reduced (one-file)  
test cases are most welcome.

> Comments welcome...time to get some sleep.

Thanks a million!

-- John



More information about the mlvm-dev mailing list