diff --git a/Builds/CMake/RippledCompiler.cmake b/Builds/CMake/RippledCompiler.cmake index 163c82823..cfcede0b6 100644 --- a/Builds/CMake/RippledCompiler.cmake +++ b/Builds/CMake/RippledCompiler.cmake @@ -17,7 +17,9 @@ target_compile_features (common INTERFACE cxx_std_20) target_compile_definitions (common INTERFACE $<$:DEBUG _DEBUG> - $<$,$>>:NDEBUG>) + $<$,$>>:NDEBUG> + # TODO: Remove once we have migrated functions from OpenSSL 1.x to 3.x. + OPENSSL_SUPPRESS_DEPRECATED) # ^^^^ NOTE: CMAKE release builds already have NDEBUG # defined, so no need to add it explicitly except for # this special case of (profile ON) and (assert OFF) diff --git a/src/ripple/app/hook/impl/HookAPI.cpp b/src/ripple/app/hook/impl/HookAPI.cpp index 92e45e86a..3c01ef69d 100644 --- a/src/ripple/app/hook/impl/HookAPI.cpp +++ b/src/ripple/app/hook/impl/HookAPI.cpp @@ -429,10 +429,26 @@ HookAPI::sto_subarray(Bytes const& data, uint32_t index_id) const // unwrap the array if it is wrapped, // by removing a byte from the start and end + // why here 0xF0? + // STI_ARRAY = 0xF0 + // eg) Signers field value = 0x03 => 0xF3 + // eg) Amounts field value = 0x5C => 0xF0, 0x5C if ((*upto & 0xF0U) == 0xF0U) { - upto++; - end--; + if (hookCtx.applyCtx.view().rules().enabled(fixHookAPI20251128) && + *upto == 0xF0U) + { + // field value > 15 + upto++; + upto++; + end--; + } + else + { + // field value <= 15 + upto++; + end--; + } } if (upto >= end) @@ -498,6 +514,31 @@ HookAPI::sto_emplace( return Unexpected(TOO_SMALL); } + if (field_object.has_value() && + hookCtx.applyCtx.view().rules().enabled(fixHookAPI20251128)) + { + // inject field should be valid sto object and it's field id should + // match the field_id + unsigned char* inject_start = (unsigned char*)(field_object->data()); + unsigned char* inject_end = + (unsigned char*)(field_object->data() + field_object->size()); + int type = -1, field = -1, payload_start = -1, payload_length = -1; + auto const length = get_stobject_length( + inject_start, + inject_end, + type, + field, + payload_start, + payload_length, + 0); + if (!length) + return Unexpected(PARSE_ERROR); + if ((type << 16) + field != field_id) + { + return Unexpected(PARSE_ERROR); + } + } + std::vector out( (size_t)( source_object.size() + (field_object ? field_object->size() : 0)), @@ -928,7 +969,7 @@ HookAPI::etxn_fee_base(ripple::Slice const& txBlob) const std::unique_ptr stpTrans = std::make_unique(std::ref(sitTrans)); - if (!hookCtx.applyCtx.view().rules().enabled(fixEtxnFeeBase)) + if (!hookCtx.applyCtx.view().rules().enabled(fixHookAPI20251128)) return Transactor::calculateBaseFee( *(applyCtx.app.openLedger().current()), *stpTrans) .drops(); diff --git a/src/ripple/app/ledger/Ledger.cpp b/src/ripple/app/ledger/Ledger.cpp index b013b35a0..5faaff588 100644 --- a/src/ripple/app/ledger/Ledger.cpp +++ b/src/ripple/app/ledger/Ledger.cpp @@ -220,7 +220,10 @@ Ledger::Ledger( { auto sle = std::make_shared(keylet::fees()); - sle->setFieldU32(sfNetworkID, config.NETWORK_ID); + + uint32_t networkID = config.NETWORK_ID; + if (networkID > 1024) + sle->setFieldU32(sfNetworkID, networkID); // Whether featureXRPFees is supported will depend on startup options. if (std::find(amendments.begin(), amendments.end(), featureXRPFees) != diff --git a/src/ripple/app/tx/impl/Transactor.cpp b/src/ripple/app/tx/impl/Transactor.cpp index 0cdc22e09..80646172a 100644 --- a/src/ripple/app/tx/impl/Transactor.cpp +++ b/src/ripple/app/tx/impl/Transactor.cpp @@ -1519,7 +1519,7 @@ Transactor::doTSH( for (auto& weakTsh : additionalWeakTSH_) tsh.emplace_back(weakTsh, false); - if (view.rules().enabled(fixEtxnFeeBase)) + if (view.rules().enabled(fixHookAPI20251128)) { // if account_ is not included in tsh , add it only once bool found = false; @@ -1547,7 +1547,7 @@ Transactor::doTSH( // blindly nominate any TSHes they find but // obviously we will never execute OTXN account // as a TSH because they already had first execution - if (!view.rules().enabled(fixEtxnFeeBase)) + if (!view.rules().enabled(fixHookAPI20251128)) { if (tshAccountID == account_) continue; @@ -1564,10 +1564,10 @@ Transactor::doTSH( touchAccount(view, tshAccountID); - if (view.rules().enabled(fixEtxnFeeBase)) + if (view.rules().enabled(fixHookAPI20251128)) { - // After fixEtxnFeeBase, the otxn account is prosessed as touched - // account + // After fixHookAPI20251128, the otxn account is prosessed as + // touched account if (tshAccountID == account_) continue; } diff --git a/src/ripple/protocol/Feature.h b/src/ripple/protocol/Feature.h index 42ac7c237..2766859dc 100644 --- a/src/ripple/protocol/Feature.h +++ b/src/ripple/protocol/Feature.h @@ -377,8 +377,7 @@ extern uint256 const featureCron; extern uint256 const fixInvalidTxFlags; extern uint256 const featureExtendedHookState; extern uint256 const fixCronStacking; -extern uint256 const fixEtxnFeeBase; - +extern uint256 const fixHookAPI20251128; } // namespace ripple #endif diff --git a/src/ripple/protocol/impl/Feature.cpp b/src/ripple/protocol/impl/Feature.cpp index 44998a4d0..24383f896 100644 --- a/src/ripple/protocol/impl/Feature.cpp +++ b/src/ripple/protocol/impl/Feature.cpp @@ -483,7 +483,7 @@ REGISTER_FEATURE(Cron, Supported::yes, VoteBehavior::De REGISTER_FIX (fixInvalidTxFlags, Supported::yes, VoteBehavior::DefaultYes); REGISTER_FEATURE(ExtendedHookState, Supported::yes, VoteBehavior::DefaultNo); REGISTER_FIX (fixCronStacking, Supported::yes, VoteBehavior::DefaultYes); -REGISTER_FIX (fixEtxnFeeBase, Supported::yes, VoteBehavior::DefaultYes); +REGISTER_FIX (fixHookAPI20251128, Supported::yes, VoteBehavior::DefaultYes); // The following amendments are obsolete, but must remain supported // because they could potentially get enabled. diff --git a/src/test/app/GenesisMint_test.cpp b/src/test/app/GenesisMint_test.cpp index 4f45ff9b6..9f183f0c6 100644 --- a/src/test/app/GenesisMint_test.cpp +++ b/src/test/app/GenesisMint_test.cpp @@ -192,7 +192,7 @@ struct GenesisMint_test : public beast::unit_test::suite } auto const postCoins = env.current()->info().drops; auto const txnFee = - env.current()->rules().enabled(fixEtxnFeeBase) ? 0 : 10; + env.current()->rules().enabled(fixHookAPI20251128) ? 0 : 10; BEAST_EXPECT( initCoins - 1'000'000 /* txn fee */ - txnFee /* emitted txn fee */ @@ -630,7 +630,7 @@ struct GenesisMint_test : public beast::unit_test::suite auto const postCoins = env.current()->info().drops; auto const txnFee = - env.current()->rules().enabled(fixEtxnFeeBase) ? 0 : 10; + env.current()->rules().enabled(fixHookAPI20251128) ? 0 : 10; BEAST_EXPECT( initCoins - 1'000'000 /* txn fee */ - txnFee /* emitted txn fee */ @@ -699,7 +699,7 @@ public: auto const sa = supported_amendments(); testWithFeats(sa); testWithFeats(sa - fixXahauV1); - testWithFeats(sa - fixEtxnFeeBase); + testWithFeats(sa - fixHookAPI20251128); } }; diff --git a/src/test/app/HookAPI_test.cpp b/src/test/app/HookAPI_test.cpp index 064c362d1..effe88351 100644 --- a/src/test/app/HookAPI_test.cpp +++ b/src/test/app/HookAPI_test.cpp @@ -646,7 +646,7 @@ public: auto const baseFee = env.closed()->fees().base; auto const blobSize = 100; auto const memoSize = 100; - if (env.closed()->rules().enabled(fixEtxnFeeBase)) + if (env.closed()->rules().enabled(fixHookAPI20251128)) BEAST_EXPECT(result.value() == baseFee + blobSize + memoSize); else BEAST_EXPECT(result.value() == baseFee + memoSize); @@ -3712,8 +3712,8 @@ public: "ABF044EE"); // {"Amendments":["42426C4D4F1009EE67080A9B7965B44656D7714D104A72F9B4369F97ABF044EE"]} - auto const result = - api.sto_emplace(source_object, field_object, sfPaths.getCode()); + auto const result = api.sto_emplace( + source_object, field_object, sfAmendments.getCode()); BEAST_EXPECT(result.has_value()); BEAST_EXPECT( result.value().size() == @@ -3785,9 +3785,7 @@ public: BEAST_EXPECT(api.sto_subarray(memos, 2).error() == DOESNT_EXIST); // { Amounts: [{AmountEntry: {Amount: "100"}}] } auto const amounts = *strUnHex("F05CE05B614000000000000064E1F1"); - // TODO: fix this - // BEAST_EXPECT(api.sto_subarray(amounts, 2).error() == - // DOESNT_EXIST); + BEAST_EXPECT(api.sto_subarray(amounts, 2).error() == DOESNT_EXIST); } { @@ -3798,10 +3796,8 @@ public: api.sto_subarray(memos, 0).value() == std::make_pair(1, 6)); // { Amounts: [{AmountEntry: {Amount: "100"}}] } auto const amounts = *strUnHex("F05CE05B614000000000000064E1F1"); - // TODO: fix this - // BEAST_EXPECT( - // api.sto_subarray(amounts, 0).value() == std::make_pair(2, - // 12)); + BEAST_EXPECT( + api.sto_subarray(amounts, 0).value() == std::make_pair(2, 12)); } } @@ -4105,7 +4101,7 @@ public: test_otxn_burden(features); test_otxn_generation(features); test_etxn_details(features); - test_etxn_fee_base(features - fixEtxnFeeBase); + test_etxn_fee_base(features - fixHookAPI20251128); test_etxn_fee_base(features); test_etxn_nonce(features); test_etxn_reserve(features); diff --git a/src/test/app/SetHook_test.cpp b/src/test/app/SetHook_test.cpp index 1a24c3a9c..ff157de0f 100644 --- a/src/test/app/SetHook_test.cpp +++ b/src/test/app/SetHook_test.cpp @@ -3236,7 +3236,7 @@ public: { auto f = features; if (!hasFix) - f = f - fixEtxnFeeBase; + f = f - fixHookAPI20251128; Env env{*this, f}; @@ -10205,15 +10205,16 @@ public: { testcase("Test sto_emplace"); using namespace jtx; - - Env env{*this, features}; - auto const bob = Account{"bob"}; auto const alice = Account{"alice"}; - env.fund(XRP(10000), alice); - env.fund(XRP(10000), bob); - TestHook hook = wasm[R"[test.hook]( + { + Env env{*this, features}; + + env.fund(XRP(10000), alice); + env.fund(XRP(10000), bob); + + TestHook hook = wasm[R"[test.hook]( #include extern int32_t _g (uint32_t id, uint32_t maxiter); #define GUARD(maxiter) _g((1ULL << 31U) + __LINE__, (maxiter)+1) @@ -10384,14 +10385,92 @@ public: } )[test.hook]"]; - // install the hook on alice - env(ripple::test::jtx::hook(alice, {{hso(hook, overrideFlag)}}, 0), - M("set sto_emplace"), - HSFEE); - env.close(); + // install the hook on alice + env(ripple::test::jtx::hook(alice, {{hso(hook, overrideFlag)}}, 0), + M("set sto_emplace"), + HSFEE); + env.close(); - // invoke the hook - env(pay(bob, alice, XRP(1)), M("test sto_emplace"), fee(XRP(1))); + // invoke the hook + env(pay(bob, alice, XRP(1)), M("test sto_emplace"), fee(XRP(1))); + } + + { + TestHook hook = wasm[R"[test.hook]( + #include + extern int32_t _g (uint32_t id, uint32_t maxiter); + #define GUARD(maxiter) _g((1ULL << 31U) + __LINE__, (maxiter)+1) + extern int64_t accept (uint32_t read_ptr, uint32_t read_len, int64_t error_code); + extern int64_t rollback (uint32_t read_ptr, uint32_t read_len, int64_t error_code); + extern int64_t sto_emplace ( + uint32_t write_ptr, uint32_t write_len, + uint32_t sread_ptr, uint32_t sread_len, + uint32_t fread_ptr, uint32_t fread_len, uint32_t field_id ); + #define PARSE_ERROR -18 + #define ASSERT(x)\ + if (!(x))\ + rollback((uint32_t)#x, sizeof(#x), __LINE__); + #define sfSequence ((2U << 16U) + 4U) + #define sfAmount ((6U << 16U) + 1U) + + // {"Account": } + uint8_t sto[] = {0x81U, 0x14U, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}; + + // {"Sequence": 1} + uint8_t ins[] = {0x24U, 0x00U, 0x00U, 0x00U, 0x01U}; + + uint8_t buf[1024]; + + int64_t hook(uint32_t reserved ) + { + _g(1,1); + + // check inject field should be valid sto object and it's field id should + // match the field_id + ASSERT(sto_emplace(buf, sizeof(buf), sto, sizeof(sto), ins, sizeof(ins), sfSequence) > 0); + int64_t result = sto_emplace(buf, sizeof(buf), sto, sizeof(sto), ins, sizeof(ins), sfAmount); + + accept(0,0,result); + } + )[test.hook]"]; + + for (auto f : {features, features - fixHookAPI20251128}) + { + Env env{*this, f}; + bool const hasFix = + env.current()->rules().enabled(fixHookAPI20251128); + + env.fund(XRP(10000), alice); + env.fund(XRP(10000), bob); + + // install the hook on alice + env(ripple::test::jtx::hook( + alice, {{hso(hook, overrideFlag)}}, 0), + M("set sto_emplace"), + HSFEE); + env.close(); + + // invoke the hook + env(pay(bob, alice, XRP(1)), + M("test sto_emplace"), + fee(XRP(1))); + env.close(); + auto meta = env.meta(); + BEAST_REQUIRE(meta); + BEAST_REQUIRE(meta->isFieldPresent(sfHookExecutions)); + auto const hookExecutions = + meta->getFieldArray(sfHookExecutions); + BEAST_REQUIRE(hookExecutions.size() == 1); + + if (hasFix) + BEAST_EXPECT( + hookExecutions[0].getFieldU64(sfHookReturnCode) == + 0x8000000000000000ULL + 18); + else + BEAST_EXPECT( + hookExecutions[0].getFieldU64(sfHookReturnCode) > 0); + } + } } void @@ -10537,14 +10616,15 @@ public: testcase("Test sto_subarray"); using namespace jtx; - Env env{*this, features}; - auto const bob = Account{"bob"}; auto const alice = Account{"alice"}; - env.fund(XRP(10000), alice); - env.fund(XRP(10000), bob); + { + Env env{*this, features}; - TestHook hook = wasm[R"[test.hook]( + env.fund(XRP(10000), alice); + env.fund(XRP(10000), bob); + + TestHook hook = wasm[R"[test.hook]( #include extern int32_t _g (uint32_t id, uint32_t maxiter); #define GUARD(maxiter) _g((1ULL << 31U) + __LINE__, (maxiter)+1) @@ -10595,14 +10675,102 @@ public: } )[test.hook]"]; - // install the hook on alice - env(ripple::test::jtx::hook(alice, {{hso(hook, overrideFlag)}}, 0), - M("set sto_subarray"), - HSFEE); - env.close(); + // install the hook on alice + env(ripple::test::jtx::hook(alice, {{hso(hook, overrideFlag)}}, 0), + M("set sto_subarray"), + HSFEE); + env.close(); - // invoke the hook - env(pay(bob, alice, XRP(1)), M("test sto_subarray"), fee(XRP(1))); + // invoke the hook + env(pay(bob, alice, XRP(1)), M("test sto_subarray"), fee(XRP(1))); + } + + { + TestHook hook = wasm[R"[test.hook]( + #include + extern int32_t _g (uint32_t id, uint32_t maxiter); + #define GUARD(maxiter) _g((1ULL << 31U) + __LINE__, (maxiter)+1) + extern int64_t accept (uint32_t read_ptr, uint32_t read_len, int64_t error_code); + extern int64_t sto_subarray( + uint32_t read_ptr, uint32_t read_len, uint32_t field_id); + #define DOESNT_EXIST -5 + + // { Amounts: [{AmountEntry: {Amount: "100"}}] } + uint8_t sto[] = + { + 0xF0U,0x5CU,0xE0U,0x5BU,0x61U,0x40U,0x00U,0x00U,0x00U,0x00U, + 0x00U,0x00U,0x64U,0xE1U,0xF1U + }; + + int64_t hook(uint32_t reserved ) + { + _g(1,1); + uint8_t hash[32]; + + // should be DOESNT_EXIST after Amendment enabled + int64_t result1 = sto_subarray(sto, sizeof(sto), 1); + + // should be position 2 length 12 + // before Amendment enabled, returns pos 1, len 33 + int64_t result2 = sto_subarray(sto, sizeof(sto), 0); + + accept(0,0,result1+result2); + } + )[test.hook]"]; + + for (auto isfixHookAPI20251128 : {true, false}) + { + Env env{ + *this, + isfixHookAPI20251128 ? features | fixHookAPI20251128 + : features - fixHookAPI20251128}; + env.fund(XRP(10000), alice, bob); + env.close(); + + // install the hook on alice + env(ripple::test::jtx::hook( + alice, {{hso(hook, overrideFlag)}}, 0), + M("set sto_subarray"), + HSFEE); + env.close(); + + // invoke the hook + env(pay(bob, alice, XRP(1)), + M("test sto_subarray"), + fee(XRP(1))); + env.close(); + + auto const meta = env.meta(); + BEAST_REQUIRE(meta); + BEAST_REQUIRE(meta->isFieldPresent(sfHookExecutions)); + auto const hookExecutions = + meta->getFieldArray(sfHookExecutions); + BEAST_REQUIRE(hookExecutions.size() == 1); + auto const hookExecution = hookExecutions[0]; + BEAST_REQUIRE(hookExecution.isFieldPresent(sfHookReturnCode)); + auto const returnCode = + hookExecution.getFieldU64(sfHookReturnCode); + if (isfixHookAPI20251128) + { + auto const doesntExistError = -5; + auto const position = 2; + auto const length = 12; + BEAST_REQUIRE( + returnCode == + (doesntExistError + ((int64_t)position << 32) + + length)); + } + else + { + auto const parseError = -18; + auto const position = 1; + auto const length = 33; + BEAST_REQUIRE( + returnCode == + (parseError + ((int64_t)position << 32) + length)); + } + } + } } void diff --git a/src/test/app/SetHook_wasm.h b/src/test/app/SetHook_wasm.h index 159fa6bdd..4918bfb45 100644 --- a/src/test/app/SetHook_wasm.h +++ b/src/test/app/SetHook_wasm.h @@ -16185,6 +16185,193 @@ std::map> wasm = { }}, /* ==== WASM: 76 ==== */ + {R"[test.hook]( + #include + extern int32_t _g (uint32_t id, uint32_t maxiter); + #define GUARD(maxiter) _g((1ULL << 31U) + __LINE__, (maxiter)+1) + extern int64_t accept (uint32_t read_ptr, uint32_t read_len, int64_t error_code); + extern int64_t rollback (uint32_t read_ptr, uint32_t read_len, int64_t error_code); + extern int64_t sto_emplace ( + uint32_t write_ptr, uint32_t write_len, + uint32_t sread_ptr, uint32_t sread_len, + uint32_t fread_ptr, uint32_t fread_len, uint32_t field_id ); + #define PARSE_ERROR -18 + #define ASSERT(x)\ + if (!(x))\ + rollback((uint32_t)#x, sizeof(#x), __LINE__); + #define sfSequence ((2U << 16U) + 4U) + #define sfAmount ((6U << 16U) + 1U) + + // {"Account": } + uint8_t sto[] = {0x81U, 0x14U, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}; + + // {"Sequence": 1} + uint8_t ins[] = {0x24U, 0x00U, 0x00U, 0x00U, 0x01U}; + + uint8_t buf[1024]; + + int64_t hook(uint32_t reserved ) + { + _g(1,1); + + // check inject field should be valid sto object and it's field id should + // match the field_id + ASSERT(sto_emplace(buf, sizeof(buf), sto, sizeof(sto), ins, sizeof(ins), sfSequence) > 0); + int64_t result = sto_emplace(buf, sizeof(buf), sto, sizeof(sto), ins, sizeof(ins), sfAmount); + + accept(0,0,result); + } + )[test.hook]", + { + 0x00U, 0x61U, 0x73U, 0x6DU, 0x01U, 0x00U, 0x00U, 0x00U, 0x01U, 0x1EU, + 0x04U, 0x60U, 0x02U, 0x7FU, 0x7FU, 0x01U, 0x7FU, 0x60U, 0x07U, 0x7FU, + 0x7FU, 0x7FU, 0x7FU, 0x7FU, 0x7FU, 0x7FU, 0x01U, 0x7EU, 0x60U, 0x03U, + 0x7FU, 0x7FU, 0x7EU, 0x01U, 0x7EU, 0x60U, 0x01U, 0x7FU, 0x01U, 0x7EU, + 0x02U, 0x38U, 0x04U, 0x03U, 0x65U, 0x6EU, 0x76U, 0x02U, 0x5FU, 0x67U, + 0x00U, 0x00U, 0x03U, 0x65U, 0x6EU, 0x76U, 0x0BU, 0x73U, 0x74U, 0x6FU, + 0x5FU, 0x65U, 0x6DU, 0x70U, 0x6CU, 0x61U, 0x63U, 0x65U, 0x00U, 0x01U, + 0x03U, 0x65U, 0x6EU, 0x76U, 0x08U, 0x72U, 0x6FU, 0x6CU, 0x6CU, 0x62U, + 0x61U, 0x63U, 0x6BU, 0x00U, 0x02U, 0x03U, 0x65U, 0x6EU, 0x76U, 0x06U, + 0x61U, 0x63U, 0x63U, 0x65U, 0x70U, 0x74U, 0x00U, 0x02U, 0x03U, 0x02U, + 0x01U, 0x03U, 0x05U, 0x03U, 0x01U, 0x00U, 0x02U, 0x06U, 0x33U, 0x08U, + 0x7FU, 0x01U, 0x41U, 0x80U, 0x91U, 0x04U, 0x0BU, 0x7FU, 0x00U, 0x41U, + 0xF2U, 0x10U, 0x0BU, 0x7FU, 0x00U, 0x41U, 0x80U, 0x08U, 0x0BU, 0x7FU, + 0x00U, 0x41U, 0x80U, 0x91U, 0x04U, 0x0BU, 0x7FU, 0x00U, 0x41U, 0x80U, + 0x08U, 0x0BU, 0x7FU, 0x00U, 0x41U, 0xA0U, 0x08U, 0x0BU, 0x7FU, 0x00U, + 0x41U, 0x80U, 0x08U, 0x0BU, 0x7FU, 0x00U, 0x41U, 0x96U, 0x08U, 0x0BU, + 0x07U, 0x08U, 0x01U, 0x04U, 0x68U, 0x6FU, 0x6FU, 0x6BU, 0x00U, 0x04U, + 0x0AU, 0x80U, 0x81U, 0x00U, 0x01U, 0xFCU, 0x80U, 0x00U, 0x01U, 0x01U, + 0x7EU, 0x41U, 0x01U, 0x41U, 0x01U, 0x10U, 0x80U, 0x80U, 0x80U, 0x80U, + 0x00U, 0x1AU, 0x02U, 0x40U, 0x41U, 0xA0U, 0x88U, 0x80U, 0x80U, 0x00U, + 0x41U, 0x80U, 0x08U, 0x41U, 0x80U, 0x88U, 0x80U, 0x80U, 0x00U, 0x41U, + 0x16U, 0x41U, 0x96U, 0x88U, 0x80U, 0x80U, 0x00U, 0x41U, 0x05U, 0x41U, + 0x84U, 0x80U, 0x08U, 0x10U, 0x81U, 0x80U, 0x80U, 0x80U, 0x00U, 0x42U, + 0x00U, 0x55U, 0x0DU, 0x00U, 0x41U, 0xA0U, 0x90U, 0x80U, 0x80U, 0x00U, + 0x41U, 0xD2U, 0x00U, 0x42U, 0x20U, 0x10U, 0x82U, 0x80U, 0x80U, 0x80U, + 0x00U, 0x1AU, 0x0BU, 0x41U, 0x00U, 0x41U, 0x00U, 0x41U, 0xA0U, 0x88U, + 0x80U, 0x80U, 0x00U, 0x41U, 0x80U, 0x08U, 0x41U, 0x80U, 0x88U, 0x80U, + 0x80U, 0x00U, 0x41U, 0x16U, 0x41U, 0x96U, 0x88U, 0x80U, 0x80U, 0x00U, + 0x41U, 0x05U, 0x41U, 0x81U, 0x80U, 0x18U, 0x10U, 0x81U, 0x80U, 0x80U, + 0x80U, 0x00U, 0x10U, 0x83U, 0x80U, 0x80U, 0x80U, 0x00U, 0x1AU, 0x20U, + 0x01U, 0x0BU, 0x0BU, 0x81U, 0x09U, 0x03U, 0x00U, 0x41U, 0x80U, 0x08U, + 0x0BU, 0x1BU, 0x81U, 0x14U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x24U, 0x00U, 0x00U, 0x00U, 0x01U, 0x00U, + 0x41U, 0xA0U, 0x08U, 0x0BU, 0x80U, 0x08U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x00U, 0x41U, 0xA0U, 0x10U, 0x0BU, 0x52U, 0x73U, 0x74U, 0x6FU, 0x5FU, + 0x65U, 0x6DU, 0x70U, 0x6CU, 0x61U, 0x63U, 0x65U, 0x28U, 0x62U, 0x75U, + 0x66U, 0x2CU, 0x20U, 0x73U, 0x69U, 0x7AU, 0x65U, 0x6FU, 0x66U, 0x28U, + 0x62U, 0x75U, 0x66U, 0x29U, 0x2CU, 0x20U, 0x73U, 0x74U, 0x6FU, 0x2CU, + 0x20U, 0x73U, 0x69U, 0x7AU, 0x65U, 0x6FU, 0x66U, 0x28U, 0x73U, 0x74U, + 0x6FU, 0x29U, 0x2CU, 0x20U, 0x69U, 0x6EU, 0x73U, 0x2CU, 0x20U, 0x73U, + 0x69U, 0x7AU, 0x65U, 0x6FU, 0x66U, 0x28U, 0x69U, 0x6EU, 0x73U, 0x29U, + 0x2CU, 0x20U, 0x73U, 0x66U, 0x53U, 0x65U, 0x71U, 0x75U, 0x65U, 0x6EU, + 0x63U, 0x65U, 0x29U, 0x20U, 0x3EU, 0x20U, 0x30U, 0x00U, + }}, + + /* ==== WASM: 77 ==== */ {R"[test.hook]( #include extern int32_t _g (uint32_t id, uint32_t maxiter); @@ -16534,7 +16721,7 @@ std::map> wasm = { 0x20U, 0x30U, 0x00U, }}, - /* ==== WASM: 77 ==== */ + /* ==== WASM: 78 ==== */ {R"[test.hook]( #include extern int32_t _g (uint32_t id, uint32_t maxiter); @@ -16670,7 +16857,66 @@ std::map> wasm = { 0x00U, }}, - /* ==== WASM: 78 ==== */ + /* ==== WASM: 79 ==== */ + {R"[test.hook]( + #include + extern int32_t _g (uint32_t id, uint32_t maxiter); + #define GUARD(maxiter) _g((1ULL << 31U) + __LINE__, (maxiter)+1) + extern int64_t accept (uint32_t read_ptr, uint32_t read_len, int64_t error_code); + extern int64_t sto_subarray( + uint32_t read_ptr, uint32_t read_len, uint32_t field_id); + #define DOESNT_EXIST -5 + + // { Amounts: [{AmountEntry: {Amount: "100"}}] } + uint8_t sto[] = + { + 0xF0U,0x5CU,0xE0U,0x5BU,0x61U,0x40U,0x00U,0x00U,0x00U,0x00U, + 0x00U,0x00U,0x64U,0xE1U,0xF1U + }; + + int64_t hook(uint32_t reserved ) + { + _g(1,1); + uint8_t hash[32]; + + // should be DOESNT_EXIST after Amendment enabled + int64_t result1 = sto_subarray(sto, sizeof(sto), 1); + + // should be position 2 length 12 + // before Amendment enabled, returns pos 1, len 33 + int64_t result2 = sto_subarray(sto, sizeof(sto), 0); + + accept(0,0,result1+result2); + } + )[test.hook]", + { + 0x00U, 0x61U, 0x73U, 0x6DU, 0x01U, 0x00U, 0x00U, 0x00U, 0x01U, 0x1AU, + 0x04U, 0x60U, 0x02U, 0x7FU, 0x7FU, 0x01U, 0x7FU, 0x60U, 0x03U, 0x7FU, + 0x7FU, 0x7FU, 0x01U, 0x7EU, 0x60U, 0x03U, 0x7FU, 0x7FU, 0x7EU, 0x01U, + 0x7EU, 0x60U, 0x01U, 0x7FU, 0x01U, 0x7EU, 0x02U, 0x2AU, 0x03U, 0x03U, + 0x65U, 0x6EU, 0x76U, 0x02U, 0x5FU, 0x67U, 0x00U, 0x00U, 0x03U, 0x65U, + 0x6EU, 0x76U, 0x0CU, 0x73U, 0x74U, 0x6FU, 0x5FU, 0x73U, 0x75U, 0x62U, + 0x61U, 0x72U, 0x72U, 0x61U, 0x79U, 0x00U, 0x01U, 0x03U, 0x65U, 0x6EU, + 0x76U, 0x06U, 0x61U, 0x63U, 0x63U, 0x65U, 0x70U, 0x74U, 0x00U, 0x02U, + 0x03U, 0x02U, 0x01U, 0x03U, 0x05U, 0x03U, 0x01U, 0x00U, 0x02U, 0x06U, + 0x27U, 0x06U, 0x7FU, 0x01U, 0x41U, 0x90U, 0x88U, 0x04U, 0x0BU, 0x7FU, + 0x00U, 0x41U, 0x8FU, 0x08U, 0x0BU, 0x7FU, 0x00U, 0x41U, 0x80U, 0x08U, + 0x0BU, 0x7FU, 0x00U, 0x41U, 0x90U, 0x88U, 0x04U, 0x0BU, 0x7FU, 0x00U, + 0x41U, 0x80U, 0x08U, 0x0BU, 0x7FU, 0x00U, 0x41U, 0x80U, 0x08U, 0x0BU, + 0x07U, 0x08U, 0x01U, 0x04U, 0x68U, 0x6FU, 0x6FU, 0x6BU, 0x00U, 0x03U, + 0x0AU, 0xC1U, 0x80U, 0x00U, 0x01U, 0xBDU, 0x80U, 0x00U, 0x01U, 0x01U, + 0x7EU, 0x41U, 0x01U, 0x41U, 0x01U, 0x10U, 0x80U, 0x80U, 0x80U, 0x80U, + 0x00U, 0x1AU, 0x41U, 0x00U, 0x41U, 0x00U, 0x41U, 0x80U, 0x88U, 0x80U, + 0x80U, 0x00U, 0x41U, 0x0FU, 0x41U, 0x01U, 0x10U, 0x81U, 0x80U, 0x80U, + 0x80U, 0x00U, 0x41U, 0x80U, 0x88U, 0x80U, 0x80U, 0x00U, 0x41U, 0x0FU, + 0x41U, 0x00U, 0x10U, 0x81U, 0x80U, 0x80U, 0x80U, 0x00U, 0x7CU, 0x10U, + 0x82U, 0x80U, 0x80U, 0x80U, 0x00U, 0x1AU, 0x20U, 0x01U, 0x0BU, 0x0BU, + 0x16U, 0x01U, 0x00U, 0x41U, 0x80U, 0x08U, 0x0BU, 0x0FU, 0xF0U, 0x5CU, + 0xE0U, 0x5BU, 0x61U, 0x40U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, + 0x64U, 0xE1U, 0xF1U, + }}, + + /* ==== WASM: 79 ==== */ {R"[test.hook]( #include extern int32_t _g (uint32_t id, uint32_t maxiter); @@ -16843,7 +17089,7 @@ std::map> wasm = { 0x54U, 0x5FU, 0x45U, 0x58U, 0x49U, 0x53U, 0x54U, 0x00U, }}, - /* ==== WASM: 79 ==== */ + /* ==== WASM: 80 ==== */ {R"[test.hook]( #include extern int32_t _g (uint32_t id, uint32_t maxiter); @@ -16991,7 +17237,7 @@ std::map> wasm = { 0x30U, 0x00U, 0x22U, 0x00U, 0x00U, 0x00U, 0x00U, }}, - /* ==== WASM: 80 ==== */ + /* ==== WASM: 81 ==== */ {R"[test.hook]( #include extern int32_t _g (uint32_t id, uint32_t maxiter); @@ -17088,7 +17334,7 @@ std::map> wasm = { 0x3DU, 0x20U, 0x30U, 0x00U, }}, - /* ==== WASM: 81 ==== */ + /* ==== WASM: 82 ==== */ {R"[test.hook]( #include extern int32_t _g (uint32_t id, uint32_t maxiter); @@ -17147,7 +17393,7 @@ std::map> wasm = { 0x4FU, 0x46U, 0x5FU, 0x42U, 0x4FU, 0x55U, 0x4EU, 0x44U, 0x53U, 0x00U, }}, - /* ==== WASM: 82 ==== */ + /* ==== WASM: 83 ==== */ {R"[test.hook]( #include extern int32_t _g (uint32_t id, uint32_t maxiter); @@ -17206,7 +17452,7 @@ std::map> wasm = { 0x4EU, 0x44U, 0x53U, 0x00U, }}, - /* ==== WASM: 83 ==== */ + /* ==== WASM: 84 ==== */ {R"[test.hook]( #include extern int32_t _g (uint32_t id, uint32_t maxiter); @@ -19035,7 +19281,7 @@ std::map> wasm = { 0x53U, 0x4DU, 0x41U, 0x4CU, 0x4CU, 0x00U, }}, - /* ==== WASM: 84 ==== */ + /* ==== WASM: 85 ==== */ {R"[test.hook]( #include extern int32_t _g (uint32_t id, uint32_t maxiter); @@ -20377,7 +20623,7 @@ std::map> wasm = { 0x20U, 0x30U, 0x2CU, 0x20U, 0x30U, 0x29U, 0x29U, 0x00U, }}, - /* ==== WASM: 85 ==== */ + /* ==== WASM: 86 ==== */ {R"[test.hook]( #include extern int32_t _g (uint32_t id, uint32_t maxiter); @@ -23310,7 +23556,7 @@ std::map> wasm = { 0x4FU, 0x4FU, 0x5FU, 0x53U, 0x4DU, 0x41U, 0x4CU, 0x4CU, 0x00U, }}, - /* ==== WASM: 86 ==== */ + /* ==== WASM: 87 ==== */ {R"[test.hook]( #include extern int32_t _g (uint32_t id, uint32_t maxiter); @@ -25275,7 +25521,7 @@ std::map> wasm = { 0x54U, 0x4FU, 0x4FU, 0x5FU, 0x53U, 0x4DU, 0x41U, 0x4CU, 0x4CU, 0x00U, }}, - /* ==== WASM: 87 ==== */ + /* ==== WASM: 88 ==== */ {R"[test.hook]( #include extern int32_t _g (uint32_t id, uint32_t maxiter); @@ -25560,7 +25806,7 @@ std::map> wasm = { 0x29U, 0x20U, 0x3DU, 0x3DU, 0x20U, 0x30U, 0x00U, }}, - /* ==== WASM: 88 ==== */ + /* ==== WASM: 89 ==== */ {R"[test.hook]( #include extern int32_t _g(uint32_t, uint32_t); @@ -26147,7 +26393,7 @@ std::map> wasm = { 0x4EU, 0x5FU, 0x46U, 0x41U, 0x49U, 0x4CU, 0x55U, 0x52U, 0x45U, 0x00U, }}, - /* ==== WASM: 89 ==== */ + /* ==== WASM: 90 ==== */ {R"[test.hook]( #include extern int32_t _g (uint32_t id, uint32_t maxiter); @@ -26176,7 +26422,7 @@ std::map> wasm = { 0x0BU, }}, - /* ==== WASM: 90 ==== */ + /* ==== WASM: 91 ==== */ {R"[test.hook]( #include extern int32_t _g (uint32_t id, uint32_t maxiter); @@ -26208,7 +26454,7 @@ std::map> wasm = { 0x20U, 0x52U, 0x65U, 0x6AU, 0x65U, 0x63U, 0x74U, 0x65U, 0x64U, 0x00U, }}, - /* ==== WASM: 91 ==== */ + /* ==== WASM: 92 ==== */ {R"[test.hook]( (module (type (;0;) (func (param i32 i32 i64) (result i64))) @@ -26235,7 +26481,7 @@ std::map> wasm = { 0x41U, 0x00U, 0x41U, 0x00U, 0x42U, 0x00U, 0x10U, 0x00U, 0x0BU, }}, - /* ==== WASM: 92 ==== */ + /* ==== WASM: 93 ==== */ {R"[test.hook]( (module (type (;0;) (func (param i32 i32) (result i32))) @@ -26288,7 +26534,7 @@ std::map> wasm = { 0x00U, 0x1AU, 0x0BU, }}, - /* ==== WASM: 93 ==== */ + /* ==== WASM: 94 ==== */ {R"[test.hook]( #include extern int32_t _g (uint32_t id, uint32_t maxiter); @@ -32931,7 +33177,7 @@ std::map> wasm = { 0x39U, 0x30U, 0x31U, 0x32U, 0x33U, 0x00U, }}, - /* ==== WASM: 94 ==== */ + /* ==== WASM: 95 ==== */ {R"[test.hook]( #include extern int32_t _g (uint32_t id, uint32_t maxiter); @@ -32977,7 +33223,7 @@ std::map> wasm = { 0x0BU, 0x06U, 0x76U, 0x61U, 0x6CU, 0x75U, 0x65U, 0x00U, }}, - /* ==== WASM: 95 ==== */ + /* ==== WASM: 96 ==== */ {R"[test.hook]( #include extern int32_t _g (uint32_t id, uint32_t maxiter); diff --git a/src/test/app/Touch_test.cpp b/src/test/app/Touch_test.cpp index 9f1906f8e..b5df8d2b9 100644 --- a/src/test/app/Touch_test.cpp +++ b/src/test/app/Touch_test.cpp @@ -1401,8 +1401,8 @@ public: using namespace test::jtx; auto const sa = supported_amendments(); testAllTxns(sa); - testAllTxns(sa - fixEtxnFeeBase); - testAllTxns(sa - featureTouch - fixEtxnFeeBase); + testAllTxns(sa - fixHookAPI20251128); + testAllTxns(sa - featureTouch - fixHookAPI20251128); } }; diff --git a/src/test/app/TxQ_test.cpp b/src/test/app/TxQ_test.cpp index 71a06bb83..a849418d3 100644 --- a/src/test/app/TxQ_test.cpp +++ b/src/test/app/TxQ_test.cpp @@ -1520,7 +1520,7 @@ public: "bob: "s + std::to_string(bobSeq) + ", " + std::to_string(env.seq(bob))); BEAST_EXPECTS( - charlieSeq + 1 == env.seq(charlie), + charlieSeq == env.seq(charlie), "charlie: "s + std::to_string(charlieSeq) + ", " + std::to_string(env.seq(charlie))); BEAST_EXPECTS( @@ -1528,7 +1528,7 @@ public: "daria: "s + std::to_string(dariaSeq) + ", " + std::to_string(env.seq(daria))); BEAST_EXPECTS( - elmoSeq == env.seq(elmo), + elmoSeq + 1 == env.seq(elmo), "elmo: "s + std::to_string(elmoSeq) + ", " + std::to_string(env.seq(elmo))); BEAST_EXPECTS( @@ -1544,18 +1544,25 @@ public: "hank: "s + std::to_string(hankSeq) + ", " + std::to_string(env.seq(hank))); - // Which sequences get incremented may change - // Match the below with the above. If + 1 then ++ + // Which sequences get incremented may change if TxQ ordering is + // changed ++aliceSeq; // ++bobSeq; // ++(++charlieSeq); - ++charlieSeq; ++dariaSeq; - // ++elmoSeq; + ++elmoSeq; ++fredSeq; ++gwenSeq; ++hankSeq; + // std::cout << "bobSeq: " << ++bobSeq << "\n"; + // std::cout << "charlieSeq: " << ++(++charlieSeq) << "\n"; + // std::cout << "dariaSeq: " << ++dariaSeq << "\n"; + // std::cout << "elmoSeq: " << ++elmoSeq << "\n"; + // std::cout << "fredSeq: " << ++fredSeq << "\n"; + // std::cout << "gwenSeq: " << ++gwenSeq << "\n"; + // std::cout << "hankSeq: " << ++hankSeq << "\n"; + auto getTxsQueued = [&]() { auto const txs = env.app().getTxQ().getTxs(); std::map result; @@ -3029,7 +3036,15 @@ public: // may not reduce to 8. env.close(); checkMetrics(__LINE__, env, 9, 50, 6, 5, 256); - BEAST_EXPECT(env.seq(alice) == aliceSeq + 17); + + // env.seq(alice): 17, aliceSeq + 15: 18 + /*std::cout + << "env.seq(alice): " + << env.seq(alice) + << ", aliceSeq + 15: " + << (aliceSeq + 15) << "\n"; + */ + BEAST_EXPECT(env.seq(alice) == aliceSeq + 15); // Close ledger 7. That should remove 7 more of alice's transactions. env.close(); @@ -5052,7 +5067,8 @@ public: testMultiTxnPerAccount(all); // fragile: hardcoded ordering by txID XOR parentHash // parentHash < txTree Hash < txMeta < PreviousTxnID - testTieBreaking(all - fixProvisionalDoubleThreading - fixEtxnFeeBase); + testTieBreaking( + all - fixProvisionalDoubleThreading - fixHookAPI20251128); testAcctTxnID(all); testMaximum(all); testUnexpectedBalanceChange(all); @@ -5073,7 +5089,7 @@ public: // fragile: hardcoded ordering by txID XOR parentHash // parentHash < txTree Hash < txMeta < PreviousTxnID testFullQueueGapFill( - all - fixProvisionalDoubleThreading - fixEtxnFeeBase); + all - fixProvisionalDoubleThreading - fixHookAPI20251128); testSignAndSubmitSequence(all); testAccountInfo(all); testServerInfo(all); diff --git a/src/test/rpc/LedgerClosed_test.cpp b/src/test/rpc/LedgerClosed_test.cpp index c6d982ec0..2f81031f8 100644 --- a/src/test/rpc/LedgerClosed_test.cpp +++ b/src/test/rpc/LedgerClosed_test.cpp @@ -37,7 +37,7 @@ public: auto lc_result = env.rpc("ledger_closed")[jss::result]; BEAST_EXPECT( lc_result[jss::ledger_hash] == - "2E6983FE0D18F04568199D75E8E69503E747A24CE8814CF1FAD638CF6DF8FBDC"); + "CCC3B3E88CCAC17F1BE6B4A648A55999411F19E3FE55EB721960EB0DF28EDDA5"); BEAST_EXPECT(lc_result[jss::ledger_index] == 2); env.close(); @@ -52,7 +52,7 @@ public: lc_result = env.rpc("ledger_closed")[jss::result]; BEAST_EXPECT( lc_result[jss::ledger_hash] == - "D39C52DE7CBF561ECA875A6D636B7C9095408DE1FAF4EC4AAF3FDD8AB3A1EA55"); + "E86DE7F3D7A4D9CE17EF7C8BA08A8F4D8F643B9552F0D895A31CDA78F541DE4E"); BEAST_EXPECT(lc_result[jss::ledger_index] == 3); } diff --git a/src/test/rpc/LedgerRPC_test.cpp b/src/test/rpc/LedgerRPC_test.cpp index efb3b196b..0f4b1c823 100644 --- a/src/test/rpc/LedgerRPC_test.cpp +++ b/src/test/rpc/LedgerRPC_test.cpp @@ -292,7 +292,7 @@ public: using namespace test::jtx; Env env{ *this, - supported_amendments() - featureXahauGenesis - fixEtxnFeeBase}; + supported_amendments() - featureXahauGenesis - fixHookAPI20251128}; Account const alice{"alice"}; env.fund(XRP(10000), alice); env.close(); @@ -2023,8 +2023,8 @@ public: // access via the ledger_hash field Json::Value jvParams; jvParams[jss::ledger_hash] = - "D39C52DE7CBF561ECA875A6D636B7C9095408DE1FAF4EC4AAF3FDD8AB3A1EA" - "55"; + "E86DE7F3D7A4D9CE17EF7C8BA08A8F4D" + "8F643B9552F0D895A31CDA78F541DE4E"; auto jrr = env.rpc( "json", "ledger", @@ -2173,7 +2173,7 @@ public: return cfg; }), supported_amendments() - featureXahauGenesis - - fixProvisionalDoubleThreading - fixEtxnFeeBase}; + fixProvisionalDoubleThreading - fixHookAPI20251128}; Json::Value jv; jv[jss::ledger_index] = "current"; @@ -2249,7 +2249,7 @@ public: if (BEAST_EXPECT(jrr[jss::queue_data].size() == 2)) { const std::string txid1 = [&]() { - auto const& txj = jrr[jss::queue_data][0u]; + auto const& txj = jrr[jss::queue_data][1u]; BEAST_EXPECT(txj[jss::account] == alice.human()); BEAST_EXPECT(txj[jss::fee_level] == "256"); BEAST_EXPECT(txj["preflight_result"] == "tesSUCCESS"); @@ -2261,7 +2261,7 @@ public: return tx[jss::hash].asString(); }(); - auto const& txj = jrr[jss::queue_data][1u]; + auto const& txj = jrr[jss::queue_data][0u]; BEAST_EXPECT(txj[jss::account] == alice.human()); BEAST_EXPECT(txj[jss::fee_level] == "256"); BEAST_EXPECT(txj["preflight_result"] == "tesSUCCESS"); @@ -2274,7 +2274,7 @@ public: uint256 tx0, tx1; BEAST_EXPECT(tx0.parseHex(txid0)); BEAST_EXPECT(tx1.parseHex(txid1)); - BEAST_EXPECT((tx1 ^ parentHash) < (tx0 ^ parentHash)); + BEAST_EXPECT((tx0 ^ parentHash) < (tx1 ^ parentHash)); return txid0; } return std::string{}; @@ -2289,14 +2289,14 @@ public: { auto const& parentHash = env.current()->info().parentHash; auto const txid1 = [&]() { - auto const& txj = jrr[jss::queue_data][0u]; + auto const& txj = jrr[jss::queue_data][1u]; BEAST_EXPECT(txj[jss::account] == alice.human()); BEAST_EXPECT(txj[jss::fee_level] == "256"); BEAST_EXPECT(txj["preflight_result"] == "tesSUCCESS"); BEAST_EXPECT(txj.isMember(jss::tx)); return txj[jss::tx].asString(); }(); - auto const& txj = jrr[jss::queue_data][1u]; + auto const& txj = jrr[jss::queue_data][0u]; BEAST_EXPECT(txj[jss::account] == alice.human()); BEAST_EXPECT(txj[jss::fee_level] == "256"); BEAST_EXPECT(txj["preflight_result"] == "tesSUCCESS"); @@ -2307,7 +2307,7 @@ public: uint256 tx0, tx1; BEAST_EXPECT(tx0.parseHex(txid0)); BEAST_EXPECT(tx1.parseHex(txid1)); - BEAST_EXPECT((tx1 ^ parentHash) < (tx0 ^ parentHash)); + BEAST_EXPECT((tx0 ^ parentHash) < (tx1 ^ parentHash)); } env.close(); @@ -2318,7 +2318,7 @@ public: jrr = env.rpc("json", "ledger", to_string(jv))[jss::result]; if (BEAST_EXPECT(jrr[jss::queue_data].size() == 2)) { - auto const& txj = jrr[jss::queue_data][1u]; + auto const& txj = jrr[jss::queue_data][0u]; BEAST_EXPECT(txj[jss::account] == alice.human()); BEAST_EXPECT(txj[jss::fee_level] == "256"); BEAST_EXPECT(txj["preflight_result"] == "tesSUCCESS"); @@ -2327,7 +2327,7 @@ public: BEAST_EXPECT(txj.isMember(jss::tx)); BEAST_EXPECT(txj[jss::tx].isMember(jss::tx_blob)); - auto const& txj2 = jrr[jss::queue_data][0u]; + auto const& txj2 = jrr[jss::queue_data][1u]; BEAST_EXPECT(txj2[jss::account] == alice.human()); BEAST_EXPECT(txj2[jss::fee_level] == "256"); BEAST_EXPECT(txj2["preflight_result"] == "tesSUCCESS"); diff --git a/src/test/rpc/LedgerRequestRPC_test.cpp b/src/test/rpc/LedgerRequestRPC_test.cpp index d19e9f811..14d06e923 100644 --- a/src/test/rpc/LedgerRequestRPC_test.cpp +++ b/src/test/rpc/LedgerRequestRPC_test.cpp @@ -31,9 +31,9 @@ namespace RPC { class LedgerRequestRPC_test : public beast::unit_test::suite { static constexpr char const* hash1 = - "3C570BEB083CBFC17ED614A7404E25ED84C5CF44E5826944FBE8DD20FCCE67FE"; + "3020EB9E7BE24EF7D7A060CB051583EC117384636D1781AFB5B87F3E348DA489"; static constexpr char const* accounthash1 = - "BD91A0C42F0055CAE81D0C0D6E47629C34B6528E380EA2D1BB9FEFFDC879480E"; + "BD8A3D72CA73DDE887AD63666EC2BAD07875CBA997A102579B5B95ECDFFEAED8"; static constexpr char const* zerohash = "0000000000000000000000000000000000000000000000000000000000000000"; @@ -196,7 +196,7 @@ public: result = env.rpc("ledger_request", "2")[jss::result]; constexpr char const* hash2 = - "2E6983FE0D18F04568199D75E8E69503E747A24CE8814CF1FAD638CF6DF8FBDC"; + "CCC3B3E88CCAC17F1BE6B4A648A55999411F19E3FE55EB721960EB0DF28EDDA5"; BEAST_EXPECT(result[jss::ledger][jss::ledger_index] == "2"); BEAST_EXPECT( result[jss::ledger][jss::total_coins] == "100000000000000000"); @@ -205,12 +205,12 @@ public: BEAST_EXPECT(result[jss::ledger][jss::parent_hash] == hash1); BEAST_EXPECT( result[jss::ledger][jss::account_hash] == - "C6C885F43A772BA455AB96456248D10D2B32E32C24377520D6B7652F3FCEEF31"); + "3C834285F7F464FBE99AFEB84D354A968EB2CAA24523FF26797A973D906A3D29"); BEAST_EXPECT(result[jss::ledger][jss::transaction_hash] == zerohash); result = env.rpc("ledger_request", "3")[jss::result]; constexpr char const* hash3 = - "6E82AE402A91025406F4A0FBC5E228CC8FE2CA6EE07B4195ED59ACA332DCECF7"; + "8D631B20BC989AF568FBA97375290544B0703A5ADC1CF9E9053580461690C9EE"; BEAST_EXPECT(result[jss::ledger][jss::ledger_index] == "3"); BEAST_EXPECT( result[jss::ledger][jss::total_coins] == "99999999999999980"); @@ -219,14 +219,14 @@ public: BEAST_EXPECT(result[jss::ledger][jss::parent_hash] == hash2); BEAST_EXPECT( result[jss::ledger][jss::account_hash] == - "692A26D06FCB0A2685F6DC269A08713E9FD8583056B2E4928CCE76862763609D"); + "BC9EF2A16BFF80BCFABA6FA84688D858D33BD0FA0435CAA9DF6DA4105A39A29E"); BEAST_EXPECT( result[jss::ledger][jss::transaction_hash] == "0213EC486C058B3942FBE3DAC6839949A5C5B02B8B4244C8998EFDF04DBD8222"); result = env.rpc("ledger_request", "4")[jss::result]; constexpr char const* hash4 = - "CDFFFA5ED6AC9D45C4863F41F3AD37432FEDE592AB987FF49D6B272E69F68559"; + "1A8E7098B23597E73094DADA58C9D62F3AB93A12C6F7666D56CA85A6CFDE530F"; BEAST_EXPECT(result[jss::ledger][jss::ledger_index] == "4"); BEAST_EXPECT( result[jss::ledger][jss::total_coins] == "99999999999999960"); @@ -235,14 +235,14 @@ public: BEAST_EXPECT(result[jss::ledger][jss::parent_hash] == hash3); BEAST_EXPECT( result[jss::ledger][jss::account_hash] == - "D6DF68C04B663B45F159AA87072479C54B3930E92E8965154C35A80D508BF958"); + "C690188F123C91355ADA8BDF4AC5B5C927076D3590C215096868A5255264C6DD"); BEAST_EXPECT( result[jss::ledger][jss::transaction_hash] == "3CBDB8F42E04333E1642166BFB93AC9A7E1C6C067092CD5D881D6F3AB3D67E76"); result = env.rpc("ledger_request", "5")[jss::result]; constexpr char const* hash5 = - "DE428CD76D4E0372C1ED6019BD49F6F8095596260E6011C51385B2C510F4C1D4"; + "C6A222D71AE65D7B4F240009EAD5DEB20D7EEDE5A4064F28BBDBFEEB6FBE48E5"; BEAST_EXPECT(result[jss::ledger][jss::ledger_index] == "5"); BEAST_EXPECT( result[jss::ledger][jss::total_coins] == "99999999999999940"); @@ -251,7 +251,7 @@ public: BEAST_EXPECT(result[jss::ledger][jss::parent_hash] == hash4); BEAST_EXPECT( result[jss::ledger][jss::account_hash] == - "6A1179D2AD9ACDF61E14A076B6FBE305FF032D2193D230DE21BF9358C7E11F09"); + "EA81CD9D36740736F00CB747E0D0E32D3C10B695823D961F0FB9A1CE7133DD4D"); BEAST_EXPECT( result[jss::ledger][jss::transaction_hash] == "C3D086CD6BDB9E97AD1D513B2C049EF2840BD21D0B3E22D84EBBB89B6D2EF59D");