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

Print this page




1411         }
1412         return defs;
1413     }
1414 
1415     /** The name of a this$n field
1416      *  @param type   The class referenced by the this$n field
1417      */
1418     Name outerThisName(Type type, Symbol owner) {
1419         Type t = type.getEnclosingType();
1420         int nestingLevel = 0;
1421         while (t.hasTag(CLASS)) {
1422             t = t.getEnclosingType();
1423             nestingLevel++;
1424         }
1425         Name result = names.fromString("this" + target.syntheticNameChar() + nestingLevel);
1426         while (owner.kind == TYP && ((ClassSymbol)owner).members().lookup(result).scope != null)
1427             result = names.fromString(result.toString() + target.syntheticNameChar());
1428         return result;
1429     }
1430 
1431     /** Definition for this$n field.
1432      *  @param pos        The source code position of the definition.
1433      *  @param owner      The class in which the definition goes.
1434      */
1435     JCVariableDecl outerThisDef(int pos, Symbol owner) {
1436         long flags = FINAL | SYNTHETIC;
1437         if (owner.kind == TYP &&
1438             target.usePrivateSyntheticFields())
1439             flags |= PRIVATE;
1440         Type target = types.erasure(owner.enclClass().type.getEnclosingType());
1441         VarSymbol outerThis = new VarSymbol(
1442             flags, outerThisName(target, owner), target, owner);
1443         outerThisStack = outerThisStack.prepend(outerThis);
1444         JCVariableDecl vd = make.at(pos).VarDef(outerThis, null);




1445         vd.vartype = access(vd.vartype);
1446         return vd;
1447     }
1448 




























1449     /** Return a list of trees that load the free variables in given list,
1450      *  in reverse order.
1451      *  @param pos          The source code position to be used for the trees.
1452      *  @param freevars     The list of free variables.
1453      */
1454     List<JCExpression> loadFreevars(DiagnosticPosition pos, List<VarSymbol> freevars) {
1455         List<JCExpression> args = List.nil();
1456         for (List<VarSymbol> l = freevars; l.nonEmpty(); l = l.tail)
1457             args = args.prepend(loadFreevar(pos, l.head));
1458         return args;
1459     }
1460 //where
1461         JCExpression loadFreevar(DiagnosticPosition pos, VarSymbol v) {
1462             return access(v, make.at(pos).Ident(v), null, false);
1463         }
1464 
1465     /** Construct a tree simulating the expression {@code C.this}.
1466      *  @param pos           The source code position to be used for the tree.
1467      *  @param c             The qualifier class.
1468      */


2534             }
2535         }
2536 
2537     /** Translate an enumeration constant and its initializer. */
2538     private void visitEnumConstantDef(JCVariableDecl var, int ordinal) {
2539         JCNewClass varDef = (JCNewClass)var.init;
2540         varDef.args = varDef.args.
2541             prepend(makeLit(syms.intType, ordinal)).
2542             prepend(makeLit(syms.stringType, var.name.toString()));
2543     }
2544 
2545     public void visitMethodDef(JCMethodDecl tree) {
2546         if (tree.name == names.init && (currentClass.flags_field&ENUM) != 0) {
2547             // Add "String $enum$name, int $enum$ordinal" to the beginning of the
2548             // argument list for each constructor of an enum.
2549             JCVariableDecl nameParam = make_at(tree.pos()).
2550                 Param(names.fromString(target.syntheticNameChar() +
2551                                        "enum" + target.syntheticNameChar() + "name"),
2552                       syms.stringType, tree.sym);
2553             nameParam.mods.flags |= SYNTHETIC; nameParam.sym.flags_field |= SYNTHETIC;
2554 
2555             JCVariableDecl ordParam = make.
2556                 Param(names.fromString(target.syntheticNameChar() +
2557                                        "enum" + target.syntheticNameChar() +
2558                                        "ordinal"),
2559                       syms.intType, tree.sym);
2560             ordParam.mods.flags |= SYNTHETIC; ordParam.sym.flags_field |= SYNTHETIC;
2561 
2562             tree.params = tree.params.prepend(ordParam).prepend(nameParam);
2563 
2564             MethodSymbol m = tree.sym;


2565             Type olderasure = m.erasure(types);
2566             m.erasure_field = new MethodType(
2567                 olderasure.getParameterTypes().prepend(syms.intType).prepend(syms.stringType),
2568                 olderasure.getReturnType(),
2569                 olderasure.getThrownTypes(),
2570                 syms.methodClass);
2571 
2572             if (target.compilerBootstrap(m.owner)) {
2573                 // Initialize synthetic name field
2574                 Symbol nameVarSym = lookupSynthetic(names.fromString("$name"),
2575                                                     tree.sym.owner.members());
2576                 JCIdent nameIdent = make.Ident(nameParam.sym);
2577                 JCIdent id1 = make.Ident(nameVarSym);
2578                 JCAssign newAssign = make.Assign(id1, nameIdent);
2579                 newAssign.type = id1.type;
2580                 JCExpressionStatement nameAssign = make.Exec(newAssign);
2581                 nameAssign.type = id1.type;
2582                 tree.body.stats = tree.body.stats.prepend(nameAssign);
2583 
2584                 // Initialize synthetic ordinal field




1411         }
1412         return defs;
1413     }
1414 
1415     /** The name of a this$n field
1416      *  @param type   The class referenced by the this$n field
1417      */
1418     Name outerThisName(Type type, Symbol owner) {
1419         Type t = type.getEnclosingType();
1420         int nestingLevel = 0;
1421         while (t.hasTag(CLASS)) {
1422             t = t.getEnclosingType();
1423             nestingLevel++;
1424         }
1425         Name result = names.fromString("this" + target.syntheticNameChar() + nestingLevel);
1426         while (owner.kind == TYP && ((ClassSymbol)owner).members().lookup(result).scope != null)
1427             result = names.fromString(result.toString() + target.syntheticNameChar());
1428         return result;
1429     }
1430 
1431     private VarSymbol makeOuterThisVarSymbol(Symbol owner, long flags) {





1432         if (owner.kind == TYP &&
1433             target.usePrivateSyntheticFields())
1434             flags |= PRIVATE;
1435         Type target = types.erasure(owner.enclClass().type.getEnclosingType());
1436         VarSymbol outerThis =
1437             new VarSymbol(flags, outerThisName(target, owner), target, owner);
1438         outerThisStack = outerThisStack.prepend(outerThis);
1439         return outerThis;
1440     }
1441 
1442     private JCVariableDecl makeOuterThisVarDecl(int pos, VarSymbol sym) {
1443         JCVariableDecl vd = make.at(pos).VarDef(sym, null);
1444         vd.vartype = access(vd.vartype);
1445         return vd;
1446     }
1447 
1448     /** Definition for this$n field.
1449      *  @param pos        The source code position of the definition.
1450      *  @param owner      The method in which the definition goes.
1451      */
1452     JCVariableDecl outerThisDef(int pos, MethodSymbol owner) {
1453         ClassSymbol c = owner.enclClass();
1454         boolean isMandated =
1455             // Anonymous constructors
1456             (owner.isConstructor() && owner.isAnonymous()) ||
1457             // Constructors of non-private inner member classes
1458             (owner.isConstructor() && c.isInner() &&
1459              !c.isPrivate() && !c.isStatic());
1460         long flags =
1461             FINAL | (isMandated ? MANDATED : SYNTHETIC);
1462         VarSymbol outerThis = makeOuterThisVarSymbol(owner, flags);
1463         owner.extraParams = owner.extraParams.prepend(outerThis);
1464         return makeOuterThisVarDecl(pos, outerThis);
1465     }
1466 
1467     /** Definition for this$n field.
1468      *  @param pos        The source code position of the definition.
1469      *  @param owner      The class in which the definition goes.
1470      */
1471     JCVariableDecl outerThisDef(int pos, ClassSymbol owner) {
1472         VarSymbol outerThis = makeOuterThisVarSymbol(owner, FINAL | SYNTHETIC);
1473         return makeOuterThisVarDecl(pos, outerThis);
1474     }
1475 
1476     /** Return a list of trees that load the free variables in given list,
1477      *  in reverse order.
1478      *  @param pos          The source code position to be used for the trees.
1479      *  @param freevars     The list of free variables.
1480      */
1481     List<JCExpression> loadFreevars(DiagnosticPosition pos, List<VarSymbol> freevars) {
1482         List<JCExpression> args = List.nil();
1483         for (List<VarSymbol> l = freevars; l.nonEmpty(); l = l.tail)
1484             args = args.prepend(loadFreevar(pos, l.head));
1485         return args;
1486     }
1487 //where
1488         JCExpression loadFreevar(DiagnosticPosition pos, VarSymbol v) {
1489             return access(v, make.at(pos).Ident(v), null, false);
1490         }
1491 
1492     /** Construct a tree simulating the expression {@code C.this}.
1493      *  @param pos           The source code position to be used for the tree.
1494      *  @param c             The qualifier class.
1495      */


2561             }
2562         }
2563 
2564     /** Translate an enumeration constant and its initializer. */
2565     private void visitEnumConstantDef(JCVariableDecl var, int ordinal) {
2566         JCNewClass varDef = (JCNewClass)var.init;
2567         varDef.args = varDef.args.
2568             prepend(makeLit(syms.intType, ordinal)).
2569             prepend(makeLit(syms.stringType, var.name.toString()));
2570     }
2571 
2572     public void visitMethodDef(JCMethodDecl tree) {
2573         if (tree.name == names.init && (currentClass.flags_field&ENUM) != 0) {
2574             // Add "String $enum$name, int $enum$ordinal" to the beginning of the
2575             // argument list for each constructor of an enum.
2576             JCVariableDecl nameParam = make_at(tree.pos()).
2577                 Param(names.fromString(target.syntheticNameChar() +
2578                                        "enum" + target.syntheticNameChar() + "name"),
2579                       syms.stringType, tree.sym);
2580             nameParam.mods.flags |= SYNTHETIC; nameParam.sym.flags_field |= SYNTHETIC;

2581             JCVariableDecl ordParam = make.
2582                 Param(names.fromString(target.syntheticNameChar() +
2583                                        "enum" + target.syntheticNameChar() +
2584                                        "ordinal"),
2585                       syms.intType, tree.sym);
2586             ordParam.mods.flags |= SYNTHETIC; ordParam.sym.flags_field |= SYNTHETIC;
2587 
2588             tree.params = tree.params.prepend(ordParam).prepend(nameParam);
2589 
2590             MethodSymbol m = tree.sym;
2591             m.extraParams = m.extraParams.prepend(ordParam.sym);
2592             m.extraParams = m.extraParams.prepend(nameParam.sym);
2593             Type olderasure = m.erasure(types);
2594             m.erasure_field = new MethodType(
2595                 olderasure.getParameterTypes().prepend(syms.intType).prepend(syms.stringType),
2596                 olderasure.getReturnType(),
2597                 olderasure.getThrownTypes(),
2598                 syms.methodClass);
2599 
2600             if (target.compilerBootstrap(m.owner)) {
2601                 // Initialize synthetic name field
2602                 Symbol nameVarSym = lookupSynthetic(names.fromString("$name"),
2603                                                     tree.sym.owner.members());
2604                 JCIdent nameIdent = make.Ident(nameParam.sym);
2605                 JCIdent id1 = make.Ident(nameVarSym);
2606                 JCAssign newAssign = make.Assign(id1, nameIdent);
2607                 newAssign.type = id1.type;
2608                 JCExpressionStatement nameAssign = make.Exec(newAssign);
2609                 nameAssign.type = id1.type;
2610                 tree.body.stats = tree.body.stats.prepend(nameAssign);
2611 
2612                 // Initialize synthetic ordinal field