From f8b9448cf0167ea3551361963ed43f46abf69df5 Mon Sep 17 00:00:00 2001 From: Jacob Evans Date: Thu, 15 Feb 2024 18:37:35 +1000 Subject: [PATCH] [ZeroEx] add test for Otc order signed by another address --- .forge-snapshots/zeroEx_otcOrder_DAI-WETH.snap | 2 +- .../zeroEx_otcOrder_USDC-WETH.snap | 2 +- .../zeroEx_otcOrder_USDT-WETH.snap | 2 +- ...zeroEx_otcOrder_allowedSigner_DAI-WETH.snap | 1 + ...eroEx_otcOrder_allowedSigner_USDC-WETH.snap | 1 + ...eroEx_otcOrder_allowedSigner_USDT-WETH.snap | 1 + test/integration/BasePairTest.t.sol | 16 +++++++++++++++- test/integration/ZeroExPairTest.t.sol | 18 +++++++++++++++++- test/integration/vendor/IZeroEx.sol | 1 + 9 files changed, 39 insertions(+), 5 deletions(-) create mode 100644 .forge-snapshots/zeroEx_otcOrder_allowedSigner_DAI-WETH.snap create mode 100644 .forge-snapshots/zeroEx_otcOrder_allowedSigner_USDC-WETH.snap create mode 100644 .forge-snapshots/zeroEx_otcOrder_allowedSigner_USDT-WETH.snap diff --git a/.forge-snapshots/zeroEx_otcOrder_DAI-WETH.snap b/.forge-snapshots/zeroEx_otcOrder_DAI-WETH.snap index a72872529..5abbad75b 100644 --- a/.forge-snapshots/zeroEx_otcOrder_DAI-WETH.snap +++ b/.forge-snapshots/zeroEx_otcOrder_DAI-WETH.snap @@ -1 +1 @@ -93071 \ No newline at end of file +78527 \ No newline at end of file diff --git a/.forge-snapshots/zeroEx_otcOrder_USDC-WETH.snap b/.forge-snapshots/zeroEx_otcOrder_USDC-WETH.snap index a73308475..8b9b5939f 100644 --- a/.forge-snapshots/zeroEx_otcOrder_USDC-WETH.snap +++ b/.forge-snapshots/zeroEx_otcOrder_USDC-WETH.snap @@ -1 +1 @@ -112545 \ No newline at end of file +98001 \ No newline at end of file diff --git a/.forge-snapshots/zeroEx_otcOrder_USDT-WETH.snap b/.forge-snapshots/zeroEx_otcOrder_USDT-WETH.snap index 5478da142..23005ab2b 100644 --- a/.forge-snapshots/zeroEx_otcOrder_USDT-WETH.snap +++ b/.forge-snapshots/zeroEx_otcOrder_USDT-WETH.snap @@ -1 +1 @@ -104183 \ No newline at end of file +89639 \ No newline at end of file diff --git a/.forge-snapshots/zeroEx_otcOrder_allowedSigner_DAI-WETH.snap b/.forge-snapshots/zeroEx_otcOrder_allowedSigner_DAI-WETH.snap new file mode 100644 index 000000000..b3efd8d79 --- /dev/null +++ b/.forge-snapshots/zeroEx_otcOrder_allowedSigner_DAI-WETH.snap @@ -0,0 +1 @@ +80812 \ No newline at end of file diff --git a/.forge-snapshots/zeroEx_otcOrder_allowedSigner_USDC-WETH.snap b/.forge-snapshots/zeroEx_otcOrder_allowedSigner_USDC-WETH.snap new file mode 100644 index 000000000..d547fdac7 --- /dev/null +++ b/.forge-snapshots/zeroEx_otcOrder_allowedSigner_USDC-WETH.snap @@ -0,0 +1 @@ +100286 \ No newline at end of file diff --git a/.forge-snapshots/zeroEx_otcOrder_allowedSigner_USDT-WETH.snap b/.forge-snapshots/zeroEx_otcOrder_allowedSigner_USDT-WETH.snap new file mode 100644 index 000000000..ff36c94f0 --- /dev/null +++ b/.forge-snapshots/zeroEx_otcOrder_allowedSigner_USDT-WETH.snap @@ -0,0 +1 @@ +91924 \ No newline at end of file diff --git a/test/integration/BasePairTest.t.sol b/test/integration/BasePairTest.t.sol index 5fa293cbc..a347a52aa 100644 --- a/test/integration/BasePairTest.t.sol +++ b/test/integration/BasePairTest.t.sol @@ -18,6 +18,8 @@ abstract contract BasePairTest is Test, GasSnapshot, Permit2Signature { address internal FROM = vm.addr(FROM_PRIVATE_KEY); uint256 internal constant MAKER_PRIVATE_KEY = 0x0ff1c1a1; address internal MAKER = vm.addr(MAKER_PRIVATE_KEY); + uint256 internal constant OTHER_MAKER_PRIVATE_KEY = 0x0cacacac; + address internal OTHER_MAKER = vm.addr(OTHER_MAKER_PRIVATE_KEY); address internal constant BURN_ADDRESS = 0x2222222222222222222222222222222222222222; @@ -78,11 +80,23 @@ abstract contract BasePairTest is Test, GasSnapshot, Permit2Signature { function warmZeroExOtcNonce(address who) internal { // mapping(address => mapping(uint64 => uint128)) txOriginNonces; // tx.origin bucket min nonce - // OtcOrders is 8th in LibStorage Enum + // OtcOrders is LibStorage[8] Enum https://github.com/0xProject/protocol/blob/master/contracts/zero-ex/contracts/src/storage/LibStorage.sol#L26 bytes32 slotId = keccak256(abi.encode(uint256(0), keccak256(abi.encode(who, (uint256(8) + 1) << 128)))); vm.store(address(ZERO_EX_ADDRESS), slotId, bytes32(uint256(1))); } + /// @dev Manually set a registered signer in 0xV4 Native Orders + /// note: we attempt to avoid touching storage by the usual means to side + /// step gas metering + function allowRegisteredSigner(address maker, address signer) internal { + // mapping(address => mapping(address => bool)) orderSignerRegistry; + // maker signer allowed + // NativeOrders is LibStorage[7] Enum https://github.com/0xProject/protocol/blob/master/contracts/zero-ex/contracts/src/storage/LibStorage.sol#L26 + // orderSignerRegistry is Storage[4] in the Storage struct https://github.com/0xProject/protocol/blob/master/contracts/zero-ex/contracts/src/storage/LibNativeOrdersStorage.sol#L38 + bytes32 slotId = keccak256(abi.encode(signer, keccak256(abi.encode(maker, ((uint256(7) + 1) << 128) + 4)))); + vm.store(address(ZERO_EX_ADDRESS), slotId, bytes32(uint256(1))); + } + modifier skipIf(bool condition) { if (!condition) { _; diff --git a/test/integration/ZeroExPairTest.t.sol b/test/integration/ZeroExPairTest.t.sol index 12b7465fe..489a1ce57 100644 --- a/test/integration/ZeroExPairTest.t.sol +++ b/test/integration/ZeroExPairTest.t.sol @@ -54,6 +54,11 @@ abstract contract ZeroExPairTest is BasePairTest { otcOrder.maker = MAKER; otcOrderHash = ZERO_EX.getOtcOrderHash(otcOrder); + // Set up MAKER to also allow signatures from OTHER_MAKER + // vm.startPrank(MAKER); + // ZERO_EX.registerAllowedOrderSigner(OTHER_MAKER, true); + allowRegisteredSigner(MAKER, OTHER_MAKER); + // MetaTransactionV2 IZeroEx.BatchSellSubcall[] memory calls = new IZeroEx.BatchSellSubcall[](1); calls[0] = IZeroEx.BatchSellSubcall({ @@ -82,10 +87,21 @@ abstract contract ZeroExPairTest is BasePairTest { } function testZeroEx_otcOrder() public { + IZeroEx.OtcOrder memory _otcOrder = otcOrder; (uint8 v, bytes32 r, bytes32 s) = vm.sign(MAKER_PRIVATE_KEY, otcOrderHash); vm.startPrank(FROM, FROM); snapStartName("zeroEx_otcOrder"); - ZERO_EX.fillOtcOrder(otcOrder, IZeroEx.Signature(IZeroEx.SignatureType.EIP712, v, r, s), uint128(amount())); + ZERO_EX.fillOtcOrder(_otcOrder, IZeroEx.Signature(IZeroEx.SignatureType.EIP712, v, r, s), uint128(amount())); + snapEnd(); + } + + function testZeroEx_otcOrder_allowedSigner() public { + IZeroEx.OtcOrder memory _otcOrder = otcOrder; + // MAKER has already registered OTHER_MAKER as a signer + (uint8 v, bytes32 r, bytes32 s) = vm.sign(OTHER_MAKER_PRIVATE_KEY, otcOrderHash); + vm.startPrank(FROM, FROM); + snapStartName("zeroEx_otcOrder_allowedSigner"); + ZERO_EX.fillOtcOrder(_otcOrder, IZeroEx.Signature(IZeroEx.SignatureType.EIP712, v, r, s), uint128(amount())); snapEnd(); } diff --git a/test/integration/vendor/IZeroEx.sol b/test/integration/vendor/IZeroEx.sol index 29c8a662a..45f8cccdb 100644 --- a/test/integration/vendor/IZeroEx.sol +++ b/test/integration/vendor/IZeroEx.sol @@ -198,6 +198,7 @@ interface IZeroEx { function getOtcOrderHash(IZeroEx.OtcOrder memory order) external view returns (bytes32 orderHash); function lastOtcTxOriginNonce(address txOrigin, uint64 nonceBucket) external view returns (uint128 lastNonce); + function registerAllowedOrderSigner(address signer, bool allowed) external; function getMetaTransactionV2Hash(IMetaTransactionsFeatureV2.MetaTransactionDataV2 calldata mtx) external