X-Git-Url: http://git.phpeclipse.com diff --git a/net.sourceforge.phpeclipse/src/net/sourceforge/phpdt/internal/compiler/parser/Scanner.java b/net.sourceforge.phpeclipse/src/net/sourceforge/phpdt/internal/compiler/parser/Scanner.java index 3391262..d7c2618 100644 --- a/net.sourceforge.phpeclipse/src/net/sourceforge/phpdt/internal/compiler/parser/Scanner.java +++ b/net.sourceforge.phpeclipse/src/net/sourceforge/phpdt/internal/compiler/parser/Scanner.java @@ -14,24 +14,24 @@ import java.util.ArrayList; import java.util.Iterator; import java.util.List; -import net.sourceforge.phpdt.core.compiler.*; +import net.sourceforge.phpdt.core.compiler.CharOperation; +import net.sourceforge.phpdt.core.compiler.IScanner; +import net.sourceforge.phpdt.core.compiler.ITerminalSymbols; +import net.sourceforge.phpdt.core.compiler.InvalidInputException; import net.sourceforge.phpdt.internal.compiler.ast.StringLiteral; public class Scanner implements IScanner, ITerminalSymbols { - /* APIs ares - - getNextToken() which return the current type of the token - (this value is not memorized by the scanner) - - getCurrentTokenSource() which provides with the token "REAL" source - (aka all unicode have been transformed into a correct char) - - sourceStart gives the position into the stream - - currentPosition-1 gives the sourceEnd position into the stream - */ + /* + * APIs ares - getNextToken() which return the current type of the token (this value is not memorized by the scanner) - + * getCurrentTokenSource() which provides with the token "REAL" source (aka all unicode have been transformed into a correct + * char) - sourceStart gives the position into the stream - currentPosition-1 gives the sourceEnd position into the stream + */ - // 1.4 feature + // 1.4 feature private boolean assertMode; public boolean useAssertAsAnIndentifier = false; - //flag indicating if processed source contains occurrences of keyword assert + //flag indicating if processed source contains occurrences of keyword assert public boolean containsAssertKeyword = false; public boolean recordLineSeparator; @@ -67,7 +67,7 @@ public class Scanner implements IScanner, ITerminalSymbols { //diet parsing support - jump over some method body when requested public boolean diet = false; - //support for the poor-line-debuggers .... + //support for the poor-line-debuggers .... //remember the position of the cr/lf public int[] lineEnds = new int[250]; public int linePtr = -1; @@ -120,7 +120,7 @@ public class Scanner implements IScanner, ITerminalSymbols { static final int TableSize = 30, InternalTableSize = 6; //30*6 = 180 entries public static final int OptimizedLength = 6; - public /*static*/ + public /* static */ final char[][][][] charArray_length = new char[OptimizedLength][TableSize][InternalTableSize][]; // support for detecting non-externalized string literals int currentLineNr = -1; @@ -135,7 +135,7 @@ public class Scanner implements IScanner, ITerminalSymbols { public boolean checkNonExternalizedStringLiterals = true; public boolean wasNonExternalizedStringLiteral = false; - /*static*/ { + /* static */ { for (int i = 0; i < 6; i++) { for (int j = 0; j < TableSize; j++) { for (int k = 0; k < InternalTableSize; k++) { @@ -151,7 +151,16 @@ public class Scanner implements IScanner, ITerminalSymbols { public static final int CurlyBracket = 2; public static final int BracketKinds = 3; - public static final boolean DEBUG = false; + // task tag support + public char[][] foundTaskTags = null; + public char[][] foundTaskMessages; + public char[][] foundTaskPriorities = null; + public int[][] foundTaskPositions; + public int foundTaskCount = 0; + public char[][] taskTags = null; + public char[][] taskPriorities = null; + + public static final boolean DEBUG = true; public Scanner() { this(false, false); @@ -161,23 +170,21 @@ public class Scanner implements IScanner, ITerminalSymbols { } /** - * Determines if the specified character is - * permissible as the first character in a PHP identifier + * Determines if the specified character is permissible as the first character in a PHP identifier */ public static boolean isPHPIdentifierStart(char ch) { return Character.isLetter(ch) || (ch == '_') || (0x7F <= ch && ch <= 0xFF); } /** - * Determines if the specified character may be part of a PHP identifier as - * other than the first character + * Determines if the specified character may be part of a PHP identifier as other than the first character */ public static boolean isPHPIdentifierPart(char ch) { return Character.isLetterOrDigit(ch) || (ch == '_') || (0x7F <= ch && ch <= 0xFF); } public final boolean atEnd() { - // This code is not relevant if source is + // This code is not relevant if source is // Only a part of the real stream input return source.length == currentPosition; @@ -218,8 +225,7 @@ public class Scanner implements IScanner, ITerminalSymbols { public int getCurrentTokenEndPosition() { return this.currentPosition - 1; } - - + public final char[] getCurrentTokenSource() { // Return the token REAL source (aka unicodes are precomputed) @@ -277,24 +283,23 @@ public class Scanner implements IScanner, ITerminalSymbols { public int getCurrentTokenStartPosition() { return this.startPosition; } - - public final char[] getCurrentStringLiteralSource() { - // Return the token REAL source (aka unicodes are precomputed) - char[] result; + public final char[] getCurrentStringLiteralSource() { + // Return the token REAL source (aka unicodes are precomputed) + + char[] result; - int length; - System.arraycopy(source, startPosition+1, result = new char[length = currentPosition - startPosition - 2], 0, length); - // } - return result; - } + int length; + System.arraycopy(source, startPosition + 1, result = new char[length = currentPosition - startPosition - 2], 0, length); + // } + return result; + } /* * Search the source position corresponding to the end of a given line number - * - * Line numbers are 1-based, and relative to the scanner initialPosition. - * Character positions are 0-based. - * + * + * Line numbers are 1-based, and relative to the scanner initialPosition. Character positions are 0-based. + * * In case the given line number is inconsistent, answers -1. */ public final int getLineEnd(int lineNumber) { @@ -313,12 +318,11 @@ public class Scanner implements IScanner, ITerminalSymbols { } /** * Search the source position corresponding to the beginning of a given line number - * - * Line numbers are 1-based, and relative to the scanner initialPosition. - * Character positions are 0-based. - * - * e.g. getLineStart(1) --> 0 i.e. first line starts at character 0. - * + * + * Line numbers are 1-based, and relative to the scanner initialPosition. Character positions are 0-based. + * + * e.g. getLineStart(1) --> 0 i.e. first line starts at character 0. + * * In case the given line number is inconsistent, answers -1. */ public final int getLineStart(int lineNumber) { @@ -344,7 +348,7 @@ public class Scanner implements IScanner, ITerminalSymbols { //Both previous lines are true if the currentCharacter is == to the testedChar //On false, no side effect has occured. - //ALL getNextChar.... ARE OPTIMIZED COPIES + //ALL getNextChar.... ARE OPTIMIZED COPIES int temp = currentPosition; try { @@ -421,7 +425,7 @@ public class Scanner implements IScanner, ITerminalSymbols { //Both previous lines are true if the currentCharacter is == to the testedChar1/2 //On false, no side effect has occured. - //ALL getNextChar.... ARE OPTIMIZED COPIES + //ALL getNextChar.... ARE OPTIMIZED COPIES int temp = currentPosition; try { @@ -503,7 +507,7 @@ public class Scanner implements IScanner, ITerminalSymbols { //Both previous lines are true if the currentCharacter is a digit //On false, no side effect has occured. - //ALL getNextChar.... ARE OPTIMIZED COPIES + //ALL getNextChar.... ARE OPTIMIZED COPIES int temp = currentPosition; try { @@ -575,7 +579,7 @@ public class Scanner implements IScanner, ITerminalSymbols { //Both previous lines are true if the currentCharacter is a digit base on radix //On false, no side effect has occured. - //ALL getNextChar.... ARE OPTIMIZED COPIES + //ALL getNextChar.... ARE OPTIMIZED COPIES int temp = currentPosition; try { @@ -647,7 +651,7 @@ public class Scanner implements IScanner, ITerminalSymbols { //Both previous lines are true if the currentCharacter is a JavaIdentifierPart //On false, no side effect has occured. - //ALL getNextChar.... ARE OPTIMIZED COPIES + //ALL getNextChar.... ARE OPTIMIZED COPIES int temp = currentPosition; try { @@ -737,7 +741,7 @@ public class Scanner implements IScanner, ITerminalSymbols { if (test >= 0) { test = getNextChar('P', 'p'); if (test >= 0) { - // ')) return TokenNameEQUAL_GREATER; return TokenNameEQUAL; @@ -1045,8 +1057,8 @@ public class Scanner implements IScanner, ITerminalSymbols { // } // } // } - // // if (getNextChar('\'')) - // // return TokenNameCharacterLiteral; + // // if (getNextChar('\'')) + // // return TokenNameCharacterLiteral; // // relocate if finding another quote fairly close: thus unicode '/u000D' will be fully consumed // for (int lookAhead = 0; lookAhead < 20; lookAhead++) { // if (currentPosition + lookAhead == source.length) @@ -1076,7 +1088,7 @@ public class Scanner implements IScanner, ITerminalSymbols { while (currentCharacter != '\'') { - /**** in PHP \r and \n are valid in string literals ****/ + /** ** in PHP \r and \n are valid in string literals *** */ // if ((currentCharacter == '\n') // || (currentCharacter == '\r')) { // // relocate if finding another quote fairly close: thus unicode '/u000D' will be fully consumed @@ -1142,7 +1154,7 @@ public class Scanner implements IScanner, ITerminalSymbols { } throw e; // rethrow } - if (checkNonExternalizedStringLiterals) { // check for presence of NLS tags //$NON-NLS-?$ where ? is an int. + if (checkNonExternalizedStringLiterals) { // check for presence of NLS tags //$NON-NLS-?$ where ? is an int. if (currentLine == null) { currentLine = new NLSLine(); lines.add(currentLine); @@ -1167,7 +1179,7 @@ public class Scanner implements IScanner, ITerminalSymbols { while (currentCharacter != '"') { - /**** in PHP \r and \n are valid in string literals ****/ + /** ** in PHP \r and \n are valid in string literals *** */ // if ((currentCharacter == '\n') // || (currentCharacter == '\r')) { // // relocate if finding another quote fairly close: thus unicode '/u000D' will be fully consumed @@ -1233,7 +1245,7 @@ public class Scanner implements IScanner, ITerminalSymbols { } throw e; // rethrow } - if (checkNonExternalizedStringLiterals) { // check for presence of NLS tags //$NON-NLS-?$ where ? is an int. + if (checkNonExternalizedStringLiterals) { // check for presence of NLS tags //$NON-NLS-?$ where ? is an int. if (currentLine == null) { currentLine = new NLSLine(); lines.add(currentLine); @@ -1258,7 +1270,7 @@ public class Scanner implements IScanner, ITerminalSymbols { while (currentCharacter != '`') { - /**** in PHP \r and \n are valid in string literals ****/ + /** ** in PHP \r and \n are valid in string literals *** */ // if ((currentCharacter == '\n') // || (currentCharacter == '\r')) { // // relocate if finding another quote fairly close: thus unicode '/u000D' will be fully consumed @@ -1324,7 +1336,7 @@ public class Scanner implements IScanner, ITerminalSymbols { } throw e; // rethrow } - if (checkNonExternalizedStringLiterals) { // check for presence of NLS tags //$NON-NLS-?$ where ? is an int. + if (checkNonExternalizedStringLiterals) { // check for presence of NLS tags //$NON-NLS-?$ where ? is an int. if (currentLine == null) { currentLine = new NLSLine(); lines.add(currentLine); @@ -1337,9 +1349,9 @@ public class Scanner implements IScanner, ITerminalSymbols { { int test; if ((currentCharacter == '#') || (test = getNextChar('/', '*')) == 0) { - //line comment + //line comment int endPositionForLineComment = 0; - try { //get the next char + try { //get the next char currentCharacter = source[currentPosition++]; // if (((currentCharacter = source[currentPosition++]) // == '\\') @@ -1494,7 +1506,7 @@ public class Scanner implements IScanner, ITerminalSymbols { currentLine = null; } } - try { //get the next char + try { //get the next char currentCharacter = source[currentPosition++]; // if (((currentCharacter = source[currentPosition++]) // == '\\') @@ -1590,7 +1602,7 @@ public class Scanner implements IScanner, ITerminalSymbols { // //At the end of this method currentCharacter holds the new visited char // //and currentPosition points right next after it // - // //ALL getNextChar.... ARE OPTIMIZED COPIES + // //ALL getNextChar.... ARE OPTIMIZED COPIES // // int c1 = 0, c2 = 0, c3 = 0, c4 = 0, unicodeSize = 6; // currentPosition++; @@ -1626,7 +1638,8 @@ public class Scanner implements IScanner, ITerminalSymbols { // } // unicodeAsBackSlash = currentCharacter == '\\'; // } - /* Tokenize a method body, assuming that curly brackets are properly balanced. + /* + * Tokenize a method body, assuming that curly brackets are properly balanced. */ public final void jumpOverMethodBody() { @@ -1740,9 +1753,9 @@ public class Scanner implements IScanner, ITerminalSymbols { { int test; if ((test = getNextChar('/', '*')) == 0) { - //line comment + //line comment try { - //get the next char + //get the next char currentCharacter = source[currentPosition++]; // if (((currentCharacter = source[currentPosition++]) == '\\') // && (source[currentPosition] == 'u')) { @@ -1778,7 +1791,7 @@ public class Scanner implements IScanner, ITerminalSymbols { // } while (currentCharacter != '\r' && currentCharacter != '\n') { - //get the next char + //get the next char currentCharacter = source[currentPosition++]; // if (((currentCharacter = source[currentPosition++]) // == '\\') @@ -1841,7 +1854,7 @@ public class Scanner implements IScanner, ITerminalSymbols { } if (recordLineSeparator && ((currentCharacter == '\r') || (currentCharacter == '\n'))) pushLineSeparator(); - try { //get the next char + try { //get the next char currentCharacter = source[currentPosition++]; // if (((currentCharacter = source[currentPosition++]) == '\\') // && (source[currentPosition] == 'u')) { @@ -1875,7 +1888,7 @@ public class Scanner implements IScanner, ITerminalSymbols { // (char) (((c1 * 16 + c2) * 16 + c3) * 16 + c4); // } // } - //loop until end of comment */ + //loop until end of comment */ while ((currentCharacter != '/') || (!star)) { if (recordLineSeparator && ((currentCharacter == '\r') || (currentCharacter == '\n'))) pushLineSeparator(); @@ -1992,7 +2005,7 @@ public class Scanner implements IScanner, ITerminalSymbols { // } // } public final int[] getLineEnds() { - //return a bounded copy of this.lineEnds + //return a bounded copy of this.lineEnds int[] copy; System.arraycopy(lineEnds, 0, copy = new int[linePtr + 1], 0, linePtr + 1); @@ -2271,7 +2284,7 @@ public class Scanner implements IScanner, ITerminalSymbols { // look-ahead for merged cr+lf try { if (source[currentPosition] == '\n') { - //System.out.println("look-ahead LF-" + currentPosition); + //System.out.println("look-ahead LF-" + currentPosition); lineEnds[linePtr] = currentPosition; currentPosition++; wasAcr = false; @@ -2286,13 +2299,13 @@ public class Scanner implements IScanner, ITerminalSymbols { if (currentCharacter == '\n') { //must merge eventual cr followed by lf if (wasAcr && (lineEnds[linePtr] == (currentPosition - 2))) { - //System.out.println("merge LF-" + (currentPosition - 1)); + //System.out.println("merge LF-" + (currentPosition - 1)); lineEnds[linePtr] = currentPosition - 1; } else { int separatorPos = currentPosition - 1; if ((linePtr > 0) && (lineEnds[linePtr] >= separatorPos)) return; - // System.out.println("LF-" + separatorPos); + // System.out.println("LF-" + separatorPos); try { lineEnds[++linePtr] = separatorPos; } catch (IndexOutOfBoundsException e) { @@ -2339,7 +2352,7 @@ public class Scanner implements IScanner, ITerminalSymbols { } // look-ahead for merged cr+lf if (source[currentPosition] == '\n') { - //System.out.println("look-ahead LF-" + currentPosition); + //System.out.println("look-ahead LF-" + currentPosition); lineEnds[linePtr] = currentPosition; currentPosition++; wasAcr = false; @@ -2351,13 +2364,13 @@ public class Scanner implements IScanner, ITerminalSymbols { if (currentCharacter == '\n') { //must merge eventual cr followed by lf if (wasAcr && (lineEnds[linePtr] == (currentPosition - 7))) { - //System.out.println("merge LF-" + (currentPosition - 1)); + //System.out.println("merge LF-" + (currentPosition - 1)); lineEnds[linePtr] = currentPosition - 6; } else { int separatorPos = currentPosition - 6; if ((linePtr > 0) && (lineEnds[linePtr] >= separatorPos)) return; - // System.out.println("LF-" + separatorPos); + // System.out.println("LF-" + separatorPos); try { lineEnds[++linePtr] = separatorPos; } catch (IndexOutOfBoundsException e) { @@ -2505,7 +2518,7 @@ public class Scanner implements IScanner, ITerminalSymbols { } else { // has read \OctalDigit NonDigit--> ignore last character currentPosition--; } - } else { // has read \OctalDigit NonOctalDigit--> ignore last character + } else { // has read \OctalDigit NonOctalDigit--> ignore last character currentPosition--; } } else { // has read \OctalDigit --> ignore last character @@ -2538,6 +2551,9 @@ public class Scanner implements IScanner, ITerminalSymbols { }; if (isVariable) { + if (new String(getCurrentTokenSource()).equals("$this")) { + return TokenNamethis; + } return TokenNameVariable; } int index, length; @@ -2573,7 +2589,7 @@ public class Scanner implements IScanner, ITerminalSymbols { firstLetter = data[index]; switch (firstLetter) { - case 'a' : // as and array + case 'a' : // as and array abstract switch (length) { case 2 : //as if ((data[++index] == 's')) { @@ -2587,11 +2603,22 @@ public class Scanner implements IScanner, ITerminalSymbols { } else { return TokenNameIdentifier; } - // case 5 : - // if ((data[++index] == 'r') && (data[++index] == 'r') && (data[++index] == 'a') && (data[++index] == 'y')) - // return TokenNamearray; - // else - // return TokenNameIdentifier; + case 5 : // array + if ((data[++index] == 'r') && (data[++index] == 'r') && (data[++index] == 'a') && (data[++index] == 'y')) + return TokenNamearray; + else + return TokenNameIdentifier; + case 8 : + if ((data[++index] == 'b') + && (data[++index] == 's') + && (data[++index] == 't') + && (data[++index] == 'r') + && (data[++index] == 'a') + && (data[++index] == 'c') + && (data[++index] == 't')) + return TokenNameabstract; + else + return TokenNameIdentifier; default : return TokenNameIdentifier; } @@ -2606,7 +2633,7 @@ public class Scanner implements IScanner, ITerminalSymbols { return TokenNameIdentifier; } - case 'c' : //case class continue + case 'c' : //case catch class const continue switch (length) { case 4 : if ((data[++index] == 'a') && (data[++index] == 's') && (data[++index] == 'e')) @@ -2614,8 +2641,12 @@ public class Scanner implements IScanner, ITerminalSymbols { else return TokenNameIdentifier; case 5 : - if ((data[++index] == 'l') && (data[++index] == 'a') && (data[++index] == 's') && (data[++index] == 's')) + if ((data[++index] == 'a') && (data[++index] == 't') && (data[++index] == 'c') && (data[++index] == 'h')) + return TokenNamecatch; + if ((data[index] == 'l') && (data[++index] == 'a') && (data[++index] == 's') && (data[++index] == 's')) return TokenNameclass; + if ((data[index] == 'o') && (data[++index] == 'n') && (data[++index] == 's') && (data[++index] == 't')) + return TokenNameconst; else return TokenNameIdentifier; case 8 : @@ -2633,13 +2664,18 @@ public class Scanner implements IScanner, ITerminalSymbols { return TokenNameIdentifier; } - case 'd' : //define default do + case 'd' : //define declare default do die switch (length) { case 2 : if ((data[++index] == 'o')) return TokenNamedo; else return TokenNameIdentifier; + case 3 : + if ((data[++index] == 'i') && (data[++index] == 'e')) + return TokenNamedie; + else + return TokenNameIdentifier; case 6 : if ((data[++index] == 'e') && (data[++index] == 'f') @@ -2651,6 +2687,14 @@ public class Scanner implements IScanner, ITerminalSymbols { return TokenNameIdentifier; case 7 : if ((data[++index] == 'e') + && (data[++index] == 'c') + && (data[++index] == 'l') + && (data[++index] == 'a') + && (data[++index] == 'r') + && (data[++index] == 'e')) + return TokenNamedeclare; + index = 0; + if ((data[++index] == 'e') && (data[++index] == 'f') && (data[++index] == 'a') && (data[++index] == 'u') @@ -2662,18 +2706,24 @@ public class Scanner implements IScanner, ITerminalSymbols { default : return TokenNameIdentifier; } - case 'e' : //echo else elseif extends + case 'e' : //echo else exit elseif extends eval switch (length) { case 4 : if ((data[++index] == 'c') && (data[++index] == 'h') && (data[++index] == 'o')) return TokenNameecho; else if ((data[index] == 'l') && (data[++index] == 's') && (data[++index] == 'e')) return TokenNameelse; + else if ((data[index] == 'x') && (data[++index] == 'i') && (data[++index] == 't')) + return TokenNameexit; + else if ((data[index] == 'v') && (data[++index] == 'a') && (data[++index] == 'l')) + return TokenNameeval; else return TokenNameIdentifier; - case 5 : // endif + case 5 : // endif empty if ((data[++index] == 'n') && (data[++index] == 'd') && (data[++index] == 'i') && (data[++index] == 'f')) return TokenNameendif; + if ((data[index] == 'm') && (data[++index] == 'p') && (data[++index] == 't') && (data[++index] == 'y')) + return TokenNameempty; else return TokenNameIdentifier; case 6 : // endfor @@ -2725,9 +2775,20 @@ public class Scanner implements IScanner, ITerminalSymbols { return TokenNameendswitch; else return TokenNameIdentifier; - case 10 : // endforeach + case 10 : // enddeclare if ((data[++index] == 'n') && (data[++index] == 'd') + && (data[++index] == 'd') + && (data[++index] == 'e') + && (data[++index] == 'c') + && (data[++index] == 'l') + && (data[++index] == 'a') + && (data[++index] == 'r') + && (data[++index] == 'e')) + return TokenNameendforeach; + index = 0; + if ((data[++index] == 'n') // endforeach + && (data[++index] == 'd') && (data[++index] == 'f') && (data[++index] == 'o') && (data[++index] == 'r') @@ -2743,7 +2804,7 @@ public class Scanner implements IScanner, ITerminalSymbols { return TokenNameIdentifier; } - case 'f' : //for false function + case 'f' : //for false final function switch (length) { case 3 : if ((data[++index] == 'o') && (data[++index] == 'r')) @@ -2753,9 +2814,11 @@ public class Scanner implements IScanner, ITerminalSymbols { case 5 : if ((data[++index] == 'a') && (data[++index] == 'l') && (data[++index] == 's') && (data[++index] == 'e')) return TokenNamefalse; + if ((data[index] == 'i') && (data[++index] == 'n') && (data[++index] == 'a') && (data[++index] == 'l')) + return TokenNamefinal; else return TokenNameIdentifier; - case 7 : // function + case 7 : // foreach if ((data[++index] == 'o') && (data[++index] == 'r') && (data[++index] == 'e') @@ -2791,7 +2854,7 @@ public class Scanner implements IScanner, ITerminalSymbols { } return TokenNameIdentifier; - case 'i' : //if int + case 'i' : //if int isset include include_once instanceof interface implements switch (length) { case 2 : if (data[++index] == 'f') @@ -2803,6 +2866,11 @@ public class Scanner implements IScanner, ITerminalSymbols { // return TokenNameint; // else // return TokenNameIdentifier; + case 5 : + if ((data[++index] == 's') && (data[++index] == 's') && (data[++index] == 'e') && (data[++index] == 't')) + return TokenNameisset; + else + return TokenNameIdentifier; case 7 : if ((data[++index] == 'n') && (data[++index] == 'c') @@ -2813,6 +2881,41 @@ public class Scanner implements IScanner, ITerminalSymbols { return TokenNameinclude; else return TokenNameIdentifier; + case 9 : // interface + if ((data[++index] == 'n') + && (data[++index] == 't') + && (data[++index] == 'e') + && (data[++index] == 'r') + && (data[++index] == 'f') + && (data[++index] == 'a') + && (data[++index] == 'c') + && (data[++index] == 'e')) + return TokenNameinterface; + else + return TokenNameIdentifier; + case 10 : // instanceof + if ((data[++index] == 'n') + && (data[++index] == 's') + && (data[++index] == 't') + && (data[++index] == 'a') + && (data[++index] == 'n') + && (data[++index] == 'c') + && (data[++index] == 'e') + && (data[++index] == 'o') + && (data[++index] == 'f')) + return TokenNameinstanceof; + if ((data[index] == 'm') + && (data[++index] == 'p') + && (data[++index] == 'l') + && (data[++index] == 'e') + && (data[++index] == 'm') + && (data[++index] == 'e') + && (data[++index] == 'n') + && (data[++index] == 't') + && (data[++index] == 's')) + return TokenNameimplements; + else + return TokenNameIdentifier; case 12 : if ((data[++index] == 'n') && (data[++index] == 'c') @@ -2879,11 +2982,44 @@ public class Scanner implements IScanner, ITerminalSymbols { // } return TokenNameIdentifier; - case 'p' : // print - if (length == 5) { - if ((data[++index] == 'r') && (data[++index] == 'i') && (data[++index] == 'n') && (data[++index] == 't')) { - return TokenNameprint; - } + case 'p' : // print public private protected + switch (length) { + case 5 : + if ((data[++index] == 'r') && (data[++index] == 'i') && (data[++index] == 'n') && (data[++index] == 't')) { + return TokenNameprint; + } else + return TokenNameIdentifier; + case 6 : + if ((data[++index] == 'u') + && (data[++index] == 'b') + && (data[++index] == 'l') + && (data[++index] == 'i') + && (data[++index] == 'c')) { + return TokenNamepublic; + } else + return TokenNameIdentifier; + case 7 : + if ((data[++index] == 'r') + && (data[++index] == 'i') + && (data[++index] == 'v') + && (data[++index] == 'a') + && (data[++index] == 't') + && (data[++index] == 'e')) { + return TokenNameprivate; + } else + return TokenNameIdentifier; + case 9 : + if ((data[++index] == 'r') + && (data[++index] == 'o') + && (data[++index] == 't') + && (data[++index] == 'e') + && (data[++index] == 'c') + && (data[++index] == 't') + && (data[++index] == 'e') + && (data[++index] == 'd')) { + return TokenNameprotected; + } else + return TokenNameIdentifier; } return TokenNameIdentifier; case 'r' : //return require require_once @@ -2921,7 +3057,7 @@ public class Scanner implements IScanner, ITerminalSymbols { } else return TokenNameIdentifier; - case 's' : //static switch + case 's' : //static switch switch (length) { case 6 : if (data[++index] == 't') @@ -2942,22 +3078,43 @@ public class Scanner implements IScanner, ITerminalSymbols { return TokenNameIdentifier; } - case 't' : // true + case 't' : // try true throw switch (length) { - + case 3 : + if ((data[++index] == 'r') && (data[++index] == 'y')) + return TokenNametry; + else + return TokenNameIdentifier; case 4 : if ((data[++index] == 'r') && (data[++index] == 'u') && (data[++index] == 'e')) return TokenNametrue; else return TokenNameIdentifier; - // if ((data[++index] == 'h') && (data[++index] == 'i') && (data[++index] == 's')) - // return TokenNamethis; + case 5 : + if ((data[++index] == 'h') && (data[++index] == 'r') && (data[++index] == 'o') && (data[++index] == 'w')) + return TokenNamethrow; + else + return TokenNameIdentifier; default : return TokenNameIdentifier; } - - case 'v' : //var + case 'u' : //use unset + switch (length) { + case 3 : + if ((data[++index] == 's') && (data[++index] == 'e')) + return TokenNameuse; + else + return TokenNameIdentifier; + case 5 : + if ((data[++index] == 'n') && (data[++index] == 's') && (data[++index] == 'e') && (data[++index] == 't')) + return TokenNameunset; + else + return TokenNameIdentifier; + default : + return TokenNameIdentifier; + } + case 'v' : //var switch (length) { case 3 : if ((data[++index] == 'a') && (data[++index] == 'r')) @@ -2969,14 +3126,15 @@ public class Scanner implements IScanner, ITerminalSymbols { return TokenNameIdentifier; } - case 'w' : //while + case 'w' : //while switch (length) { case 5 : if ((data[++index] == 'h') && (data[++index] == 'i') && (data[++index] == 'l') && (data[++index] == 'e')) return TokenNamewhile; else return TokenNameIdentifier; - //case 6:if ( (data[++index] =='i') && (data[++index]=='d') && (data[++index]=='e') && (data[++index]=='f')&& (data[++index]=='p')) + //case 6:if ( (data[++index] =='i') && (data[++index]=='d') && (data[++index]=='e') && (data[++index]=='f')&& + // (data[++index]=='p')) //return TokenNamewidefp ; //else //return TokenNameIdentifier; @@ -3154,7 +3312,7 @@ public class Scanner implements IScanner, ITerminalSymbols { } /** * Search the line number corresponding to a specific position - * + * */ public final int getLineNumber(int position) { @@ -3229,7 +3387,7 @@ public class Scanner implements IScanner, ITerminalSymbols { switch (act) { case TokenNameERROR : - return "ScannerError(" + new String(getCurrentTokenSource()) + ")"; //$NON-NLS-1$ + return "ScannerError"; // + new String(getCurrentTokenSource()) + ")"; //$NON-NLS-1$ case TokenNameStopPHP : return "StopPHP(" + new String(getCurrentTokenSource()) + ")"; //$NON-NLS-1$ //$NON-NLS-2$ case TokenNameIdentifier : @@ -3310,6 +3468,8 @@ public class Scanner implements IScanner, ITerminalSymbols { return "var"; //$NON-NLS-1$ case TokenNamewhile : return "while"; //$NON-NLS-1$ + case TokenNamethis : + return "$this"; //$NON-NLS-1$ case TokenNameIntegerLiteral : return "Integer(" + new String(getCurrentTokenSource()) + ")"; //$NON-NLS-1$ //$NON-NLS-2$ case TokenNameDoubleLiteral : @@ -3329,6 +3489,8 @@ public class Scanner implements IScanner, ITerminalSymbols { return "--"; //$NON-NLS-1$ case TokenNameEQUAL_EQUAL : return "=="; //$NON-NLS-1$ + case TokenNameEQUAL_EQUAL_EQUAL : + return "==="; //$NON-NLS-1$ case TokenNameEQUAL_GREATER : return "=>"; //$NON-NLS-1$ case TokenNameLESS_EQUAL : @@ -3337,6 +3499,8 @@ public class Scanner implements IScanner, ITerminalSymbols { return ">="; //$NON-NLS-1$ case TokenNameNOT_EQUAL : return "!="; //$NON-NLS-1$ + case TokenNameNOT_EQUAL_EQUAL : + return "!=="; //$NON-NLS-1$ case TokenNameLEFT_SHIFT : return "<<"; //$NON-NLS-1$ case TokenNameRIGHT_SHIFT : @@ -3500,4 +3664,195 @@ public class Scanner implements IScanner, ITerminalSymbols { } currentLine = null; } + + public final void scanEscapeCharacter() throws InvalidInputException { + // the string with "\\u" is a legal string of two chars \ and u + //thus we use a direct access to the source (for regular cases). + + if (unicodeAsBackSlash) { + // consume next character + unicodeAsBackSlash = false; + // if (((currentCharacter = source[currentPosition++]) == '\\') && (source[currentPosition] == 'u')) { + // getNextUnicodeChar(); + // } else { + if (withoutUnicodePtr != 0) { + withoutUnicodeBuffer[++withoutUnicodePtr] = currentCharacter; + // } + } + } else + currentCharacter = source[currentPosition++]; + switch (currentCharacter) { + case 'b' : + currentCharacter = '\b'; + break; + case 't' : + currentCharacter = '\t'; + break; + case 'n' : + currentCharacter = '\n'; + break; + case 'f' : + currentCharacter = '\f'; + break; + case 'r' : + currentCharacter = '\r'; + break; + case '\"' : + currentCharacter = '\"'; + break; + case '\'' : + currentCharacter = '\''; + break; + case '\\' : + currentCharacter = '\\'; + break; + default : + // -----------octal escape-------------- + // OctalDigit + // OctalDigit OctalDigit + // ZeroToThree OctalDigit OctalDigit + + int number = Character.getNumericValue(currentCharacter); + if (number >= 0 && number <= 7) { + boolean zeroToThreeNot = number > 3; + if (Character.isDigit(currentCharacter = source[currentPosition++])) { + int digit = Character.getNumericValue(currentCharacter); + if (digit >= 0 && digit <= 7) { + number = (number * 8) + digit; + if (Character.isDigit(currentCharacter = source[currentPosition++])) { + if (zeroToThreeNot) { // has read \NotZeroToThree OctalDigit Digit --> ignore last character + currentPosition--; + } else { + digit = Character.getNumericValue(currentCharacter); + if (digit >= 0 && digit <= 7) { // has read \ZeroToThree OctalDigit OctalDigit + number = (number * 8) + digit; + } else { // has read \ZeroToThree OctalDigit NonOctalDigit --> ignore last character + currentPosition--; + } + } + } else { // has read \OctalDigit NonDigit--> ignore last character + currentPosition--; + } + } else { // has read \OctalDigit NonOctalDigit--> ignore last character + currentPosition--; + } + } else { // has read \OctalDigit --> ignore last character + currentPosition--; + } + if (number > 255) + throw new InvalidInputException(INVALID_ESCAPE); + currentCharacter = (char) number; + } else + throw new InvalidInputException(INVALID_ESCAPE); + } + } + + // chech presence of task: tags + public void checkTaskTag(int commentStart, int commentEnd) { + + // only look for newer task: tags + if (this.foundTaskCount > 0 && this.foundTaskPositions[this.foundTaskCount - 1][0] >= commentStart) { + return; + } + int foundTaskIndex = this.foundTaskCount; + nextChar : for (int i = commentStart; i < commentEnd && i < this.eofPosition; i++) { + + char[] tag = null; + char[] priority = null; + + // check for tag occurrence + nextTag : for (int itag = 0; itag < this.taskTags.length; itag++) { + tag = this.taskTags[itag]; + priority = this.taskPriorities != null && itag < this.taskPriorities.length ? this.taskPriorities[itag] : null; + int tagLength = tag.length; + for (int t = 0; t < tagLength; t++) { + if (this.source[i + t] != tag[t]) + continue nextTag; + } + + if (this.foundTaskTags == null) { + this.foundTaskTags = new char[5][]; + this.foundTaskMessages = new char[5][]; + this.foundTaskPriorities = new char[5][]; + this.foundTaskPositions = new int[5][]; + } else if (this.foundTaskCount == this.foundTaskTags.length) { + System.arraycopy(this.foundTaskTags, 0, this.foundTaskTags = new char[this.foundTaskCount * 2][], 0, this.foundTaskCount); + System.arraycopy( + this.foundTaskMessages, + 0, + this.foundTaskMessages = new char[this.foundTaskCount * 2][], + 0, + this.foundTaskCount); + System.arraycopy( + this.foundTaskPriorities, + 0, + this.foundTaskPriorities = new char[this.foundTaskCount * 2][], + 0, + this.foundTaskCount); + System.arraycopy( + this.foundTaskPositions, + 0, + this.foundTaskPositions = new int[this.foundTaskCount * 2][], + 0, + this.foundTaskCount); + } + this.foundTaskTags[this.foundTaskCount] = tag; + this.foundTaskPriorities[this.foundTaskCount] = priority; + this.foundTaskPositions[this.foundTaskCount] = new int[] { i, i + tagLength - 1 }; + this.foundTaskMessages[this.foundTaskCount] = CharOperation.NO_CHAR; + this.foundTaskCount++; + + i += tagLength - 1; // will be incremented when looping + } + } + + for (int i = foundTaskIndex; i < this.foundTaskCount; i++) { + // retrieve message start and end positions + int msgStart = this.foundTaskPositions[i][0] + this.foundTaskTags[i].length; + int max_value = i + 1 < this.foundTaskCount ? this.foundTaskPositions[i + 1][0] - 1 : commentEnd - 1; + // at most beginning of next task + if (max_value < msgStart) + max_value = msgStart; // would only occur if tag is before EOF. + int end = -1; + char c; + + for (int j = msgStart; j < max_value; j++) { + if ((c = this.source[j]) == '\n' || c == '\r') { + end = j - 1; + break; + } + } + + if (end == -1) { + for (int j = max_value; j > msgStart; j--) { + if ((c = this.source[j]) == '*') { + end = j - 1; + break; + } + } + if (end == -1) + end = max_value; + } + + if (msgStart == end) + continue; // empty + + // trim the message + while (CharOperation.isWhitespace(source[end]) && msgStart <= end) + end--; + while (CharOperation.isWhitespace(source[msgStart]) && msgStart <= end) + msgStart++; + + // update the end position of the task + this.foundTaskPositions[i][1] = end; + + // get the message source + final int messageLength = end - msgStart + 1; + char[] message = new char[messageLength]; + + System.arraycopy(source, msgStart, message, 0, messageLength); + this.foundTaskMessages[i] = message; + } + } + }