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 2fa5f0b..1ff0619 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,7 +14,10 @@ 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 { @@ -150,7 +153,16 @@ public class Scanner implements IScanner, ITerminalSymbols { public static final int SquareBracket = 1; public static final int CurlyBracket = 2; public static final int BracketKinds = 3; - + + // 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 = false; public Scanner() { @@ -218,6 +230,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) @@ -275,6 +288,18 @@ 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; + + 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 * @@ -851,8 +876,12 @@ public class Scanner implements IScanner, ITerminalSymbols { return TokenNameTWIDDLE_EQUAL; return TokenNameTWIDDLE; case '!' : - if (getNextChar('=')) + if (getNextChar('=')) { + if (getNextChar('=')) { + return TokenNameNOT_EQUAL_EQUAL; + } return TokenNameNOT_EQUAL; + } return TokenNameNOT; case '*' : if (getNextChar('=')) @@ -932,8 +961,12 @@ public class Scanner implements IScanner, ITerminalSymbols { return TokenNameGREATER; } case '=' : - if (getNextChar('=')) + if (getNextChar('=')) { + if (getNextChar('=')) { + return TokenNameEQUAL_EQUAL_EQUAL; + } return TokenNameEQUAL_EQUAL; + } if (getNextChar('>')) return TokenNameEQUAL_GREATER; return TokenNameEQUAL; @@ -2524,6 +2557,9 @@ public class Scanner implements IScanner, ITerminalSymbols { }; if (isVariable) { + if (new String(getCurrentTokenSource()).equals("$this")) { + return TokenNamethis; + } return TokenNameVariable; } int index, length; @@ -3215,7 +3251,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 : @@ -3296,6 +3332,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 : @@ -3315,6 +3353,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 : @@ -3323,6 +3363,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 : @@ -3486,4 +3528,177 @@ 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; + } +} + }