Skip to content

Commit e8fdedc

Browse files
committed
Check if modules contain packages before attempting to open/export
1 parent b33c897 commit e8fdedc

File tree

3 files changed

+58
-37
lines changed

3 files changed

+58
-37
lines changed

substratevm/src/com.oracle.svm.core/src/com/oracle/svm/core/NativeImageClassLoaderOptions.java

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -32,7 +32,6 @@
3232

3333
public class NativeImageClassLoaderOptions {
3434
public static final String AddExportsAndOpensFormat = "<module>/<package>=<target-module>(,<target-module>)*";
35-
3635
public static final String AddReadsFormat = "<module>=<target-module>(,<target-module>)*";
3736

3837
@APIOption(name = "add-exports", extra = true, launcherOption = true, valueSeparator = {APIOption.WHITESPACE_SEPARATOR, '='})//

substratevm/src/com.oracle.svm.hosted/src/com/oracle/svm/hosted/NativeImageClassLoaderSupport.java

Lines changed: 39 additions & 34 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,7 @@
3232
import java.io.File;
3333
import java.io.IOException;
3434
import java.lang.module.Configuration;
35+
import java.lang.module.FindException;
3536
import java.lang.module.ModuleDescriptor;
3637
import java.lang.module.ModuleFinder;
3738
import java.lang.module.ModuleReader;
@@ -389,21 +390,29 @@ void processClassLoaderOptions() {
389390
}
390391

391392
processOption(NativeImageClassLoaderOptions.AddExports).forEach(val -> {
392-
if (val.targetModules.isEmpty()) {
393-
Modules.addExportsToAllUnnamed(val.module, val.packageName);
394-
} else {
395-
for (Module targetModule : val.targetModules) {
396-
Modules.addExports(val.module, val.packageName, targetModule);
393+
if (val.module.getPackages().contains(val.packageName)) {
394+
if (val.targetModules.isEmpty()) {
395+
Modules.addExportsToAllUnnamed(val.module, val.packageName);
396+
} else {
397+
for (Module targetModule : val.targetModules) {
398+
Modules.addExports(val.module, val.packageName, targetModule);
399+
}
397400
}
401+
} else {
402+
warn("package " + val.packageName + " not in " + val.module.getName());
398403
}
399404
});
400405
processOption(NativeImageClassLoaderOptions.AddOpens).forEach(val -> {
401-
if (val.targetModules.isEmpty()) {
402-
Modules.addOpensToAllUnnamed(val.module, val.packageName);
403-
} else {
404-
for (Module targetModule : val.targetModules) {
405-
Modules.addOpens(val.module, val.packageName, targetModule);
406+
if (val.module.getPackages().contains(val.packageName)) {
407+
if (val.targetModules.isEmpty()) {
408+
Modules.addOpensToAllUnnamed(val.module, val.packageName);
409+
} else {
410+
for (Module targetModule : val.targetModules) {
411+
Modules.addOpens(val.module, val.packageName, targetModule);
412+
}
406413
}
414+
} else {
415+
warn("package " + val.packageName + " not in " + val.module.getName());
407416
}
408417
});
409418
processOption(NativeImageClassLoaderOptions.AddReads).forEach(val -> {
@@ -417,6 +426,10 @@ void processClassLoaderOptions() {
417426
});
418427
}
419428

429+
private static void warn(String m) {
430+
LogUtils.warning("WARNING", m, true);
431+
}
432+
420433
private static void processListModulesOption(ModuleLayer layer) {
421434
Class<?> launcherHelperClass = ReflectionUtil.lookupClass(false, "sun.launcher.LauncherHelper");
422435
Method initOutputMethod = ReflectionUtil.lookupMethod(launcherHelperClass, "initOutput", boolean.class);
@@ -499,33 +512,20 @@ private Stream<AddExportsAndOpensAndReadsFormatValue> processOption(OptionKey<Ac
499512
Stream<AddExportsAndOpensAndReadsFormatValue> parsedOptions = valuesWithOrigins.flatMap(valWithOrig -> {
500513
try {
501514
return Stream.of(asAddExportsAndOpensAndReadsFormatValue(specificOption, valWithOrig));
502-
} catch (UserError.UserException e) {
503-
if (ModuleSupport.modulePathBuild && classpath().isEmpty()) {
504-
throw e;
505-
} else {
506-
/*
507-
* Until we switch to always running the image-builder on module-path we have to
508-
* be tolerant if invalid --add-exports -add-opens or --add-reads options are
509-
* used. GR-30433
510-
*/
511-
LogUtils.warning(e.getMessage());
512-
return Stream.empty();
513-
}
515+
} catch (FindException e) {
516+
/*
517+
* Print a specially-formatted warning to be 100% compatible with the output of
518+
* `java` in this case.
519+
*/
520+
LogUtils.warning("WARNING", e.getMessage(), true);
521+
return Stream.empty();
514522
}
515523
});
516524
return parsedOptions;
517525
}
518526

519-
private static final class AddExportsAndOpensAndReadsFormatValue {
520-
private final Module module;
521-
private final String packageName;
522-
private final List<Module> targetModules;
523-
524-
private AddExportsAndOpensAndReadsFormatValue(Module module, String packageName, List<Module> targetModules) {
525-
this.module = module;
526-
this.packageName = packageName;
527-
this.targetModules = targetModules;
528-
}
527+
private record AddExportsAndOpensAndReadsFormatValue(Module module, String packageName,
528+
List<Module> targetModules) {
529529
}
530530

531531
private AddExportsAndOpensAndReadsFormatValue asAddExportsAndOpensAndReadsFormatValue(OptionKey<?> option, Pair<String, OptionOrigin> valueOrigin) {
@@ -581,15 +581,15 @@ private AddExportsAndOpensAndReadsFormatValue asAddExportsAndOpensAndReadsFormat
581581
}
582582

583583
Module module = findModule(moduleName).orElseThrow(() -> {
584-
return userErrorAddExportsAndOpensAndReads(option, optionOrigin, optionValue, " Specified module '" + moduleName + "' is unknown.");
584+
throw userWarningModuleNotFound(option, moduleName);
585585
});
586586
List<Module> targetModules;
587587
if (targetModuleNamesList.contains("ALL-UNNAMED")) {
588588
targetModules = Collections.emptyList();
589589
} else {
590590
targetModules = targetModuleNamesList.stream().map(mn -> {
591591
return findModule(mn).orElseThrow(() -> {
592-
throw userErrorAddExportsAndOpensAndReads(option, optionOrigin, optionValue, " Specified target-module '" + mn + "' is unknown.");
592+
throw userWarningModuleNotFound(option, mn);
593593
});
594594
}).collect(Collectors.toList());
595595
}
@@ -601,6 +601,11 @@ private static UserError.UserException userErrorAddExportsAndOpensAndReads(Optio
601601
return UserError.abort("Invalid option %s provided by %s.%s", SubstrateOptionsParser.commandArgument(option, value), origin, detailMessage);
602602
}
603603

604+
private static FindException userWarningModuleNotFound(OptionKey<?> option, String moduleName) {
605+
String optionName = SubstrateOptionsParser.commandArgument(option, "");
606+
return new FindException("Unknown module: " + moduleName + " specified to " + optionName);
607+
}
608+
604609
Class<?> loadClassFromModule(Module module, String className) {
605610
assert isModuleClassLoader(classLoader, module.getClassLoader()) : "Argument `module` is java.lang.Module from unknown ClassLoader";
606611
return Class.forName(module, className);

substratevm/src/com.oracle.svm.util/src/com/oracle/svm/util/LogUtils.java

Lines changed: 19 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -27,13 +27,22 @@
2727
import org.graalvm.nativeimage.Platform;
2828
import org.graalvm.nativeimage.Platforms;
2929

30+
import java.io.PrintStream;
31+
3032
// Checkstyle: Allow raw info or warning printing - begin
3133
public class LogUtils {
3234
/**
3335
* Print an info message.
3436
*/
3537
public static void info(String message) {
36-
System.out.println("Info: " + message);
38+
info("Info", message);
39+
}
40+
41+
/**
42+
* Print an info message with the given prefix.
43+
*/
44+
public static void info(String prefix, String message) {
45+
System.out.println(prefix + ": " + message);
3746
}
3847

3948
/**
@@ -53,7 +62,15 @@ public static void info(String format, Object... args) {
5362
* Print a warning.
5463
*/
5564
public static void warning(String message) {
56-
System.out.println("Warning: " + message);
65+
warning("Warning", message, false);
66+
}
67+
68+
/**
69+
* Print a warning message with the given prefix, optionally to stderr.
70+
*/
71+
public static void warning(String prefix, String message, boolean stderr) {
72+
PrintStream out = stderr ? System.err : System.out;
73+
out.println(prefix + ": " + message);
5774
}
5875

5976
/**

0 commit comments

Comments
 (0)