From 82b1b6de3e43f5fe7f2a2fd99394ba8462d8c40d Mon Sep 17 00:00:00 2001 From: Kelvin Fichter Date: Tue, 25 Aug 2020 16:38:32 -0400 Subject: [PATCH 1/3] Added mocked xdomain message contracts --- .../CrossDomainMessageReceiver.interface.sol | 17 +++ .../bridge/CrossDomainMessenger.interface.sol | 29 ++++ .../bridge/MockCrossDomainMessageReceiver.sol | 109 +++++++++++++++ .../bridge/MockCrossDomainMessenger.sol | 80 +++++++++++ .../SimpleStorageMessageReceiver.sol | 33 +++++ packages/contracts/package.json | 5 +- .../MockCrossDomainMessageReceiver.spec.ts | 85 ++++++++++++ .../bridge/MockCrossDomainMessenger.spec.ts | 130 ++++++++++++++++++ yarn.lock | 123 ++++++++++++++++- 9 files changed, 604 insertions(+), 7 deletions(-) create mode 100644 packages/contracts/contracts/optimistic-ethereum/bridge/CrossDomainMessageReceiver.interface.sol create mode 100644 packages/contracts/contracts/optimistic-ethereum/bridge/CrossDomainMessenger.interface.sol create mode 100644 packages/contracts/contracts/optimistic-ethereum/bridge/MockCrossDomainMessageReceiver.sol create mode 100644 packages/contracts/contracts/optimistic-ethereum/bridge/MockCrossDomainMessenger.sol create mode 100644 packages/contracts/contracts/test-helpers/SimpleStorageMessageReceiver.sol create mode 100644 packages/contracts/test/contracts/bridge/MockCrossDomainMessageReceiver.spec.ts create mode 100644 packages/contracts/test/contracts/bridge/MockCrossDomainMessenger.spec.ts diff --git a/packages/contracts/contracts/optimistic-ethereum/bridge/CrossDomainMessageReceiver.interface.sol b/packages/contracts/contracts/optimistic-ethereum/bridge/CrossDomainMessageReceiver.interface.sol new file mode 100644 index 00000000000..d9f8633e4d2 --- /dev/null +++ b/packages/contracts/contracts/optimistic-ethereum/bridge/CrossDomainMessageReceiver.interface.sol @@ -0,0 +1,17 @@ +pragma solidity ^0.5.0; + +contract ICrossDomainMessageReceiver { + /** + * Receives a message from a cross domain messenger. + * @param _sender Address of the message sender. + * @param _message Calldata being received. + * @param _timestamp Time the message was sent. + * @param _blockNumber Block the message was sent in. + */ + function receiveMessage( + address _sender, + bytes memory _message, + uint256 _timestamp, + uint256 _blockNumber + ) public; +} \ No newline at end of file diff --git a/packages/contracts/contracts/optimistic-ethereum/bridge/CrossDomainMessenger.interface.sol b/packages/contracts/contracts/optimistic-ethereum/bridge/CrossDomainMessenger.interface.sol new file mode 100644 index 00000000000..85ba8b2dcb5 --- /dev/null +++ b/packages/contracts/contracts/optimistic-ethereum/bridge/CrossDomainMessenger.interface.sol @@ -0,0 +1,29 @@ +pragma solidity ^0.5.0; + +contract ICrossDomainMessenger { + /** + * Relays a message to a given target contract. + * @param _target Address of the target contract. + * @param _sender Address of the message sender. + * @param _message Calldata to relay. + * @param _timestamp Time the message was relayed. + * @param _blockNumber Block number the message was relayed in. + */ + function relayMessage( + address _target, + address _sender, + bytes memory _message, + uint256 _timestamp, + uint256 _blockNumber + ) public; + + /** + * Sends a message to another cross domain messenger to be relayed. + * @param _target Address of the target contract. + * @param _message Calldata to relay. + */ + function sendMessage( + address _target, + bytes memory _message + ) public; +} \ No newline at end of file diff --git a/packages/contracts/contracts/optimistic-ethereum/bridge/MockCrossDomainMessageReceiver.sol b/packages/contracts/contracts/optimistic-ethereum/bridge/MockCrossDomainMessageReceiver.sol new file mode 100644 index 00000000000..5e28d755cd8 --- /dev/null +++ b/packages/contracts/contracts/optimistic-ethereum/bridge/MockCrossDomainMessageReceiver.sol @@ -0,0 +1,109 @@ +pragma solidity ^0.5.0; + +/* Interface Imports */ +import { ICrossDomainMessageReceiver } from "./CrossDomainMessageReceiver.interface.sol"; +import { ICrossDomainMessenger } from "./CrossDomainMessenger.interface.sol"; + +/** + * @title MockCrossDomainMessageReceiver + */ +contract MockCrossDomainMessageReceiver is ICrossDomainMessageReceiver { + /* + * Contract Variables + */ + + ICrossDomainMessenger public crossDomainMessenger; + + + /* + * Modifiers + */ + + modifier onlyMessenger() { + require( + msg.sender == address(crossDomainMessenger), + "Only the CrossDomainMessenger can call this function." + ); + _; + } + + + /* + * Public Functions + */ + + /** + * Receives a message from the cross domain messenger. + * .inheritdoc ICrossDomainMessageReceiver + */ + function receiveMessage( + address _sender, + bytes memory _message, + uint256 _timestamp, + uint256 _blockNumber + ) + public + onlyMessenger + { + onMessageReceived( + _sender, + _message, + _timestamp, + _blockNumber + ); + + uint256 messageSize = _message.length; + bool success = false; + assembly { + success := call( + gas, + address, + 0, + add(_message, 0x20), + messageSize, + 0, + 0 + ) + } + + if (!success) { + revert("Received message reverted during execution."); + } + } + + /** + * Sets the address of the cross domain messenger. + * @param _crossDomainMessenger Cross domain messenger address. + */ + function setMessenger( + address _crossDomainMessenger + ) + public + { + crossDomainMessenger = ICrossDomainMessenger(_crossDomainMessenger); + } + + + /* + * Internal Functions + */ + + /** + * Triggered whenever a message is received. + * @param _sender Address of the message sender. + * @param _message Calldata being received. + * @param _timestamp Time the message was sent. + * @param _blockNumber Block the message was sent in. + */ + function onMessageReceived( + address _sender, + bytes memory _message, + uint256 _timestamp, + uint256 _blockNumber + ) + internal + { + // Implement me! + return; + } +} diff --git a/packages/contracts/contracts/optimistic-ethereum/bridge/MockCrossDomainMessenger.sol b/packages/contracts/contracts/optimistic-ethereum/bridge/MockCrossDomainMessenger.sol new file mode 100644 index 00000000000..46d8114ea50 --- /dev/null +++ b/packages/contracts/contracts/optimistic-ethereum/bridge/MockCrossDomainMessenger.sol @@ -0,0 +1,80 @@ +pragma solidity ^0.5.0; + +/* Interface Imports */ +import { ICrossDomainMessenger } from "./CrossDomainMessenger.interface.sol"; +import { ICrossDomainMessageReceiver } from "./CrossDomainMessageReceiver.interface.sol"; + +/** + * @title MockCrossDomainMessenger + */ +contract MockCrossDomainMessenger is ICrossDomainMessenger { + /* + * Contract Variables + */ + + ICrossDomainMessenger targetMessenger; + + + /* + * Public Functions + */ + + /** + * Relays a message to a target contract. + * .inheritdoc ICrossDomainMessenger + */ + function relayMessage( + address _target, + address _sender, + bytes memory _message, + uint256 _timestamp, + uint256 _blockNumber + ) + public + { + ICrossDomainMessageReceiver target = ICrossDomainMessageReceiver(_target); + + target.receiveMessage( + _sender, + _message, + _timestamp, + _blockNumber + ); + } + + /** + * Sends a message to the target messenger. + * .inheritdoc ICrossDomainMessenger + */ + function sendMessage( + address _target, + bytes memory _message + ) + public + { + require( + address(targetMessenger) != address(0), + "Cannot send a message without setting the target messenger." + ); + + targetMessenger.relayMessage( + _target, + msg.sender, + _message, + block.timestamp, + block.number + ); + } + + /** + * Sets the target messenger. + * @param _messenger Target messenger address. + */ + function setTargetMessenger( + address _messenger + ) + public + { + targetMessenger = ICrossDomainMessenger(_messenger); + } +} diff --git a/packages/contracts/contracts/test-helpers/SimpleStorageMessageReceiver.sol b/packages/contracts/contracts/test-helpers/SimpleStorageMessageReceiver.sol new file mode 100644 index 00000000000..cd1a87b2c4b --- /dev/null +++ b/packages/contracts/contracts/test-helpers/SimpleStorageMessageReceiver.sol @@ -0,0 +1,33 @@ +pragma solidity ^0.5.0; + +import { MockCrossDomainMessageReceiver } from "../optimistic-ethereum/bridge/MockCrossDomainMessageReceiver.sol"; +import { SimpleStorage } from "./SimpleStorage.sol"; + +contract SimpleStorageMessageReceiver is SimpleStorage, MockCrossDomainMessageReceiver { + struct Message { + address sender; + bytes message; + uint256 timestamp; + uint256 blockNumber; + } + + mapping (uint256 => Message) public messages; + uint256 public totalMessages; + + function onMessageReceived( + address _sender, + bytes memory _message, + uint256 _timestamp, + uint256 _blockNumber + ) + internal + { + messages[totalMessages] = Message({ + sender: _sender, + message: _message, + timestamp: _timestamp, + blockNumber: _blockNumber + }); + totalMessages += 1; + } +} \ No newline at end of file diff --git a/packages/contracts/package.json b/packages/contracts/package.json index 9152a3b4b95..e1aa352efcd 100644 --- a/packages/contracts/package.json +++ b/packages/contracts/package.json @@ -26,9 +26,11 @@ "test:contracts": "cross-env SOLPP_FLAGS=\"FLAG_IS_TEST,FLAG_IS_DEBUG\" buidler test --show-stack-traces", "coverage": "yarn run coverage:contracts", "coverage:contracts": "cross-env SOLPP_FLAGS=\"FLAG_IS_TEST\" buidler coverage --network coverage --show-stack-traces --testfiles \"test/contracts/**/*.spec.ts\"", - "build": "yarn run build:contracts && yarn run build:typescript", + "build": "yarn run build:contracts && yarn run build:typescript && yarn run build:copy", "build:contracts": "buidler compile", "build:typescript": "tsc -p .", + "build:copy": "yarn run build:copy:contracts", + "build:copy:contracts": "copyfiles -u 2 \"contracts/optimistic-ethereum/**/*.sol\" \"build/contracts\"", "clean": "rm -rf ./artifacts ./build ./cache", "lint": "yarn run lint:typescript", "lint:typescript": "tslint --format stylish --project .", @@ -61,6 +63,7 @@ "typescript": "^3.9.5" }, "devDependencies": { + "copyfiles": "^2.3.0", "cross-env": "^7.0.2", "glob": "^7.1.6", "solidity-coverage": "^0.7.9" diff --git a/packages/contracts/test/contracts/bridge/MockCrossDomainMessageReceiver.spec.ts b/packages/contracts/test/contracts/bridge/MockCrossDomainMessageReceiver.spec.ts new file mode 100644 index 00000000000..fa1b84aacfe --- /dev/null +++ b/packages/contracts/test/contracts/bridge/MockCrossDomainMessageReceiver.spec.ts @@ -0,0 +1,85 @@ +import { expect } from '../../setup' + +/* External Imports */ +import { ethers } from '@nomiclabs/buidler' +import { ContractFactory, Contract, Signer } from 'ethers' + +describe('MockCrossDomainMessageReceiver', () => { + let wallet: Signer + let wallet2: Signer + before(async () => { + ;[wallet, wallet2] = await ethers.getSigners() + }) + + let SimpleStorageMessageReceiverFactory: ContractFactory + before(async () => { + SimpleStorageMessageReceiverFactory = await ethers.getContractFactory('SimpleStorageMessageReceiver') + }) + + let L2SimpleStorageMessageReceiver: Contract + beforeEach(async () => { + L2SimpleStorageMessageReceiver = await SimpleStorageMessageReceiverFactory.deploy() + + await L2SimpleStorageMessageReceiver.setMessenger(await wallet.getAddress()) + }) + + describe('receiveMessage', () => { + it('should successfully receive a message from the messenger', async () => { + const expectedStorageKey = ethers.utils.keccak256('0x1234') + const expectedStorageValue = ethers.utils.keccak256('0x5678') + + const calldata = L2SimpleStorageMessageReceiver.interface.encodeFunctionData( + 'setStorage', + [ + expectedStorageKey, + expectedStorageValue + ] + ) + + const expectedMessage = [ + await wallet.getAddress(), + calldata, + ethers.BigNumber.from(Date.now()), + ethers.BigNumber.from(123) + ] + + await L2SimpleStorageMessageReceiver.receiveMessage( + ...expectedMessage, + { + from: await wallet.getAddress() + } + ) + + const actualStorageValue = await L2SimpleStorageMessageReceiver.getStorage(expectedStorageKey) + expect(actualStorageValue).to.equal(expectedStorageValue) + + const actualMessage = await L2SimpleStorageMessageReceiver.messages(0) + expect(actualMessage).to.deep.equal(expectedMessage) + }) + + it('should fail if the message is not received from the messenger', async () => { + const expectedStorageKey = ethers.utils.keccak256('0x1234') + const expectedStorageValue = ethers.utils.keccak256('0x5678') + + const calldata = L2SimpleStorageMessageReceiver.interface.encodeFunctionData( + 'setStorage', + [ + expectedStorageKey, + expectedStorageValue + ] + ) + + const expectedMessage = [ + await wallet.getAddress(), + calldata, + ethers.BigNumber.from(Date.now()), + ethers.BigNumber.from(123) + ] + + L2SimpleStorageMessageReceiver = L2SimpleStorageMessageReceiver.connect(wallet2) + await expect(L2SimpleStorageMessageReceiver.receiveMessage( + ...expectedMessage + )).to.be.revertedWith('Only the CrossDomainMessenger can call this function.') + }) + }) +}) \ No newline at end of file diff --git a/packages/contracts/test/contracts/bridge/MockCrossDomainMessenger.spec.ts b/packages/contracts/test/contracts/bridge/MockCrossDomainMessenger.spec.ts new file mode 100644 index 00000000000..62c89fa79a2 --- /dev/null +++ b/packages/contracts/test/contracts/bridge/MockCrossDomainMessenger.spec.ts @@ -0,0 +1,130 @@ +import { expect } from '../../setup' + +/* External Imports */ +import { ethers } from '@nomiclabs/buidler' +import { ContractFactory, Contract, Signer } from 'ethers' +import { NULL_ADDRESS } from '@eth-optimism/core-utils' + +describe('MockCrossDomainMessenger', () => { + let wallet: Signer + before(async () => { + ;[wallet] = await ethers.getSigners() + }) + + let MockCrossDomainMessengerFactory: ContractFactory + let SimpleStorageMessageReceiverFactory: ContractFactory + before(async () => { + MockCrossDomainMessengerFactory = await ethers.getContractFactory('MockCrossDomainMessenger') + SimpleStorageMessageReceiverFactory = await ethers.getContractFactory('SimpleStorageMessageReceiver') + }) + + let L1MockCrossDomainMessenger: Contract + let L2MockCrossDomainMessenger: Contract + beforeEach(async () => { + L1MockCrossDomainMessenger = await MockCrossDomainMessengerFactory.deploy() + L2MockCrossDomainMessenger = await MockCrossDomainMessengerFactory.deploy() + + await L1MockCrossDomainMessenger.setTargetMessenger(L2MockCrossDomainMessenger.address) + await L2MockCrossDomainMessenger.setTargetMessenger(L1MockCrossDomainMessenger.address) + }) + + let L2SimpleStorageMessageReceiver: Contract + beforeEach(async () => { + L2SimpleStorageMessageReceiver = await SimpleStorageMessageReceiverFactory.deploy() + + await L2SimpleStorageMessageReceiver.setMessenger(L2MockCrossDomainMessenger.address) + }) + + describe('relayMessage', () => { + it('should successfully relay a message to the target receiver', async () => { + const expectedStorageKey = ethers.utils.keccak256('0x1234') + const expectedStorageValue = ethers.utils.keccak256('0x5678') + + const calldata = L2SimpleStorageMessageReceiver.interface.encodeFunctionData( + 'setStorage', + [ + expectedStorageKey, + expectedStorageValue + ] + ) + + const expectedMessage = [ + await wallet.getAddress(), + calldata, + ethers.BigNumber.from(Date.now()), + ethers.BigNumber.from(123) + ] + + await L2MockCrossDomainMessenger.relayMessage( + L2SimpleStorageMessageReceiver.address, + ...expectedMessage + ) + + const actualStorageValue = await L2SimpleStorageMessageReceiver.getStorage(expectedStorageKey) + expect(actualStorageValue).to.equal(expectedStorageValue) + + const actualMessage = await L2SimpleStorageMessageReceiver.messages(0) + expect(actualMessage).to.deep.equal(expectedMessage) + }) + }) + + describe('sendMessage', () => { + it('should successfully send a message to another messenger', async () => { + const expectedStorageKey = ethers.utils.keccak256('0x1234') + const expectedStorageValue = ethers.utils.keccak256('0x5678') + + const calldata = L2SimpleStorageMessageReceiver.interface.encodeFunctionData( + 'setStorage', + [ + expectedStorageKey, + expectedStorageValue + ] + ) + + await L1MockCrossDomainMessenger.sendMessage( + L2SimpleStorageMessageReceiver.address, + calldata, + { + from: await wallet.getAddress(), + } + ) + + const currentBlock = await ethers.provider.getBlock('latest') + const expectedMessage = [ + await wallet.getAddress(), + calldata, + ethers.BigNumber.from(currentBlock.timestamp), + ethers.BigNumber.from(currentBlock.number), + ] + + const actualStorageValue = await L2SimpleStorageMessageReceiver.getStorage(expectedStorageKey) + expect(actualStorageValue).to.equal(expectedStorageValue) + + const actualMessage = await L2SimpleStorageMessageReceiver.messages(0) + expect(actualMessage).to.deep.equal(expectedMessage) + }) + + it('should revert if its target messenger is not set', async () => { + const expectedStorageKey = ethers.utils.keccak256('0x1234') + const expectedStorageValue = ethers.utils.keccak256('0x5678') + + const calldata = L2SimpleStorageMessageReceiver.interface.encodeFunctionData( + 'setStorage', + [ + expectedStorageKey, + expectedStorageValue + ] + ) + + await L1MockCrossDomainMessenger.setTargetMessenger(NULL_ADDRESS) + + await expect(L1MockCrossDomainMessenger.sendMessage( + L2SimpleStorageMessageReceiver.address, + calldata, + { + from: await wallet.getAddress(), + } + )).to.be.revertedWith('Cannot send a message without setting the target messenger.') + }) + }) +}) \ No newline at end of file diff --git a/yarn.lock b/yarn.lock index a29504eef20..1b2e82093ae 100644 --- a/yarn.lock +++ b/yarn.lock @@ -1752,6 +1752,11 @@ resolved "https://registry.yarnpkg.com/@types/chai/-/chai-4.2.12.tgz#6160ae454cd89dae05adc3bb97997f488b608201" integrity sha512-aN5IAC8QNtSUdQzxu7lGBgYAOuU1tmRU4c9dIq5OKGf/SBVjXo+ffM2wEjudAWbgpOhy60nLoAGH1xm8fpCKFQ== +"@types/color-name@^1.1.1": + version "1.1.1" + resolved "https://registry.yarnpkg.com/@types/color-name/-/color-name-1.1.1.tgz#1c1261bbeaa10a8055bbc5d8ab84b7b2afc846a0" + integrity sha512-rr+OQyAjxze7GgWrSaJwydHStIhHq2lvY3BOC2Mj7KnzI7XK0Uw1TOOdI9lDoajEbSWLiYgoo4f1R51erQfhPQ== + "@types/debug@^4.1.5": version "4.1.5" resolved "https://registry.yarnpkg.com/@types/debug/-/debug-4.1.5.tgz#b14efa8852b7768d898906613c23f688713e02cd" @@ -2117,6 +2122,11 @@ ansi-regex@^4.1.0: resolved "https://registry.yarnpkg.com/ansi-regex/-/ansi-regex-4.1.0.tgz#8b9f8f08cf1acb843756a839ca8c7e3168c51997" integrity sha512-1apePfXM1UOSqw0o9IiFAovVz9M5S1Dg+4TrDwfMewQ6p/rmMueb7tWZjQ1rx4Loy1ArBggoqGpfqqdI4rondg== +ansi-regex@^5.0.0: + version "5.0.0" + resolved "https://registry.yarnpkg.com/ansi-regex/-/ansi-regex-5.0.0.tgz#388539f55179bf39339c81af30a654d69f87cb75" + integrity sha512-bY6fj56OUQ0hU1KjFNDQuJFezqKdrAyFdIevADiqrWHwSlbmBNMHp5ak2f40Pm8JTFyM2mqxkG6ngkHO11f/lg== + ansi-styles@^2.2.1: version "2.2.1" resolved "https://registry.yarnpkg.com/ansi-styles/-/ansi-styles-2.2.1.tgz#b432dd3358b634cf75e1e4664368240533c1ddbe" @@ -2129,6 +2139,14 @@ ansi-styles@^3.2.0, ansi-styles@^3.2.1: dependencies: color-convert "^1.9.0" +ansi-styles@^4.0.0: + version "4.2.1" + resolved "https://registry.yarnpkg.com/ansi-styles/-/ansi-styles-4.2.1.tgz#90ae75c424d008d2624c5bf29ead3177ebfcf359" + integrity sha512-9VGjrMsG1vePxcSweQsN20KY/c4zN0h9fLjqAbwbPfahM3t+NL+M9HC8xeXG2I8pX5NoamTGNuomEUFI7fcUjA== + dependencies: + "@types/color-name" "^1.1.1" + color-convert "^2.0.1" + ansi-wrap@0.1.0, ansi-wrap@^0.1.0: version "0.1.0" resolved "https://registry.yarnpkg.com/ansi-wrap/-/ansi-wrap-0.1.0.tgz#a82250ddb0015e9a27ca82e82ea603bbfa45efaf" @@ -3769,6 +3787,15 @@ cliui@^5.0.0: strip-ansi "^5.2.0" wrap-ansi "^5.1.0" +cliui@^6.0.0: + version "6.0.0" + resolved "https://registry.yarnpkg.com/cliui/-/cliui-6.0.0.tgz#511d702c0c4e41ca156d7d0e96021f23e13225b1" + integrity sha512-t6wbgtoCXvAzst7QgXxJYqPt0usEfbgQdftEPbLL/cvv6HPE5VgvqCuAIDR0NgU52ds6rFwqrgakNLrHEjCbrQ== + dependencies: + string-width "^4.2.0" + strip-ansi "^6.0.0" + wrap-ansi "^6.2.0" + clone-buffer@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/clone-buffer/-/clone-buffer-1.0.0.tgz#e3e25b207ac4e701af721e2cb5a16792cac3dc58" @@ -3843,11 +3870,23 @@ color-convert@^1.9.0: dependencies: color-name "1.1.3" +color-convert@^2.0.1: + version "2.0.1" + resolved "https://registry.yarnpkg.com/color-convert/-/color-convert-2.0.1.tgz#72d3a68d598c9bdb3af2ad1e84f21d896abd4de3" + integrity sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ== + dependencies: + color-name "~1.1.4" + color-name@1.1.3: version "1.1.3" resolved "https://registry.yarnpkg.com/color-name/-/color-name-1.1.3.tgz#a7d0558bd89c42f795dd42328f740831ca53bc25" integrity sha1-p9BVi9icQveV3UIyj3QIMcpTvCU= +color-name@~1.1.4: + version "1.1.4" + resolved "https://registry.yarnpkg.com/color-name/-/color-name-1.1.4.tgz#c2a09a87acbde69543de6f63fa3995c826c536a2" + integrity sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA== + color-support@^1.1.3: version "1.1.3" resolved "https://registry.yarnpkg.com/color-support/-/color-support-1.1.3.tgz#93834379a1cc9a0c61f82f52f0d04322251bd5a2" @@ -4090,6 +4129,18 @@ copy-props@^2.0.1: each-props "^1.3.0" is-plain-object "^2.0.1" +copyfiles@^2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/copyfiles/-/copyfiles-2.3.0.tgz#1c26ebbe3d46bba2d309a3fd8e3aaccf53af8c76" + integrity sha512-73v7KFuDFJ/ofkQjZBMjMBFWGgkS76DzXvBMUh7djsMOE5EELWtAO/hRB6Wr5Vj5Zg+YozvoHemv0vnXpqxmOQ== + dependencies: + glob "^7.0.5" + minimatch "^3.0.3" + mkdirp "^1.0.4" + noms "0.0.0" + through2 "^2.0.1" + yargs "^15.3.1" + core-js-pure@^3.0.1: version "3.6.5" resolved "https://registry.yarnpkg.com/core-js-pure/-/core-js-pure-3.6.5.tgz#c79e75f5e38dbc85a662d91eea52b8256d53b813" @@ -4734,6 +4785,11 @@ emoji-regex@^7.0.1: resolved "https://registry.yarnpkg.com/emoji-regex/-/emoji-regex-7.0.3.tgz#933a04052860c85e83c122479c4748a8e4c72156" integrity sha512-CwBLREIQ7LvYFB0WyRvwhq5N5qPhc6PMjD6bYggFlI5YyDgl+0vxq5VHbMOFqLg7hfWzmu8T5Z1QofhmTIhItA== +emoji-regex@^8.0.0: + version "8.0.0" + resolved "https://registry.yarnpkg.com/emoji-regex/-/emoji-regex-8.0.0.tgz#e818fd69ce5ccfcb404594f842963bf53164cc37" + integrity sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A== + encodeurl@~1.0.2: version "1.0.2" resolved "https://registry.yarnpkg.com/encodeurl/-/encodeurl-1.0.2.tgz#ad3ff4c86ec2d029322f5a02c3a9a606c95b3f59" @@ -6640,7 +6696,7 @@ glob@7.1.3: once "^1.3.0" path-is-absolute "^1.0.0" -glob@7.1.6, glob@^7.0.0, glob@^7.1.1, glob@^7.1.2, glob@^7.1.3, glob@^7.1.4, glob@^7.1.6, glob@~7.1.6: +glob@7.1.6, glob@^7.0.0, glob@^7.0.5, glob@^7.1.1, glob@^7.1.2, glob@^7.1.3, glob@^7.1.4, glob@^7.1.6, glob@~7.1.6: version "7.1.6" resolved "https://registry.yarnpkg.com/glob/-/glob-7.1.6.tgz#141f33b81a7c2492e125594307480c46679278a6" integrity sha512-LwaxwyZ72Lk7vZINtNNrywX0ZuLyStrdDtabefZKAY5ZGJhVtgdznluResxNmPitE0SAO+O26sWTHeKSI2wMBA== @@ -7480,6 +7536,11 @@ is-fullwidth-code-point@^2.0.0: resolved "https://registry.yarnpkg.com/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz#a3b30a5c4f199183167aaab93beefae3ddfb654f" integrity sha1-o7MKXE8ZkYMWeqq5O+764937ZU8= +is-fullwidth-code-point@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/is-fullwidth-code-point/-/is-fullwidth-code-point-3.0.0.tgz#f116f8064fe90b3f7844a38997c0b75051269f1d" + integrity sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg== + is-function@^1.0.1: version "1.0.2" resolved "https://registry.yarnpkg.com/is-function/-/is-function-1.0.2.tgz#4f097f30abf6efadac9833b17ca5dc03f8144e08" @@ -8859,7 +8920,7 @@ minimalistic-crypto-utils@^1.0.0, minimalistic-crypto-utils@^1.0.1: resolved "https://registry.yarnpkg.com/minimalistic-crypto-utils/-/minimalistic-crypto-utils-1.0.1.tgz#f6c00c1c0b082246e5c4d99dfb8c7c083b2b582a" integrity sha1-9sAMHAsIIkblxNmd+4x8CDsrWCo= -"minimatch@2 || 3", minimatch@3.0.4, minimatch@^3.0.4: +"minimatch@2 || 3", minimatch@3.0.4, minimatch@^3.0.3, minimatch@^3.0.4: version "3.0.4" resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-3.0.4.tgz#5166e286457f03306064be5497e8dbb0c3d32083" integrity sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA== @@ -8934,7 +8995,7 @@ mkdirp-promise@^5.0.1: dependencies: mkdirp "*" -mkdirp@*: +mkdirp@*, mkdirp@^1.0.4: version "1.0.4" resolved "https://registry.yarnpkg.com/mkdirp/-/mkdirp-1.0.4.tgz#3eb5ed62622756d79a5f0e2a221dfebad75c2f7e" integrity sha512-vVqVZQyf3WLx2Shd0qJ9xuvqgAyKPLAiqITEtqW0oIUjzo3PePDd6fW9iFz30ef7Ysp/oiWqbhszeGWW2T6Gzw== @@ -9298,6 +9359,14 @@ node-gyp@^5.0.2: tar "^4.4.12" which "^1.3.1" +noms@0.0.0: + version "0.0.0" + resolved "https://registry.yarnpkg.com/noms/-/noms-0.0.0.tgz#da8ebd9f3af9d6760919b27d9cdc8092a7332859" + integrity sha1-2o69nzr51nYJGbJ9nNyAkqczKFk= + dependencies: + inherits "^2.0.1" + readable-stream "~1.0.31" + nopt@3.x: version "3.0.6" resolved "https://registry.yarnpkg.com/nopt/-/nopt-3.0.6.tgz#c6465dbf08abcd4db359317f79ac68a646b28ff9" @@ -10589,7 +10658,7 @@ readable-stream@^1.0.33: isarray "0.0.1" string_decoder "~0.10.x" -readable-stream@~1.0.15: +readable-stream@~1.0.15, readable-stream@~1.0.31: version "1.0.34" resolved "https://registry.yarnpkg.com/readable-stream/-/readable-stream-1.0.34.tgz#125820e34bc842d2f2aaafafe4c2916ee32c157c" integrity sha1-Elgg40vIQtLyqq+v5MKRbuMsFXw= @@ -11711,6 +11780,15 @@ string-width@^3.0.0, string-width@^3.1.0: is-fullwidth-code-point "^2.0.0" strip-ansi "^5.1.0" +string-width@^4.1.0, string-width@^4.2.0: + version "4.2.0" + resolved "https://registry.yarnpkg.com/string-width/-/string-width-4.2.0.tgz#952182c46cc7b2c313d1596e623992bd163b72b5" + integrity sha512-zUz5JD+tgqtuDjMhwIg5uFVV3dtqZ9yQJlZVfq4I01/K5Paj5UHj7VyrQOJvzawSVlKpObApbfD0Ed6yJc+1eg== + dependencies: + emoji-regex "^8.0.0" + is-fullwidth-code-point "^3.0.0" + strip-ansi "^6.0.0" + string.prototype.trim@~1.2.1: version "1.2.1" resolved "https://registry.yarnpkg.com/string.prototype.trim/-/string.prototype.trim-1.2.1.tgz#141233dff32c82bfad80684d7e5f0869ee0fb782" @@ -11776,6 +11854,13 @@ strip-ansi@^5.0.0, strip-ansi@^5.1.0, strip-ansi@^5.2.0: dependencies: ansi-regex "^4.1.0" +strip-ansi@^6.0.0: + version "6.0.0" + resolved "https://registry.yarnpkg.com/strip-ansi/-/strip-ansi-6.0.0.tgz#0b1571dd7669ccd4f3e06e14ef1eed26225ae532" + integrity sha512-AuvKTrTfQNYNIctbR1K/YGTR1756GycPsg7b9bdV9Duqur4gv6aKqHXah67Z8ImS7WEz5QVcOtlfW2rZEugt6w== + dependencies: + ansi-regex "^5.0.0" + strip-bom@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/strip-bom/-/strip-bom-2.0.0.tgz#6219a85616520491f35788bdbf1447a99c7e6b0e" @@ -12068,7 +12153,7 @@ through2-filter@^3.0.0: through2 "~2.0.0" xtend "~4.0.0" -through2@^2.0.0, through2@^2.0.2, through2@^2.0.3, through2@~2.0.0: +through2@^2.0.0, through2@^2.0.1, through2@^2.0.2, through2@^2.0.3, through2@~2.0.0: version "2.0.5" resolved "https://registry.yarnpkg.com/through2/-/through2-2.0.5.tgz#01c1e39eb31d07cb7d03a96a70823260b23132cd" integrity sha512-/mrRod8xqpA+IHSLyGCQ2s8SPHiCDEeQJSep1jqLYeEUClOFG2Qsh+4FU6G9VeqpZnGW/Su8LQGc4YKni5rYSQ== @@ -14363,6 +14448,15 @@ wrap-ansi@^5.1.0: string-width "^3.0.0" strip-ansi "^5.0.0" +wrap-ansi@^6.2.0: + version "6.2.0" + resolved "https://registry.yarnpkg.com/wrap-ansi/-/wrap-ansi-6.2.0.tgz#e9393ba07102e6c91a3b221478f0257cd2856e53" + integrity sha512-r6lPcBGxZXlIcymEu7InxDMhdW0KDxpLgoFLcguasxCaJ/SOIZwINatK9KY/tf+ZrlywOKU0UDj3ATXUBfxJXA== + dependencies: + ansi-styles "^4.0.0" + string-width "^4.1.0" + strip-ansi "^6.0.0" + wrappy@1: version "1.0.2" resolved "https://registry.yarnpkg.com/wrappy/-/wrappy-1.0.2.tgz#b5243d8f3ec1aa35f1364605bc0d1036e30ab69f" @@ -14552,7 +14646,7 @@ yargs-parser@^15.0.1: camelcase "^5.0.0" decamelize "^1.2.0" -yargs-parser@^18.1.3: +yargs-parser@^18.1.2, yargs-parser@^18.1.3: version "18.1.3" resolved "https://registry.yarnpkg.com/yargs-parser/-/yargs-parser-18.1.3.tgz#be68c4975c6b2abf469236b0c870362fab09a7b0" integrity sha512-o50j0JeToy/4K6OZcaQmW6lyXXKhq7csREXcDwk2omFPJEwUNOVtJKvmDr9EI1fAJZUyZcRF7kxGBWmRXudrCQ== @@ -14652,6 +14746,23 @@ yargs@^14.2.2: y18n "^4.0.0" yargs-parser "^15.0.1" +yargs@^15.3.1: + version "15.4.1" + resolved "https://registry.yarnpkg.com/yargs/-/yargs-15.4.1.tgz#0d87a16de01aee9d8bec2bfbf74f67851730f4f8" + integrity sha512-aePbxDmcYW++PaqBsJ+HYUFwCdv4LVvdnhBy78E57PIor8/OVvhMrADFFEDh8DHDFRv/O9i3lPhsENjO7QX0+A== + dependencies: + cliui "^6.0.0" + decamelize "^1.2.0" + find-up "^4.1.0" + get-caller-file "^2.0.1" + require-directory "^2.1.1" + require-main-filename "^2.0.0" + set-blocking "^2.0.0" + string-width "^4.2.0" + which-module "^2.0.0" + y18n "^4.0.0" + yargs-parser "^18.1.2" + yargs@^4.7.1: version "4.8.1" resolved "https://registry.yarnpkg.com/yargs/-/yargs-4.8.1.tgz#c0c42924ca4aaa6b0e6da1739dfb216439f9ddc0" From 0113612339d96ebdedab6608ce8abce4528d4c6a Mon Sep 17 00:00:00 2001 From: Kevin Ho Date: Wed, 26 Aug 2020 15:11:03 -0400 Subject: [PATCH 2/3] remove CrossDomainMessageReceiver --- .../CrossDomainMessageReceiver.interface.sol | 17 --- .../bridge/CrossDomainMessenger.interface.sol | 8 +- .../bridge/MockCrossDomainMessageReceiver.sol | 109 ----------------- .../bridge/MockCrossDomainMessenger.sol | 22 +--- .../test-helpers/CrossDomainSimpleStorage.sol | 18 +++ .../SimpleStorageMessageReceiver.sol | 33 ------ .../MockCrossDomainMessageReceiver.spec.ts | 85 ------------- .../bridge/MockCrossDomainMessenger.spec.ts | 112 +++++++++--------- 8 files changed, 81 insertions(+), 323 deletions(-) delete mode 100644 packages/contracts/contracts/optimistic-ethereum/bridge/CrossDomainMessageReceiver.interface.sol delete mode 100644 packages/contracts/contracts/optimistic-ethereum/bridge/MockCrossDomainMessageReceiver.sol create mode 100644 packages/contracts/contracts/test-helpers/CrossDomainSimpleStorage.sol delete mode 100644 packages/contracts/contracts/test-helpers/SimpleStorageMessageReceiver.sol delete mode 100644 packages/contracts/test/contracts/bridge/MockCrossDomainMessageReceiver.spec.ts diff --git a/packages/contracts/contracts/optimistic-ethereum/bridge/CrossDomainMessageReceiver.interface.sol b/packages/contracts/contracts/optimistic-ethereum/bridge/CrossDomainMessageReceiver.interface.sol deleted file mode 100644 index d9f8633e4d2..00000000000 --- a/packages/contracts/contracts/optimistic-ethereum/bridge/CrossDomainMessageReceiver.interface.sol +++ /dev/null @@ -1,17 +0,0 @@ -pragma solidity ^0.5.0; - -contract ICrossDomainMessageReceiver { - /** - * Receives a message from a cross domain messenger. - * @param _sender Address of the message sender. - * @param _message Calldata being received. - * @param _timestamp Time the message was sent. - * @param _blockNumber Block the message was sent in. - */ - function receiveMessage( - address _sender, - bytes memory _message, - uint256 _timestamp, - uint256 _blockNumber - ) public; -} \ No newline at end of file diff --git a/packages/contracts/contracts/optimistic-ethereum/bridge/CrossDomainMessenger.interface.sol b/packages/contracts/contracts/optimistic-ethereum/bridge/CrossDomainMessenger.interface.sol index 85ba8b2dcb5..8dc382732d9 100644 --- a/packages/contracts/contracts/optimistic-ethereum/bridge/CrossDomainMessenger.interface.sol +++ b/packages/contracts/contracts/optimistic-ethereum/bridge/CrossDomainMessenger.interface.sol @@ -1,20 +1,18 @@ pragma solidity ^0.5.0; contract ICrossDomainMessenger { + address public crossDomainMsgSender; + /** * Relays a message to a given target contract. * @param _target Address of the target contract. * @param _sender Address of the message sender. * @param _message Calldata to relay. - * @param _timestamp Time the message was relayed. - * @param _blockNumber Block number the message was relayed in. */ function relayMessage( address _target, address _sender, - bytes memory _message, - uint256 _timestamp, - uint256 _blockNumber + bytes memory _message ) public; /** diff --git a/packages/contracts/contracts/optimistic-ethereum/bridge/MockCrossDomainMessageReceiver.sol b/packages/contracts/contracts/optimistic-ethereum/bridge/MockCrossDomainMessageReceiver.sol deleted file mode 100644 index 5e28d755cd8..00000000000 --- a/packages/contracts/contracts/optimistic-ethereum/bridge/MockCrossDomainMessageReceiver.sol +++ /dev/null @@ -1,109 +0,0 @@ -pragma solidity ^0.5.0; - -/* Interface Imports */ -import { ICrossDomainMessageReceiver } from "./CrossDomainMessageReceiver.interface.sol"; -import { ICrossDomainMessenger } from "./CrossDomainMessenger.interface.sol"; - -/** - * @title MockCrossDomainMessageReceiver - */ -contract MockCrossDomainMessageReceiver is ICrossDomainMessageReceiver { - /* - * Contract Variables - */ - - ICrossDomainMessenger public crossDomainMessenger; - - - /* - * Modifiers - */ - - modifier onlyMessenger() { - require( - msg.sender == address(crossDomainMessenger), - "Only the CrossDomainMessenger can call this function." - ); - _; - } - - - /* - * Public Functions - */ - - /** - * Receives a message from the cross domain messenger. - * .inheritdoc ICrossDomainMessageReceiver - */ - function receiveMessage( - address _sender, - bytes memory _message, - uint256 _timestamp, - uint256 _blockNumber - ) - public - onlyMessenger - { - onMessageReceived( - _sender, - _message, - _timestamp, - _blockNumber - ); - - uint256 messageSize = _message.length; - bool success = false; - assembly { - success := call( - gas, - address, - 0, - add(_message, 0x20), - messageSize, - 0, - 0 - ) - } - - if (!success) { - revert("Received message reverted during execution."); - } - } - - /** - * Sets the address of the cross domain messenger. - * @param _crossDomainMessenger Cross domain messenger address. - */ - function setMessenger( - address _crossDomainMessenger - ) - public - { - crossDomainMessenger = ICrossDomainMessenger(_crossDomainMessenger); - } - - - /* - * Internal Functions - */ - - /** - * Triggered whenever a message is received. - * @param _sender Address of the message sender. - * @param _message Calldata being received. - * @param _timestamp Time the message was sent. - * @param _blockNumber Block the message was sent in. - */ - function onMessageReceived( - address _sender, - bytes memory _message, - uint256 _timestamp, - uint256 _blockNumber - ) - internal - { - // Implement me! - return; - } -} diff --git a/packages/contracts/contracts/optimistic-ethereum/bridge/MockCrossDomainMessenger.sol b/packages/contracts/contracts/optimistic-ethereum/bridge/MockCrossDomainMessenger.sol index 46d8114ea50..310c8e09482 100644 --- a/packages/contracts/contracts/optimistic-ethereum/bridge/MockCrossDomainMessenger.sol +++ b/packages/contracts/contracts/optimistic-ethereum/bridge/MockCrossDomainMessenger.sol @@ -2,7 +2,6 @@ pragma solidity ^0.5.0; /* Interface Imports */ import { ICrossDomainMessenger } from "./CrossDomainMessenger.interface.sol"; -import { ICrossDomainMessageReceiver } from "./CrossDomainMessageReceiver.interface.sol"; /** * @title MockCrossDomainMessenger @@ -13,7 +12,7 @@ contract MockCrossDomainMessenger is ICrossDomainMessenger { */ ICrossDomainMessenger targetMessenger; - + address public crossDomainMsgSender; /* * Public Functions @@ -26,20 +25,13 @@ contract MockCrossDomainMessenger is ICrossDomainMessenger { function relayMessage( address _target, address _sender, - bytes memory _message, - uint256 _timestamp, - uint256 _blockNumber + bytes memory _message ) public { - ICrossDomainMessageReceiver target = ICrossDomainMessageReceiver(_target); - - target.receiveMessage( - _sender, - _message, - _timestamp, - _blockNumber - ); + crossDomainMsgSender = _sender; + (bool success,) = _target.call(_message); + require(success, "Received message reverted during execution."); } /** @@ -60,9 +52,7 @@ contract MockCrossDomainMessenger is ICrossDomainMessenger { targetMessenger.relayMessage( _target, msg.sender, - _message, - block.timestamp, - block.number + _message ); } diff --git a/packages/contracts/contracts/test-helpers/CrossDomainSimpleStorage.sol b/packages/contracts/contracts/test-helpers/CrossDomainSimpleStorage.sol new file mode 100644 index 00000000000..5cb60e2c7da --- /dev/null +++ b/packages/contracts/contracts/test-helpers/CrossDomainSimpleStorage.sol @@ -0,0 +1,18 @@ +pragma solidity ^0.5.0; + +import { ICrossDomainMessenger} from "../optimistic-ethereum/bridge/CrossDomainMessenger.interface.sol"; +import { SimpleStorage } from "./SimpleStorage.sol"; + +contract CrossDomainSimpleStorage is SimpleStorage { + ICrossDomainMessenger crossDomainMessenger; + address public crossDomainMsgSender; + + function setMessenger(address _crossDomainMessengerAddress) public { + crossDomainMessenger = ICrossDomainMessenger(_crossDomainMessengerAddress); + } + + function crossDomainSetStorage(bytes32 key, bytes32 value) public { + crossDomainMsgSender = crossDomainMessenger.crossDomainMsgSender(); + setStorage(key, value); + } +} \ No newline at end of file diff --git a/packages/contracts/contracts/test-helpers/SimpleStorageMessageReceiver.sol b/packages/contracts/contracts/test-helpers/SimpleStorageMessageReceiver.sol deleted file mode 100644 index cd1a87b2c4b..00000000000 --- a/packages/contracts/contracts/test-helpers/SimpleStorageMessageReceiver.sol +++ /dev/null @@ -1,33 +0,0 @@ -pragma solidity ^0.5.0; - -import { MockCrossDomainMessageReceiver } from "../optimistic-ethereum/bridge/MockCrossDomainMessageReceiver.sol"; -import { SimpleStorage } from "./SimpleStorage.sol"; - -contract SimpleStorageMessageReceiver is SimpleStorage, MockCrossDomainMessageReceiver { - struct Message { - address sender; - bytes message; - uint256 timestamp; - uint256 blockNumber; - } - - mapping (uint256 => Message) public messages; - uint256 public totalMessages; - - function onMessageReceived( - address _sender, - bytes memory _message, - uint256 _timestamp, - uint256 _blockNumber - ) - internal - { - messages[totalMessages] = Message({ - sender: _sender, - message: _message, - timestamp: _timestamp, - blockNumber: _blockNumber - }); - totalMessages += 1; - } -} \ No newline at end of file diff --git a/packages/contracts/test/contracts/bridge/MockCrossDomainMessageReceiver.spec.ts b/packages/contracts/test/contracts/bridge/MockCrossDomainMessageReceiver.spec.ts deleted file mode 100644 index fa1b84aacfe..00000000000 --- a/packages/contracts/test/contracts/bridge/MockCrossDomainMessageReceiver.spec.ts +++ /dev/null @@ -1,85 +0,0 @@ -import { expect } from '../../setup' - -/* External Imports */ -import { ethers } from '@nomiclabs/buidler' -import { ContractFactory, Contract, Signer } from 'ethers' - -describe('MockCrossDomainMessageReceiver', () => { - let wallet: Signer - let wallet2: Signer - before(async () => { - ;[wallet, wallet2] = await ethers.getSigners() - }) - - let SimpleStorageMessageReceiverFactory: ContractFactory - before(async () => { - SimpleStorageMessageReceiverFactory = await ethers.getContractFactory('SimpleStorageMessageReceiver') - }) - - let L2SimpleStorageMessageReceiver: Contract - beforeEach(async () => { - L2SimpleStorageMessageReceiver = await SimpleStorageMessageReceiverFactory.deploy() - - await L2SimpleStorageMessageReceiver.setMessenger(await wallet.getAddress()) - }) - - describe('receiveMessage', () => { - it('should successfully receive a message from the messenger', async () => { - const expectedStorageKey = ethers.utils.keccak256('0x1234') - const expectedStorageValue = ethers.utils.keccak256('0x5678') - - const calldata = L2SimpleStorageMessageReceiver.interface.encodeFunctionData( - 'setStorage', - [ - expectedStorageKey, - expectedStorageValue - ] - ) - - const expectedMessage = [ - await wallet.getAddress(), - calldata, - ethers.BigNumber.from(Date.now()), - ethers.BigNumber.from(123) - ] - - await L2SimpleStorageMessageReceiver.receiveMessage( - ...expectedMessage, - { - from: await wallet.getAddress() - } - ) - - const actualStorageValue = await L2SimpleStorageMessageReceiver.getStorage(expectedStorageKey) - expect(actualStorageValue).to.equal(expectedStorageValue) - - const actualMessage = await L2SimpleStorageMessageReceiver.messages(0) - expect(actualMessage).to.deep.equal(expectedMessage) - }) - - it('should fail if the message is not received from the messenger', async () => { - const expectedStorageKey = ethers.utils.keccak256('0x1234') - const expectedStorageValue = ethers.utils.keccak256('0x5678') - - const calldata = L2SimpleStorageMessageReceiver.interface.encodeFunctionData( - 'setStorage', - [ - expectedStorageKey, - expectedStorageValue - ] - ) - - const expectedMessage = [ - await wallet.getAddress(), - calldata, - ethers.BigNumber.from(Date.now()), - ethers.BigNumber.from(123) - ] - - L2SimpleStorageMessageReceiver = L2SimpleStorageMessageReceiver.connect(wallet2) - await expect(L2SimpleStorageMessageReceiver.receiveMessage( - ...expectedMessage - )).to.be.revertedWith('Only the CrossDomainMessenger can call this function.') - }) - }) -}) \ No newline at end of file diff --git a/packages/contracts/test/contracts/bridge/MockCrossDomainMessenger.spec.ts b/packages/contracts/test/contracts/bridge/MockCrossDomainMessenger.spec.ts index 62c89fa79a2..aba1fce27ce 100644 --- a/packages/contracts/test/contracts/bridge/MockCrossDomainMessenger.spec.ts +++ b/packages/contracts/test/contracts/bridge/MockCrossDomainMessenger.spec.ts @@ -5,17 +5,21 @@ import { ethers } from '@nomiclabs/buidler' import { ContractFactory, Contract, Signer } from 'ethers' import { NULL_ADDRESS } from '@eth-optimism/core-utils' -describe('MockCrossDomainMessenger', () => { +describe.only('MockCrossDomainMessenger', () => { let wallet: Signer before(async () => { ;[wallet] = await ethers.getSigners() }) let MockCrossDomainMessengerFactory: ContractFactory - let SimpleStorageMessageReceiverFactory: ContractFactory + let CrossDomainSimpleStorageFactory: ContractFactory before(async () => { - MockCrossDomainMessengerFactory = await ethers.getContractFactory('MockCrossDomainMessenger') - SimpleStorageMessageReceiverFactory = await ethers.getContractFactory('SimpleStorageMessageReceiver') + MockCrossDomainMessengerFactory = await ethers.getContractFactory( + 'MockCrossDomainMessenger' + ) + CrossDomainSimpleStorageFactory = await ethers.getContractFactory( + 'CrossDomainSimpleStorage' + ) }) let L1MockCrossDomainMessenger: Contract @@ -24,47 +28,44 @@ describe('MockCrossDomainMessenger', () => { L1MockCrossDomainMessenger = await MockCrossDomainMessengerFactory.deploy() L2MockCrossDomainMessenger = await MockCrossDomainMessengerFactory.deploy() - await L1MockCrossDomainMessenger.setTargetMessenger(L2MockCrossDomainMessenger.address) - await L2MockCrossDomainMessenger.setTargetMessenger(L1MockCrossDomainMessenger.address) + await L1MockCrossDomainMessenger.setTargetMessenger( + L2MockCrossDomainMessenger.address + ) + await L2MockCrossDomainMessenger.setTargetMessenger( + L1MockCrossDomainMessenger.address + ) }) - let L2SimpleStorageMessageReceiver: Contract + let L2SimpleStorage: Contract beforeEach(async () => { - L2SimpleStorageMessageReceiver = await SimpleStorageMessageReceiverFactory.deploy() - - await L2SimpleStorageMessageReceiver.setMessenger(L2MockCrossDomainMessenger.address) - }) + L2SimpleStorage = await CrossDomainSimpleStorageFactory.deploy() + await L2SimpleStorage.setMessenger(L2MockCrossDomainMessenger.address) + }) describe('relayMessage', () => { it('should successfully relay a message to the target receiver', async () => { const expectedStorageKey = ethers.utils.keccak256('0x1234') const expectedStorageValue = ethers.utils.keccak256('0x5678') - const calldata = L2SimpleStorageMessageReceiver.interface.encodeFunctionData( - 'setStorage', - [ - expectedStorageKey, - expectedStorageValue - ] + const calldata = L2SimpleStorage.interface.encodeFunctionData( + 'crossDomainSetStorage', + [expectedStorageKey, expectedStorageValue] ) - const expectedMessage = [ - await wallet.getAddress(), - calldata, - ethers.BigNumber.from(Date.now()), - ethers.BigNumber.from(123) - ] + const expectedMessage = [await wallet.getAddress(), calldata] await L2MockCrossDomainMessenger.relayMessage( - L2SimpleStorageMessageReceiver.address, + L2SimpleStorage.address, ...expectedMessage ) - const actualStorageValue = await L2SimpleStorageMessageReceiver.getStorage(expectedStorageKey) + const actualStorageValue = await L2SimpleStorage.getStorage( + expectedStorageKey + ) expect(actualStorageValue).to.equal(expectedStorageValue) - - const actualMessage = await L2SimpleStorageMessageReceiver.messages(0) - expect(actualMessage).to.deep.equal(expectedMessage) + expect(await L2SimpleStorage.crossDomainMsgSender()).to.equal( + await wallet.getAddress() + ) }) }) @@ -73,16 +74,13 @@ describe('MockCrossDomainMessenger', () => { const expectedStorageKey = ethers.utils.keccak256('0x1234') const expectedStorageValue = ethers.utils.keccak256('0x5678') - const calldata = L2SimpleStorageMessageReceiver.interface.encodeFunctionData( - 'setStorage', - [ - expectedStorageKey, - expectedStorageValue - ] + const calldata = L2SimpleStorage.interface.encodeFunctionData( + 'crossDomainSetStorage', + [expectedStorageKey, expectedStorageValue] ) await L1MockCrossDomainMessenger.sendMessage( - L2SimpleStorageMessageReceiver.address, + L2SimpleStorage.address, calldata, { from: await wallet.getAddress(), @@ -90,41 +88,39 @@ describe('MockCrossDomainMessenger', () => { ) const currentBlock = await ethers.provider.getBlock('latest') - const expectedMessage = [ - await wallet.getAddress(), - calldata, - ethers.BigNumber.from(currentBlock.timestamp), - ethers.BigNumber.from(currentBlock.number), - ] + const expectedMessage = [await wallet.getAddress(), calldata] - const actualStorageValue = await L2SimpleStorageMessageReceiver.getStorage(expectedStorageKey) + const actualStorageValue = await L2SimpleStorage.getStorage( + expectedStorageKey + ) expect(actualStorageValue).to.equal(expectedStorageValue) - - const actualMessage = await L2SimpleStorageMessageReceiver.messages(0) - expect(actualMessage).to.deep.equal(expectedMessage) + expect(await L2SimpleStorage.crossDomainMsgSender()).to.equal( + await wallet.getAddress() + ) }) it('should revert if its target messenger is not set', async () => { const expectedStorageKey = ethers.utils.keccak256('0x1234') const expectedStorageValue = ethers.utils.keccak256('0x5678') - const calldata = L2SimpleStorageMessageReceiver.interface.encodeFunctionData( + const calldata = L2SimpleStorage.interface.encodeFunctionData( 'setStorage', - [ - expectedStorageKey, - expectedStorageValue - ] + [expectedStorageKey, expectedStorageValue] ) await L1MockCrossDomainMessenger.setTargetMessenger(NULL_ADDRESS) - await expect(L1MockCrossDomainMessenger.sendMessage( - L2SimpleStorageMessageReceiver.address, - calldata, - { - from: await wallet.getAddress(), - } - )).to.be.revertedWith('Cannot send a message without setting the target messenger.') + await expect( + L1MockCrossDomainMessenger.sendMessage( + L2SimpleStorage.address, + calldata, + { + from: await wallet.getAddress(), + } + ) + ).to.be.revertedWith( + 'Cannot send a message without setting the target messenger.' + ) }) }) -}) \ No newline at end of file +}) From 9eda25ed2c5d2e5ea9fd045129fe86647ff0db8c Mon Sep 17 00:00:00 2001 From: Kevin Ho Date: Wed, 26 Aug 2020 15:11:44 -0400 Subject: [PATCH 3/3] lint --- .../test/contracts/bridge/MockCrossDomainMessenger.spec.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/contracts/test/contracts/bridge/MockCrossDomainMessenger.spec.ts b/packages/contracts/test/contracts/bridge/MockCrossDomainMessenger.spec.ts index aba1fce27ce..58bdbac6c90 100644 --- a/packages/contracts/test/contracts/bridge/MockCrossDomainMessenger.spec.ts +++ b/packages/contracts/test/contracts/bridge/MockCrossDomainMessenger.spec.ts @@ -5,7 +5,7 @@ import { ethers } from '@nomiclabs/buidler' import { ContractFactory, Contract, Signer } from 'ethers' import { NULL_ADDRESS } from '@eth-optimism/core-utils' -describe.only('MockCrossDomainMessenger', () => { +describe('MockCrossDomainMessenger', () => { let wallet: Signer before(async () => { ;[wallet] = await ethers.getSigners()