8020843: javac crashes on accessibility check with method reference with typevar receiver

Thu, 25 Jul 2013 14:51:40 +0100

author
mcimadamore
date
Thu, 25 Jul 2013 14:51:40 +0100
changeset 1921
dae52d74c1fc
parent 1920
b02f28bf7f1c
child 1922
37048aa3ac19

8020843: javac crashes on accessibility check with method reference with typevar receiver
Summary: method reference overload check doesn't walk through type-variable receivers
Reviewed-by: jjg

src/share/classes/com/sun/tools/javac/comp/Resolve.java file | annotate | diff | comparison | revisions
src/share/classes/com/sun/tools/javac/resources/compiler.properties file | annotate | diff | comparison | revisions
test/tools/javac/diags/examples/ReportAccessFragment.java file | annotate | diff | comparison | revisions
test/tools/javac/lambda/8020843/T8020843a.java file | annotate | diff | comparison | revisions
test/tools/javac/lambda/8020843/T8020843a.out file | annotate | diff | comparison | revisions
test/tools/javac/lambda/8020843/T8020843b.java file | annotate | diff | comparison | revisions
test/tools/javac/lambda/8020843/T8020843b.out file | annotate | diff | comparison | revisions
test/tools/javac/lambda/MethodReference28.out file | annotate | diff | comparison | revisions
     1.1 --- a/src/share/classes/com/sun/tools/javac/comp/Resolve.java	Thu Jul 25 14:49:16 2013 +0100
     1.2 +++ b/src/share/classes/com/sun/tools/javac/comp/Resolve.java	Thu Jul 25 14:51:40 2013 +0100
     1.3 @@ -2649,6 +2649,13 @@
     1.4                                    InferenceContext inferenceContext) {
     1.5          MethodResolutionPhase maxPhase = boxingAllowed ? VARARITY : BASIC;
     1.6  
     1.7 +        if (site.hasTag(TYPEVAR)) {
     1.8 +            return resolveMemberReference(pos, env, referenceTree, site.getUpperBound(),
     1.9 +                    name, argtypes, typeargtypes, boxingAllowed, methodCheck, inferenceContext);
    1.10 +        }
    1.11 +
    1.12 +        site = types.capture(site);
    1.13 +
    1.14          ReferenceLookupHelper boundLookupHelper;
    1.15          if (!name.equals(names.init)) {
    1.16              //method reference
    1.17 @@ -2675,24 +2682,52 @@
    1.18  
    1.19          //merge results
    1.20          Pair<Symbol, ReferenceLookupHelper> res;
    1.21 -        if (!lookupSuccess(unboundSym)) {
    1.22 -            res = new Pair<Symbol, ReferenceLookupHelper>(boundSym, boundLookupHelper);
    1.23 -            env.info.pendingResolutionPhase = boundEnv.info.pendingResolutionPhase;
    1.24 -        } else if (lookupSuccess(boundSym)) {
    1.25 -            res = new Pair<Symbol, ReferenceLookupHelper>(ambiguityError(boundSym, unboundSym), boundLookupHelper);
    1.26 -            env.info.pendingResolutionPhase = boundEnv.info.pendingResolutionPhase;
    1.27 -        } else {
    1.28 -            res = new Pair<Symbol, ReferenceLookupHelper>(unboundSym, unboundLookupHelper);
    1.29 -            env.info.pendingResolutionPhase = unboundEnv.info.pendingResolutionPhase;
    1.30 -        }
    1.31 +        Symbol bestSym = choose(boundSym, unboundSym);
    1.32 +        res = new Pair<Symbol, ReferenceLookupHelper>(bestSym,
    1.33 +                bestSym == unboundSym ? unboundLookupHelper : boundLookupHelper);
    1.34 +        env.info.pendingResolutionPhase = bestSym == unboundSym ?
    1.35 +                unboundEnv.info.pendingResolutionPhase :
    1.36 +                boundEnv.info.pendingResolutionPhase;
    1.37  
    1.38          return res;
    1.39      }
    1.40 -    //private
    1.41 -        boolean lookupSuccess(Symbol s) {
    1.42 +    //where
    1.43 +        private Symbol choose(Symbol s1, Symbol s2) {
    1.44 +            if (lookupSuccess(s1) && lookupSuccess(s2)) {
    1.45 +                return ambiguityError(s1, s2);
    1.46 +            } else if (lookupSuccess(s1) ||
    1.47 +                    (canIgnore(s2) && !canIgnore(s1))) {
    1.48 +                return s1;
    1.49 +            } else if (lookupSuccess(s2) ||
    1.50 +                    (canIgnore(s1) && !canIgnore(s2))) {
    1.51 +                return s2;
    1.52 +            } else {
    1.53 +                return s1;
    1.54 +            }
    1.55 +        }
    1.56 +
    1.57 +        private boolean lookupSuccess(Symbol s) {
    1.58              return s.kind == MTH || s.kind == AMBIGUOUS;
    1.59          }
    1.60  
    1.61 +        private boolean canIgnore(Symbol s) {
    1.62 +            switch (s.kind) {
    1.63 +                case ABSENT_MTH:
    1.64 +                    return true;
    1.65 +                case WRONG_MTH:
    1.66 +                    InapplicableSymbolError errSym =
    1.67 +                            (InapplicableSymbolError)s;
    1.68 +                    return new Template(MethodCheckDiag.ARITY_MISMATCH.regex())
    1.69 +                            .matches(errSym.errCandidate().snd);
    1.70 +                case WRONG_MTHS:
    1.71 +                    InapplicableSymbolsError errSyms =
    1.72 +                            (InapplicableSymbolsError)s;
    1.73 +                    return errSyms.filterCandidates(errSyms.mapCandidates()).isEmpty();
    1.74 +                default:
    1.75 +                    return false;
    1.76 +            }
    1.77 +        }
    1.78 +
    1.79      /**
    1.80       * Helper for defining custom method-like lookup logic; a lookup helper
    1.81       * provides hooks for (i) the actual lookup logic and (ii) accessing the
    1.82 @@ -3504,7 +3539,9 @@
    1.83                  List<Type> argtypes,
    1.84                  List<Type> typeargtypes) {
    1.85              Map<Symbol, JCDiagnostic> candidatesMap = mapCandidates();
    1.86 -            Map<Symbol, JCDiagnostic> filteredCandidates = filterCandidates(candidatesMap);
    1.87 +            Map<Symbol, JCDiagnostic> filteredCandidates = compactMethodDiags ?
    1.88 +                    filterCandidates(candidatesMap) :
    1.89 +                    mapCandidates();
    1.90              if (filteredCandidates.isEmpty()) {
    1.91                  filteredCandidates = candidatesMap;
    1.92              }
    1.93 @@ -3556,8 +3593,7 @@
    1.94                  Map<Symbol, JCDiagnostic> candidates = new LinkedHashMap<Symbol, JCDiagnostic>();
    1.95                  for (Map.Entry<Symbol, JCDiagnostic> _entry : candidatesMap.entrySet()) {
    1.96                      JCDiagnostic d = _entry.getValue();
    1.97 -                    if (!compactMethodDiags ||
    1.98 -                            !new Template(MethodCheckDiag.ARITY_MISMATCH.regex()).matches(d)) {
    1.99 +                    if (!new Template(MethodCheckDiag.ARITY_MISMATCH.regex()).matches(d)) {
   1.100                          candidates.put(_entry.getKey(), d);
   1.101                      }
   1.102                  }
     2.1 --- a/src/share/classes/com/sun/tools/javac/resources/compiler.properties	Thu Jul 25 14:49:16 2013 +0100
     2.2 +++ b/src/share/classes/com/sun/tools/javac/resources/compiler.properties	Thu Jul 25 14:51:40 2013 +0100
     2.3 @@ -905,6 +905,10 @@
     2.4  compiler.err.report.access=\
     2.5      {0} has {1} access in {2}
     2.6  
     2.7 +# 0: symbol, 1: set of modifier, 2: symbol
     2.8 +compiler.misc.report.access=\
     2.9 +    {0} has {1} access in {2}
    2.10 +
    2.11  compiler.err.ret.outside.meth=\
    2.12      return outside method
    2.13  
     3.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     3.2 +++ b/test/tools/javac/diags/examples/ReportAccessFragment.java	Thu Jul 25 14:51:40 2013 +0100
     3.3 @@ -0,0 +1,32 @@
     3.4 +/*
     3.5 + * Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
     3.6 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
     3.7 + *
     3.8 + * This code is free software; you can redistribute it and/or modify it
     3.9 + * under the terms of the GNU General Public License version 2 only, as
    3.10 + * published by the Free Software Foundation.
    3.11 + *
    3.12 + * This code is distributed in the hope that it will be useful, but WITHOUT
    3.13 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
    3.14 + * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
    3.15 + * version 2 for more details (a copy is included in the LICENSE file that
    3.16 + * accompanied this code).
    3.17 + *
    3.18 + * You should have received a copy of the GNU General Public License version
    3.19 + * 2 along with this work; if not, write to the Free Software Foundation,
    3.20 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
    3.21 + *
    3.22 + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
    3.23 + * or visit www.oracle.com if you need additional information or have any
    3.24 + * questions.
    3.25 + */
    3.26 +
    3.27 +// key: compiler.err.prob.found.req
    3.28 +// key: compiler.misc.invalid.mref
    3.29 +// key: compiler.misc.report.access
    3.30 +
    3.31 +class ReportAccessFragment {
    3.32 +    void test(Object o) {
    3.33 +        Runnable r = o::clone;
    3.34 +    }
    3.35 +}
     4.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     4.2 +++ b/test/tools/javac/lambda/8020843/T8020843a.java	Thu Jul 25 14:51:40 2013 +0100
     4.3 @@ -0,0 +1,16 @@
     4.4 +/*
     4.5 + * @test /nodynamiccopyright/
     4.6 + * @bug 8020843
     4.7 + * @summary javac crashes on accessibility check with method reference with typevar receiver
     4.8 + * @compile/fail/ref=T8020843a.out -XDrawDiagnostics T8020843a.java
     4.9 + */
    4.10 +
    4.11 +class T8020843a {
    4.12 +    interface Function<X, Y> {
    4.13 +        Y m(X x);
    4.14 +    }
    4.15 +
    4.16 +    <T> void test(T t) {
    4.17 +        Function<T, Object> ss = T::clone;
    4.18 +    }
    4.19 +}
     5.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     5.2 +++ b/test/tools/javac/lambda/8020843/T8020843a.out	Thu Jul 25 14:51:40 2013 +0100
     5.3 @@ -0,0 +1,2 @@
     5.4 +T8020843a.java:14:34: compiler.err.prob.found.req: (compiler.misc.invalid.mref: kindname.method, (compiler.misc.report.access: clone(), protected, java.lang.Object))
     5.5 +1 error
     6.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     6.2 +++ b/test/tools/javac/lambda/8020843/T8020843b.java	Thu Jul 25 14:51:40 2013 +0100
     6.3 @@ -0,0 +1,27 @@
     6.4 +/*
     6.5 + * @test /nodynamiccopyright/
     6.6 + * @bug 8020843
     6.7 + * @summary javac crashes on accessibility check with method reference with typevar receiver
     6.8 + * @compile/fail/ref=T8020843b.out -XDrawDiagnostics T8020843b.java
     6.9 + */
    6.10 +
    6.11 +class T8020843b {
    6.12 +    interface Function<X, Y> {
    6.13 +        Y m(X x);
    6.14 +    }
    6.15 +
    6.16 +    interface BiFunction<X, Y, Z> {
    6.17 +        Z m(X x, Y y);
    6.18 +    }
    6.19 +
    6.20 +    Object m(int i) { return null; }
    6.21 +    static Object m(String t) { return null; }
    6.22 +
    6.23 +    Object m2(int i) { return null; }
    6.24 +    static Object m2(long t) { return null; }
    6.25 +
    6.26 +    static void test() {
    6.27 +        Function<T8020843b, Object> f1 = T8020843b::m; //show bound case diag
    6.28 +        BiFunction<T8020843b, String, Object> f2 = T8020843b::m2; //show unbound case diag
    6.29 +    }
    6.30 +}
     7.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     7.2 +++ b/test/tools/javac/lambda/8020843/T8020843b.out	Thu Jul 25 14:51:40 2013 +0100
     7.3 @@ -0,0 +1,3 @@
     7.4 +T8020843b.java:24:42: compiler.err.prob.found.req: (compiler.misc.invalid.mref: kindname.method, (compiler.misc.cant.apply.symbols: kindname.method, m, T8020843b,{(compiler.misc.inapplicable.method: kindname.method, T8020843b, m(int), (compiler.misc.no.conforming.assignment.exists: (compiler.misc.inconvertible.types: T8020843b, int))),(compiler.misc.inapplicable.method: kindname.method, T8020843b, m(java.lang.String), (compiler.misc.no.conforming.assignment.exists: (compiler.misc.inconvertible.types: T8020843b, java.lang.String)))}))
     7.5 +T8020843b.java:25:52: compiler.err.prob.found.req: (compiler.misc.invalid.mref: kindname.method, (compiler.misc.cant.apply.symbols: kindname.method, m2, T8020843b,java.lang.String,{(compiler.misc.inapplicable.method: kindname.method, T8020843b, m2(int), (compiler.misc.no.conforming.assignment.exists: (compiler.misc.inconvertible.types: java.lang.String, int))),(compiler.misc.inapplicable.method: kindname.method, T8020843b, m2(long), (compiler.misc.no.conforming.assignment.exists: (compiler.misc.inconvertible.types: java.lang.String, long)))}))
     7.6 +2 errors
     8.1 --- a/test/tools/javac/lambda/MethodReference28.out	Thu Jul 25 14:49:16 2013 +0100
     8.2 +++ b/test/tools/javac/lambda/MethodReference28.out	Thu Jul 25 14:51:40 2013 +0100
     8.3 @@ -9,6 +9,6 @@
     8.4  MethodReference28.java:46:19: compiler.err.prob.found.req: (compiler.misc.invalid.mref: kindname.method, (compiler.misc.cant.apply.symbol: kindname.method, m3, java.lang.String, int, kindname.class, MethodReference28, (compiler.misc.no.conforming.assignment.exists: (compiler.misc.inconvertible.types: int, java.lang.String))))
     8.5  MethodReference28.java:47:19: compiler.err.prob.found.req: (compiler.misc.invalid.mref: kindname.method, (compiler.misc.cant.apply.symbol: kindname.method, m4, java.lang.String[], int, kindname.class, MethodReference28, (compiler.misc.varargs.argument.mismatch: (compiler.misc.inconvertible.types: int, java.lang.String))))
     8.6  MethodReference28.java:52:19: compiler.err.prob.found.req: (compiler.misc.invalid.mref: kindname.method, (compiler.misc.cant.apply.symbol: kindname.method, m2, java.lang.Integer,java.lang.Integer, MethodReference28,int, kindname.class, MethodReference28, (compiler.misc.no.conforming.assignment.exists: (compiler.misc.inconvertible.types: MethodReference28, java.lang.Integer))))
     8.7 -MethodReference28.java:53:19: compiler.err.prob.found.req: (compiler.misc.invalid.mref: kindname.method, (compiler.misc.cant.apply.symbol: kindname.method, m3, java.lang.String, MethodReference28,int, kindname.class, MethodReference28, (compiler.misc.arg.length.mismatch)))
     8.8 +MethodReference28.java:53:19: compiler.err.prob.found.req: (compiler.misc.invalid.mref: kindname.method, (compiler.misc.cant.apply.symbol: kindname.method, m3, java.lang.String, MethodReference28,int, kindname.class, MethodReference28, (compiler.misc.no.conforming.assignment.exists: (compiler.misc.inconvertible.types: int, java.lang.String))))
     8.9  MethodReference28.java:54:19: compiler.err.prob.found.req: (compiler.misc.invalid.mref: kindname.method, (compiler.misc.cant.apply.symbol: kindname.method, m4, java.lang.String[], MethodReference28,int, kindname.class, MethodReference28, (compiler.misc.varargs.argument.mismatch: (compiler.misc.inconvertible.types: MethodReference28, java.lang.String))))
    8.10  13 errors

mercurial