Skip to content

Commit

Permalink
[GR-53420] Replicate hosted module graph relations for unnamed modules
Browse files Browse the repository at this point in the history
PullRequest: graal/17658
  • Loading branch information
ivan-ristovic committed May 21, 2024
2 parents 97bf193 + 6a065ce commit dd8dcad
Show file tree
Hide file tree
Showing 2 changed files with 64 additions and 64 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -201,13 +201,15 @@ private void scanRuntimeBootLayerPrototype(BeforeAnalysisAccessImpl accessImpl)
public void afterAnalysis(AfterAnalysisAccess access) {
AfterAnalysisAccessImpl accessImpl = (AfterAnalysisAccessImpl) access;

Set<Module> runtimeImageNamedModules = accessImpl.getUniverse().getTypes()
Set<Module> runtimeImageModules = accessImpl.getUniverse().getTypes()
.stream()
.filter(ModuleLayerFeature::typeIsReachable)
.map(t -> t.getJavaClass().getModule())
.filter(Module::isNamed)
.collect(Collectors.toSet());

Set<Module> runtimeImageNamedModules = runtimeImageModules.stream().filter(Module::isNamed).collect(Collectors.toSet());
Set<Module> runtimeImageUnnamedModules = runtimeImageModules.stream().filter(Predicate.not(Module::isNamed)).collect(Collectors.toSet());

/*
* Parse explicitly added modules via --add-modules. This is done early as this information
* is required when filtering the analysis reachable module set.
Expand Down Expand Up @@ -257,7 +259,7 @@ public void afterAnalysis(AfterAnalysisAccess access) {
* Ensure that runtime modules have the same relations (i.e., reads, opens and exports) as
* the originals.
*/
replicateVisibilityModifications(runtimeBootLayer, accessImpl, accessImpl.imageClassLoader, runtimeImageNamedModules);
replicateVisibilityModifications(runtimeBootLayer, accessImpl, accessImpl.imageClassLoader, runtimeImageNamedModules, runtimeImageUnnamedModules);
replicateNativeAccess(accessImpl, runtimeImageNamedModules);
}

Expand Down Expand Up @@ -461,61 +463,70 @@ private ModuleLayer synthesizeRuntimeModuleLayer(List<ModuleLayer> parentLayers,
}
}

private void replicateVisibilityModifications(ModuleLayer runtimeBootLayer, AfterAnalysisAccessImpl accessImpl, ImageClassLoader cl, Set<Module> analysisReachableNamedModules) {
private void replicateVisibilityModifications(ModuleLayer runtimeBootLayer, AfterAnalysisAccessImpl accessImpl, ImageClassLoader cl, Set<Module> analysisReachableNamedModules,
Set<Module> analysisReachableUnnamedModules) {
List<Module> applicationModules = findApplicationModules(runtimeBootLayer, cl.applicationModulePath());

Map<Module, Module> modulePairs = analysisReachableNamedModules
Map<Module, Module> namedModulePairs = analysisReachableNamedModules
.stream()
.collect(Collectors.toMap(m -> m, m -> moduleLayerFeatureUtils.getRuntimeModuleForHostedModule(m, false)));
modulePairs.put(moduleLayerFeatureUtils.allUnnamedModule, moduleLayerFeatureUtils.allUnnamedModule);
modulePairs.put(moduleLayerFeatureUtils.everyoneModule, moduleLayerFeatureUtils.everyoneModule);
.collect(Collectors.toMap(Function.identity(), m -> moduleLayerFeatureUtils.getRuntimeModuleForHostedModule(m, false)));
Map<Module, Module> unnamedModulePairs = analysisReachableUnnamedModules
.stream()
.collect(Collectors.toMap(Function.identity(), m -> moduleLayerFeatureUtils.getRuntimeModuleForHostedModule(m, false)));
unnamedModulePairs.put(moduleLayerFeatureUtils.allUnnamedModule, moduleLayerFeatureUtils.allUnnamedModule);
unnamedModulePairs.put(moduleLayerFeatureUtils.everyoneModule, moduleLayerFeatureUtils.everyoneModule);

try {
for (Map.Entry<Module, Module> e1 : namedModulePairs.entrySet()) {
Module hostedFrom = e1.getKey();
Module runtimeFrom = e1.getValue();
for (Map.Entry<Module, Module> e2 : namedModulePairs.entrySet()) {
replicateVisibilityModification(accessImpl, applicationModules, hostedFrom, e2.getKey(), runtimeFrom, e2.getValue());
}
for (Map.Entry<Module, Module> e2 : unnamedModulePairs.entrySet()) {
replicateVisibilityModification(accessImpl, applicationModules, hostedFrom, e2.getKey(), runtimeFrom, e2.getValue());
}
}
} catch (IllegalAccessException ex) {
throw VMError.shouldNotReachHere("Failed to transfer hosted module relations to the runtime boot module layer.", ex);
}
}

private void replicateVisibilityModification(AfterAnalysisAccessImpl accessImpl, List<Module> applicationModules, Module hostedFrom, Module hostedTo, Module runtimeFrom, Module runtimeTo)
throws IllegalAccessException {
if (hostedTo == hostedFrom) {
return;
}

Module builderModule = ModuleLayerFeatureUtils.getBuilderModule();
assert builderModule != null;

try {
for (Map.Entry<Module, Module> e1 : modulePairs.entrySet()) {
Module hostedFrom = e1.getKey();
if (!hostedFrom.isNamed()) {
continue;
if (ModuleLayerFeatureUtils.isModuleSynthetic(hostedFrom) || hostedFrom.canRead(hostedTo)) {
moduleLayerFeatureUtils.addReads(accessImpl, runtimeFrom, runtimeTo);
if (hostedFrom == builderModule) {
for (Module appModule : applicationModules) {
moduleLayerFeatureUtils.addReads(accessImpl, appModule, runtimeTo);
}
Module runtimeFrom = e1.getValue();
for (Map.Entry<Module, Module> e2 : modulePairs.entrySet()) {
Module hostedTo = e2.getKey();
if (hostedTo == hostedFrom) {
continue;
}
Module runtimeTo = e2.getValue();
if (ModuleLayerFeatureUtils.isModuleSynthetic(hostedFrom) || hostedFrom.canRead(hostedTo)) {
moduleLayerFeatureUtils.addReads(accessImpl, runtimeFrom, runtimeTo);
if (hostedFrom == builderModule) {
for (Module appModule : applicationModules) {
moduleLayerFeatureUtils.addReads(accessImpl, appModule, runtimeTo);
}
}
}
}

for (String pn : runtimeFrom.getPackages()) {
if (ModuleLayerFeatureUtils.isModuleSynthetic(hostedFrom) || hostedFrom.isOpen(pn, hostedTo)) {
moduleLayerFeatureUtils.addOpens(accessImpl, runtimeFrom, pn, runtimeTo);
if (hostedTo == builderModule) {
for (Module appModule : applicationModules) {
moduleLayerFeatureUtils.addOpens(accessImpl, runtimeFrom, pn, appModule);
}
for (String pn : runtimeFrom.getPackages()) {
if (ModuleLayerFeatureUtils.isModuleSynthetic(hostedFrom) || hostedFrom.isOpen(pn, hostedTo)) {
moduleLayerFeatureUtils.addOpens(accessImpl, runtimeFrom, pn, runtimeTo);
if (hostedTo == builderModule) {
for (Module appModule : applicationModules) {
moduleLayerFeatureUtils.addOpens(accessImpl, runtimeFrom, pn, appModule);
}
}
}
if (ModuleLayerFeatureUtils.isModuleSynthetic(hostedFrom) || hostedFrom.isExported(pn, hostedTo)) {
moduleLayerFeatureUtils.addExports(accessImpl, runtimeFrom, pn, runtimeTo);
if (hostedTo == builderModule) {
for (Module appModule : applicationModules) {
moduleLayerFeatureUtils.addExports(accessImpl, runtimeFrom, pn, appModule);
}
}
}
}
}
if (ModuleLayerFeatureUtils.isModuleSynthetic(hostedFrom) || hostedFrom.isExported(pn, hostedTo)) {
moduleLayerFeatureUtils.addExports(accessImpl, runtimeFrom, pn, runtimeTo);
if (hostedTo == builderModule) {
for (Module appModule : applicationModules) {
moduleLayerFeatureUtils.addExports(accessImpl, runtimeFrom, pn, appModule);
}
}
}
} catch (IllegalAccessException ex) {
throw VMError.shouldNotReachHere("Failed to transfer hosted module relations to the runtime boot module layer.", ex);
}
}

Expand Down Expand Up @@ -761,24 +772,8 @@ public ModuleFinder getAppModuleFinder() {
public Module getRuntimeModuleForHostedModule(Module hostedModule, boolean optional) {
if (hostedModule.isNamed()) {
return getRuntimeModuleForHostedModule(hostedModule.getClassLoader(), hostedModule.getName(), optional);
}

/*
* EVERYONE and ALL_UNNAMED modules are unnamed module instances that are used as
* markers throughout the JDK and therefore we need them in the image heap.
*
* We make an optimization that all hosted unnamed modules except EVERYONE module have
* the same runtime unnamed module. This does not break the module visibility semantics
* as unnamed modules can access all named modules, and visibility modifications that
* include unnamed modules do not depend on the actual instance, but only on the fact
* that the module is unnamed e.g., calling addExports from/to an unnamed module will do
* nothing.
*/

if (hostedModule == everyoneModule) {
return everyoneModule;
} else {
return allUnnamedModule;
return hostedModule;
}
}

Expand Down Expand Up @@ -808,7 +803,7 @@ public Module getOrCreateRuntimeModuleForHostedModule(Module hostedModule) {
if (hostedModule.isNamed()) {
return getOrCreateRuntimeModuleForHostedModule(hostedModule.getClassLoader(), hostedModule.getName(), hostedModule.getDescriptor());
} else {
return hostedModule == everyoneModule ? everyoneModule : allUnnamedModule;
return hostedModule;
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -141,4 +141,9 @@ public static void accessModuleByClass(Access access, Class<?> accessingClass, M
}
access.giveAccess(namedAccessingModule, declaringModule, packageName);
}

@Platforms(Platform.HOSTED_ONLY.class)
public static void accessModule(Access access, Module accessingModule, Module declaringModule, String packageName) {
access.giveAccess(accessingModule, declaringModule, packageName);
}
}

0 comments on commit dd8dcad

Please sign in to comment.