1
0
Fork 0
mirror of https://github.com/ethauvin/JSON-java.git synced 2025-06-17 07:50:52 -07:00

Merge pull request #352 from johnjaylward/ErrorMessagePositionFixes

Error message position fixes
This commit is contained in:
Sean Leary 2017-07-06 18:07:50 -05:00 committed by GitHub
commit 5024f2d210
3 changed files with 117 additions and 65 deletions

View file

@ -70,9 +70,12 @@ public class CDL {
c = x.next();
if (c == q) {
//Handle escaped double-quote
if(x.next() != '\"')
{
char nextC = x.next();
if(nextC != '\"') {
// if our quote was the end of the file, don't step
if(nextC > 0) {
x.back();
}
break;
}
}

View file

@ -39,7 +39,7 @@ SOFTWARE.
* @version 2014-05-03
*/
public class JSONTokener {
/** current read character. */
/** current read character position on the current line. */
private long character;
/** flag to indicate if the end of the input has been found. */
private boolean eof;
@ -47,16 +47,18 @@ public class JSONTokener {
private long index;
/** current line of the input. */
private long line;
/** previous index of the input. */
/** previous character read from the input. */
private char previous;
/** Reader for the input. */
private final Reader reader;
/** flag to indicate that a previous character was requested. */
private boolean usePrevious;
/** the number of characters read in the previous line. */
private long characterPreviousLine;
/**
* Construct a JSONTokener from a Reader.
* Construct a JSONTokener from a Reader. The caller must close the Reader.
*
* @param reader A reader.
*/
@ -69,12 +71,13 @@ public class JSONTokener {
this.previous = 0;
this.index = 0;
this.character = 1;
this.characterPreviousLine = 0;
this.line = 1;
}
/**
* Construct a JSONTokener from an InputStream.
* Construct a JSONTokener from an InputStream. The caller must close the input stream.
* @param inputStream The source.
*/
public JSONTokener(InputStream inputStream) {
@ -103,12 +106,23 @@ public class JSONTokener {
if (this.usePrevious || this.index <= 0) {
throw new JSONException("Stepping back two steps is not supported");
}
this.index -= 1;
this.character -= 1;
this.decrementIndexes();
this.usePrevious = true;
this.eof = false;
}
/**
* Decrements the indexes for the {@link #back()} method based on the previous character read.
*/
private void decrementIndexes() {
this.index--;
if(this.previous=='\r' || this.previous == '\n') {
this.line--;
this.character=this.characterPreviousLine ;
} else if(this.character > 0){
this.character--;
}
}
/**
* Get the hex value of a character (base16).
@ -130,6 +144,8 @@ public class JSONTokener {
}
/**
* Checks if the end of the input has been reached.
*
* @return true if at the end of the file and we didn't step back
*/
public boolean end() {
@ -145,11 +161,24 @@ public class JSONTokener {
* or backward while checking for more data.
*/
public boolean more() throws JSONException {
this.next();
if (this.end()) {
if(this.usePrevious) {
return true;
}
try {
this.reader.mark(1);
} catch (IOException e) {
throw new JSONException("Unable to preserve stream position", e);
}
try {
// -1 is EOF, but next() can not consume the null character '\0'
if(this.reader.read() <= 0) {
this.eof = true;
return false;
}
this.back();
this.reader.reset();
} catch (IOException e) {
throw new JSONException("Unable to read the next character from the stream", e);
}
return true;
}
@ -171,26 +200,39 @@ public class JSONTokener {
} catch (IOException exception) {
throw new JSONException(exception);
}
}
if (c <= 0) { // End of stream
this.eof = true;
c = 0;
}
}
this.index += 1;
if (this.previous == '\r') {
this.line += 1;
this.character = c == '\n' ? 0 : 1;
} else if (c == '\n') {
this.line += 1;
this.character = 0;
} else {
this.character += 1;
return 0;
}
this.incrementIndexes(c);
this.previous = (char) c;
return this.previous;
}
/**
* Increments the internal indexes according to the previous character
* read and the character passed as the current character.
* @param c the current character read.
*/
private void incrementIndexes(int c) {
if(c > 0) {
this.index++;
if(c=='\r') {
this.line++;
this.characterPreviousLine = this.character;
this.character=0;
}else if (c=='\n') {
if(this.previous != '\r') {
this.line++;
this.characterPreviousLine = this.character;
}
this.character=0;
} else {
this.character++;
}
}
}
/**
* Consume the next character, and check that it matches a specified
@ -202,9 +244,12 @@ public class JSONTokener {
public char next(char c) throws JSONException {
char n = this.next();
if (n != c) {
if(n > 0) {
throw this.syntaxError("Expected '" + c + "' and instead saw '" +
n + "'");
}
throw this.syntaxError("Expected '" + c + "' and instead saw ''");
}
return n;
}
@ -432,13 +477,17 @@ public class JSONTokener {
do {
c = this.next();
if (c == 0) {
// in some readers, reset() may throw an exception if
// the remaining portion of the input is greater than
// the mark size (1,000,000 above).
this.reader.reset();
this.index = startIndex;
this.character = startCharacter;
this.line = startLine;
return c;
return 0;
}
} while (c != to);
this.reader.mark(1);
} catch (IOException exception) {
throw new JSONException(exception);
}
@ -446,7 +495,6 @@ public class JSONTokener {
return c;
}
/**
* Make a JSONException to signal a syntax error.
*

View file

@ -64,11 +64,8 @@ public class XMLTokener extends JSONTokener {
char c;
int i;
StringBuilder sb = new StringBuilder();
for (;;) {
while (more()) {
c = next();
if (end()) {
throw syntaxError("Unclosed CDATA");
}
sb.append(c);
i = sb.length() - 3;
if (i >= 0 && sb.charAt(i) == ']' &&
@ -77,6 +74,7 @@ public class XMLTokener extends JSONTokener {
return sb.toString();
}
}
throw syntaxError("Unclosed CDATA");
}
@ -103,7 +101,10 @@ public class XMLTokener extends JSONTokener {
}
sb = new StringBuilder();
for (;;) {
if (c == '<' || c == 0) {
if (c == 0) {
return sb.toString().trim();
}
if (c == '<') {
back();
return sb.toString().trim();
}