This proposes a new static `Proxy::invokeDefaultMethod` method to invoke the given default method on the given proxy instance.
The implementation looks up a method handle for `invokespecial` instruction as if called from with the proxy class as the caller, equivalent to calling `X.super::m` where `X` is a proxy interface of the proxy class and `X.super::m` will resolve to the specified default method. The implementation will call a private static `proxyClassLookup(Lookup caller)` method of the proxy class to obtain its private Lookup. This private method in the proxy class only allows a caller Lookup on java.lang.reflect.Proxy class with full privilege access to use, or else `IllegalAccessException` will be thrown. This patch also proposes to define a proxy class in an unnamed module to a dynamic module to strengthen encapsulation such that they are only unconditionally exported from a named module but not open for deep reflective access. This only applies to the case if all the proxy interfaces are public and in a package that is exported or open. One dynamic module is created for each class loader that defines proxies. The change changes the dynamic module to contain another package (same name as the module) that is unconditionally exported and is opened to `java.base` only. There is no change to the package and module of the proxy class for the following cases: - if at least one proxy interface is non-public, then the proxy class is defined in the package and module of the non-public interfaces - if at least one proxy is in a package that is non-exported and non-open, if all proxy interfaces are public, then the proxy class is defined in a non-exported, non-open package of a dynamic module. The spec change is that a proxy class used to be defined in an unnamed module, i.e. in a exported and open package, is defined in an unconditionally exported but non-open package. Programs that assume it to be open unconditionally will be affected and cannot do deep reflection on such proxy classes. Peter Levart contributed an initial prototype [1] (thanks Peter). I think the exceptions could be simplified as more checking should be done prior to the invocation of the method handle like checking the types of the arguments with the method type. This approach avoids defining a public API `protected Proxy::$$proxyClassLookup$$` method. Instead it defines a private static method that is restricted for Proxy class to use (by taking a caller parameter to ensure it's a private lookup on Proxy class). javadoc/specdiff: http://cr.openjdk.java.net/~mchung/jdk16/webrevs/8159746/api/ http://cr.openjdk.java.net/~mchung/jdk16/webrevs/8159746/specdiff/ [1] http://mail.openjdk.java.net/pipermail/core-libs-dev/2016-June/041629.html ------------- Commit messages: - Merge branch 'master' of https://github.com/openjdk/jdk into proxy-default-method - fix regression tests due to proxy name change - minor bug fix - Merge branch 'master' of https://github.com/openjdk/jdk into proxy-default-method - generate private accessor method to obtain private lookup - Merge branch 'master' of https://github.com/openjdk/jdk into proxy-default-method - more clean up - Merge branch 'master' of https://github.com/openjdk/jdk into proxy-default-method - Revise the API to take a default method - Merge branch 'master' of https://github.com/openjdk/jdk into proxy-default-method - ... and 1 more: https://git.openjdk.java.net/jdk/compare/3320fc0f...c311a744 Changes: https://git.openjdk.java.net/jdk/pull/313/files Webrev: https://webrevs.openjdk.java.net/?repo=jdk&pr=313&range=00 Issue: https://bugs.openjdk.java.net/browse/JDK-8159746 Stats: 896 lines in 19 files changed: 810 ins; 27 del; 59 mod Patch: https://git.openjdk.java.net/jdk/pull/313.diff Fetch: git fetch https://git.openjdk.java.net/jdk pull/313/head:pull/313 PR: https://git.openjdk.java.net/jdk/pull/313