< prev index next >

src/jdk.compiler/share/classes/com/sun/tools/javac/comp/Attr.java

Print this page

 167         Options options = Options.instance(context);
 168 
 169         Source source = Source.instance(context);
 170         allowReifiableTypesInInstanceof = Feature.REIFIABLE_TYPES_INSTANCEOF.allowedInSource(source);
 171         allowRecords = Feature.RECORDS.allowedInSource(source);
 172         allowPatternSwitch = (preview.isEnabled() || !preview.isPreview(Feature.PATTERN_SWITCH)) &&
 173                              Feature.PATTERN_SWITCH.allowedInSource(source);
 174         allowUnconditionalPatternsInstanceOf =
 175                              Feature.UNCONDITIONAL_PATTERN_IN_INSTANCEOF.allowedInSource(source);
 176         sourceName = source.name;
 177         useBeforeDeclarationWarning = options.isSet("useBeforeDeclarationWarning");
 178 
 179         statInfo = new ResultInfo(KindSelector.NIL, Type.noType);
 180         varAssignmentInfo = new ResultInfo(KindSelector.ASG, Type.noType);
 181         unknownExprInfo = new ResultInfo(KindSelector.VAL, Type.noType);
 182         methodAttrInfo = new MethodAttrInfo();
 183         unknownTypeInfo = new ResultInfo(KindSelector.TYP, Type.noType);
 184         unknownTypeExprInfo = new ResultInfo(KindSelector.VAL_TYP, Type.noType);
 185         recoveryInfo = new RecoveryInfo(deferredAttr.emptyDeferredAttrContext);
 186         initBlockType = new MethodType(List.nil(), syms.voidType, List.nil(), syms.methodClass);


 187     }
 188 
 189     /** Switch: reifiable types in instanceof enabled?
 190      */
 191     boolean allowReifiableTypesInInstanceof;
 192 
 193     /** Are records allowed
 194      */
 195     private final boolean allowRecords;
 196 
 197     /** Are patterns in switch allowed
 198      */
 199     private final boolean allowPatternSwitch;
 200 
 201     /** Are unconditional patterns in instanceof allowed
 202      */
 203     private final boolean allowUnconditionalPatternsInstanceOf;
 204 




 205     /**
 206      * Switch: warn about use of variable before declaration?
 207      * RFE: 6425594
 208      */
 209     boolean useBeforeDeclarationWarning;
 210 
 211     /**
 212      * Switch: name of source level; used for error reporting.
 213      */
 214     String sourceName;
 215 
 216     /** Check kind and type of given tree against protokind and prototype.
 217      *  If check succeeds, store type in tree and return it.
 218      *  If check fails, store errType in tree and return it.
 219      *  No checks are performed if the prototype is a method type.
 220      *  It is not necessary in this case since we know that kind and type
 221      *  are correct.
 222      *
 223      *  @param tree     The tree whose kind and type is checked
 224      *  @param found    The computed type of the tree

1103                          *     - have an accessibility stricter than that of the record type
1104                          *     - explicitly invoke any other constructor
1105                          */
1106                         if ((tree.sym.flags_field & GENERATEDCONSTR) == 0) {
1107                             if (Check.protection(m.flags()) > Check.protection(env.enclClass.sym.flags())) {
1108                                 log.error(tree,
1109                                         (env.enclClass.sym.flags() & AccessFlags) == 0 ?
1110                                             Errors.InvalidCanonicalConstructorInRecord(
1111                                                 Fragments.Canonical,
1112                                                 env.enclClass.sym.name,
1113                                                 Fragments.CanonicalMustNotHaveStrongerAccess("package")
1114                                             ) :
1115                                             Errors.InvalidCanonicalConstructorInRecord(
1116                                                     Fragments.Canonical,
1117                                                     env.enclClass.sym.name,
1118                                                     Fragments.CanonicalMustNotHaveStrongerAccess(asFlagSet(env.enclClass.sym.flags() & AccessFlags))
1119                                             )
1120                                 );
1121                             }
1122 
1123                             if (TreeInfo.hasAnyConstructorCall(tree)) {
1124                                 log.error(tree, Errors.InvalidCanonicalConstructorInRecord(
1125                                         Fragments.Canonical, env.enclClass.sym.name,
1126                                         Fragments.CanonicalMustNotContainExplicitConstructorInvocation));
1127                             }
1128                         }
1129 
1130                         // also we want to check that no type variables have been defined
1131                         if (!tree.typarams.isEmpty()) {
1132                             log.error(tree, Errors.InvalidCanonicalConstructorInRecord(
1133                                     Fragments.Canonical, env.enclClass.sym.name, Fragments.CanonicalMustNotDeclareTypeVariables));
1134                         }
1135 
1136                         /* and now we need to check that the constructor's arguments are exactly the same as those of the
1137                          * record components
1138                          */
1139                         List<? extends RecordComponent> recordComponents = env.enclClass.sym.getRecordComponents();
1140                         List<Type> recordFieldTypes = TreeInfo.recordFields(env.enclClass).map(vd -> vd.sym.type);
1141                         for (JCVariableDecl param: tree.params) {
1142                             boolean paramIsVarArgs = (param.sym.flags_field & VARARGS) != 0;
1143                             if (!types.isSameType(param.type, recordFieldTypes.head) ||

1185                 }
1186                 if (isDefaultMethod || (tree.sym.flags() & (ABSTRACT | NATIVE)) == 0)
1187                     log.error(tree.pos(), Errors.MissingMethBodyOrDeclAbstract);
1188             } else {
1189                 if ((tree.sym.flags() & (ABSTRACT|DEFAULT|PRIVATE)) == ABSTRACT) {
1190                     if ((owner.flags() & INTERFACE) != 0) {
1191                         log.error(tree.body.pos(), Errors.IntfMethCantHaveBody);
1192                     } else {
1193                         log.error(tree.pos(), Errors.AbstractMethCantHaveBody);
1194                     }
1195                 } else if ((tree.mods.flags & NATIVE) != 0) {
1196                     log.error(tree.pos(), Errors.NativeMethCantHaveBody);
1197                 }
1198                 // Add an implicit super() call unless an explicit call to
1199                 // super(...) or this(...) is given
1200                 // or we are compiling class java.lang.Object.
1201                 if (isConstructor && owner.type != syms.objectType) {
1202                     if (!TreeInfo.hasAnyConstructorCall(tree)) {
1203                         JCStatement supCall = make.at(tree.body.pos).Exec(make.Apply(List.nil(),
1204                                 make.Ident(names._super), make.Idents(List.nil())));
1205                         tree.body.stats = tree.body.stats.prepend(supCall);




1206                     } else if ((env.enclClass.sym.flags() & ENUM) != 0 &&
1207                             (tree.mods.flags & GENERATEDCONSTR) == 0 &&
1208                             TreeInfo.hasConstructorCall(tree, names._super)) {
1209                         // enum constructors are not allowed to call super
1210                         // directly, so make sure there aren't any super calls
1211                         // in enum constructors, except in the compiler
1212                         // generated one.
1213                         log.error(tree.body.stats.head.pos(),
1214                                   Errors.CallToSuperNotAllowedInEnumCtor(env.enclClass.sym));
1215                     }
1216                     if (env.enclClass.sym.isRecord() && (tree.sym.flags_field & RECORD) != 0) { // we are seeing the canonical constructor
1217                         List<Name> recordComponentNames = TreeInfo.recordFields(env.enclClass).map(vd -> vd.sym.name);
1218                         List<Name> initParamNames = tree.sym.params.map(p -> p.name);
1219                         if (!initParamNames.equals(recordComponentNames)) {
1220                             log.error(tree, Errors.InvalidCanonicalConstructorInRecord(
1221                                     Fragments.Canonical, env.enclClass.sym.name, Fragments.CanonicalWithNameMismatch));
1222                         }
1223                         if (tree.sym.type.asMethodType().thrown != null && !tree.sym.type.asMethodType().thrown.isEmpty()) {
1224                             log.error(tree,
1225                                     Errors.InvalidCanonicalConstructorInRecord(

1295         chk.validate(tree.vartype, env, !isImplicitLambdaParameter && !tree.isImplicitlyTyped());
1296 
1297         try {
1298             v.getConstValue(); // ensure compile-time constant initializer is evaluated
1299             deferredLintHandler.flush(tree, lint);
1300             chk.checkDeprecatedAnnotation(tree.pos(), v);
1301 
1302             if (tree.init != null) {
1303                 if ((v.flags_field & FINAL) == 0 ||
1304                     !memberEnter.needsLazyConstValue(tree.init)) {
1305                     // Not a compile-time constant
1306                     // Attribute initializer in a new environment
1307                     // with the declared variable as owner.
1308                     // Check that initializer conforms to variable's declared type.
1309                     Env<AttrContext> initEnv = memberEnter.initEnv(tree, env);
1310                     initEnv.info.lint = lint;
1311                     // In order to catch self-references, we set the variable's
1312                     // declaration position to maximal possible value, effectively
1313                     // marking the variable as undefined.
1314                     initEnv.info.enclVar = v;
1315                     attribExpr(tree.init, initEnv, v.type);
1316                     if (tree.isImplicitlyTyped()) {
1317                         //fixup local variable type
1318                         v.type = chk.checkLocalVarType(tree, tree.init.type, tree.name);









1319                     }
1320                 }
1321                 if (tree.isImplicitlyTyped()) {
1322                     setSyntheticVariableType(tree, v.type);
1323                 }
1324             }
1325             result = tree.type = v.type;
1326             if (env.enclClass.sym.isRecord() && tree.sym.owner.kind == TYP && !v.isStatic()) {
1327                 if (isNonArgsMethodInObject(v.name)) {
1328                     log.error(tree, Errors.IllegalRecordComponentName(v));
1329                 }
1330             }
1331         }
1332         finally {
1333             chk.setLint(prevLint);
1334         }
1335     }
1336 
1337     private void doQueueScanTreeAndTypeAnnotateForVarInit(JCVariableDecl tree, Env<AttrContext> env) {
1338         if (tree.init != null &&

1418             }
1419         }
1420     }
1421 
1422     public void visitSkip(JCSkip tree) {
1423         result = null;
1424     }
1425 
1426     public void visitBlock(JCBlock tree) {
1427         if (env.info.scope.owner.kind == TYP || env.info.scope.owner.kind == ERR) {
1428             // Block is a static or instance initializer;
1429             // let the owner of the environment be a freshly
1430             // created BLOCK-method.
1431             Symbol fakeOwner =
1432                 new MethodSymbol(tree.flags | BLOCK |
1433                     env.info.scope.owner.flags() & STRICTFP, names.empty, initBlockType,
1434                     env.info.scope.owner);
1435             final Env<AttrContext> localEnv =
1436                 env.dup(tree, env.info.dup(env.info.scope.dupUnshared(fakeOwner)));
1437 
1438             if ((tree.flags & STATIC) != 0) localEnv.info.staticLevel++;




1439             // Attribute all type annotations in the block
1440             annotate.queueScanTreeAndTypeAnnotate(tree, localEnv, localEnv.info.scope.owner, null);
1441             annotate.flush();
1442             attribStats(tree.stats, localEnv);
1443 
1444             {
1445                 // Store init and clinit type annotations with the ClassSymbol
1446                 // to allow output in Gen.normalizeDefs.
1447                 ClassSymbol cs = (ClassSymbol)env.info.scope.owner;
1448                 List<Attribute.TypeCompound> tas = localEnv.info.scope.owner.getRawTypeAttributes();
1449                 if ((tree.flags & STATIC) != 0) {
1450                     cs.appendClassInitTypeAttributes(tas);
1451                 } else {
1452                     cs.appendInitTypeAttributes(tas);
1453                 }
1454             }
1455         } else {
1456             // Create a new local environment with a local scope.
1457             Env<AttrContext> localEnv =
1458                 env.dup(tree, env.info.dup(env.info.scope.dup()));

1927     // where
1928     /** Return the selected enumeration constant symbol, or null. */
1929     private Symbol enumConstant(JCTree tree, Type enumType) {
1930         if (tree.hasTag(IDENT)) {
1931             JCIdent ident = (JCIdent)tree;
1932             Name name = ident.name;
1933             for (Symbol sym : enumType.tsym.members().getSymbolsByName(name)) {
1934                 if (sym.kind == VAR) {
1935                     Symbol s = ident.sym = sym;
1936                     ((VarSymbol)s).getConstValue(); // ensure initializer is evaluated
1937                     ident.type = s.type;
1938                     return ((s.flags_field & Flags.ENUM) == 0)
1939                         ? null : s;
1940                 }
1941             }
1942         }
1943         return null;
1944     }
1945 
1946     public void visitSynchronized(JCSynchronized tree) {
1947         chk.checkRefType(tree.pos(), attribExpr(tree.lock, env));
1948         if (isValueBased(tree.lock.type)) {
1949             env.info.lint.logIfEnabled(tree.pos(), LintWarnings.AttemptToSynchronizeOnInstanceOfValueBasedClass);
1950         }
1951         attribStat(tree.body, env);
1952         result = null;
1953     }
1954         // where
1955         private boolean isValueBased(Type t) {
1956             return t != null && t.tsym != null && (t.tsym.flags() & VALUE_BASED) != 0;
1957         }
1958 
1959 
1960     public void visitTry(JCTry tree) {
1961         // Create a new local environment with a local
1962         Env<AttrContext> localEnv = env.dup(tree, env.info.dup(env.info.scope.dup()));
1963         try {
1964             boolean isTryWithResource = tree.resources.nonEmpty();
1965             // Create a nested environment for attributing the try block if needed
1966             Env<AttrContext> tryEnv = isTryWithResource ?
1967                 env.dup(tree, localEnv.info.dup(localEnv.info.scope.dup())) :
1968                 localEnv;
1969             try {
1970                 // Attribute resource declarations
1971                 for (JCTree resource : tree.resources) {
1972                     CheckContext twrContext = new Check.NestedCheckContext(resultInfo.checkContext) {
1973                         @Override
1974                         public void report(DiagnosticPosition pos, JCDiagnostic details) {
1975                             chk.basicHandler.report(pos, diags.fragment(Fragments.TryNotApplicableToType(details)));
1976                         }
1977                     };
1978                     ResultInfo twrResult =
1979                         new ResultInfo(KindSelector.VAR,

4372     }
4373 
4374     public void visitSelect(JCFieldAccess tree) {
4375         // Determine the expected kind of the qualifier expression.
4376         KindSelector skind = KindSelector.NIL;
4377         if (tree.name == names._this || tree.name == names._super ||
4378                 tree.name == names._class)
4379         {
4380             skind = KindSelector.TYP;
4381         } else {
4382             if (pkind().contains(KindSelector.PCK))
4383                 skind = KindSelector.of(skind, KindSelector.PCK);
4384             if (pkind().contains(KindSelector.TYP))
4385                 skind = KindSelector.of(skind, KindSelector.TYP, KindSelector.PCK);
4386             if (pkind().contains(KindSelector.VAL_MTH))
4387                 skind = KindSelector.of(skind, KindSelector.VAL, KindSelector.TYP);
4388         }
4389 
4390         // Attribute the qualifier expression, and determine its symbol (if any).
4391         Type site = attribTree(tree.selected, env, new ResultInfo(skind, Type.noType));

4392         if (!pkind().contains(KindSelector.TYP_PCK))
4393             site = capture(site); // Capture field access
4394 
4395         // don't allow T.class T[].class, etc
4396         if (skind == KindSelector.TYP) {
4397             Type elt = site;
4398             while (elt.hasTag(ARRAY))
4399                 elt = ((ArrayType)elt).elemtype;
4400             if (elt.hasTag(TYPEVAR)) {
4401                 log.error(tree.pos(), Errors.TypeVarCantBeDeref);
4402                 result = tree.type = types.createErrorType(tree.name, site.tsym, site);
4403                 tree.sym = tree.type.tsym;
4404                 return ;
4405             }
4406         }
4407 
4408         // If qualifier symbol is a type or `super', assert `selectSuper'
4409         // for the selection. This is relevant for determining whether
4410         // protected symbols are accessible.
4411         Symbol sitesym = TreeInfo.symbol(tree.selected);

5470                                                       .filter(s -> s.tsym.isSealed())
5471                                                       .map(s -> (ClassSymbol) s.tsym)
5472                                                       .collect(List.collector());
5473 
5474                 if (sealedSupers.isEmpty()) {
5475                     if ((c.flags_field & Flags.NON_SEALED) != 0) {
5476                         boolean hasErrorSuper = false;
5477 
5478                         hasErrorSuper |= types.directSupertypes(c.type)
5479                                               .stream()
5480                                               .anyMatch(s -> s.tsym.kind == Kind.ERR);
5481 
5482                         ClassType ct = (ClassType) c.type;
5483 
5484                         hasErrorSuper |= !ct.isCompound() && ct.interfaces_field != ct.all_interfaces_field;
5485 
5486                         if (!hasErrorSuper) {
5487                             log.error(TreeInfo.diagnosticPositionFor(c, env.tree), Errors.NonSealedWithNoSealedSupertype(c));
5488                         }
5489                     }
5490                 } else {
5491                     if (c.isDirectlyOrIndirectlyLocal() && !c.isEnum()) {
5492                         log.error(TreeInfo.diagnosticPositionFor(c, env.tree), Errors.LocalClassesCantExtendSealed(c.isAnonymous() ? Fragments.Anonymous : Fragments.Local));
5493                     }
5494 
5495                     if (!c.type.isCompound()) {
5496                         for (ClassSymbol supertypeSym : sealedSupers) {
5497                             if (!supertypeSym.isPermittedSubclass(c.type.tsym)) {
5498                                 log.error(TreeInfo.diagnosticPositionFor(c.type.tsym, env.tree), Errors.CantInheritFromSealed(supertypeSym));
5499                             }
5500                         }
5501                         if (!c.isNonSealed() && !c.isFinal() && !c.isSealed()) {
5502                             log.error(TreeInfo.diagnosticPositionFor(c, env.tree),
5503                                     c.isInterface() ?
5504                                             Errors.NonSealedOrSealedExpected :
5505                                             Errors.NonSealedSealedOrFinalExpected);
5506                         }
5507                     }
5508                 }
5509 
5510                 deferredLintHandler.flush(env.tree, env.info.lint);
5511                 env.info.returnResult = null;
5512                 // java.lang.Enum may not be subclassed by a non-enum
5513                 if (st.tsym == syms.enumSym &&
5514                     ((c.flags_field & (Flags.ENUM|Flags.COMPOUND)) == 0))
5515                     log.error(env.tree.pos(), Errors.EnumNoSubclassing);
5516 
5517                 // Enums may not be extended by source-level classes
5518                 if (st.tsym != null &&
5519                     ((st.tsym.flags_field & Flags.ENUM) != 0) &&
5520                     ((c.flags_field & (Flags.ENUM | Flags.COMPOUND)) == 0)) {
5521                     log.error(env.tree.pos(), Errors.EnumTypesNotExtensible);
5522                 }
5523 
5524                 if (rs.isSerializable(c.type)) {
5525                     env.info.isSerializable = true;
5526                 }
5527 





5528                 attribClassBody(env, c);
5529 
5530                 chk.checkDeprecatedAnnotation(env.tree.pos(), c);
5531                 chk.checkClassOverrideEqualsAndHashIfNeeded(env.tree.pos(), c);
5532                 chk.checkFunctionalInterface((JCClassDecl) env.tree, c);
5533                 chk.checkLeaksNotAccessible(env, (JCClassDecl) env.tree);
5534 
5535                 if (c.isImplicit()) {
5536                     chk.checkHasMain(env.tree.pos(), c);
5537                 }
5538             } finally {
5539                 env.info.returnResult = prevReturnRes;
5540                 log.useSource(prev);
5541                 chk.setLint(prevLint);
5542             }
5543 
5544         }
5545     }
5546 
5547     public void visitImport(JCImport tree) {

5650                         sym.kind != VAR ||
5651                         sym.getConstValue() == null)
5652                     log.error(l.head.pos(), Errors.IclsCantHaveStaticDecl(c));
5653             }
5654         }
5655 
5656         // Check for proper placement of super()/this() calls.
5657         chk.checkSuperInitCalls(tree);
5658 
5659         // Check for cycles among non-initial constructors.
5660         chk.checkCyclicConstructors(tree);
5661 
5662         // Check for cycles among annotation elements.
5663         chk.checkNonCyclicElements(tree);
5664 
5665         // Check for proper use of serialVersionUID and other
5666         // serialization-related fields and methods
5667         if (env.info.lint.isEnabled(LintCategory.SERIAL)
5668                 && rs.isSerializable(c.type)
5669                 && !c.isAnonymous()) {
5670             chk.checkSerialStructure(tree, c);
5671         }
5672         // Correctly organize the positions of the type annotations
5673         typeAnnotations.organizeTypeAnnotationsBodies(tree);
5674 
5675         // Check type annotations applicability rules
5676         validateTypeAnnotations(tree, false);
5677     }
5678         // where
5679         /** get a diagnostic position for an attribute of Type t, or null if attribute missing */
5680         private DiagnosticPosition getDiagnosticPosition(JCClassDecl tree, Type t) {
5681             for(List<JCAnnotation> al = tree.mods.annotations; !al.isEmpty(); al = al.tail) {
5682                 if (types.isSameType(al.head.annotationType.type, t))
5683                     return al.head.pos();
5684             }
5685 
5686             return null;
5687         }
5688 
5689     private Type capture(Type type) {
5690         return types.capture(type);

 167         Options options = Options.instance(context);
 168 
 169         Source source = Source.instance(context);
 170         allowReifiableTypesInInstanceof = Feature.REIFIABLE_TYPES_INSTANCEOF.allowedInSource(source);
 171         allowRecords = Feature.RECORDS.allowedInSource(source);
 172         allowPatternSwitch = (preview.isEnabled() || !preview.isPreview(Feature.PATTERN_SWITCH)) &&
 173                              Feature.PATTERN_SWITCH.allowedInSource(source);
 174         allowUnconditionalPatternsInstanceOf =
 175                              Feature.UNCONDITIONAL_PATTERN_IN_INSTANCEOF.allowedInSource(source);
 176         sourceName = source.name;
 177         useBeforeDeclarationWarning = options.isSet("useBeforeDeclarationWarning");
 178 
 179         statInfo = new ResultInfo(KindSelector.NIL, Type.noType);
 180         varAssignmentInfo = new ResultInfo(KindSelector.ASG, Type.noType);
 181         unknownExprInfo = new ResultInfo(KindSelector.VAL, Type.noType);
 182         methodAttrInfo = new MethodAttrInfo();
 183         unknownTypeInfo = new ResultInfo(KindSelector.TYP, Type.noType);
 184         unknownTypeExprInfo = new ResultInfo(KindSelector.VAL_TYP, Type.noType);
 185         recoveryInfo = new RecoveryInfo(deferredAttr.emptyDeferredAttrContext);
 186         initBlockType = new MethodType(List.nil(), syms.voidType, List.nil(), syms.methodClass);
 187         allowValueClasses = (!preview.isPreview(Feature.VALUE_CLASSES) || preview.isEnabled()) &&
 188                 Feature.VALUE_CLASSES.allowedInSource(source);
 189     }
 190 
 191     /** Switch: reifiable types in instanceof enabled?
 192      */
 193     boolean allowReifiableTypesInInstanceof;
 194 
 195     /** Are records allowed
 196      */
 197     private final boolean allowRecords;
 198 
 199     /** Are patterns in switch allowed
 200      */
 201     private final boolean allowPatternSwitch;
 202 
 203     /** Are unconditional patterns in instanceof allowed
 204      */
 205     private final boolean allowUnconditionalPatternsInstanceOf;
 206 
 207     /** Are value classes allowed
 208      */
 209     private final boolean allowValueClasses;
 210 
 211     /**
 212      * Switch: warn about use of variable before declaration?
 213      * RFE: 6425594
 214      */
 215     boolean useBeforeDeclarationWarning;
 216 
 217     /**
 218      * Switch: name of source level; used for error reporting.
 219      */
 220     String sourceName;
 221 
 222     /** Check kind and type of given tree against protokind and prototype.
 223      *  If check succeeds, store type in tree and return it.
 224      *  If check fails, store errType in tree and return it.
 225      *  No checks are performed if the prototype is a method type.
 226      *  It is not necessary in this case since we know that kind and type
 227      *  are correct.
 228      *
 229      *  @param tree     The tree whose kind and type is checked
 230      *  @param found    The computed type of the tree

1109                          *     - have an accessibility stricter than that of the record type
1110                          *     - explicitly invoke any other constructor
1111                          */
1112                         if ((tree.sym.flags_field & GENERATEDCONSTR) == 0) {
1113                             if (Check.protection(m.flags()) > Check.protection(env.enclClass.sym.flags())) {
1114                                 log.error(tree,
1115                                         (env.enclClass.sym.flags() & AccessFlags) == 0 ?
1116                                             Errors.InvalidCanonicalConstructorInRecord(
1117                                                 Fragments.Canonical,
1118                                                 env.enclClass.sym.name,
1119                                                 Fragments.CanonicalMustNotHaveStrongerAccess("package")
1120                                             ) :
1121                                             Errors.InvalidCanonicalConstructorInRecord(
1122                                                     Fragments.Canonical,
1123                                                     env.enclClass.sym.name,
1124                                                     Fragments.CanonicalMustNotHaveStrongerAccess(asFlagSet(env.enclClass.sym.flags() & AccessFlags))
1125                                             )
1126                                 );
1127                             }
1128 
1129                             if (!allowValueClasses && TreeInfo.hasAnyConstructorCall(tree)) {
1130                                 log.error(tree, Errors.InvalidCanonicalConstructorInRecord(
1131                                         Fragments.Canonical, env.enclClass.sym.name,
1132                                         Fragments.CanonicalMustNotContainExplicitConstructorInvocation));
1133                             }
1134                         }
1135 
1136                         // also we want to check that no type variables have been defined
1137                         if (!tree.typarams.isEmpty()) {
1138                             log.error(tree, Errors.InvalidCanonicalConstructorInRecord(
1139                                     Fragments.Canonical, env.enclClass.sym.name, Fragments.CanonicalMustNotDeclareTypeVariables));
1140                         }
1141 
1142                         /* and now we need to check that the constructor's arguments are exactly the same as those of the
1143                          * record components
1144                          */
1145                         List<? extends RecordComponent> recordComponents = env.enclClass.sym.getRecordComponents();
1146                         List<Type> recordFieldTypes = TreeInfo.recordFields(env.enclClass).map(vd -> vd.sym.type);
1147                         for (JCVariableDecl param: tree.params) {
1148                             boolean paramIsVarArgs = (param.sym.flags_field & VARARGS) != 0;
1149                             if (!types.isSameType(param.type, recordFieldTypes.head) ||

1191                 }
1192                 if (isDefaultMethod || (tree.sym.flags() & (ABSTRACT | NATIVE)) == 0)
1193                     log.error(tree.pos(), Errors.MissingMethBodyOrDeclAbstract);
1194             } else {
1195                 if ((tree.sym.flags() & (ABSTRACT|DEFAULT|PRIVATE)) == ABSTRACT) {
1196                     if ((owner.flags() & INTERFACE) != 0) {
1197                         log.error(tree.body.pos(), Errors.IntfMethCantHaveBody);
1198                     } else {
1199                         log.error(tree.pos(), Errors.AbstractMethCantHaveBody);
1200                     }
1201                 } else if ((tree.mods.flags & NATIVE) != 0) {
1202                     log.error(tree.pos(), Errors.NativeMethCantHaveBody);
1203                 }
1204                 // Add an implicit super() call unless an explicit call to
1205                 // super(...) or this(...) is given
1206                 // or we are compiling class java.lang.Object.
1207                 if (isConstructor && owner.type != syms.objectType) {
1208                     if (!TreeInfo.hasAnyConstructorCall(tree)) {
1209                         JCStatement supCall = make.at(tree.body.pos).Exec(make.Apply(List.nil(),
1210                                 make.Ident(names._super), make.Idents(List.nil())));
1211                         if (allowValueClasses && (owner.isValueClass() || owner.hasStrict() || ((owner.flags_field & RECORD) != 0))) {
1212                             tree.body.stats = tree.body.stats.append(supCall);
1213                         } else {
1214                             tree.body.stats = tree.body.stats.prepend(supCall);
1215                         }
1216                     } else if ((env.enclClass.sym.flags() & ENUM) != 0 &&
1217                             (tree.mods.flags & GENERATEDCONSTR) == 0 &&
1218                             TreeInfo.hasConstructorCall(tree, names._super)) {
1219                         // enum constructors are not allowed to call super
1220                         // directly, so make sure there aren't any super calls
1221                         // in enum constructors, except in the compiler
1222                         // generated one.
1223                         log.error(tree.body.stats.head.pos(),
1224                                   Errors.CallToSuperNotAllowedInEnumCtor(env.enclClass.sym));
1225                     }
1226                     if (env.enclClass.sym.isRecord() && (tree.sym.flags_field & RECORD) != 0) { // we are seeing the canonical constructor
1227                         List<Name> recordComponentNames = TreeInfo.recordFields(env.enclClass).map(vd -> vd.sym.name);
1228                         List<Name> initParamNames = tree.sym.params.map(p -> p.name);
1229                         if (!initParamNames.equals(recordComponentNames)) {
1230                             log.error(tree, Errors.InvalidCanonicalConstructorInRecord(
1231                                     Fragments.Canonical, env.enclClass.sym.name, Fragments.CanonicalWithNameMismatch));
1232                         }
1233                         if (tree.sym.type.asMethodType().thrown != null && !tree.sym.type.asMethodType().thrown.isEmpty()) {
1234                             log.error(tree,
1235                                     Errors.InvalidCanonicalConstructorInRecord(

1305         chk.validate(tree.vartype, env, !isImplicitLambdaParameter && !tree.isImplicitlyTyped());
1306 
1307         try {
1308             v.getConstValue(); // ensure compile-time constant initializer is evaluated
1309             deferredLintHandler.flush(tree, lint);
1310             chk.checkDeprecatedAnnotation(tree.pos(), v);
1311 
1312             if (tree.init != null) {
1313                 if ((v.flags_field & FINAL) == 0 ||
1314                     !memberEnter.needsLazyConstValue(tree.init)) {
1315                     // Not a compile-time constant
1316                     // Attribute initializer in a new environment
1317                     // with the declared variable as owner.
1318                     // Check that initializer conforms to variable's declared type.
1319                     Env<AttrContext> initEnv = memberEnter.initEnv(tree, env);
1320                     initEnv.info.lint = lint;
1321                     // In order to catch self-references, we set the variable's
1322                     // declaration position to maximal possible value, effectively
1323                     // marking the variable as undefined.
1324                     initEnv.info.enclVar = v;
1325                     boolean previousCtorPrologue = initEnv.info.ctorPrologue;
1326                     try {
1327                         if (v.owner.kind == TYP && !v.isStatic() && v.isStrict()) {
1328                             // strict instance initializer in a value class
1329                             initEnv.info.ctorPrologue = true;
1330                         }
1331                         attribExpr(tree.init, initEnv, v.type);
1332                         if (tree.isImplicitlyTyped()) {
1333                             //fixup local variable type
1334                             v.type = chk.checkLocalVarType(tree, tree.init.type, tree.name);
1335                         }
1336                     } finally {
1337                         initEnv.info.ctorPrologue = previousCtorPrologue;
1338                     }
1339                 }
1340                 if (tree.isImplicitlyTyped()) {
1341                     setSyntheticVariableType(tree, v.type);
1342                 }
1343             }
1344             result = tree.type = v.type;
1345             if (env.enclClass.sym.isRecord() && tree.sym.owner.kind == TYP && !v.isStatic()) {
1346                 if (isNonArgsMethodInObject(v.name)) {
1347                     log.error(tree, Errors.IllegalRecordComponentName(v));
1348                 }
1349             }
1350         }
1351         finally {
1352             chk.setLint(prevLint);
1353         }
1354     }
1355 
1356     private void doQueueScanTreeAndTypeAnnotateForVarInit(JCVariableDecl tree, Env<AttrContext> env) {
1357         if (tree.init != null &&

1437             }
1438         }
1439     }
1440 
1441     public void visitSkip(JCSkip tree) {
1442         result = null;
1443     }
1444 
1445     public void visitBlock(JCBlock tree) {
1446         if (env.info.scope.owner.kind == TYP || env.info.scope.owner.kind == ERR) {
1447             // Block is a static or instance initializer;
1448             // let the owner of the environment be a freshly
1449             // created BLOCK-method.
1450             Symbol fakeOwner =
1451                 new MethodSymbol(tree.flags | BLOCK |
1452                     env.info.scope.owner.flags() & STRICTFP, names.empty, initBlockType,
1453                     env.info.scope.owner);
1454             final Env<AttrContext> localEnv =
1455                 env.dup(tree, env.info.dup(env.info.scope.dupUnshared(fakeOwner)));
1456 
1457             if ((tree.flags & STATIC) != 0) {
1458                 localEnv.info.staticLevel++;
1459             } else {
1460                 localEnv.info.instanceInitializerBlock = true;
1461             }
1462             // Attribute all type annotations in the block
1463             annotate.queueScanTreeAndTypeAnnotate(tree, localEnv, localEnv.info.scope.owner, null);
1464             annotate.flush();
1465             attribStats(tree.stats, localEnv);
1466 
1467             {
1468                 // Store init and clinit type annotations with the ClassSymbol
1469                 // to allow output in Gen.normalizeDefs.
1470                 ClassSymbol cs = (ClassSymbol)env.info.scope.owner;
1471                 List<Attribute.TypeCompound> tas = localEnv.info.scope.owner.getRawTypeAttributes();
1472                 if ((tree.flags & STATIC) != 0) {
1473                     cs.appendClassInitTypeAttributes(tas);
1474                 } else {
1475                     cs.appendInitTypeAttributes(tas);
1476                 }
1477             }
1478         } else {
1479             // Create a new local environment with a local scope.
1480             Env<AttrContext> localEnv =
1481                 env.dup(tree, env.info.dup(env.info.scope.dup()));

1950     // where
1951     /** Return the selected enumeration constant symbol, or null. */
1952     private Symbol enumConstant(JCTree tree, Type enumType) {
1953         if (tree.hasTag(IDENT)) {
1954             JCIdent ident = (JCIdent)tree;
1955             Name name = ident.name;
1956             for (Symbol sym : enumType.tsym.members().getSymbolsByName(name)) {
1957                 if (sym.kind == VAR) {
1958                     Symbol s = ident.sym = sym;
1959                     ((VarSymbol)s).getConstValue(); // ensure initializer is evaluated
1960                     ident.type = s.type;
1961                     return ((s.flags_field & Flags.ENUM) == 0)
1962                         ? null : s;
1963                 }
1964             }
1965         }
1966         return null;
1967     }
1968 
1969     public void visitSynchronized(JCSynchronized tree) {
1970         boolean identityType = chk.checkIdentityType(tree.pos(), attribExpr(tree.lock, env));
1971         if (identityType && isValueBased(tree.lock.type)) {
1972             env.info.lint.logIfEnabled(tree.pos(), LintWarnings.AttemptToSynchronizeOnInstanceOfValueBasedClass);
1973         }
1974         attribStat(tree.body, env);
1975         result = null;
1976     }
1977         // where
1978         private boolean isValueBased(Type t) {
1979             return t != null && t.tsym != null && (t.tsym.flags() & VALUE_BASED) != 0;
1980         }
1981 

1982     public void visitTry(JCTry tree) {
1983         // Create a new local environment with a local
1984         Env<AttrContext> localEnv = env.dup(tree, env.info.dup(env.info.scope.dup()));
1985         try {
1986             boolean isTryWithResource = tree.resources.nonEmpty();
1987             // Create a nested environment for attributing the try block if needed
1988             Env<AttrContext> tryEnv = isTryWithResource ?
1989                 env.dup(tree, localEnv.info.dup(localEnv.info.scope.dup())) :
1990                 localEnv;
1991             try {
1992                 // Attribute resource declarations
1993                 for (JCTree resource : tree.resources) {
1994                     CheckContext twrContext = new Check.NestedCheckContext(resultInfo.checkContext) {
1995                         @Override
1996                         public void report(DiagnosticPosition pos, JCDiagnostic details) {
1997                             chk.basicHandler.report(pos, diags.fragment(Fragments.TryNotApplicableToType(details)));
1998                         }
1999                     };
2000                     ResultInfo twrResult =
2001                         new ResultInfo(KindSelector.VAR,

4394     }
4395 
4396     public void visitSelect(JCFieldAccess tree) {
4397         // Determine the expected kind of the qualifier expression.
4398         KindSelector skind = KindSelector.NIL;
4399         if (tree.name == names._this || tree.name == names._super ||
4400                 tree.name == names._class)
4401         {
4402             skind = KindSelector.TYP;
4403         } else {
4404             if (pkind().contains(KindSelector.PCK))
4405                 skind = KindSelector.of(skind, KindSelector.PCK);
4406             if (pkind().contains(KindSelector.TYP))
4407                 skind = KindSelector.of(skind, KindSelector.TYP, KindSelector.PCK);
4408             if (pkind().contains(KindSelector.VAL_MTH))
4409                 skind = KindSelector.of(skind, KindSelector.VAL, KindSelector.TYP);
4410         }
4411 
4412         // Attribute the qualifier expression, and determine its symbol (if any).
4413         Type site = attribTree(tree.selected, env, new ResultInfo(skind, Type.noType));
4414         Assert.check(site == tree.selected.type);
4415         if (!pkind().contains(KindSelector.TYP_PCK))
4416             site = capture(site); // Capture field access
4417 
4418         // don't allow T.class T[].class, etc
4419         if (skind == KindSelector.TYP) {
4420             Type elt = site;
4421             while (elt.hasTag(ARRAY))
4422                 elt = ((ArrayType)elt).elemtype;
4423             if (elt.hasTag(TYPEVAR)) {
4424                 log.error(tree.pos(), Errors.TypeVarCantBeDeref);
4425                 result = tree.type = types.createErrorType(tree.name, site.tsym, site);
4426                 tree.sym = tree.type.tsym;
4427                 return ;
4428             }
4429         }
4430 
4431         // If qualifier symbol is a type or `super', assert `selectSuper'
4432         // for the selection. This is relevant for determining whether
4433         // protected symbols are accessible.
4434         Symbol sitesym = TreeInfo.symbol(tree.selected);

5493                                                       .filter(s -> s.tsym.isSealed())
5494                                                       .map(s -> (ClassSymbol) s.tsym)
5495                                                       .collect(List.collector());
5496 
5497                 if (sealedSupers.isEmpty()) {
5498                     if ((c.flags_field & Flags.NON_SEALED) != 0) {
5499                         boolean hasErrorSuper = false;
5500 
5501                         hasErrorSuper |= types.directSupertypes(c.type)
5502                                               .stream()
5503                                               .anyMatch(s -> s.tsym.kind == Kind.ERR);
5504 
5505                         ClassType ct = (ClassType) c.type;
5506 
5507                         hasErrorSuper |= !ct.isCompound() && ct.interfaces_field != ct.all_interfaces_field;
5508 
5509                         if (!hasErrorSuper) {
5510                             log.error(TreeInfo.diagnosticPositionFor(c, env.tree), Errors.NonSealedWithNoSealedSupertype(c));
5511                         }
5512                     }
5513                 } else if ((c.flags_field & Flags.COMPOUND) == 0) {
5514                     if (c.isDirectlyOrIndirectlyLocal() && !c.isEnum()) {
5515                         log.error(TreeInfo.diagnosticPositionFor(c, env.tree), Errors.LocalClassesCantExtendSealed(c.isAnonymous() ? Fragments.Anonymous : Fragments.Local));
5516                     }
5517 
5518                     if (!c.type.isCompound()) {
5519                         for (ClassSymbol supertypeSym : sealedSupers) {
5520                             if (!supertypeSym.isPermittedSubclass(c.type.tsym)) {
5521                                 log.error(TreeInfo.diagnosticPositionFor(c.type.tsym, env.tree), Errors.CantInheritFromSealed(supertypeSym));
5522                             }
5523                         }
5524                         if (!c.isNonSealed() && !c.isFinal() && !c.isSealed()) {
5525                             log.error(TreeInfo.diagnosticPositionFor(c, env.tree),
5526                                     c.isInterface() ?
5527                                             Errors.NonSealedOrSealedExpected :
5528                                             Errors.NonSealedSealedOrFinalExpected);
5529                         }
5530                     }
5531                 }
5532 
5533                 deferredLintHandler.flush(env.tree, env.info.lint);
5534                 env.info.returnResult = null;
5535                 // java.lang.Enum may not be subclassed by a non-enum
5536                 if (st.tsym == syms.enumSym &&
5537                     ((c.flags_field & (Flags.ENUM|Flags.COMPOUND)) == 0))
5538                     log.error(env.tree.pos(), Errors.EnumNoSubclassing);
5539 
5540                 // Enums may not be extended by source-level classes
5541                 if (st.tsym != null &&
5542                     ((st.tsym.flags_field & Flags.ENUM) != 0) &&
5543                     ((c.flags_field & (Flags.ENUM | Flags.COMPOUND)) == 0)) {
5544                     log.error(env.tree.pos(), Errors.EnumTypesNotExtensible);
5545                 }
5546 
5547                 if (rs.isSerializable(c.type)) {
5548                     env.info.isSerializable = true;
5549                 }
5550 
5551                 if (c.isValueClass()) {
5552                     Assert.check(env.tree.hasTag(CLASSDEF));
5553                     chk.checkConstraintsOfValueClass((JCClassDecl) env.tree, c);
5554                 }
5555 
5556                 attribClassBody(env, c);
5557 
5558                 chk.checkDeprecatedAnnotation(env.tree.pos(), c);
5559                 chk.checkClassOverrideEqualsAndHashIfNeeded(env.tree.pos(), c);
5560                 chk.checkFunctionalInterface((JCClassDecl) env.tree, c);
5561                 chk.checkLeaksNotAccessible(env, (JCClassDecl) env.tree);
5562 
5563                 if (c.isImplicit()) {
5564                     chk.checkHasMain(env.tree.pos(), c);
5565                 }
5566             } finally {
5567                 env.info.returnResult = prevReturnRes;
5568                 log.useSource(prev);
5569                 chk.setLint(prevLint);
5570             }
5571 
5572         }
5573     }
5574 
5575     public void visitImport(JCImport tree) {

5678                         sym.kind != VAR ||
5679                         sym.getConstValue() == null)
5680                     log.error(l.head.pos(), Errors.IclsCantHaveStaticDecl(c));
5681             }
5682         }
5683 
5684         // Check for proper placement of super()/this() calls.
5685         chk.checkSuperInitCalls(tree);
5686 
5687         // Check for cycles among non-initial constructors.
5688         chk.checkCyclicConstructors(tree);
5689 
5690         // Check for cycles among annotation elements.
5691         chk.checkNonCyclicElements(tree);
5692 
5693         // Check for proper use of serialVersionUID and other
5694         // serialization-related fields and methods
5695         if (env.info.lint.isEnabled(LintCategory.SERIAL)
5696                 && rs.isSerializable(c.type)
5697                 && !c.isAnonymous()) {
5698             chk.checkSerialStructure(env, tree, c);
5699         }
5700         // Correctly organize the positions of the type annotations
5701         typeAnnotations.organizeTypeAnnotationsBodies(tree);
5702 
5703         // Check type annotations applicability rules
5704         validateTypeAnnotations(tree, false);
5705     }
5706         // where
5707         /** get a diagnostic position for an attribute of Type t, or null if attribute missing */
5708         private DiagnosticPosition getDiagnosticPosition(JCClassDecl tree, Type t) {
5709             for(List<JCAnnotation> al = tree.mods.annotations; !al.isEmpty(); al = al.tail) {
5710                 if (types.isSameType(al.head.annotationType.type, t))
5711                     return al.head.pos();
5712             }
5713 
5714             return null;
5715         }
5716 
5717     private Type capture(Type type) {
5718         return types.capture(type);
< prev index next >