question on exports to

Remi Forax forax at univ-mlv.fr
Wed Jun 1 09:03:25 UTC 2016



----- Mail original -----
> De: "Jochen Theodorou" <blackdrag at gmx.org>
> À: jigsaw-dev at openjdk.java.net
> Envoyé: Mercredi 1 Juin 2016 10:34:47
> Objet: Re: question on exports to
> 
> 
> 
> On 01.06.2016 02:37, Alex Buckley wrote:
> > On 5/31/2016 5:09 PM, Jochen Theodorou wrote:

[...]

> >
> > If x.class returns a class in some module other than MyOtherLib, then
> > whether code in module GeneralInvoker can reflect over the class depends
> > on whether the class is exported to GeneralInvoker.
> >
> > You mention module x having readability of module y only if they have a
> > transitive exports-requires relationship ... but exports is nothing to
> > do with readability. The two-sided relationship that matters is
> > X-reads-Y + Y-exports-to-at-least-X, and what it matters for is
> > accessibility, a higher level thing than readability.  Have you watched
> > my "Project Jigsaw: Under The Hood" video from JavaOne 2015?
> 
> now I have, and it points the exports-requires part out more clearly,
> true. But you know, hearing something is one thing... understanding it
> and then be able to integrate it in my own thoughts is something else.
> And even if something is supposed to be easy, it not always is, because
> your thoughts have been led astray by something else, or you are trying
> to match that system against a totally different one, maybe even without
> being aware of it. Anyway... it made me think, that I actually made an
> early error...
> 
> MyOtherLib will require GeneralInvoker, because it is calling a method
> from it. GeneralInvoker will export the package with the classes
> MyOtherLib requires. So all fine here. But now I want GeneralInvoker to
> be able to use classes form MyOtherLib, without GeneralInvoker knowing
> MyOtherLib at compile time. That's where I came up with the exports-to.
> But there is no requires in GeneralInvoker. Which then means to me this
> will (a) not work and (b) adding a requires (which is not possible in my
> scenario) would produce a circular dependency and fail again.
> 
> Then again you said: """
> Accessibility is a two-part check: i) does the accessing module read the
> accessed module, and ii) does the accessed module export the right
> package to at least the accessing module?
> 
> When you use the Core Reflection API, the answer to (i) is always "yes".
> You never need to call Module::addReads. That is, when code in module M
> manipulates a Class/Field/Method object, it's as if M reads whichever
> module holds <<the class corresponding to the Class object>>/<<the class
> declaring the field corresponding to the Field object>>/<<the class
> declaring the method corresponding to the Executable object>>. The
> accessibility question depends solely on (ii) -- whether that module
> exports the right package to at least M.
> """
> 
> Which means the Core Reflection API has rights beyond what I described.
> And the question to me is what GeneralInvoker has to do, to get similar
> rights.... to for example not use the core reflection API, but its own,
> runtime generated classes to do something similar. And that again would
> lead me to believe GeneralInvoker has to call Module::addReads, on its
> own module with the module of MyOtherLib as argument... and hope there
> is no circular dependency check at this point. Well... actually that
> addReads has to be for the part actually doing the invocation as well...
> which leads me back to the problem of how to enable a dynamic named
> module to read an "internal" API from a named module.

No circular dependency is not something checked at runtime after the 'modules being deployed'.
You can not have a circular dependencies when all the module-info.class are read during start up time but you can have circular dependencies after when you add addReads dynamically.

> 
> This now looks to me like this... GeneralInvoker will have to call
> generalInvokerModule.addReads(myOtherLibModule), to enable to inspect
> the classes from that library. It will then spawn a layer with a named
> module, which contains the invocation code. This layerModule will
> contain code to call layerModule.addReads(myOtherLibModule), so it can
> access the classes in MyOtherLib if they are exported.... and since that
> is not yet the case, I will have to cause MyOtherLib to call
> myOtherLib.addExports("my.lib", layerModule).
> 
> Which still means I cannot replace reflection completely, since it does
> not have to cause MyOtherLib to call myOtherLib.addExports("my.lib",
> layerModule). Or it means I still lack understanding - which would not
> surprise me at all.
> 
> bye Jochen
> 

cheers,
Rémi


More information about the jigsaw-dev mailing list