From a658fee5a1f03189af738275abd37ced0edc1b5c Mon Sep 17 00:00:00 2001 From: abhisheks-gh Date: Thu, 1 Jan 2026 19:03:06 +0530 Subject: [PATCH] Add fix for issue #357 - strick parsing of null, true and false keywords --- src/main/java/com/jsoniter/IterImpl.java | 9 +++---- .../com/jsoniter/IterImplForStreaming.java | 12 +++------ .../java/com/jsoniter/IterImplObject.java | 6 +++-- src/main/java/com/jsoniter/IterImplSkip.java | 8 +++--- src/main/java/com/jsoniter/JsonIterator.java | 27 ++++++++++++++----- 5 files changed, 37 insertions(+), 25 deletions(-) diff --git a/src/main/java/com/jsoniter/IterImpl.java b/src/main/java/com/jsoniter/IterImpl.java index ad779fd8..5deabb5b 100644 --- a/src/main/java/com/jsoniter/IterImpl.java +++ b/src/main/java/com/jsoniter/IterImpl.java @@ -183,13 +183,12 @@ public static Any readAny(JsonIterator iter) throws IOException { skipString(iter); return Any.lazyString(iter.buf, start, iter.head); case 't': - skipFixedBytes(iter, 3); - return Any.wrap(true); case 'f': - skipFixedBytes(iter, 4); - return Any.wrap(false); + iter.unreadByte(); + return Any.wrap(iter.readBoolean()); case 'n': - skipFixedBytes(iter, 3); + iter.unreadByte(); + iter.readNull(); return Any.wrap((Object) null); case '[': skipArray(iter); diff --git a/src/main/java/com/jsoniter/IterImplForStreaming.java b/src/main/java/com/jsoniter/IterImplForStreaming.java index 2cef3a16..7d20455a 100644 --- a/src/main/java/com/jsoniter/IterImplForStreaming.java +++ b/src/main/java/com/jsoniter/IterImplForStreaming.java @@ -326,16 +326,12 @@ public static Any readAny(JsonIterator iter) throws IOException { byte[] copied = copySkippedBytes(iter); return Any.lazyString(copied, 0, copied.length); case 't': - skipFixedBytes(iter, 3); - iter.skipStartedAt = -1; - return Any.wrap(true); case 'f': - skipFixedBytes(iter, 4); - iter.skipStartedAt = -1; - return Any.wrap(false); + iter.unreadByte(); + return Any.wrap(iter.readBoolean()); case 'n': - skipFixedBytes(iter, 3); - iter.skipStartedAt = -1; + iter.unreadByte(); + iter.readNull(); return Any.wrap((Object) null); case '[': skipArray(iter); diff --git a/src/main/java/com/jsoniter/IterImplObject.java b/src/main/java/com/jsoniter/IterImplObject.java index 64468d94..10484505 100644 --- a/src/main/java/com/jsoniter/IterImplObject.java +++ b/src/main/java/com/jsoniter/IterImplObject.java @@ -8,8 +8,10 @@ public static final String readObject(JsonIterator iter) throws IOException { byte c = IterImpl.nextToken(iter); switch (c) { case 'n': - IterImpl.skipFixedBytes(iter, 3); - return null; + iter.unreadByte(); + if (iter.readNull()) { + return null; + } case '{': c = IterImpl.nextToken(iter); if (c == '"') { diff --git a/src/main/java/com/jsoniter/IterImplSkip.java b/src/main/java/com/jsoniter/IterImplSkip.java index c9a82afd..9ba34c31 100644 --- a/src/main/java/com/jsoniter/IterImplSkip.java +++ b/src/main/java/com/jsoniter/IterImplSkip.java @@ -35,12 +35,14 @@ public static final void skip(JsonIterator iter) throws IOException { case '9': IterImpl.skipUntilBreak(iter); return; - case 't': case 'n': - IterImpl.skipFixedBytes(iter, 3); // true or null + iter.unreadByte(); + iter.readNull(); return; + case 't': case 'f': - IterImpl.skipFixedBytes(iter, 4); // false + iter.unreadByte(); + iter.readBoolean(); // true or false return; case '[': IterImpl.skipArray(iter); diff --git a/src/main/java/com/jsoniter/JsonIterator.java b/src/main/java/com/jsoniter/JsonIterator.java index c198540b..cf5d968a 100644 --- a/src/main/java/com/jsoniter/JsonIterator.java +++ b/src/main/java/com/jsoniter/JsonIterator.java @@ -163,21 +163,34 @@ public final boolean readNull() throws IOException { unreadByte(); return false; } - IterImpl.skipFixedBytes(this, 3); // null - return true; + if (IterImpl.readByte(this) == 'u' && + IterImpl.readByte(this) == 'l' && + IterImpl.readByte(this) == 'l') { + return true; // null + } + throw reportError("readNull", "expect null"); } public final boolean readBoolean() throws IOException { byte c = IterImpl.nextToken(this); if ('t' == c) { - IterImpl.skipFixedBytes(this, 3); // true - return true; + if (IterImpl.readByte(this) == 'r' && + IterImpl.readByte(this) == 'u' && + IterImpl.readByte(this) == 'e') { + return true; + } + throw reportError("readBoolean", "expect true"); } if ('f' == c) { - IterImpl.skipFixedBytes(this, 4); // false - return false; + if (IterImpl.readByte(this) == 'a' && + IterImpl.readByte(this) == 'l' && + IterImpl.readByte(this) == 's' && + IterImpl.readByte(this) == 'e') { + return false; + } + throw reportError("readBoolean", "expect false"); } - throw reportError("readBoolean", "expect t or f, found: " + c); + throw reportError("readBoolean", "expect true or false"); } public final short readShort() throws IOException {