From 4a6831a5990dc76411e59a069c200e10a454a578 Mon Sep 17 00:00:00 2001 From: Nathan Sweet Date: Tue, 12 Nov 2013 21:55:53 +0100 Subject: [PATCH 1/5] Create README.md --- README.md | 79 +++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 79 insertions(+) create mode 100644 README.md diff --git a/README.md b/README.md new file mode 100644 index 0000000..532b451 --- /dev/null +++ b/README.md @@ -0,0 +1,79 @@ +## Overview + +ReflectASM is a very small Java library that provides high performance reflection by using code generation. An access class is generated to set/get fields, call methods, or create a new instance. The access class uses bytecode rather than Java's reflection, so it is much faster. It can also access primitive fields via bytecode to avoid boxing. + +## Performance + +![](http://chart.apis.google.com/chart?chma=100&chtt=Field%20Set/Get&chs=700x62&chd=t:1402081,11339107&chds=0,11339107&chxl=0:|Java%20Reflection|FieldAccess&cht=bhg&chbh=10&chxt=y&chco=6600FF) + +![](http://chart.apis.google.com/chart?chma=100&chtt=Method%20Call&chs=700x62&chd=t:97390,208750&chds=0,208750&chxl=0:|Java%20Reflection|MethodAccess&cht=bhg&chbh=10&chxt=y&chco=6600AA) + +![](http://chart.apis.google.com/chart?chma=100&chtt=Constructor&chs=700x62&chd=t:2853063,5828993&chds=0,5828993&chxl=0:|Java%20Reflection|ConstructorAccess&cht=bhg&chbh=10&chxt=y&chco=660066) + +The source code for these benchmarks is included in the project. The above charts were generated on Oracle's Java 7u3, server VM. + +## Usage + +Method reflection with ReflectASM: + +```java + SomeClass someObject = ... + MethodAccess access = MethodAccess.get(SomeClass.class); + access.invoke(someObject, "setName", "Awesome McLovin"); + String name = (String)access.invoke(someObject, "getName"); +``` + +Field reflection with ReflectASM: + +```java + SomeClass someObject = ... + FieldAccess access = FieldAccess.get(SomeClass.class); + access.set(someObject, "name", "Awesome McLovin"); + String name = (String)access.get(someObject, "name"); +``` + +Constructor reflection with ReflectASM: + +```java + ConstructorAccess access = ConstructorAccess.get(SomeClass.class); + SomeClass someObject = access.newInstance(); +``` + +## Avoiding Name Lookup + +For maximum performance when methods or fields are accessed repeatedly, the method or field index should be used instead of the name: + +```java + SomeClass someObject = ... + MethodAccess access = MethodAccess.get(SomeClass.class); + int addNameIndex = access.getIndex("addName"); + for (String name : names) + access.invoke(someObject, addNameIndex, "Awesome McLovin"); +``` + +## Visibility + +ReflectASM can always access public members. An attempt is made to define access classes in the same classloader (using setAccessible) and package as the accessed class. If the security manager allows setAccessible to succeed, then protected and default access (package private) members can be accessed. If setAccessible fails, no exception is thrown, but only public members can be accessed. Private members can never be accessed. + +## Exceptions + +Stack traces when using ReflectASM are a bit cleaner. Here is Java's reflection calling a method that throws a RuntimeException: + + Exception in thread "main" java.lang.reflect.InvocationTargetException + at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) + at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39) + at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25) + at java.lang.reflect.Method.invoke(Method.java:597) + at com.example.SomeCallingCode.doit(SomeCallingCode.java:22) + Caused by: java.lang.RuntimeException + at com.example.SomeClass.someMethod(SomeClass.java:48) + ... 5 more + +Here is the same but when ReflectASM is used: + + Exception in thread "main" java.lang.RuntimeException + at com.example.SomeClass.someMethod(SomeClass.java:48) + at com.example.SomeClassMethodAccess.invoke(Unknown Source) + at com.example.SomeCallingCode.doit(SomeCallingCode.java:22) + +If ReflectASM is used to invoke code that throws a checked exception, the checked exception is thrown. Because it is a compilation error to use try/catch with a checked exception around code that doesn't declare that exception as being thrown, you must catch Exception if you care about catching a checked exception in code you invoke with ReflectASM. From 85a0bd56c39f1e112ec0d18f7888296cd303c9fe Mon Sep 17 00:00:00 2001 From: Nathan Sweet Date: Tue, 12 Nov 2013 21:58:48 +0100 Subject: [PATCH 2/5] Update README.md --- README.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/README.md b/README.md index 532b451..a3aecc9 100644 --- a/README.md +++ b/README.md @@ -1,3 +1,5 @@ +![](https://raw.github.com/wiki/EsotericSoftware/kryonet/images/logo.jpg) + ## Overview ReflectASM is a very small Java library that provides high performance reflection by using code generation. An access class is generated to set/get fields, call methods, or create a new instance. The access class uses bytecode rather than Java's reflection, so it is much faster. It can also access primitive fields via bytecode to avoid boxing. From e1fb536d2fe06418de5912c9c35cff9457835f1e Mon Sep 17 00:00:00 2001 From: Nathan Sweet Date: Tue, 12 Nov 2013 21:59:00 +0100 Subject: [PATCH 3/5] Update README.md --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index a3aecc9..6345d8a 100644 --- a/README.md +++ b/README.md @@ -1,4 +1,4 @@ -![](https://raw.github.com/wiki/EsotericSoftware/kryonet/images/logo.jpg) +![](https://raw.github.com/wiki/EsotericSoftware/reflectasm/images/logo.jpg) ## Overview From cd3a0f3f19bf53ac1b92eabb8691513fc37f8f3a Mon Sep 17 00:00:00 2001 From: Nathan Sweet Date: Tue, 12 Nov 2013 22:00:35 +0100 Subject: [PATCH 4/5] Update README.md --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 6345d8a..6da9ca1 100644 --- a/README.md +++ b/README.md @@ -1,4 +1,4 @@ -![](https://raw.github.com/wiki/EsotericSoftware/reflectasm/images/logo.jpg) +![](https://raw.github.com/wiki/EsotericSoftware/reflectasm/images/logo.png) ## Overview From cb27e7559a3104e13c923b6afee5e898061722f0 Mon Sep 17 00:00:00 2001 From: Nathan Sweet Date: Tue, 12 Nov 2013 22:04:05 +0100 Subject: [PATCH 5/5] Update README.md --- README.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/README.md b/README.md index 6da9ca1..ced8487 100644 --- a/README.md +++ b/README.md @@ -1,5 +1,7 @@ ![](https://raw.github.com/wiki/EsotericSoftware/reflectasm/images/logo.png) +Please use the [ReflectASM discussion group](http://groups.google.com/group/reflectasm-users) for support. + ## Overview ReflectASM is a very small Java library that provides high performance reflection by using code generation. An access class is generated to set/get fields, call methods, or create a new instance. The access class uses bytecode rather than Java's reflection, so it is much faster. It can also access primitive fields via bytecode to avoid boxing.