fix: Check the result of STI_VL against kMaxWasmDataLength on host side

This commit is contained in:
TimothyBanks
2026-09-24 17:14:02 -04:00
parent f04386dcf7
commit 60e5c4d2dd
2 changed files with 41 additions and 0 deletions

View File

@@ -4,6 +4,7 @@
#include <xrpl/protocol/Asset.h>
#include <xrpl/protocol/Indexes.h>
#include <xrpl/protocol/MPTIssue.h>
#include <xrpl/protocol/Protocol.h>
#include <xrpl/protocol/SField.h>
#include <xrpl/protocol/STBase.h>
#include <xrpl/protocol/STBitString.h>
@@ -77,6 +78,10 @@ getAnyFieldData(STBase const* obj)
case STI_VL: {
auto const* vl(static_cast<STBlob const*>(obj)); // NOLINT
auto const& data = vl->value();
if (data.size() > kMaxWasmDataLength)
{
return std::unexpected{HostFunctionError::DataFieldTooLarge};
}
return Bytes{data.begin(), data.end()};
}

View File

@@ -1,7 +1,9 @@
#include <xrpl/protocol/Indexes.h>
#include <xrpl/protocol/Issue.h>
#include <xrpl/protocol/MPTIssue.h>
#include <xrpl/protocol/Protocol.h>
#include <xrpl/protocol/SField.h>
#include <xrpl/protocol/STObject.h>
#include <xrpl/protocol/TxFormats.h>
#include <xrpl/protocol/UintTypes.h>
#include <xrpl/tx/wasm/WasmCommon.h>
@@ -12,6 +14,7 @@
#include <tx/wasm/fixtures/RealHostFixture.h>
#include <tx/wasm/fixtures/WasmLedger.h>
#include <cstddef>
#include <cstdint>
#include <iterator>
#include <utility>
@@ -169,4 +172,37 @@ TEST_F(TxFieldImpl, EscrowTxMatchesGeneric)
owner, sfGeneric, escrowFinishTx(ledger, owner), HostFunctionError::FieldNotFound);
}
namespace {
TxAssembler
bytecodeTx(Account const& acct, std::size_t size)
{
return {.type = ttESCROW_CREATE, .build = [acct, size](STObject& obj) {
obj.setAccountID(sfAccount, acct.id());
obj.setFieldVL(sfBytecode, Bytes(size, 0x42));
}};
}
} // namespace
TEST_F(TxFieldImpl, AnOversizedBlobIsRefusedWhereItIsRead)
{
auto const owner = Account{"owner"};
ledger.createAccount(owner, XRP(1000));
checkTxFieldError(
owner,
sfBytecode,
bytecodeTx(owner, kMaxWasmDataLength + 1),
HostFunctionError::DataFieldTooLarge);
}
TEST_F(TxFieldImpl, ABlobAtTheCapIsStillRead)
{
auto const owner = Account{"owner"};
ledger.createAccount(owner, XRP(1000));
checkTxField(owner, sfBytecode, bytecodeTx(owner, kMaxWasmDataLength), [] {
return Bytes(kMaxWasmDataLength, 0x42);
});
}
} // namespace xrpl::test