src/share/classes/com/sun/tools/javac/comp/Check.java

changeset 746
a7ea58fa3e9a
parent 700
7b413ac1a720
child 780
1d625fbe6c22
equal deleted inserted replaced
745:4328728e0409 746:a7ea58fa3e9a
1508 1508
1509 public boolean checkCompatibleAbstracts(DiagnosticPosition pos, 1509 public boolean checkCompatibleAbstracts(DiagnosticPosition pos,
1510 Type t1, 1510 Type t1,
1511 Type t2, 1511 Type t2,
1512 Type site) { 1512 Type site) {
1513 Symbol sym = firstIncompatibility(t1, t2, site); 1513 return firstIncompatibility(pos, t1, t2, site) == null;
1514 if (sym != null) {
1515 log.error(pos, "types.incompatible.diff.ret",
1516 t1, t2, sym.name +
1517 "(" + types.memberType(t2, sym).getParameterTypes() + ")");
1518 return false;
1519 }
1520 return true;
1521 } 1514 }
1522 1515
1523 /** Return the first method which is defined with same args 1516 /** Return the first method which is defined with same args
1524 * but different return types in two given interfaces, or null if none 1517 * but different return types in two given interfaces, or null if none
1525 * exists. 1518 * exists.
1526 * @param t1 The first type. 1519 * @param t1 The first type.
1527 * @param t2 The second type. 1520 * @param t2 The second type.
1528 * @param site The most derived type. 1521 * @param site The most derived type.
1529 * @returns symbol from t2 that conflicts with one in t1. 1522 * @returns symbol from t2 that conflicts with one in t1.
1530 */ 1523 */
1531 private Symbol firstIncompatibility(Type t1, Type t2, Type site) { 1524 private Symbol firstIncompatibility(DiagnosticPosition pos, Type t1, Type t2, Type site) {
1532 Map<TypeSymbol,Type> interfaces1 = new HashMap<TypeSymbol,Type>(); 1525 Map<TypeSymbol,Type> interfaces1 = new HashMap<TypeSymbol,Type>();
1533 closure(t1, interfaces1); 1526 closure(t1, interfaces1);
1534 Map<TypeSymbol,Type> interfaces2; 1527 Map<TypeSymbol,Type> interfaces2;
1535 if (t1 == t2) 1528 if (t1 == t2)
1536 interfaces2 = interfaces1; 1529 interfaces2 = interfaces1;
1537 else 1530 else
1538 closure(t2, interfaces1, interfaces2 = new HashMap<TypeSymbol,Type>()); 1531 closure(t2, interfaces1, interfaces2 = new HashMap<TypeSymbol,Type>());
1539 1532
1540 for (Type t3 : interfaces1.values()) { 1533 for (Type t3 : interfaces1.values()) {
1541 for (Type t4 : interfaces2.values()) { 1534 for (Type t4 : interfaces2.values()) {
1542 Symbol s = firstDirectIncompatibility(t3, t4, site); 1535 Symbol s = firstDirectIncompatibility(pos, t3, t4, site);
1543 if (s != null) return s; 1536 if (s != null) return s;
1544 } 1537 }
1545 } 1538 }
1546 return null; 1539 return null;
1547 } 1540 }
1566 closure(i, typesSkip, typeMap); 1559 closure(i, typesSkip, typeMap);
1567 } 1560 }
1568 } 1561 }
1569 1562
1570 /** Return the first method in t2 that conflicts with a method from t1. */ 1563 /** Return the first method in t2 that conflicts with a method from t1. */
1571 private Symbol firstDirectIncompatibility(Type t1, Type t2, Type site) { 1564 private Symbol firstDirectIncompatibility(DiagnosticPosition pos, Type t1, Type t2, Type site) {
1572 for (Scope.Entry e1 = t1.tsym.members().elems; e1 != null; e1 = e1.sibling) { 1565 for (Scope.Entry e1 = t1.tsym.members().elems; e1 != null; e1 = e1.sibling) {
1573 Symbol s1 = e1.sym; 1566 Symbol s1 = e1.sym;
1574 Type st1 = null; 1567 Type st1 = null;
1575 if (s1.kind != MTH || !s1.isInheritedIn(site.tsym, types)) continue; 1568 if (s1.kind != MTH || !s1.isInheritedIn(site.tsym, types)) continue;
1576 Symbol impl = ((MethodSymbol)s1).implementation(site.tsym, types, false); 1569 Symbol impl = ((MethodSymbol)s1).implementation(site.tsym, types, false);
1590 types.isSameType(rt1, rt2) || 1583 types.isSameType(rt1, rt2) ||
1591 rt1.tag >= CLASS && rt2.tag >= CLASS && 1584 rt1.tag >= CLASS && rt2.tag >= CLASS &&
1592 (types.covariantReturnType(rt1, rt2, Warner.noWarnings) || 1585 (types.covariantReturnType(rt1, rt2, Warner.noWarnings) ||
1593 types.covariantReturnType(rt2, rt1, Warner.noWarnings)) || 1586 types.covariantReturnType(rt2, rt1, Warner.noWarnings)) ||
1594 checkCommonOverriderIn(s1,s2,site); 1587 checkCommonOverriderIn(s1,s2,site);
1595 if (!compat) return s2; 1588 if (!compat) {
1589 log.error(pos, "types.incompatible.diff.ret",
1590 t1, t2, s2.name +
1591 "(" + types.memberType(t2, s2).getParameterTypes() + ")");
1592 return s2;
1593 }
1594 } else if (!checkNameClash((ClassSymbol)site.tsym, s1, s2)) {
1595 log.error(pos,
1596 "name.clash.same.erasure.no.override",
1597 s1, s1.location(),
1598 s2, s2.location());
1599 return s2;
1596 } 1600 }
1597 } 1601 }
1598 } 1602 }
1599 return null; 1603 return null;
1600 } 1604 }
1642 if ((origin.flags() & ENUM) != 0 && names.finalize.equals(m.name)) 1646 if ((origin.flags() & ENUM) != 0 && names.finalize.equals(m.name))
1643 if (m.overrides(syms.enumFinalFinalize, origin, types, false)) { 1647 if (m.overrides(syms.enumFinalFinalize, origin, types, false)) {
1644 log.error(tree.pos(), "enum.no.finalize"); 1648 log.error(tree.pos(), "enum.no.finalize");
1645 return; 1649 return;
1646 } 1650 }
1647 for (Type t = types.supertype(origin.type); t.tag == CLASS; 1651 for (Type t = origin.type; t.tag == CLASS;
1648 t = types.supertype(t)) { 1652 t = types.supertype(t)) {
1649 TypeSymbol c = t.tsym; 1653 if (t != origin.type) {
1650 Scope.Entry e = c.members().lookup(m.name); 1654 checkOverride(tree, t, origin, m);
1651 while (e.scope != null) { 1655 }
1652 if (m.overrides(e.sym, origin, types, false)) 1656 for (Type t2 : types.interfaces(t)) {
1657 checkOverride(tree, t2, origin, m);
1658 }
1659 }
1660 }
1661
1662 void checkOverride(JCTree tree, Type site, ClassSymbol origin, MethodSymbol m) {
1663 TypeSymbol c = site.tsym;
1664 Scope.Entry e = c.members().lookup(m.name);
1665 while (e.scope != null) {
1666 if (m.overrides(e.sym, origin, types, false)) {
1667 if ((e.sym.flags() & ABSTRACT) == 0) {
1653 checkOverride(tree, m, (MethodSymbol)e.sym, origin); 1668 checkOverride(tree, m, (MethodSymbol)e.sym, origin);
1654 else if (e.sym.kind == MTH && 1669 }
1655 e.sym.isInheritedIn(origin, types) && 1670 }
1656 (e.sym.flags() & SYNTHETIC) == 0 && 1671 else if (!checkNameClash(origin, e.sym, m)) {
1657 !m.isConstructor()) { 1672 log.error(tree,
1658 Type er1 = m.erasure(types); 1673 "name.clash.same.erasure.no.override",
1659 Type er2 = e.sym.erasure(types); 1674 m, m.location(),
1660 if (types.isSameTypes(er1.getParameterTypes(), 1675 e.sym, e.sym.location());
1661 er2.getParameterTypes())) { 1676 }
1662 log.error(TreeInfo.diagnosticPositionFor(m, tree), 1677 e = e.next();
1663 "name.clash.same.erasure.no.override", 1678 }
1664 m, m.location(), 1679 }
1665 e.sym, e.sym.location()); 1680
1666 } 1681 private boolean checkNameClash(ClassSymbol origin, Symbol s1, Symbol s2) {
1667 } 1682 if (s1.kind == MTH &&
1668 e = e.next(); 1683 s1.isInheritedIn(origin, types) &&
1669 } 1684 (s1.flags() & SYNTHETIC) == 0 &&
1670 } 1685 !s2.isConstructor()) {
1671 } 1686 Type er1 = s2.erasure(types);
1687 Type er2 = s1.erasure(types);
1688 if (types.isSameTypes(er1.getParameterTypes(),
1689 er2.getParameterTypes())) {
1690 return false;
1691 }
1692 }
1693 return true;
1694 }
1695
1672 1696
1673 /** Check that all abstract members of given class have definitions. 1697 /** Check that all abstract members of given class have definitions.
1674 * @param pos Position to be used for error reporting. 1698 * @param pos Position to be used for error reporting.
1675 * @param c The class. 1699 * @param c The class.
1676 */ 1700 */

mercurial