This document summarizes Charles Nutter's involvement with JSR 292 (invokedynamic) and JRuby performance over several years. It describes early experiments adding invokedynamic support to JRuby in 2008-2009 before the Java 7 implementation. After Java 7's release, performance was still much slower than regular calls. The document lists efforts by Nutter and the Hotspot team from 2010-2011 to improve performance through JIT optimizations and other changes. It discusses options for dealing with invokedynamic's poor performance in Java 7 and monitoring future JVM versions for improvements.
* История JRuby;
* Платформа JVM и ее возможности;
* Почему стоит попробовать JRuby;
* Как мы в Хот Спот используем JRuby для разработки;
* Сравнение с другими JVM языками.
Objective-C is a Smalltalk-like Object-Oriented layer on top of the C language. It is the official language of OS X and iOS. Assuming you have a background in Object-Oriented Programming and a basic understanding of the C language or syntax, this talk will cover everything you need to know about Objective-C. By the end of the talk, you will understand how to make and use your own objects, the Foundation Framework and the data structures it provides, and the Objective-C specific language constructs and syntactic-sugar.
Just a brief introduction I have given my team to get into the OSGi topic. Guess it is not the highest academic level, but should be enough to understand the fundamentals of OSGi.
* История JRuby;
* Платформа JVM и ее возможности;
* Почему стоит попробовать JRuby;
* Как мы в Хот Спот используем JRuby для разработки;
* Сравнение с другими JVM языками.
Objective-C is a Smalltalk-like Object-Oriented layer on top of the C language. It is the official language of OS X and iOS. Assuming you have a background in Object-Oriented Programming and a basic understanding of the C language or syntax, this talk will cover everything you need to know about Objective-C. By the end of the talk, you will understand how to make and use your own objects, the Foundation Framework and the data structures it provides, and the Objective-C specific language constructs and syntactic-sugar.
Just a brief introduction I have given my team to get into the OSGi topic. Guess it is not the highest academic level, but should be enough to understand the fundamentals of OSGi.
Objective-C is a Smalltalk-like Object-Oriented layer on top of the C language. It is the official language of OS X and iOS. Assuming you have a background in Object-Oriented Programming and a basic understanding of the C language or syntax, this talk will cover everything you need to know about Objective-C. By the end of the talk, you will understand how to make and use your own objects, the Foundation Framework and the data structures it provides, and the Objective-C specific language constructs and syntactic-sugar.
My goals have been:
- focusing on several project areas, where you can use jruby successfully
- share the experience that I made using ruby in the last years
- proove that things can be done easier as they are done in typical java projects
My presentation in SDCC 2012 (http://sdcc.csdn.net/index_en.html). The video recording of this session is available at http://v.csdn.hudong.com/s/article.html?arcid=2810640
Objective-C is a Smalltalk-like Object-Oriented layer on top of the C language. It is the official language of OS X and iOS. Assuming you have a background in Object-Oriented Programming and a basic understanding of the C language or syntax, this talk will cover everything you need to know about Objective-C. By the end of the talk, you will understand how to make and use your own objects, the Foundation Framework and the data structures it provides, and the Objective-C specific language constructs and syntactic-sugar.
My goals have been:
- focusing on several project areas, where you can use jruby successfully
- share the experience that I made using ruby in the last years
- proove that things can be done easier as they are done in typical java projects
My presentation in SDCC 2012 (http://sdcc.csdn.net/index_en.html). The video recording of this session is available at http://v.csdn.hudong.com/s/article.html?arcid=2810640
Introduction to node.js by Ran Mizrahi @ Reversim SummitRan Mizrahi
Node.js is a platform built on Chrome V8 javascript runtime engine for building fast and scalable, non-blocking, real-time and network applications. In this session I'll introduce you to node.js and developing large code bases using it. We'll cover the following aspects:
* What is node.js?
* Apache vs. Nginx performance (One thread per connection vs. event loop) and what it has to do with node.js.
* Why node was written in Javascript?
* Main tools and frameworks (Express, socket.io, mongoose etc.)
* TDD/BDD with node.js using mocha and Expect.js
The Spring framework packs a lot of punch, out of the box! The surface-level component model's extraordinarily flexible, and works well with in most situations, but the real power of Spring lays just underneath, in the numerous SPIs that Spring exposes, so that you can tailor the component model to your own use cases. Spring's SPI's are a great example of what Bob Martin describes as the open-closed principle, and it provides the solid underpinnings upon which the other Spring frameworks, including Spring Integration, Spring MVC and Spring Batch are built. In this talk, Josh Long, the Spring developer advocate from SpringSource, provides a walking tour of Spring's extension points.
Welcome to the Symfony2 World - FOSDEM 2013Lukas Smith
Symfony2 is more then just another PHP framework. It's backed by a community of people working together to bring innovative solutions to solve customer needs. This talk will give you an introducing to Symfony2 describing commonly used components. It will further discuss the ecosystem around Symfony2 with projects such a Symfony CMF and Vespolina.
Ab(Using) the MetaCPAN API for Fun and Profit v2013Olaf Alders
This talk builds on the previous Ab(Using) the MetaCPAN API talk from 2012. There are links to comprehensive examples and there is a more in-depth look at the available endpoints.
Symfony2 and MongoDB - MidwestPHP 2013 Pablo Godel
In this talk we will see how to use MongoDB in Symfony2 projects to speed up the development of web applications. We will give an introduction of MongoDB as a NoSQL database server and look at the options on how to work with it from Symfony2 and PHP applications.
This is an all day course focused on building good PhoneGap applications. This is not a class for newbies or those wanting to learn programming. It is intended for those who have some programming experience and some knowledge of JavaScript or other curly brace language. This class is hands-on and focused on development. You will write code, not watch slides.
A status update on JRuby, covering compatibility, Rails, and next-gen performance numbers. JRuby is currently the fastest way to run Rails apps, and we're doing work to make it even faster in the future.
JRuby 9000 introduced a new intermediate representation that allows us to use classic compiler strategies to optimize Ruby. This talk describes what we're doing with this new IR and why current JVM capabilities are not sufficient.
Fast as C: How to Write Really Terrible JavaCharles Nutter
For years we’ve been told that the JVM’s amazing optimizers can take your running code and make it “fast” or “as fast as C++” or “as fast as C”…or sometimes “faster than C”. And yet we don’t often see this happen in practice, due in large part to (good and bad) development patterns that have taken hold in the Java world.
In this talk, we’ll explore the main reasons why Java code rarely runs as fast as C or C++ and how you can write really bad Java code that the JVM will do a better job of optimizing. We’ll take some popular microbenchmarks and burn them to the ground, monitoring JIT logs and assembly dumps along the way.
Have you ever used an open source project? Of course you have, but have you made any contributions yourself? Filed a bug report? Submitted a patch? Have you ever started your own OSS project, or taken a closed/private project public? What licenses should you use? How do you manage contributions? How do you encourage contributors and get work done? In this talk we'll go over the basics of OSS: how to get involved, how to start a project, how to manage contributions. We'll discuss project lifecycles, legal CYA tips, and how to keep projects moving. You'll see the inner workings of real OSS projects, and learn how to be a better OSS user and producer.
Presented at Jfokus 2015
InvokeBinder: Fluent Programming for Method HandlesCharles Nutter
The MethodHandle API provides a powerful way to build optimized function pointers that do a wide variety of call-path adaptations. Unfortunately, the API as designed requires mental contortions to write anything more than trivial handle chains by hand. Adaptations must be made backwards from the target, argument-list modifications are done by index and length, and debugging failed adaptations can be a terrific challenge. InvokeBinder seeks to make method handles fun and easy to use by providing a fluent API, building adaptations from the call forward, allowing argument-list manipulation by name and wildcard, and much more. We'll explore everything InvokeBinder does today and talk about improvements for the future.
JRuby 9000 represents the biggest-ever leap forward for JRuby. Not only have we caught up on compatibility (9000 will be 2.2-compatible from release), but we've completely redesigned our JVM-based runtime and have opened our codebase up to the JRuby+Truffle research project from Oracle Labs. The changes we've made will make it easier to keep up with MRI on compatibility and give us the potential to run Ruby as fast as Java or C. The entire Ruby world will change over the next year, and JRuby 9000 will be leading the way. We'll talk about what Ruby's going to look like once JRuby is "over 9000".
Have you ever used an open source project? Well of course you have, but how about contributed to one? Filed a bug report? Submitted a patch? Have you ever started your own OSS project, or taken a closed/private project public? What licenses should you use? How do you manage contributions? How do you encourage contributors and get work done? In this talk we'll go over the basics of OSS: how to get involved, how to start a project, how to manage contributions. We'll discuss project lifecycles, legal CYA tips, and how to keep projects moving. You'll see the inner workings of real OSS projects, and learn how to be a better OSS user and producer.
A survey of all the hard problems JRuby developers have had to solve, whether the JVM likes it or not. Topics include parsing, interpreting, compiling, optimization, native libraries, posix, startup time, console features, and much more.
1. invokedynamic
Tales from the Trenches
Sunday, February 3, 13
2. Me
• Charles Oliver Nutter
• Programmer my whole life
• Professional Java since 1996
• headius@headius.com, @headius
• “Full time” JRuby guy
• Sun (06-09), Engine Yard (09-12), Red Hat
Sunday, February 3, 13
3. invokedynamic 101
• invokevirtual, invokestatic, etc
• Predefined behavior
• Based on simple VM primitives
• invokedynamic
• User-defined bytecode
• Primitives available as an IR
Sunday, February 3, 13
4. invokedynamic 101
• Emit invokedynamic bytecode
• Name + signature + bootstrap pointer
• On first call, bootstrap called
• Name + signature + lookup context
• Return a CallSite
• Subsequent calls go through CallSite
Sunday, February 3, 13
5. Terminology
• Invokedynamic: bytecode or JSR 292
• Call site: place in code where a call is made
• Bootstrap: method called to set up indy call
site
Sunday, February 3, 13
6. Terminology
• Method handle: endpoint (call, field, ...) or
logic (branches, arg manip, ...) to wrap an
endpoint handle
• Guard: logic to ensure site is bound to the
proper target
• GWT: guard-with-test, branch based on user
test
• SwitchPoint: on-until-off branch handle
Sunday, February 3, 13
7. Promises
• “invokedynamic should be no slower than
invokeinterface”
• “all Hotspot optimizations should apply
through indy sites”
• “SwitchPoint should be ‘free’ when valid”
Sunday, February 3, 13
8. Promises
• “JRuby plus invokedynamic will be fast”
• “The fully-working optimized OpenJDK
indy impl is just around the corner”
Sunday, February 3, 13
10. 2006
• Tom Enebo and I join Sun Microsystems
• Working on JRuby full time
• Dream come true!
• Sun officially starts promoting JVM as a
multi-language platform
• Needed some work to get there...
Sunday, February 3, 13
11. 2007
• Talks start between JRuby and John Rose
• How does JRuby work?
• What do we need?
• JSR 292 restarts with John Rose leading
• Not much to see yet
Sunday, February 3, 13
12. 2008
• Early design work in JSR
• Ola Bini represented JRuby
• Few working builds
• John Rose private builds
• Multi-Language VM (Da Vinci) later on
• We banked on the future
Sunday, February 3, 13
13. 2008
• “A First Taste of InvokeDynamic”
• http://blog.headius.com/2008/09/first-
taste-of-invokedynamic.html
• 11 Sept, 2008
• ~7000 words, ~26k views
Sunday, February 3, 13
14. JRuby 1.1.5
• First version with indy support
• Based on early proposal
• invokeinterface on java.dyn.Dynamic
• Dynamic type treated specially
• Manual bootstrap setup
• Worked...sorta
Sunday, February 3, 13
15. java.dyn.Dynamic
public java.lang.Object doDynamicCall(java.lang.Object);
Code:
0: aload_1
1: invokeinterface #3;
//Method java/dyn/Dynamic.myDynamicMethod:()V
4: areturn
Sunday, February 3, 13
17. 2009
• Continuing evolution of JSR 292
• We tracked design changes
• Performance work deferred
• We kept up the faith :-)
• First RI rev lands
Sunday, February 3, 13
18. Running on What?
• Still no standard builds for OS X
• MLVM repo
• Based on bsd-port
• External, periodic dump of indy work
• Incubator for other projects
• Henri Gomez: openjdk-osx-build
Sunday, February 3, 13
19. hotspot
2009-04-21; 6655646: dynamic languages need dynamically linked call
sites
Summary: invokedynamic instruction (JSR 292 RI)
2009-07-21; 6862576: vmIntrinsics needs cleanup in order to support
JSR 292 intrinsics
Summary: remove useless lazy evaluation of intrinsics; add
LAST_COMPILER_INLINE to help categorize them
2009-09-15; 6863023: need non-perm oops in code cache for JSR 292
Summary: Make a special root-list for those few nmethods which might
contain non-perm oops.
2009-12-16; 6829192: JSR 292 needs to support 64-bit x86
Summary: changes for method handles and invokedynamic
Sunday, February 3, 13
20. jdk
2009-05-05; 6829144: JSR 292 JVM features need a provisional Java API
Summary: JDK API and runtime (partial) for anonk, meth, indy
2009-10-21; 6891770: JSR 292 API needs initial unit tests
Summary: backport working mlvm regression test to M3 implementation of
JSR 292; requires jtreg 4.1
Sunday, February 3, 13
21. Meanwhile...
• Mirah: statically-typed, Ruby-like language
• Because why not
• Local type inference
• No runtime library
• .java and .class backends
• Way more interest than I expected...
Sunday, February 3, 13
24. What If This...
public class Foo {
private int a;
public Foo(int a) {
this.a = a;
}
public void show() {
System.out.println(a);
}
}
Sunday, February 3, 13
25. ...Could Be This
class Foo
def initialize(a)
@a = a
end
def show
puts @a
end
end
Sunday, February 3, 13
26. Mirah
class Foo
def initialize(a:int)
@a = a
end
def show
puts @a
end
end
Sunday, February 3, 13
27. Mirah
class Foo
def initialize(a:dynamic)
@a = a
end
def show
puts @a
end
end
Sunday, February 3, 13
29. 2010
• Performance work starts a bit
• Back and forth with Hotspot team
• Testing JRuby, dumping assembly
• Things start to look promising
• Inlining thresholds biggest issue
Sunday, February 3, 13
30. 2010-01-05; 6829187: compiler optimizations required for JSR 292
2010-01-13; 6912065: final fields in objects need to support inlining optimizations for JSR 292
2010-01-29; 6917766: JSR 292 needs its own deopt handler
2010-02-01; 6921352: JSR 292 needs its own deopt handler
2010-02-01; 6921799: JSR 292 call sites should not be fixed-up
2010-02-23; 6928839: JSR 292 typo in x86 _adapter_check_cast
2010-03-08; 6932536: JSR 292 modified JDK MethodHandlesTest fails on x86_64
2010-03-09; 6919934: JSR 292 needs to support x86 C1
2010-03-16; 6934494: JSR 292 MethodHandles adapters should be generated into their own CodeBlob
2010-03-17; 6934966: JSR 292 add C1 logic for saved SP over MethodHandle calls
2010-03-18; 6932091: JSR 292 x86 code cleanup
2010-03-31; 6939731: JSR 292 Zero build fix after 6934494
2010-04-29; 6829193: JSR 292 needs to support SPARC
2010-05-01; 6939134: JSR 292 adjustments to method handle invocation
2010-05-21; 6930772: JSR 292 needs to support SPARC C1
2010-05-25; 6934104: JSR 292 needs to support SPARC C2
2010-06-09; 6939203: JSR 292 needs method handle constants
2010-07-15; 6964498: JSR 292 invokedynamic sites need local bootstrap methods
2010-09-24; 6986944: JSR 292 assert(caller_nm->is_method_handle_return(caller_frame.pc())) failed:
must be MH call site
2010-09-29; 6987634: JSR 292 assert(start_bci() >= 0 && start_bci() < code_size()) failed: correct
osr_bci argument
2010-10-11; 6829194: JSR 292 needs to support compressed oops
2010-10-13; 6987555: JSR 292 unboxing to a boolean value fails on big-endian SPARC
2010-10-18; 6991596: JSR 292 unimplemented adapter_opt_i2i and adapter_opt_l2i on SPARC
2010-10-30; 6981777: implement JSR 292 EG adjustments from summer 2010
2010-10-30; 6984311: JSR 292 needs optional bootstrap method parameters
2010-11-04; 6997459: JSR 292 after 6994093 getting: on return to interpreted call, restored SP is
corrupted
2010-11-09; 6998737: JSR 292: Remove the plug guarding the use of compressed oops
2010-11-30; 7001363: java/dyn/InvokeDynamic should not be a well-known class in the JVM
2010-12-22; 7007377: JSR 292 MethodHandlesTest.testCastFailure fails on SPARC with -Xcomp
+DeoptimizeALot
Sunday, February 3, 13
31. 2011
• Wrapping things up for FCS
• Focus on correctness
• Some JIT work landing for perf
• JRuby a primary test case
Sunday, February 3, 13
32. Java 7 GA
• Changes within couple months of release
• Signature polymorphism
• Minor API and naming adjustments
• java.lang.invoke package name
• Performance still dismal
• JIT work not completed in time
Sunday, February 3, 13
33. 2011-04-25; 7030715: JSR 292 JRuby test/test_super_call_site_caching.rb asserts with
+DoEscapeAnalysis
2011-05-10; 7042122: JSR 292: adjust various inline thresholds for JSR 292 API methods and method
handle adapters
2011-05-17; 7045513: JSR 292 inlining causes crashes in methodHandleWalk.cpp
2011-05-26; 7047961: JSR 292 MethodHandleWalk swap args doesn't handle T_LONG and T_DOUBLE properly
2011-06-22; 7057587: JSR 292 - crash with jruby in test/test_respond_to.rb
Sunday, February 3, 13
34. 2011-02-11; 7013417: JSR 292 needs to support variadic method handle calls
2011-02-11; 7012650: implement JSR 292 EG adjustments through January 2010
2011-02-11; 7013730: JSR 292 reflective operations should report errors with standard exception types
2011-02-15; 7016261: JSR 292 MethodType objects should be serializable
2011-02-15; 7014755: JSR 292 member lookup interaction with security manager
2011-02-15; 7016520: JSR 292 rules for polymorphic signature processing must be in package-info
2011-03-18; 6839872: remove implementation inheritance from JSR 292 APIs
2011-03-23; 7012648: move JSR 292 to package java.lang.invoke and adjust names
2011-04-07; 6817525: turn on method handle functionality by default for JSR 292
2011-05-12; 7034977: JSR 292 MethodHandle.invokeGeneric should be renamed MethodHandle.invoke
2011-05-17; 7044892: JSR 292: API entry points sometimes throw the wrong exceptions or doesn't throw
the expected one
2011-05-26; 7032323: code changes for JSR 292 EG adjustments to API, through Public Review
2011-06-03; 7051206: JSR 292 method name SwitchPoint.isValid is misleading to unwary users; should be
hasBeenInvalidated
Sunday, February 3, 13
37. What to Do?
• GA indy perf slower than non-indy!
Sunday, February 3, 13
38. What to Do?
• GA indy perf slower than non-indy!
• Enable indy, knowing perf is bad?
Sunday, February 3, 13
39. What to Do?
• GA indy perf slower than non-indy!
• Enable indy, knowing perf is bad?
• Disable, despite promises of future perf?
Sunday, February 3, 13
40. What to Do?
• GA indy perf slower than non-indy!
• Enable indy, knowing perf is bad?
• Disable, despite promises of future perf?
• Detect JVM version?
Sunday, February 3, 13
41. What to Do?
• GA indy perf slower than non-indy!
• Enable indy, knowing perf is bad?
• Disable, despite promises of future perf?
• Detect JVM version?
• Detect VM version?
Sunday, February 3, 13
42. 2011-08-31; 7078382: JSR 292: don't count method handle adapters against inlining budgets
2011-09-02; 7071709: JSR 292: switchpoint invalidation should be pushed not pulled
2011-09-08; 7085860: JSR 292: implement CallSite.setTargetNormal and setTargetVolatile as native
methods
2011-10-12; 7092712: JSR 292: unloaded invokedynamic call sites can lead to a crash with signature
types not on BCP
2011-10-24; 7090904: JSR 292: JRuby junit test crashes in PSScavengeRootsClosure::do_oop
2011-10-25; 7094138: JSR 292: JRuby junit test fails in CallSite.setTargetNormal: obj->is_oop()
failed: sanity check
2011-11-17; 7108383: JSR 292: JRuby bench_define_method_methods.rb: assert(slow_jvms != NULL) failed:
miss path must not
Sunday, February 3, 13
43. Java 7u2
• Performance work finally released!
• JRuby users put indy into production
• NoClassDefFound era (ha!) begins
• To this day, no 100% working Hotspot indy!
• ...and apparently J9 is not much better
• Maybe we should have Java syntax for indy?
Sunday, February 3, 13
44. NCDFE Bug
• Method handles operate at bootstrap level
• Must be able to bind user-loaded classes
• Handle impl only handled first type right
• Subsequent types presented incorrectly
• NCDFE resulted in JITed code
Sunday, February 3, 13
45. NCDFE Workarounds
• Load everything on bootstrap
• JRuby does this for noverify
• Not practical for server setups
• Erase all types to bootstrap classes
• Introduced checkcasts hurt perf
• Impossible to maintain both versions
Sunday, February 3, 13
46. Other Issues
• Inlining thresholds must be special-cased
• Native handles are opaque
• Native handles are expensive to create
• Native handles are hard to inspect
• Many optz can’t cross indy site
Sunday, February 3, 13
47. 2012
• Rewrite of Hotspot’s 292 subsystem
• Mostly-native moves into Java code
• LambdaForm instead of native
• @ForceInline hints added for JIT purposes
• Erases types, avoiding NCDFE issues
Sunday, February 3, 13
48. LambdaForm
• Java objects represent MH chain
• Unjitted, call directly through LFs
• LF “compiler” emits bytecoded adapters
• Bytecode inlined, optimized as normal
• JIT becomes more important
• Not universally loved...
Sunday, February 3, 13
49. def foo
bar
end
def bar
baz
end
def baz
sleep
end
foo
Sunday, February 3, 13
50. at
LF pre-JIT
org.jruby.RubyKernel.sleep(RubyKernel.java:801)
at org.jruby.RubyKernel$INVOKER$s$0$1$sleep.call(RubyKernel$INVOKER$s$0$1$sleep.gen)
at org.jruby.internal.runtime.methods.JavaMethod$JavaMethodN.call(JavaMethod.java:642)
at org.jruby.internal.runtime.methods.DynamicMethod.call(DynamicMethod.java:197)
at java.lang.invoke.LambdaForm$DMH/692342133.invokeVirtual_LLLLL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLLL_L(LambdaForm.java:1112)
at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136)
at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625)
at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604)
at java.lang.invoke.LambdaForm$LFI/1395089624.interpret_L(LambdaForm$LFI)
at java.lang.invoke.LambdaForm$NFI/792791759.invoke_LLLLLL_L(LambdaForm$NFI)
at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136)
at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625)
at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604)
at java.lang.invoke.LambdaForm$LFI/1254526270.interpret_L(LambdaForm$LFI)
at java.lang.invoke.LambdaForm$DMH/1744347043.invokeSpecial_LLLL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLL_L(LambdaForm.java:1107)
at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136)
at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625)
at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604)
at java.lang.invoke.LambdaForm$LFI/874088044.interpret_L(LambdaForm$LFI)
at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLL_L(LambdaForm.java:1107)
at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136)
at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625)
at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604)
at java.lang.invoke.LambdaForm$LFI/1837543557.interpret_L(LambdaForm$LFI)
at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLLL_L(LambdaForm.java:1112)
Sunday, February 3, 13
51. Anonymous Classes
at java.lang.invoke.LambdaForm$LFI/1395089624.interpret_L(LambdaForm$LFI)
at java.lang.invoke.LambdaForm$NFI/792791759.invoke_LLLLLL_L(LambdaForm$NFI)
at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH)
• Shared class metadata
• Patched versions of existing classes
• Reduced impact on symbol table, permgen
Sunday, February 3, 13
52. at org.jruby.RubyKernel.sleep(RubyKernel.java:801) at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLLL_L(LambdaForm.java:1112)
at org.jruby.RubyKernel$INVOKER$s$0$1$sleep.call(RubyKernel$INVOKER$s$0$1$sleep.gen) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH)
sleep
at org.jruby.internal.runtime.methods.JavaMethod$JavaMethodN.call(JavaMethod.java:642) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136)
at org.jruby.internal.runtime.methods.DynamicMethod.call(DynamicMethod.java:197) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625)
at java.lang.invoke.LambdaForm$DMH/692342133.invokeVirtual_LLLLL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604)
at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLLL_L(LambdaForm.java:1112) at java.lang.invoke.LambdaForm$LFI/1837543557.interpret_L(LambdaForm$LFI)
at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$DMH/1191747167.invokeSpecial_LLLLLL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm$NFI/792791759.invoke_LLLLLL_L(LambdaForm$NFI) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604)
at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$LFI/662441761.interpret_L(LambdaForm$LFI)
at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm$NamedFunction.invoke_LL_L(LambdaForm.java:1097)
at java.lang.invoke.LambdaForm$LFI/1395089624.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm$NFI/792791759.invoke_LLLLLL_L(LambdaForm$NFI) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136)
at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$LFI/1395089624.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625)
at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm$NFI/792791759.invoke_LLLLLL_L(LambdaForm$NFI) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604)
at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$LFI/662441761.interpret_L(LambdaForm$LFI)
at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm$MH/1190524793.invokeExact_MT(LambdaForm$MH)
at java.lang.invoke.LambdaForm$LFI/1254526270.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.MethodHandle.invokeWithArguments(MethodHandle.java:599)
at java.lang.invoke.LambdaForm$DMH/1744347043.invokeSpecial_LLLL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at org.jruby.runtime.invokedynamic.InvocationLinker.invocationFallback(InvocationLinker.java:138)
at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLL_L(LambdaForm.java:1107) at java.lang.invoke.LambdaForm$LFI/1837543557.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm$DMH/1304836502.invokeStatic_LLLL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$DMH/1191747167.invokeSpecial_LLLLLL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$DMH/1151020327.invokeSpecial_LLLLL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm$NFI/792791759.invoke_LLLLLL_L(LambdaForm$NFI) at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLLL_L(LambdaForm.java:1112)
at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136)
at java.lang.invoke.LambdaForm$LFI/874088044.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625)
at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLL_L(LambdaForm.java:1107) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604)
at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$LFI/874088044.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm$LFI/1254526270.interpret_L(LambdaForm$LFI)
at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLL_L(LambdaForm.java:1107) at java.lang.invoke.LambdaForm$MH/1451043227.linkToCallSite(LambdaForm$MH)
at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at ruby.__dash_e__.method__0$RUBY$foo(-e:1)
at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm$DMH/1304836502.invokeStatic_LLLL_L(LambdaForm$DMH)
foo
at java.lang.invoke.LambdaForm$LFI/1837543557.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm$DMH/1151020327.invokeSpecial_LLLLL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLLL_L(LambdaForm.java:1112) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLLL_L(LambdaForm.java:1112)
at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$LFI/874088044.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLL_L(LambdaForm.java:1107) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136)
at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625)
at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604)
at java.lang.invoke.LambdaForm$LFI/1837543557.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm$LFI/1254526270.interpret_L(LambdaForm$LFI)
at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLLL_L(LambdaForm.java:1112) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm$DMH/1744347043.invokeSpecial_LLLL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$LFI/662441761.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLL_L(LambdaForm.java:1107)
at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm$NamedFunction.invoke_LL_L(LambdaForm.java:1097) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136)
at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625)
at java.lang.invoke.LambdaForm$LFI/1837543557.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604)
at java.lang.invoke.LambdaForm$DMH/1191747167.invokeSpecial_LLLLLL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm$LFI/874088044.interpret_L(LambdaForm$LFI)
at java.lang.invoke.LambdaForm$NFI/792791759.invoke_LLLLLL_L(LambdaForm$NFI) at java.lang.invoke.LambdaForm$LFI/662441761.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLL_L(LambdaForm.java:1107)
at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$MH/1190524793.invokeExact_MT(LambdaForm$MH) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.MethodHandle.invokeWithArguments(MethodHandle.java:599) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136)
at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at org.jruby.runtime.invokedynamic.InvocationLinker.invocationFallback(InvocationLinker.java:138) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625)
at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm$DMH/1304836502.invokeStatic_LLLL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604)
at java.lang.invoke.LambdaForm$LFI/1395089624.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm$DMH/1151020327.invokeSpecial_LLLLL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$LFI/1837543557.interpret_L(LambdaForm$LFI)
at java.lang.invoke.LambdaForm$NFI/792791759.invoke_LLLLLL_L(LambdaForm$NFI) at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLLL_L(LambdaForm.java:1112) at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLLL_L(LambdaForm.java:1112)
at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136)
at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625)
at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604)
at java.lang.invoke.LambdaForm$LFI/1837543557.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm$LFI/1254526270.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm$LFI/1837543557.interpret_L(LambdaForm$LFI)
at java.lang.invoke.LambdaForm$DMH/1191747167.invokeSpecial_LLLLLL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$MH/1451043227.linkToCallSite(LambdaForm$MH) at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLLL_L(LambdaForm.java:1112)
at java.lang.invoke.LambdaForm$NFI/792791759.invoke_LLLLLL_L(LambdaForm$NFI) at ruby.__dash_e__.method__1$RUBY$bar(-e:1) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$DMH/1304836502.invokeStatic_LLLL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136)
bar
at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm$DMH/1151020327.invokeSpecial_LLLLL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625)
at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLLL_L(LambdaForm.java:1112) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604)
at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$LFI/1837543557.interpret_L(LambdaForm$LFI)
at java.lang.invoke.LambdaForm$LFI/874088044.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm$DMH/1191747167.invokeSpecial_LLLLLL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLL_L(LambdaForm.java:1107) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm$NFI/792791759.invoke_LLLLLL_L(LambdaForm$NFI)
at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm$LFI/1254526270.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136)
at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm$DMH/1744347043.invokeSpecial_LLLL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625)
at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLL_L(LambdaForm.java:1107) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604)
at java.lang.invoke.LambdaForm$LFI/874088044.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$LFI/1395089624.interpret_L(LambdaForm$LFI)
at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLL_L(LambdaForm.java:1107) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm$NFI/792791759.invoke_LLLLLL_L(LambdaForm$NFI)
at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136)
at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm$LFI/874088044.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625)
at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLL_L(LambdaForm.java:1107) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604)
at java.lang.invoke.LambdaForm$LFI/662441761.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$LFI/1837543557.interpret_L(LambdaForm$LFI)
at java.lang.invoke.LambdaForm$NamedFunction.invoke_LL_L(LambdaForm.java:1097) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm$DMH/1191747167.invokeSpecial_LLLLLL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm$NFI/792791759.invoke_LLLLLL_L(LambdaForm$NFI)
at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm$LFI/1837543557.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136)
at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLLL_L(LambdaForm.java:1112) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625)
at java.lang.invoke.LambdaForm$LFI/662441761.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604)
at java.lang.invoke.LambdaForm$MH/1190524793.invokeExact_MT(LambdaForm$MH) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm$LFI/874088044.interpret_L(LambdaForm$LFI)
at java.lang.invoke.MethodHandle.invokeWithArguments(MethodHandle.java:599) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLL_L(LambdaForm.java:1107)
at org.jruby.runtime.invokedynamic.InvocationLinker.invocationFallback(InvocationLinker.java:138) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm$DMH/1304836502.invokeStatic_LLLL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$LFI/1837543557.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136)
at java.lang.invoke.LambdaForm$DMH/1151020327.invokeSpecial_LLLLL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLLL_L(LambdaForm.java:1112) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625)
at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLLL_L(LambdaForm.java:1112) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604)
at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm$LFI/874088044.interpret_L(LambdaForm$LFI)
at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLL_L(LambdaForm.java:1107)
at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm$LFI/1837543557.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136)
at java.lang.invoke.LambdaForm$LFI/1254526270.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm$DMH/1191747167.invokeSpecial_LLLLLL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625)
at java.lang.invoke.LambdaForm$MH/1451043227.linkToCallSite(LambdaForm$MH) at java.lang.invoke.LambdaForm$NFI/792791759.invoke_LLLLLL_L(LambdaForm$NFI) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604)
at ruby.__dash_e__.method__2$RUBY$baz(-e:1) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$LFI/662441761.interpret_L(LambdaForm$LFI)
at java.lang.invoke.LambdaForm$DMH/1304836502.invokeStatic_LLLL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm$NamedFunction.invoke_LL_L(LambdaForm.java:1097)
baz
at java.lang.invoke.LambdaForm$DMH/1151020327.invokeSpecial_LLLLL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLLL_L(LambdaForm.java:1112) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136)
at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$LFI/1395089624.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625)
at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm$NFI/792791759.invoke_LLLLLL_L(LambdaForm$NFI) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604)
at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$LFI/662441761.interpret_L(LambdaForm$LFI)
at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm$MH/1190524793.invokeExact_MT(LambdaForm$MH)
at java.lang.invoke.LambdaForm$LFI/1254526270.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.MethodHandle.invokeWithArguments(MethodHandle.java:599)
at java.lang.invoke.LambdaForm$DMH/1744347043.invokeSpecial_LLLL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at org.jruby.runtime.invokedynamic.InvocationLinker.invocationFallback(InvocationLinker.java:138)
at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLL_L(LambdaForm.java:1107) at java.lang.invoke.LambdaForm$LFI/1837543557.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm$DMH/1304836502.invokeStatic_LLLL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$DMH/1191747167.invokeSpecial_LLLLLL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$DMH/1151020327.invokeSpecial_LLLLL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm$NFI/792791759.invoke_LLLLLL_L(LambdaForm$NFI) at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLLL_L(LambdaForm.java:1112)
at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136)
at java.lang.invoke.LambdaForm$LFI/874088044.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625)
at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLL_L(LambdaForm.java:1107) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604)
at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$LFI/874088044.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm$LFI/1254526270.interpret_L(LambdaForm$LFI)
at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLL_L(LambdaForm.java:1107) at java.lang.invoke.LambdaForm$MH/1451043227.linkToCallSite(LambdaForm$MH)
at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at ruby.__dash_e__.__file__(-e:1)
top-level of script
at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136)
at java.lang.invoke.LambdaForm$LFI/1837543557.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625)
at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLLL_L(LambdaForm.java:1112) at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604)
at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH) at java.lang.invoke.LambdaForm$LFI/874088044.interpret_L(LambdaForm$LFI)
at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136) at java.lang.invoke.LambdaForm$NamedFunction.invoke_LLLL_L(LambdaForm.java:1107)
at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625) at java.lang.invoke.LambdaForm$DMH/1627674070.invokeStatic_LL_L(LambdaForm$DMH)
at java.lang.invoke.LambdaForm.interpretWithArguments(LambdaForm.java:604) at java.lang.invoke.LambdaForm$NamedFunction.invokeWithArguments(LambdaForm.java:1136)
at java.lang.invoke.LambdaForm$LFI/1837543557.interpret_L(LambdaForm$LFI) at java.lang.invoke.LambdaForm.interpretName(LambdaForm.java:625)
Sunday, February 3, 13
53. Java Release?
• Work-in-progress until recent months
• Only made it to OpenJDK8 this fall
• Targeted for 7u12/14 right now
• Approval seems to be going well
• Still no 100% working indy release!
Sunday, February 3, 13
54. How Good Is It?
• We’ll come back to this
Sunday, February 3, 13
55. Meanwhile...
• RubyFlux: Ruby to .java compiler
• Dynamic calls converted to virtual
• Generated superclass with all methods
• method_missing, send, etc possible
• Eclipse JDT for generating source
• Early prototype
Sunday, February 3, 13
56. def foo
bar
end
def bar
self
end
a = 100_000_000
while a > 0
foo; foo; foo; foo; foo
a -= 1
end
Sunday, February 3, 13
57. public class foo_bar extends RObject {
public static void main(String[] args) {
new foo_bar().$main();
}
public void $main() {
RObject $last = RNil;
RObject a = RNil;
$last = a = new RFixnum(100000000L);
while (a.$greater(new RFixnum(0L)).toBoolean()) {
$last = foo();
$last = foo();
$last = foo();
$last = foo();
$last = foo();
$last = a = a.$minus(new RFixnum(1L));
;
}
$last = RNil;
;
}
public RObject foo() {
RObject $last = RNil;
$last = bar();
return $last;
}
public RObject bar() {
RObject $last = RNil;
$last = RNil;
return $last;
}
}
Sunday, February 3, 13
58. Other Pain
• Performance
• Debugging
• Security
• MethodHandle API
Sunday, February 3, 13
60. Performance
• I believe, I really do
Sunday, February 3, 13
61. Performance
• I believe, I really do
• But it has gone back and forth
Sunday, February 3, 13
62. Performance
• I believe, I really do
• But it has gone back and forth
• And I have shamefully not contributed
Sunday, February 3, 13
63. Performance
• I believe, I really do
• But it has gone back and forth
• And I have shamefully not contributed
• Other than whining and providing benches
Sunday, February 3, 13
64. Performance
• I believe, I really do
• But it has gone back and forth
• And I have shamefully not contributed
• Other than whining and providing benches
• I vow to change this in 2013
Sunday, February 3, 13
65. Debugging
• MethodHandle errors are often cryptic
• No MH chain inspection
• Backward binding flips brain ugh bad
• Errors may occur after repeated calls
• Site rebinding bugs
• PIC bugs
• Failure path bugs
Sunday, February 3, 13
66. Security
• With great power...comes great exploits
• Recent hacks related to indy, MHs
• I knew at least one would come out
• ...so I helped test recent fixes
• Imagine building reflection API today
• In the presence of stack hacks!
Sunday, February 3, 13
67. MethodHandle API
• MH API is very bare bones, low level
• InvokeBinder - fluent DSL for MH chains
• Build forward, not backward
• Track signature, arg names
• Many conveniences
• https://github.com/headius/invokebinder
Sunday, February 3, 13
72. try/finally
MethodHandle exceptionHandler = Binder
.from(target.type().insertParameterTypes(0, Throwable.class).changeReturnType(void.class))
.drop(0)
.invoke(post);
MethodHandle rethrow = Binder
.from(target.type().insertParameterTypes(0, Throwable.class))
.fold(exceptionHandler)
.drop(1, target.type().parameterCount())
.throwException();
target = MethodHandles.catchException(target, Throwable.class, rethrow);
// if target returns a value, we must return it regardless of post
MethodHandle realPost = post;
if (target.type().returnType() != void.class) {
// modify post to ignore return value
MethodHandle newPost = Binder
.from(target.type().insertParameterTypes(0, target.type().returnType()).changeReturnType(void.class))
.drop(0)
.invoke(post);
// fold post into an identity chain that only returns the value
realPost = Binder
.from(target.type().insertParameterTypes(0, target.type().returnType()))
.fold(newPost)
.drop(1, target.type().parameterCount())
.identity();
}
return MethodHandles.foldArguments(realPost, target);
Sunday, February 3, 13
73. Symbolic Arguments
• Easier to follow than indices
• Easier to adapt to different signatures
• Arity less of a challenge
Sunday, February 3, 13
84. def foo
self
end
def bar
foo
end
100_000.times do
bar
end
Sunday, February 3, 13
85. HERE BE DRAGONS
• x86_64 ASM output from Hotspot
• Google “hotspot printassembly”
• hsdis shared lib
• Drop into JVM dylib dir
• -XX:+UnlockDiagnosticVMOptions -XX:
+PrintAssembly
• PROFIT
Sunday, February 3, 13
88. Better Than Java?
• Polymorphic calls
• Hotspot inlines up to bimorphic
• JRuby: trimorphic PIC, configurable
• Smarter type checks possible
• Eliminate boxing at call site
Sunday, February 3, 13
89. Constants
• Lexical lazily-defined variables
• Redefinable, but usually static
• Single global invalidator (SwitchPoint)
• Mostly due to lexical scoping
• Constant target
Sunday, February 3, 13
90. Global Variables
• Global, thread-local, frame-local
• Only global gets cached
• Per-variable guard
• Constant value
• Failover to lookup after N invalidations
Sunday, February 3, 13
91. Foo = 1
$bar = 1
def get_foo
Foo
end
def get_bar
$bar
end
Sunday, February 3, 13
96. Better Than Java?
• Constant folding
• Lazy static finals can’t fold in Hotspot
• SwitchPoint + constant value can!
• Broke several benchmarks :-)
Sunday, February 3, 13
97. Better Than Java?
• Constant folding Fixed in 7
• Lazy static finals can’t fold in Hotspot
• SwitchPoint + constant value can!
• Broke several benchmarks :-)
Sunday, February 3, 13
98. public class JavaLazyFinal {
private static final long FINAL = System.currentTimeMillis();
private static long accum = 0 ;
public static void main(String[] args) {
for (int i = 0; i < 1000000; i++) {
accumulate();
}
System.out.println(accum);
}
public static void accumulate() {
accum += FINAL;
}
}
Sunday, February 3, 13
101. Instance Variables
• Per-class mutable table of “fields”
• Class maps names to offsets
• Type guard
• Specificity is up for debate...
• Offset cached in MH chain directly
• Future: true Java fields?
Sunday, February 3, 13
103. Thread Event Guard
• Global SwitchPoint
• Target is a no-op
• Fallback checks thread events
• On event, invalidate SP
• All code thrown out
• Looking at hybrid volatile + SP options
Sunday, February 3, 13
104. Lazy Literals
• Numbers, Strings, Regexp, True/False/Nil
• Local caching of JRuby runtime
• ConstantCallSite for runtime-isolated
• MutableCallSite for runtime-specific
• Classloader fails us here anyway
• Do isolated constant handles pointing at
same objects fold away?
Sunday, February 3, 13
109. Smooth sort of a small array
JRuby 90593
Rubinius 2.0.0rc1 60232.3
MagLev 23954.5
MacRuby 0.12 19609.5
Ruby 2.0.0 19590.7
Ruby 1.9.3 11439
Ruby 1.8.7 4750
0 25000 50000 75000 100000
Iterations per second
Sunday, February 3, 13
110. red/black tree, pure Ruby versus native
jruby + Java ext 0.1
jruby + Ruby 0.29
ruby-2.0.0 + C ext 0.51
ruby-1.9.3 + C ext 0.51
rbx-2.0.0rc1 + Ruby 0.51
macruby-0.12 + Ruby 1.19
maglev + Ruby 1.39
ruby-2.0.0 + Ruby 2.48
ruby-1.9.3 + Ruby 3.96
0 1 2 3 4
Runtime per iteration
Sunday, February 3, 13
111. Future
• Ongoing tuning of JIT, inlining
• Reduce perf cliff for unjitted or uninlined
• Partial inlining helping a lot here
• Inlining through closure receivers
• Tie inlining to closure-receiving site?
• Better EA! value types? tagged values?
• Android!
Sunday, February 3, 13