Suggestion: allow accessible reflection on protected methods of exported types.

Jochen Theodorou blackdrag at gmx.org
Tue Jan 3 18:13:46 UTC 2017


On 03.01.2017 17:28, Alan Bateman wrote:
> On 29/12/2016 16:24, Rafael Winterhalter wrote:
>
>> :
>>
>> I argue that this module system should not be responsible to assert the
>> usage of such protected methods on exported types. Such methods are not
>> really encapsulated as they are considered official API by subclasses.
> Right, they are intended to be used by sub-classes and this hasn't
> changed, meaning that you should have no issue accessing a protected
> member defined in the super class with bytecode or core reflection as
> before (no setAccessible in the picture).

Alan, can you please give me a relevant example where it makes sense for 
a subclass to invoke a super class protected method by reflection rather 
than by direct invocation? The case of "you should have no issue 
accessing a protected member defined in the super class with [...] core 
reflection" sounds awfully constructed. Especially since reflection does 
not do invokespecial but invokevirtual logic, which means if the 
subclass overrides the method, the override will be called instead of 
the super class member.

> With strong encapsulation then having setAccessible treat protected
> members as public would mean we would be back to the hole that is
> #AwkwardStrongEncapsulation. It would mean anyone could access protected
> members that are not intended to be accessed in this way. Also in the
> case of the core modules then it conflicts with the goal to mprove
> platform integrity.

you could access protected members in exported classes, yes. But it 
would help the application compatibility.

> As regards the change you are seeing now then it has been in the Jigsaw
> EA builds for some time but only merged into the JDK 9 builds at
> jdk-9+148. There is further spec work required to deal with
> protected-static and protected constructors but that is a topic for
> another thread.

I there is still time for that?

> There is of course a compatibility impact with this
> change. It will expose many hacks, a number of them have come up on this
> mailing list already. It will also impact code that relies on being able
> to use setAccessible to get at protected-instance methods that it would
> not otherwise have access to in bytecode.

not have access otherwise means the class is final, afaik. Are there any 
other cases?

> For mitigation then the `--add-opens` command line option can be used to
> open any package of any module and so can be used to keep existing code
> working.

We had many, many discussion on this list as of why this is problematic. 
By now you need so many --add-opens, that you have to put them in a file 
to not exceed maximum command line length. And it means a container will 
need a JVM restart to be able to give the "module" all functionality if 
it requires adding an opens. I see this for example as a problem for 
tomcat. This could of course be made more easy if you could just open 
all modules, but this was silently rejected. And for something like 
scripting this stuff is extremely bothersome. I am not sure there are 
even solutions to all cases.

But from the lengthy and rarely fruitful discussions here I also get 
that jigsaw is supposed to be a breaking change.

> Ideally of course this would not be needed but it requires
> effort from the maintainers of many important libraries and tools.

You sound as if there are equal good alternative solutions to all these 
cases. For example changing the environment for a subprocess after its 
creation.... No, there is no clean solution. The only solution that does 
not require an opens is to do it by custom native code.

> There
> has been an outreach effort going on for the last 2+ years to try to get
> an many projects and libraries working with us so that the eco system
> will be in reasonable shape by the time that JDK 9 ships.

shortly before the last Java One things changed majorly with 
#AwkwardStrongEncapsulation. If we would still have the same situation 
we had 5 months ago I would have been much more happy. But then again 
this thread here would probably not have come into existence as well.

You know the funny part about #AwkwardStrongEncapsulation is that I 
think it was supposed to say that the old encapsulation was awkward... 
but for me it means the new one is.

[...]
> One final point about ClassLoader::defineClass is that java agents and
> tools doing bytecode instrumentation have the power to redefine modules
> and classes and so can break into all modules. I guess you are very
> familiar with this already.

I prognose a different solution... A custom application loader that will 
be able to dynamically load modules and will add opens to all of them, 
plus a big list of add-opens on startup for all the JDK stuff. That 
means the only not-core module the JVM would start with is the module 
that opens all the modules.

bye Jochen


More information about the jigsaw-dev mailing list