# HG changeset patch # User jlahoda # Date 1484635264 -3600 # Node ID 047a57b0839af83954556c9f80a7c3c3bbd30cd0 # Parent 9d11c46bd7bfdcb61d4b995fb49925e0e13b7149 8172262: packages missing from docs build Summary: Do not return packages without members from Elements.getPackageElement(String), to avoid ambiguities among such packages in multiple modules. Reviewed-by: jjg diff -r 9d11c46bd7bf -r 047a57b0839a langtools/src/jdk.compiler/share/classes/com/sun/tools/javac/model/JavacElements.java --- a/langtools/src/jdk.compiler/share/classes/com/sun/tools/javac/model/JavacElements.java Tue Jan 17 09:17:10 2017 +0530 +++ b/langtools/src/jdk.compiler/share/classes/com/sun/tools/javac/model/JavacElements.java Tue Jan 17 07:41:04 2017 +0100 @@ -25,9 +25,11 @@ package com.sun.tools.javac.model; +import java.util.HashSet; import java.util.LinkedHashSet; import java.util.Map; import java.util.Set; +import java.util.stream.Collectors; import javax.lang.model.AnnotatedConstruct; import javax.lang.model.SourceVersion; @@ -67,6 +69,7 @@ import com.sun.tools.javac.comp.Modules; import com.sun.tools.javac.comp.Resolve; import com.sun.tools.javac.comp.Resolve.RecoveryLoadClass; +import com.sun.tools.javac.resources.CompilerProperties.Notes; import static com.sun.tools.javac.tree.JCTree.Tag.*; /** @@ -87,6 +90,8 @@ private final Enter enter; private final Resolve resolve; private final JavacTaskImpl javacTaskImpl; + private final Log log; + private final boolean allowModules; public static JavacElements instance(Context context) { JavacElements instance = context.get(JavacElements.class); @@ -106,6 +111,9 @@ resolve = Resolve.instance(context); JavacTask t = context.get(JavacTask.class); javacTaskImpl = t instanceof JavacTaskImpl ? (JavacTaskImpl) t : null; + log = Log.instance(context); + Source source = Source.instance(context); + allowModules = source.allowModules(); } @Override @DefinedBy(Api.LANGUAGE_MODEL) @@ -134,7 +142,7 @@ ensureEntered("getPackageElement"); if (name.length() == 0) return syms.unnamedModule.unnamedPackage; - return doGetElement(module, name, PackageSymbol.class); + return doGetElement(module, "getPackageElement", name, PackageSymbol.class); } @Override @DefinedBy(Api.LANGUAGE_MODEL) @@ -151,22 +159,27 @@ private ClassSymbol doGetTypeElement(ModuleElement module, CharSequence name) { ensureEntered("getTypeElement"); - return doGetElement(module, name, ClassSymbol.class); + return doGetElement(module, "getTypeElement", name, ClassSymbol.class); } - private S doGetElement(ModuleElement module, CharSequence name, Class clazz) { + private S doGetElement(ModuleElement module, String methodName, + CharSequence name, Class clazz) { String strName = name.toString(); if (!SourceVersion.isName(strName)) { return null; } if (module == null) { - return unboundNameToSymbol(strName, clazz); + return unboundNameToSymbol(methodName, strName, clazz); } else { return nameToSymbol((ModuleSymbol) module, strName, clazz); } } - private S unboundNameToSymbol(String nameStr, Class clazz) { + private final Set alreadyWarnedDuplicates = new HashSet<>(); + + private S unboundNameToSymbol(String methodName, + String nameStr, + Class clazz) { if (modules.getDefaultModule() == syms.noModule) { //not a modular mode: return nameToSymbol(syms.noModule, nameStr, clazz); } @@ -179,12 +192,25 @@ S sym = nameToSymbol(msym, nameStr, clazz); if (sym != null) { - found.add(sym); + if (!allowModules || clazz == ClassSymbol.class || !sym.members().isEmpty()) { + //do not add packages without members: + found.add(sym); + } } } if (found.size() == 1) { return found.iterator().next(); + } else if (found.size() > 1) { + //more than one element found, produce a note: + if (alreadyWarnedDuplicates.add(methodName + ":" + nameStr)) { + String moduleNames = found.stream() + .map(s -> s.packge().modle) + .map(m -> m.toString()) + .collect(Collectors.joining(", ")); + log.note(Notes.MultipleElements(methodName, nameStr, moduleNames)); + } + return null; } else { //not found, or more than one element found: return null; diff -r 9d11c46bd7bf -r 047a57b0839a langtools/src/jdk.compiler/share/classes/com/sun/tools/javac/resources/compiler.properties --- a/langtools/src/jdk.compiler/share/classes/com/sun/tools/javac/resources/compiler.properties Tue Jan 17 09:17:10 2017 +0530 +++ b/langtools/src/jdk.compiler/share/classes/com/sun/tools/javac/resources/compiler.properties Tue Jan 17 07:41:04 2017 +0100 @@ -1,5 +1,5 @@ # -# Copyright (c) 1999, 2016, Oracle and/or its affiliates. All rights reserved. +# Copyright (c) 1999, 2017, Oracle and/or its affiliates. All rights reserved. # DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. # # This code is free software; you can redistribute it and/or modify it @@ -1436,6 +1436,10 @@ compiler.note.proc.messager=\ {0} +# 0: string, 1: string, 2: string +compiler.note.multiple.elements=\ + Multiple elements named '{1}' in modules '{2}' were found by javax.lang.model.util.Elements.{0}. + ##### # 0: number diff -r 9d11c46bd7bf -r 047a57b0839a langtools/test/tools/javac/diags/examples.not-yet.txt --- a/langtools/test/tools/javac/diags/examples.not-yet.txt Tue Jan 17 09:17:10 2017 +0530 +++ b/langtools/test/tools/javac/diags/examples.not-yet.txt Tue Jan 17 07:41:04 2017 +0100 @@ -120,6 +120,7 @@ compiler.misc.bad.const.pool.entry # constant pool entry has wrong type compiler.warn.access.to.member.from.serializable.lambda # in order to generate it we need to modify a restricted package compiler.warn.invalid.path # this warning is generated only in Windows systems +compiler.note.multiple.elements # needs user code # The following module-related messages will have to stay on the not-yet list for various reasons: compiler.warn.locn.unknown.file.on.module.path # Never issued ATM (short circuited with an if (false)) diff -r 9d11c46bd7bf -r 047a57b0839a langtools/test/tools/javac/modules/AnnotationProcessing.java --- a/langtools/test/tools/javac/modules/AnnotationProcessing.java Tue Jan 17 09:17:10 2017 +0530 +++ b/langtools/test/tools/javac/modules/AnnotationProcessing.java Tue Jan 17 07:41:04 2017 +0100 @@ -1,5 +1,5 @@ /* - * Copyright (c) 2015, 2016, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2015, 2017, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -23,7 +23,7 @@ /** * @test - * @bug 8133884 8162711 8133896 8172158 + * @bug 8133884 8162711 8133896 8172158 8172262 * @summary Verify that annotation processing works. * @library /tools/lib * @modules @@ -50,6 +50,7 @@ import java.util.Set; import java.util.concurrent.Callable; import java.util.function.Function; +import java.util.regex.Pattern; import java.util.stream.Collectors; import javax.annotation.processing.AbstractProcessor; @@ -1067,24 +1068,43 @@ "package impl1; public class Impl { }", "package impl.conflict.module; class Impl { }", "package impl.conflict.clazz; public class pkg { public static class I { } }", - "package impl.conflict.src; public class Impl { }"); + "package impl.conflict.src; public class Impl { }", + "package nested.pack.pack; public class Impl { }", + "package unique.nested; public class Impl { }"); tb.writeJavaFiles(m2, "module m2x { }", "package impl2; public class Impl { }", "package impl.conflict.module; class Impl { }", - "package impl.conflict; public class clazz { public static class pkg { } }"); + "package impl.conflict; public class clazz { public static class pkg { } }", + "package nested.pack; public class Impl { }"); //from source: - new JavacTask(tb) + String log = new JavacTask(tb) .options("--module-source-path", moduleSrc.toString(), "--source-path", src.toString(), "-processorpath", System.getProperty("test.class.path"), - "-processor", UnboundLookup.class.getName()) + "-processor", UnboundLookup.class.getName(), + "-XDrawDiagnostics") .outdir(classes) .files(findJavaFiles(moduleSrc)) .run() - .writeAll(); + .writeAll() + .getOutput(OutputKind.DIRECT); + + String moduleImplConflictString = + "- compiler.note.multiple.elements: getTypeElement, impl.conflict.module.Impl, m2x, m1x"; + String srcConflictString = + "- compiler.note.multiple.elements: getTypeElement, impl.conflict.src.Impl, m1x, unnamed module"; + + if (!log.contains(moduleImplConflictString) || + !log.contains(srcConflictString)) { + throw new AssertionError("Expected output not found: " + log); + } + + if (log.split(Pattern.quote(moduleImplConflictString)).length > 2) { + throw new AssertionError("Too many warnings in: " + log); + } new JavacTask(tb) .options("--source-path", src.toString()) @@ -1130,11 +1150,17 @@ assertTypeElementExists("impl.conflict.clazz", "m2x"); assertPackageElementExists("impl.conflict.clazz", "m1x"); assertPackageElementExists("impl2", "m2x"); + assertPackageElementExists("nested.pack.pack", "m1x"); + assertPackageElementExists("nested.pack", "m2x"); + assertTypeElementExists("unique.nested.Impl", "m1x"); assertTypeElementNotFound("impl.conflict.module.Impl"); + assertTypeElementNotFound("impl.conflict.module.Impl"); //check that the warning/note is produced only once assertPackageElementNotFound("impl.conflict.module"); assertTypeElementNotFound("impl.conflict.src.Impl"); assertPackageElementNotFound("impl.conflict.src"); assertTypeElementNotFound("impl.conflict.clazz.pkg"); + assertPackageElementNotFound("unique"); //do not return packages without members in module mode + assertTypeElementNotFound("nested"); //cannot distinguish between m1x and m2x return false; }