759 JCExpression term2Rest(JCExpression t, int minprec) { |
759 JCExpression term2Rest(JCExpression t, int minprec) { |
760 List<JCExpression[]> savedOd = odStackSupply.elems; |
760 List<JCExpression[]> savedOd = odStackSupply.elems; |
761 JCExpression[] odStack = newOdStack(); |
761 JCExpression[] odStack = newOdStack(); |
762 List<Token[]> savedOp = opStackSupply.elems; |
762 List<Token[]> savedOp = opStackSupply.elems; |
763 Token[] opStack = newOpStack(); |
763 Token[] opStack = newOpStack(); |
|
764 List<int[]> savedPos = posStackSupply.elems; |
|
765 int[] posStack = newPosStack(); |
764 // optimization, was odStack = new Tree[...]; opStack = new Tree[...]; |
766 // optimization, was odStack = new Tree[...]; opStack = new Tree[...]; |
765 int top = 0; |
767 int top = 0; |
766 odStack[0] = t; |
768 odStack[0] = t; |
767 int startPos = S.pos(); |
769 int startPos = S.pos(); |
768 Token topOp = ERROR; |
770 Token topOp = ERROR; |
|
771 int topOpPos = Position.NOPOS; |
769 while (prec(S.token()) >= minprec) { |
772 while (prec(S.token()) >= minprec) { |
|
773 posStack[top] = topOpPos; |
770 opStack[top] = topOp; |
774 opStack[top] = topOp; |
771 top++; |
775 top++; |
772 topOp = S.token(); |
776 topOp = S.token(); |
773 int pos = S.pos(); |
777 topOpPos = S.pos(); |
774 S.nextToken(); |
778 S.nextToken(); |
775 odStack[top] = topOp == INSTANCEOF ? parseType() : term3(); |
779 odStack[top] = (topOp == INSTANCEOF) ? parseType() : term3(); |
776 while (top > 0 && prec(topOp) >= prec(S.token())) { |
780 while (top > 0 && prec(topOp) >= prec(S.token())) { |
777 odStack[top-1] = makeOp(pos, topOp, odStack[top-1], |
781 odStack[top-1] = makeOp(topOpPos, topOp, odStack[top-1], |
778 odStack[top]); |
782 odStack[top]); |
779 top--; |
783 top--; |
780 topOp = opStack[top]; |
784 topOp = opStack[top]; |
|
785 topOpPos = posStack[top]; |
781 } |
786 } |
782 } |
787 } |
783 assert top == 0; |
788 assert top == 0; |
784 t = odStack[0]; |
789 t = odStack[0]; |
785 |
790 |
843 /** optimization: To save allocating a new operand/operator stack |
849 /** optimization: To save allocating a new operand/operator stack |
844 * for every binary operation, we use supplys. |
850 * for every binary operation, we use supplys. |
845 */ |
851 */ |
846 ListBuffer<JCExpression[]> odStackSupply = new ListBuffer<JCExpression[]>(); |
852 ListBuffer<JCExpression[]> odStackSupply = new ListBuffer<JCExpression[]>(); |
847 ListBuffer<Token[]> opStackSupply = new ListBuffer<Token[]>(); |
853 ListBuffer<Token[]> opStackSupply = new ListBuffer<Token[]>(); |
|
854 ListBuffer<int[]> posStackSupply = new ListBuffer<int[]>(); |
848 |
855 |
849 private JCExpression[] newOdStack() { |
856 private JCExpression[] newOdStack() { |
850 if (odStackSupply.elems == odStackSupply.last) |
857 if (odStackSupply.elems == odStackSupply.last) |
851 odStackSupply.append(new JCExpression[infixPrecedenceLevels + 1]); |
858 odStackSupply.append(new JCExpression[infixPrecedenceLevels + 1]); |
852 JCExpression[] odStack = odStackSupply.elems.head; |
859 JCExpression[] odStack = odStackSupply.elems.head; |
858 if (opStackSupply.elems == opStackSupply.last) |
865 if (opStackSupply.elems == opStackSupply.last) |
859 opStackSupply.append(new Token[infixPrecedenceLevels + 1]); |
866 opStackSupply.append(new Token[infixPrecedenceLevels + 1]); |
860 Token[] opStack = opStackSupply.elems.head; |
867 Token[] opStack = opStackSupply.elems.head; |
861 opStackSupply.elems = opStackSupply.elems.tail; |
868 opStackSupply.elems = opStackSupply.elems.tail; |
862 return opStack; |
869 return opStack; |
|
870 } |
|
871 |
|
872 private int[] newPosStack() { |
|
873 if (posStackSupply.elems == posStackSupply.last) |
|
874 posStackSupply.append(new int[infixPrecedenceLevels + 1]); |
|
875 int[] posStack = posStackSupply.elems.head; |
|
876 posStackSupply.elems = posStackSupply.elems.tail; |
|
877 return posStack; |
863 } |
878 } |
864 |
879 |
865 /** Expression3 = PrefixOp Expression3 |
880 /** Expression3 = PrefixOp Expression3 |
866 * | "(" Expr | TypeNoParams ")" Expression3 |
881 * | "(" Expr | TypeNoParams ")" Expression3 |
867 * | Primary {Selector} {PostfixOp} |
882 * | Primary {Selector} {PostfixOp} |
937 while (S.token() == COMMA) { |
952 while (S.token() == COMMA) { |
938 S.nextToken(); |
953 S.nextToken(); |
939 args.append(typeArgument()); |
954 args.append(typeArgument()); |
940 } |
955 } |
941 accept(GT); |
956 accept(GT); |
942 t = F.at(pos1).TypeApply(t, args.toList()); |
957 t = toP(F.at(pos1).TypeApply(t, args.toList())); |
943 checkGenerics(); |
958 checkGenerics(); |
944 while (S.token() == DOT) { |
959 while (S.token() == DOT) { |
945 S.nextToken(); |
960 S.nextToken(); |
946 mode = TYPE; |
961 mode = TYPE; |
947 t = toP(F.at(S.pos()).Select(t, ident())); |
962 t = toP(F.at(S.pos()).Select(t, ident())); |
948 t = typeArgumentsOpt(t); |
963 t = typeArgumentsOpt(t); |
949 } |
964 } |
950 t = bracketsOpt(toP(t)); |
965 t = bracketsOpt(toP(t)); |
951 } else if ((mode & EXPR) != 0) { |
966 } else if ((mode & EXPR) != 0) { |
952 mode = EXPR; |
967 mode = EXPR; |
953 t = F.at(pos1).Binary(op, t, term2Rest(t1, TreeInfo.shiftPrec)); |
968 JCExpression e = term2Rest(t1, TreeInfo.shiftPrec); |
|
969 t = F.at(pos1).Binary(op, t, e); |
954 t = termRest(term1Rest(term2Rest(t, TreeInfo.orPrec))); |
970 t = termRest(term1Rest(term2Rest(t, TreeInfo.orPrec))); |
955 } else { |
971 } else { |
956 accept(GT); |
972 accept(GT); |
957 } |
973 } |
958 } |
974 } |
996 } else return illegal(); |
1012 } else return illegal(); |
997 break; |
1013 break; |
998 case SUPER: |
1014 case SUPER: |
999 if ((mode & EXPR) != 0) { |
1015 if ((mode & EXPR) != 0) { |
1000 mode = EXPR; |
1016 mode = EXPR; |
1001 t = to(superSuffix(typeArgs, F.at(pos).Ident(names._super))); |
1017 t = to(F.at(pos).Ident(names._super)); |
|
1018 t = superSuffix(typeArgs, t); |
1002 typeArgs = null; |
1019 typeArgs = null; |
1003 } else return illegal(); |
1020 } else return illegal(); |
1004 break; |
1021 break; |
1005 case INTLITERAL: case LONGLITERAL: case FLOATLITERAL: case DOUBLELITERAL: |
1022 case INTLITERAL: case LONGLITERAL: case FLOATLITERAL: case DOUBLELITERAL: |
1006 case CHARLITERAL: case STRINGLITERAL: |
1023 case CHARLITERAL: case STRINGLITERAL: |
1378 if (S.token() != QUES) return parseType(annotations); |
1395 if (S.token() != QUES) return parseType(annotations); |
1379 int pos = S.pos(); |
1396 int pos = S.pos(); |
1380 S.nextToken(); |
1397 S.nextToken(); |
1381 JCExpression result; |
1398 JCExpression result; |
1382 if (S.token() == EXTENDS) { |
1399 if (S.token() == EXTENDS) { |
1383 TypeBoundKind t = to(F.at(S.pos()).TypeBoundKind(BoundKind.EXTENDS)); |
1400 TypeBoundKind t = to(F.at(pos).TypeBoundKind(BoundKind.EXTENDS)); |
1384 S.nextToken(); |
1401 S.nextToken(); |
1385 result = F.at(pos).Wildcard(t, parseType()); |
1402 JCExpression bound = parseType(); |
|
1403 result = F.at(pos).Wildcard(t, bound); |
1386 } else if (S.token() == SUPER) { |
1404 } else if (S.token() == SUPER) { |
1387 TypeBoundKind t = to(F.at(S.pos()).TypeBoundKind(BoundKind.SUPER)); |
1405 TypeBoundKind t = to(F.at(pos).TypeBoundKind(BoundKind.SUPER)); |
1388 S.nextToken(); |
1406 S.nextToken(); |
1389 result = F.at(pos).Wildcard(t, parseType()); |
1407 JCExpression bound = parseType(); |
|
1408 result = F.at(pos).Wildcard(t, bound); |
1390 } else if (S.token() == IDENTIFIER) { |
1409 } else if (S.token() == IDENTIFIER) { |
1391 //error recovery |
1410 //error recovery |
1392 reportSyntaxError(S.prevEndPos(), "expected3", |
1411 reportSyntaxError(S.prevEndPos(), "expected3", |
1393 GT, EXTENDS, SUPER); |
1412 GT, EXTENDS, SUPER); |
1394 TypeBoundKind t = F.at(Position.NOPOS).TypeBoundKind(BoundKind.UNBOUND); |
1413 TypeBoundKind t = F.at(Position.NOPOS).TypeBoundKind(BoundKind.UNBOUND); |
1395 JCExpression wc = toP(F.at(pos).Wildcard(t, null)); |
1414 JCExpression wc = toP(F.at(pos).Wildcard(t, null)); |
1396 JCIdent id = toP(F.at(S.pos()).Ident(ident())); |
1415 JCIdent id = toP(F.at(S.pos()).Ident(ident())); |
1397 result = F.at(pos).Erroneous(List.<JCTree>of(wc, id)); |
1416 result = F.at(pos).Erroneous(List.<JCTree>of(wc, id)); |
1398 } else { |
1417 } else { |
1399 TypeBoundKind t = F.at(Position.NOPOS).TypeBoundKind(BoundKind.UNBOUND); |
1418 TypeBoundKind t = toP(F.at(pos).TypeBoundKind(BoundKind.UNBOUND)); |
1400 result = toP(F.at(pos).Wildcard(t, null)); |
1419 result = toP(F.at(pos).Wildcard(t, null)); |
1401 } |
1420 } |
1402 if (!annotations.isEmpty()) |
1421 if (!annotations.isEmpty()) |
1403 result = toP(F.at(annotations.head.pos).AnnotatedType(annotations,result)); |
1422 result = toP(F.at(annotations.head.pos).AnnotatedType(annotations,result)); |
1404 return result; |
1423 return result; |
2115 */ |
2134 */ |
2116 JCModifiers modifiersOpt() { |
2135 JCModifiers modifiersOpt() { |
2117 return modifiersOpt(null); |
2136 return modifiersOpt(null); |
2118 } |
2137 } |
2119 JCModifiers modifiersOpt(JCModifiers partial) { |
2138 JCModifiers modifiersOpt(JCModifiers partial) { |
2120 long flags = (partial == null) ? 0 : partial.flags; |
2139 long flags; |
|
2140 ListBuffer<JCAnnotation> annotations = new ListBuffer<JCAnnotation>(); |
|
2141 int pos; |
|
2142 if (partial == null) { |
|
2143 flags = 0; |
|
2144 pos = S.pos(); |
|
2145 } else { |
|
2146 flags = partial.flags; |
|
2147 annotations.appendList(partial.annotations); |
|
2148 pos = partial.pos; |
|
2149 } |
2121 if (S.deprecatedFlag()) { |
2150 if (S.deprecatedFlag()) { |
2122 flags |= Flags.DEPRECATED; |
2151 flags |= Flags.DEPRECATED; |
2123 S.resetDeprecatedFlag(); |
2152 S.resetDeprecatedFlag(); |
2124 } |
2153 } |
2125 ListBuffer<JCAnnotation> annotations = new ListBuffer<JCAnnotation>(); |
|
2126 if (partial != null) annotations.appendList(partial.annotations); |
|
2127 int pos = S.pos(); |
|
2128 int lastPos = Position.NOPOS; |
2154 int lastPos = Position.NOPOS; |
2129 loop: |
2155 loop: |
2130 while (true) { |
2156 while (true) { |
2131 long flag; |
2157 long flag; |
2132 switch (S.token()) { |
2158 switch (S.token()) { |
2148 lastPos = S.pos(); |
2174 lastPos = S.pos(); |
2149 S.nextToken(); |
2175 S.nextToken(); |
2150 if (flag == Flags.ANNOTATION) { |
2176 if (flag == Flags.ANNOTATION) { |
2151 checkAnnotations(); |
2177 checkAnnotations(); |
2152 if (S.token() != INTERFACE) { |
2178 if (S.token() != INTERFACE) { |
2153 JCAnnotation ann = annotation(lastPos, AnnotationKind.DEFAULT_ANNO); |
2179 JCAnnotation ann = annotation(lastPos, AnnotationKind.DEFAULT_ANNO); |
2154 // if first modifier is an annotation, set pos to annotation's. |
2180 // if first modifier is an annotation, set pos to annotation's. |
2155 if (flags == 0 && annotations.isEmpty()) |
2181 if (flags == 0 && annotations.isEmpty()) |
2156 pos = ann.pos; |
2182 pos = ann.pos; |
2157 annotations.append(ann); |
2183 annotations.append(ann); |
2158 lastPos = ann.pos; |
2184 lastPos = ann.pos; |
2159 flag = 0; |
2185 flag = 0; |
2160 } |
2186 } |
2161 } |
2187 } |
2162 flags |= flag; |
2188 flags |= flag; |
2163 } |
2189 } |
2167 default: break; |
2193 default: break; |
2168 } |
2194 } |
2169 |
2195 |
2170 /* A modifiers tree with no modifier tokens or annotations |
2196 /* A modifiers tree with no modifier tokens or annotations |
2171 * has no text position. */ |
2197 * has no text position. */ |
2172 if (flags == 0 && annotations.isEmpty()) |
2198 if ((flags & Flags.ModifierFlags) == 0 && annotations.isEmpty()) |
2173 pos = Position.NOPOS; |
2199 pos = Position.NOPOS; |
2174 |
2200 |
2175 JCModifiers mods = F.at(pos).Modifiers(flags, annotations.toList()); |
2201 JCModifiers mods = F.at(pos).Modifiers(flags, annotations.toList()); |
2176 if (pos != Position.NOPOS) |
2202 if (pos != Position.NOPOS) |
2177 storeEnd(mods, S.prevEndPos()); |
2203 storeEnd(mods, S.prevEndPos()); |
2541 S.nextToken(); |
2568 S.nextToken(); |
2542 implementing = typeList(); |
2569 implementing = typeList(); |
2543 } |
2570 } |
2544 |
2571 |
2545 List<JCTree> defs = enumBody(name); |
2572 List<JCTree> defs = enumBody(name); |
2546 JCModifiers newMods = |
2573 mods.flags |= Flags.ENUM; |
2547 F.at(mods.pos).Modifiers(mods.flags|Flags.ENUM, mods.annotations); |
|
2548 JCClassDecl result = toP(F.at(pos). |
2574 JCClassDecl result = toP(F.at(pos). |
2549 ClassDef(newMods, name, List.<JCTypeParameter>nil(), |
2575 ClassDef(mods, name, List.<JCTypeParameter>nil(), |
2550 null, implementing, defs)); |
2576 null, implementing, defs)); |
2551 attach(result, dc); |
2577 attach(result, dc); |
2552 return result; |
2578 return result; |
2553 } |
2579 } |
2554 |
2580 |
2693 mods.annotations.isEmpty()) { |
2719 mods.annotations.isEmpty()) { |
2694 return List.<JCTree>of(block(pos, mods.flags)); |
2720 return List.<JCTree>of(block(pos, mods.flags)); |
2695 } else { |
2721 } else { |
2696 pos = S.pos(); |
2722 pos = S.pos(); |
2697 List<JCTypeParameter> typarams = typeParametersOpt(); |
2723 List<JCTypeParameter> typarams = typeParametersOpt(); |
2698 // Hack alert: if there are type arguments but no Modifiers, the start |
|
2699 // position will be lost unless we set the Modifiers position. There |
|
2700 // should be an AST node for type parameters (BugId 5005090). |
|
2701 if (typarams.length() > 0 && mods.pos == Position.NOPOS) { |
|
2702 mods.pos = pos; |
|
2703 } |
|
2704 |
|
2705 List<JCAnnotation> annosAfterParams = annotationsOpt(AnnotationKind.DEFAULT_ANNO); |
2724 List<JCAnnotation> annosAfterParams = annotationsOpt(AnnotationKind.DEFAULT_ANNO); |
2706 |
2725 |
2707 Token token = S.token(); |
|
2708 Name name = S.name(); |
2726 Name name = S.name(); |
2709 pos = S.pos(); |
2727 pos = S.pos(); |
2710 JCExpression type; |
2728 JCExpression type; |
2711 boolean isVoid = S.token() == VOID; |
2729 boolean isVoid = S.token() == VOID; |
2712 if (isVoid) { |
2730 if (isVoid) { |
2713 if (annosAfterParams.nonEmpty()) |
2731 if (annosAfterParams.nonEmpty()) |
2714 illegal(annosAfterParams.head.pos); |
2732 illegal(annosAfterParams.head.pos); |
2715 type = to(F.at(pos).TypeIdent(TypeTags.VOID)); |
2733 type = to(F.at(pos).TypeIdent(TypeTags.VOID)); |
2716 S.nextToken(); |
2734 S.nextToken(); |
2717 } else { |
2735 } else { |
2718 mods.annotations = mods.annotations.appendList(annosAfterParams); |
2736 if (annosAfterParams.nonEmpty()) { |
|
2737 mods.annotations = mods.annotations.appendList(annosAfterParams); |
|
2738 if (mods.pos == Position.NOPOS) |
|
2739 mods.pos = mods.annotations.head.pos; |
|
2740 } |
2719 // method returns types are un-annotated types |
2741 // method returns types are un-annotated types |
2720 type = unannotatedType(); |
2742 type = unannotatedType(); |
2721 } |
2743 } |
2722 if (S.token() == LPAREN && !isInterface && type.getTag() == JCTree.IDENT) { |
2744 if (S.token() == LPAREN && !isInterface && type.getTag() == JCTree.IDENT) { |
2723 if (isInterface || name != className) |
2745 if (isInterface || name != className) |
2811 if (S.token() == LBRACE) { |
2833 if (S.token() == LBRACE) { |
2812 body = block(); |
2834 body = block(); |
2813 } |
2835 } |
2814 } |
2836 } |
2815 } |
2837 } |
|
2838 |
2816 JCMethodDecl result = |
2839 JCMethodDecl result = |
2817 toP(F.at(pos).MethodDef(mods, name, type, typarams, |
2840 toP(F.at(pos).MethodDef(mods, name, type, typarams, |
2818 params, receiverAnnotations, thrown, |
2841 params, receiverAnnotations, thrown, |
2819 body, defaultValue)); |
2842 body, defaultValue)); |
2820 attach(result, dc); |
2843 attach(result, dc); |