fix: JSON parsing of negative STNumber and STAmount (#5990)

This change fixes JSON parsing of negative `int` input in `STNumber` and `STAmount`. The conversion of JSON to `STNumber` or `STAmount` may trigger a condition where we negate smallest possible `int` value, which is undefined behaviour. We use a temporary storage as `int64_t` to avoid this bug. Note that this only affects RPC, because we do not parse JSON in the protocol layer, and hence no amendment is needed.
This commit is contained in:
Bronek Kozicki
2025-11-10 17:33:20 +00:00
committed by GitHub
parent 3968efb5f1
commit 3b810c305a
8 changed files with 454 additions and 61 deletions

View File

@@ -2,6 +2,7 @@
#include <xrpl/beast/unit_test/suite.h>
#include <xrpl/json/json_forwards.h>
#include <xrpl/protocol/Issue.h>
#include <xrpl/protocol/SField.h>
#include <xrpl/protocol/STAmount.h>
#include <xrpl/protocol/STNumber.h>
@@ -126,6 +127,30 @@ struct STNumber_test : public beast::unit_test::suite
BEAST_EXPECT(
numberFromJson(sfNumber, "-0.000e6") == STNumber(sfNumber, 0));
constexpr auto imin = std::numeric_limits<int>::min();
BEAST_EXPECT(
numberFromJson(sfNumber, imin) ==
STNumber(sfNumber, Number(imin, 0)));
BEAST_EXPECT(
numberFromJson(sfNumber, std::to_string(imin)) ==
STNumber(sfNumber, Number(imin, 0)));
constexpr auto imax = std::numeric_limits<int>::max();
BEAST_EXPECT(
numberFromJson(sfNumber, imax) ==
STNumber(sfNumber, Number(imax, 0)));
BEAST_EXPECT(
numberFromJson(sfNumber, std::to_string(imax)) ==
STNumber(sfNumber, Number(imax, 0)));
constexpr auto umax = std::numeric_limits<unsigned int>::max();
BEAST_EXPECT(
numberFromJson(sfNumber, umax) ==
STNumber(sfNumber, Number(umax, 0)));
BEAST_EXPECT(
numberFromJson(sfNumber, std::to_string(umax)) ==
STNumber(sfNumber, Number(umax, 0)));
// Obvious non-numbers tested here
try
{