From cba1c352e3c4236205dc96de643e780abb3c7b64 Mon Sep 17 00:00:00 2001 From: m-holger Date: Tue, 24 Jan 2023 11:47:06 +0000 Subject: [PATCH] In JSONParser add lex_state ls_number_minus --- libqpdf/JSON.cc | 24 +++++++++++++++++++++--- libtests/libtests.testcov | 3 +-- libtests/qtest/json_parse.test | 2 ++ libtests/qtest/json_parse/bad-31.out | 2 +- libtests/qtest/json_parse/bad-41.json | 2 ++ libtests/qtest/json_parse/bad-41.out | 1 + libtests/qtest/json_parse/bad-42.json | 1 + libtests/qtest/json_parse/bad-42.out | 1 + 8 files changed, 30 insertions(+), 6 deletions(-) create mode 100644 libtests/qtest/json_parse/bad-41.json create mode 100644 libtests/qtest/json_parse/bad-41.out create mode 100644 libtests/qtest/json_parse/bad-42.json create mode 100644 libtests/qtest/json_parse/bad-42.out diff --git a/libqpdf/JSON.cc b/libqpdf/JSON.cc index 5205d4f9..c881811b 100644 --- a/libqpdf/JSON.cc +++ b/libqpdf/JSON.cc @@ -647,6 +647,7 @@ namespace enum lex_state_e { ls_top, ls_number, + ls_number_minus, ls_alpha, ls_string, ls_backslash, @@ -861,7 +862,7 @@ JSONParser::getToken() } else if ((*p >= 'a') && (*p <= 'z')) { lex_state = ls_alpha; } else if (*p == '-') { - lex_state = ls_number; + lex_state = ls_number_minus; number_before_point = 0; number_after_point = 0; number_after_e = 0; @@ -891,6 +892,21 @@ JSONParser::getToken() } break; + case ls_number_minus: + if ((*p >= '1') && (*p <= '9')) { + ++number_before_point; + lex_state = ls_number; + } else if (*p == '0') { + ++number_before_point; + lex_state = ls_number; + } else { + QTC::TC("libtests", "JSON parse number minus no digits"); + throw std::runtime_error( + "JSON: offset " + std::to_string(offset) + + ": numeric literal: no digit after minus sign"); + } + break; + case ls_number: if ((*p >= '0') && (*p <= '9')) { if (number_saw_e) { @@ -1020,6 +1036,7 @@ JSONParser::getToken() break; case ls_number: + case ls_number_minus: case ls_alpha: // okay break; @@ -1093,8 +1110,9 @@ JSONParser::handleToken() break; case ls_number: + case ls_number_minus: if (number_saw_point && (number_after_point == 0)) { - QTC::TC("libtests", "JSON parse decimal with no digits"); + // QTC::TC("libtests", "JSON parse decimal with no digits"); throw std::runtime_error( "JSON: offset " + std::to_string(offset) + ": decimal point with no digits"); @@ -1108,7 +1126,7 @@ JSONParser::handleToken() ": number with leading zero"); } if ((number_before_point == 0) && (number_after_point == 0)) { - QTC::TC("libtests", "JSON parse number no digits"); + // QTC::TC("libtests", "JSON parse number no digits"); throw std::runtime_error( "JSON: offset " + std::to_string(offset) + ": number with no digits"); diff --git a/libtests/libtests.testcov b/libtests/libtests.testcov index 2ceef541..26cf2048 100644 --- a/libtests/libtests.testcov +++ b/libtests/libtests.testcov @@ -58,7 +58,6 @@ QPDFArgParser bad option for help 0 QPDFArgParser bad topic for help 0 QPDFArgParser invalid choice handler to unknown 0 JSON parse junk after object 0 -JSON parse decimal with no digits 0 JSON parse invalid keyword 0 JSON parse expected colon 0 JSON parse expected , or } 0 @@ -76,11 +75,11 @@ JSON parse duplicate point 0 JSON parse duplicate e 0 JSON parse unexpected sign 0 JSON parse numeric bad character 0 +JSON parse number minus no digits 0 JSON parse keyword bad character 0 JSON parse backslash bad character 0 JSON parse unterminated string 0 JSON parse leading zero 0 -JSON parse number no digits 0 JSON parse premature end of u 0 JSON parse bad hex after u 0 JSONHandler unhandled value 0 diff --git a/libtests/qtest/json_parse.test b/libtests/qtest/json_parse.test index 112da0a9..7c64e3bd 100644 --- a/libtests/qtest/json_parse.test +++ b/libtests/qtest/json_parse.test @@ -121,6 +121,8 @@ my @bad = ( "high high surrogate", # 38 "dangling high surrogate", # 39 "duplicate dictionary key", # 40 + "decimal point after minus",# 41 + "e after minus", # 42 ); my $i = 0; diff --git a/libtests/qtest/json_parse/bad-31.out b/libtests/qtest/json_parse/bad-31.out index 344f42e8..2228d08d 100644 --- a/libtests/qtest/json_parse/bad-31.out +++ b/libtests/qtest/json_parse/bad-31.out @@ -1 +1 @@ -exception: bad-31.json: JSON: offset 2: number with no digits +exception: bad-31.json: JSON: offset 1: numeric literal: no digit after minus sign diff --git a/libtests/qtest/json_parse/bad-41.json b/libtests/qtest/json_parse/bad-41.json new file mode 100644 index 00000000..dad59049 --- /dev/null +++ b/libtests/qtest/json_parse/bad-41.json @@ -0,0 +1,2 @@ +-.123 + diff --git a/libtests/qtest/json_parse/bad-41.out b/libtests/qtest/json_parse/bad-41.out new file mode 100644 index 00000000..bebcfdb9 --- /dev/null +++ b/libtests/qtest/json_parse/bad-41.out @@ -0,0 +1 @@ +exception: bad-41.json: JSON: offset 1: numeric literal: no digit after minus sign diff --git a/libtests/qtest/json_parse/bad-42.json b/libtests/qtest/json_parse/bad-42.json new file mode 100644 index 00000000..2f9148b0 --- /dev/null +++ b/libtests/qtest/json_parse/bad-42.json @@ -0,0 +1 @@ +-e123 diff --git a/libtests/qtest/json_parse/bad-42.out b/libtests/qtest/json_parse/bad-42.out new file mode 100644 index 00000000..96e9a0a3 --- /dev/null +++ b/libtests/qtest/json_parse/bad-42.out @@ -0,0 +1 @@ +exception: bad-42.json: JSON: offset 1: numeric literal: no digit after minus sign