Proposal: Allow illegal reflective access by default in JDK 9

Peter Levart peter.levart at
Fri May 19 13:54:19 UTC 2017

Hi Alan,

On 05/19/2017 02:28 PM, Alan Bateman wrote:
> On 19/05/2017 13:02, Peter Levart wrote:
>> Ok, I can understand that such interpretation of "opens" is necessary 
>> for JDK 8 compatibility story. If something is "open" then it behaves 
>> exactly like in JDK 8 or before (apart from compilation) regardless 
>> of packages being exported or not. But from consistency perspective, 
>> explicit "exports" should be required just like "public" modifiers 
>> are required to access members without .setAccessible(true) or 
>> without .privateLookupIn().
>> This would not hinder the ability for frameworks to access members. 
>> It would just require them to call 
>> .setAccessible(true)/.privateLookupIn() in more places, but would be 
>> safer too as "suppressAccessChecks" permission would be required for 
>> non-exported package access like it is required for "private" members.
>> I'm sorry I haven't noticed this before. It is probably to late to 
>> change this now. Was this deliberate choice (to promote compatibility 
>> with existing code)?
> `opens` is intended to open a package for reflective access. Code can 
> use the reflection APIs to get at public members of public types in 
> the package, it shouldn't need setAccessible to do that.

Then "opens" is a sharp tool. And the proposal is about applying this 
tool to the whole JDK by default!

Why I think this is not good? Because "opens", as it is, caries two 
aspects or purposes at the same time. One is the purpose of giving 
access to frameworks that introspect classes of a module and also access 
them (DI frameworks for example) and this is a desirable purpose. The 
other is the undesirable consequence of giving "unrestricted" access to 
public types in the opened package during runtime. Introspective access 
should be paired with a runtime permission in a secured system while 
"unrestricted" access should only be given explicitly - using good old 

I see the problem with that. "opens" and "exports" are applied to 
packages, but "open" can also be applied to the whole module and we 
don't have an equivalent for "exports" on the module-level. But is that 
really needed? Introspective frameworks should not have a problem with 
invoking .setAccessible() as they could do that mechanically.

Opening the whole JDK (--illegal-access=permit by default) means that 
all internal "public" APIs are made accessible if by chance someone can 
grab an instance of target object and/or an instance of Method/Field 
object. Imagine a JDK developer that thought that by putting a public 
type into a concealed package was equivalent to making the type 
module-private. This is a big surprise from the security perspective and 
jdk.internal.misc.Unsafe.getUnsafe() might not be a lone example.

> The static reference case that Volker brought up is somewhat of a 
> corner case in this discussion. Readability aside, it would be 
> inconsistent if reflection APIs could access public members of public 
> types in the package but bytecode could not. The other corner case is 
> code generation at run-time which also should also work (assuming both 
> visibility and readability).

I get that. Generated code would have less access than reflection and 
generated code is often used to replace reflection to speed things up.

Huh, not an easy choice, I agree...

Regards, Peter

> -Alan

More information about the jigsaw-dev mailing list