src/share/classes/com/sun/tools/javac/parser/JavacParser.java

Print this page




 114     /** Construct a parser from a given scanner, tree factory and log.
 115      */
 116     protected JavacParser(ParserFactory fac,
 117                      Lexer S,
 118                      boolean keepDocComments,
 119                      boolean keepLineMap) {
 120         this.S = S;
 121         S.nextToken(); // prime the pump
 122         this.F = fac.F;
 123         this.log = fac.log;
 124         this.names = fac.names;
 125         this.keywords = fac.keywords;
 126         this.source = fac.source;
 127         this.allowGenerics = source.allowGenerics();
 128         this.allowVarargs = source.allowVarargs();
 129         this.allowAsserts = source.allowAsserts();
 130         this.allowEnums = source.allowEnums();
 131         this.allowForeach = source.allowForeach();
 132         this.allowStaticImport = source.allowStaticImport();
 133         this.allowAnnotations = source.allowAnnotations();

 134         this.allowDiamond = source.allowDiamond();
 135         this.allowMulticatch = source.allowMulticatch();
 136         this.allowTypeAnnotations = source.allowTypeAnnotations();
 137         this.keepDocComments = keepDocComments;
 138         if (keepDocComments)
 139             docComments = new HashMap<JCTree,String>();
 140         this.keepLineMap = keepLineMap;
 141         this.errorTree = F.Erroneous();
 142         this.debugJSR308 = fac.options.get("TA:parser") != null;
 143     }
 144 
 145     /** Switch: debug output for type-annotations operations
 146      */
 147     boolean debugJSR308;
 148 
 149     /** Switch: Should generics be recognized?
 150      */
 151     boolean allowGenerics;
 152 
 153     /** Switch: Should diamond operator be recognized?


 169     /** Switch: should we recognize enums, or just give a warning?
 170      */
 171     boolean allowEnums;
 172 
 173     /** Switch: should we recognize foreach?
 174      */
 175     boolean allowForeach;
 176 
 177     /** Switch: should we recognize foreach?
 178      */
 179     boolean allowStaticImport;
 180 
 181     /** Switch: should we recognize annotations?
 182      */
 183     boolean allowAnnotations;
 184 
 185     /** Switch: should we recognize type annotations?
 186      */
 187     boolean allowTypeAnnotations;
 188 




 189     /** Switch: should we keep docComments?
 190      */
 191     boolean keepDocComments;
 192 
 193     /** Switch: should we keep line table?
 194      */
 195     boolean keepLineMap;
 196 
 197     /** When terms are parsed, the mode determines which is expected:
 198      *     mode = EXPR        : an expression
 199      *     mode = TYPE        : a type
 200      *     mode = NOPARAMS    : no parameters allowed for type
 201      *     mode = TYPEARG     : type argument
 202      */
 203     static final int EXPR = 0x1;
 204     static final int TYPE = 0x2;
 205     static final int NOPARAMS = 0x4;
 206     static final int TYPEARG = 0x8;
 207     static final int DIAMOND = 0x10;
 208 


1895                 return F.at(pos).ForLoop(inits, cond, steps, body);
1896             }
1897         }
1898         case WHILE: {
1899             S.nextToken();
1900             JCExpression cond = parExpression();
1901             JCStatement body = parseStatement();
1902             return F.at(pos).WhileLoop(cond, body);
1903         }
1904         case DO: {
1905             S.nextToken();
1906             JCStatement body = parseStatement();
1907             accept(WHILE);
1908             JCExpression cond = parExpression();
1909             JCDoWhileLoop t = to(F.at(pos).DoLoop(body, cond));
1910             accept(SEMI);
1911             return t;
1912         }
1913         case TRY: {
1914             S.nextToken();







1915             JCBlock body = block();
1916             ListBuffer<JCCatch> catchers = new ListBuffer<JCCatch>();
1917             JCBlock finalizer = null;
1918             if (S.token() == CATCH || S.token() == FINALLY) {
1919                 while (S.token() == CATCH) catchers.append(catchClause());
1920                 if (S.token() == FINALLY) {
1921                     S.nextToken();
1922                     finalizer = block();
1923                 }
1924             } else {




1925                 log.error(pos, "try.without.catch.or.finally");
1926             }
1927             return F.at(pos).Try(body, catchers.toList(), finalizer);
1928         }
1929         case SWITCH: {
1930             S.nextToken();
1931             JCExpression selector = parExpression();
1932             accept(LBRACE);
1933             List<JCCase> cases = switchBlockStatementGroups();
1934             JCSwitch t = to(F.at(pos).Switch(selector, cases));
1935             accept(RBRACE);
1936             return t;
1937         }
1938         case SYNCHRONIZED: {
1939             S.nextToken();
1940             JCExpression lock = parExpression();
1941             JCBlock body = block();
1942             return F.at(pos).Synchronized(lock, body);
1943         }
1944         case RETURN: {
1945             S.nextToken();
1946             JCExpression result = S.token() == SEMI ? null : parseExpression();
1947             JCReturn t = to(F.at(pos).Return(result));


2368             S.nextToken();
2369             init = variableInitializer();
2370         }
2371         else if (reqInit) syntaxError(S.pos(), "expected", EQ);
2372         JCVariableDecl result =
2373             toP(F.at(pos).VarDef(mods, name, type, init));
2374         attach(result, dc);
2375         return result;
2376     }
2377 
2378     /** VariableDeclaratorId = Ident BracketsOpt
2379      */
2380     JCVariableDecl variableDeclaratorId(JCModifiers mods, JCExpression type) {
2381         int pos = S.pos();
2382         Name name = ident();
2383         if ((mods.flags & Flags.VARARGS) == 0)
2384             type = bracketsOpt(type);
2385         return toP(F.at(pos).VarDef(mods, name, type, null));
2386     }
2387 





























2388     /** CompilationUnit = [ { "@" Annotation } PACKAGE Qualident ";"] {ImportDeclaration} {TypeDeclaration}
2389      */
2390     public JCTree.JCCompilationUnit parseCompilationUnit() {
2391         int pos = S.pos();
2392         JCExpression pid = null;
2393         String dc = S.docComment();
2394         JCModifiers mods = null;
2395         List<JCAnnotation> packageAnnotations = List.nil();
2396         if (S.token() == MONKEYS_AT)
2397             mods = modifiersOpt();
2398 
2399         if (S.token() == PACKAGE) {
2400             if (mods != null) {
2401                 checkNoMods(mods.flags);
2402                 packageAnnotations = mods.annotations;
2403                 mods = null;
2404             }
2405             S.nextToken();
2406             pid = qualident();
2407             accept(SEMI);


3201         }
3202     }
3203     void checkTypeAnnotations() {
3204         if (!allowTypeAnnotations) {
3205             log.error(S.pos(), "type.annotations.not.supported.in.source", source.name);
3206             allowTypeAnnotations = true;
3207         }
3208     }
3209     void checkDiamond() {
3210         if (!allowDiamond) {
3211             log.error(S.pos(), "diamond.not.supported.in.source", source.name);
3212             allowDiamond = true;
3213         }
3214     }
3215     void checkMulticatch() {
3216         if (!allowMulticatch) {
3217             log.error(S.pos(), "multicatch.not.supported.in.source", source.name);
3218             allowMulticatch = true;
3219             }
3220     }






3221 }


 114     /** Construct a parser from a given scanner, tree factory and log.
 115      */
 116     protected JavacParser(ParserFactory fac,
 117                      Lexer S,
 118                      boolean keepDocComments,
 119                      boolean keepLineMap) {
 120         this.S = S;
 121         S.nextToken(); // prime the pump
 122         this.F = fac.F;
 123         this.log = fac.log;
 124         this.names = fac.names;
 125         this.keywords = fac.keywords;
 126         this.source = fac.source;
 127         this.allowGenerics = source.allowGenerics();
 128         this.allowVarargs = source.allowVarargs();
 129         this.allowAsserts = source.allowAsserts();
 130         this.allowEnums = source.allowEnums();
 131         this.allowForeach = source.allowForeach();
 132         this.allowStaticImport = source.allowStaticImport();
 133         this.allowAnnotations = source.allowAnnotations();
 134         this.allowARM = source.allowAutomaticResourceManagement();
 135         this.allowDiamond = source.allowDiamond();
 136         this.allowMulticatch = source.allowMulticatch();
 137         this.allowTypeAnnotations = source.allowTypeAnnotations();
 138         this.keepDocComments = keepDocComments;
 139         if (keepDocComments)
 140             docComments = new HashMap<JCTree,String>();
 141         this.keepLineMap = keepLineMap;
 142         this.errorTree = F.Erroneous();
 143         this.debugJSR308 = fac.options.get("TA:parser") != null;
 144     }
 145 
 146     /** Switch: debug output for type-annotations operations
 147      */
 148     boolean debugJSR308;
 149 
 150     /** Switch: Should generics be recognized?
 151      */
 152     boolean allowGenerics;
 153 
 154     /** Switch: Should diamond operator be recognized?


 170     /** Switch: should we recognize enums, or just give a warning?
 171      */
 172     boolean allowEnums;
 173 
 174     /** Switch: should we recognize foreach?
 175      */
 176     boolean allowForeach;
 177 
 178     /** Switch: should we recognize foreach?
 179      */
 180     boolean allowStaticImport;
 181 
 182     /** Switch: should we recognize annotations?
 183      */
 184     boolean allowAnnotations;
 185 
 186     /** Switch: should we recognize type annotations?
 187      */
 188     boolean allowTypeAnnotations;
 189 
 190     /** Switch: should we recognize automatic resource management?
 191      */
 192     boolean allowARM;
 193 
 194     /** Switch: should we keep docComments?
 195      */
 196     boolean keepDocComments;
 197 
 198     /** Switch: should we keep line table?
 199      */
 200     boolean keepLineMap;
 201 
 202     /** When terms are parsed, the mode determines which is expected:
 203      *     mode = EXPR        : an expression
 204      *     mode = TYPE        : a type
 205      *     mode = NOPARAMS    : no parameters allowed for type
 206      *     mode = TYPEARG     : type argument
 207      */
 208     static final int EXPR = 0x1;
 209     static final int TYPE = 0x2;
 210     static final int NOPARAMS = 0x4;
 211     static final int TYPEARG = 0x8;
 212     static final int DIAMOND = 0x10;
 213 


1900                 return F.at(pos).ForLoop(inits, cond, steps, body);
1901             }
1902         }
1903         case WHILE: {
1904             S.nextToken();
1905             JCExpression cond = parExpression();
1906             JCStatement body = parseStatement();
1907             return F.at(pos).WhileLoop(cond, body);
1908         }
1909         case DO: {
1910             S.nextToken();
1911             JCStatement body = parseStatement();
1912             accept(WHILE);
1913             JCExpression cond = parExpression();
1914             JCDoWhileLoop t = to(F.at(pos).DoLoop(body, cond));
1915             accept(SEMI);
1916             return t;
1917         }
1918         case TRY: {
1919             S.nextToken();
1920             List<JCTree> resources = List.<JCTree>nil();
1921             if (S.token() == LPAREN) {
1922                 checkAutomaticResourceManagement();
1923                 S.nextToken();
1924                 resources = resourceDeclarators();
1925                 accept(RPAREN);
1926             }
1927             JCBlock body = block();
1928             ListBuffer<JCCatch> catchers = new ListBuffer<JCCatch>();
1929             JCBlock finalizer = null;
1930             if (S.token() == CATCH || S.token() == FINALLY) {
1931                 while (S.token() == CATCH) catchers.append(catchClause());
1932                 if (S.token() == FINALLY) {
1933                     S.nextToken();
1934                     finalizer = block();
1935                 }
1936             } else {
1937                 if (allowARM) {
1938                     if (resources.isEmpty())
1939                         log.error(pos, "try.without.catch.finally.or.resource.decls");
1940                 } else
1941                     log.error(pos, "try.without.catch.or.finally");
1942             }
1943             return F.at(pos).Try(body, catchers.toList(), finalizer, resources);
1944         }
1945         case SWITCH: {
1946             S.nextToken();
1947             JCExpression selector = parExpression();
1948             accept(LBRACE);
1949             List<JCCase> cases = switchBlockStatementGroups();
1950             JCSwitch t = to(F.at(pos).Switch(selector, cases));
1951             accept(RBRACE);
1952             return t;
1953         }
1954         case SYNCHRONIZED: {
1955             S.nextToken();
1956             JCExpression lock = parExpression();
1957             JCBlock body = block();
1958             return F.at(pos).Synchronized(lock, body);
1959         }
1960         case RETURN: {
1961             S.nextToken();
1962             JCExpression result = S.token() == SEMI ? null : parseExpression();
1963             JCReturn t = to(F.at(pos).Return(result));


2384             S.nextToken();
2385             init = variableInitializer();
2386         }
2387         else if (reqInit) syntaxError(S.pos(), "expected", EQ);
2388         JCVariableDecl result =
2389             toP(F.at(pos).VarDef(mods, name, type, init));
2390         attach(result, dc);
2391         return result;
2392     }
2393 
2394     /** VariableDeclaratorId = Ident BracketsOpt
2395      */
2396     JCVariableDecl variableDeclaratorId(JCModifiers mods, JCExpression type) {
2397         int pos = S.pos();
2398         Name name = ident();
2399         if ((mods.flags & Flags.VARARGS) == 0)
2400             type = bracketsOpt(type);
2401         return toP(F.at(pos).VarDef(mods, name, type, null));
2402     }
2403 
2404     /** ResourceDeclarators = ResourceDeclarator { "," ResourceDeclarator }
2405      */
2406     List<JCTree> resourceDeclarators() {
2407         ListBuffer<JCTree> defs = new ListBuffer<JCTree>();
2408         defs.append(resourceDeclarator());
2409         while (S.token() == SEMI) {
2410             // All but last of multiple declarators subsume a semicolon
2411             storeEnd(defs.elems.last(), S.endPos());
2412             S.nextToken();
2413             defs.append(resourceDeclarator());
2414         }
2415         return defs.toList();
2416     }
2417 
2418     /** ResourceDeclarator = LocalVariableDeclaration */
2419     JCTree resourceDeclarator() {
2420         if (S.token() == FINAL || S.token() == MONKEYS_AT) {
2421             return variableDeclaratorRest(S.pos(), optFinal(0), parseType(),
2422                                           ident(), true, null);
2423         } else {
2424             JCExpression t = term(EXPR | TYPE);
2425             if ((lastmode & TYPE) != 0 && S.token() == IDENTIFIER)
2426                 return variableDeclaratorRest(S.pos(), modifiersOpt(), t,
2427                                               ident(), true, null);
2428             else
2429                 return t;
2430         }
2431     }
2432 
2433     /** CompilationUnit = [ { "@" Annotation } PACKAGE Qualident ";"] {ImportDeclaration} {TypeDeclaration}
2434      */
2435     public JCTree.JCCompilationUnit parseCompilationUnit() {
2436         int pos = S.pos();
2437         JCExpression pid = null;
2438         String dc = S.docComment();
2439         JCModifiers mods = null;
2440         List<JCAnnotation> packageAnnotations = List.nil();
2441         if (S.token() == MONKEYS_AT)
2442             mods = modifiersOpt();
2443 
2444         if (S.token() == PACKAGE) {
2445             if (mods != null) {
2446                 checkNoMods(mods.flags);
2447                 packageAnnotations = mods.annotations;
2448                 mods = null;
2449             }
2450             S.nextToken();
2451             pid = qualident();
2452             accept(SEMI);


3246         }
3247     }
3248     void checkTypeAnnotations() {
3249         if (!allowTypeAnnotations) {
3250             log.error(S.pos(), "type.annotations.not.supported.in.source", source.name);
3251             allowTypeAnnotations = true;
3252         }
3253     }
3254     void checkDiamond() {
3255         if (!allowDiamond) {
3256             log.error(S.pos(), "diamond.not.supported.in.source", source.name);
3257             allowDiamond = true;
3258         }
3259     }
3260     void checkMulticatch() {
3261         if (!allowMulticatch) {
3262             log.error(S.pos(), "multicatch.not.supported.in.source", source.name);
3263             allowMulticatch = true;
3264             }
3265     }
3266     void checkAutomaticResourceManagement() {
3267         if (!allowARM) {
3268             log.error(S.pos(), "automatic.resource.management.not.supported.in.source", source.name);
3269             allowARM = true;
3270         }
3271     }
3272 }