From 65e87aab3087c4b9d9b53150aad01f8f81c1d835 Mon Sep 17 00:00:00 2001 From: cam-schultz Date: Wed, 22 Nov 2023 16:29:21 +0000 Subject: [PATCH 01/10] standalone getting started guide --- .../CrossChainApplications/GETTING_STARTED.md | 197 +++++++++++++++++ .../src/CrossChainApplications/README.md | 208 ------------------ 2 files changed, 197 insertions(+), 208 deletions(-) create mode 100644 contracts/src/CrossChainApplications/GETTING_STARTED.md diff --git a/contracts/src/CrossChainApplications/GETTING_STARTED.md b/contracts/src/CrossChainApplications/GETTING_STARTED.md new file mode 100644 index 000000000..274eff99d --- /dev/null +++ b/contracts/src/CrossChainApplications/GETTING_STARTED.md @@ -0,0 +1,197 @@ +# Getting Started with an Example Application + +This section walks through how to build an example cross-chain application on top of the Teleporter protocol, recreating the `ExampleCrossChainMessenger` contract that sends arbitrary string data from one chain to another. Note that this tutorial is meant for education purposes only. The resulting code is not intended for use in production environments. + +### Step 1: Create Initial Contract + +Create a new file called `MyExampleCrossChainMessenger.sol` in the directory that will hold the application. + +At the top of the file define the Solidity version to work with, and import the necessary types and interfaces. + +```solidity +pragma solidity 0.8.18; + +import {ITeleporterMessenger, TeleporterMessageInput, TeleporterFeeInfo} from "../../Teleporter/ITeleporterMessenger.sol"; +import {ITeleporterReceiver} from "../../Teleporter/ITeleporterReceiver.sol"; +``` + +Next, define the initial empty contract. + +```solidity +contract MyExampleCrossChainMessenger {} +``` + +### Step 2: Integrating Teleporter Messenger + +Now that the initial empty `MyExampleCrossChainMessenger` is defined, it's time to integrate the `ITeleporterMessenger` that will provide the functionality to deliver cross chain messages. + +Create a state variable of `ITeleporterMessenger` type called `teleporterMessenger`. Then create a constructor for our contract that takes in an address where the Teleporter Messenger would be deployed on this chain, and set our state variable with it. + +```solidity +contract ExampleCrossChainMessenger { + ITeleporterMessenger public immutable teleporterMessenger; + + constructor(address teleporterMessengerAddress) { + teleporterMessenger = ITeleporterMessenger(teleporterMessengerAddress); + } +} +``` + +### Step 3: Send and Receive + +Now that `MyExampleCrossChainMessenger` has an instantiation of `ITeleporterMessenger`, the next step is to add in functionality of sending and receiving arbitrary string data between chains. + +To start, create the function declarations for `sendMessage`, which will send string data cross-chain to the specified destination address' receiver. This function allows callers to specify the destination chain ID, destination address to send to, relayer fees, required gas limit for message execution on destination address, and the actual message data. + +```solidity +// Send a new message to another chain. +function sendMessage( + bytes32 destinationChainID, + address destinationAddress, + address feeTokenAddress, + uint256 feeAmount, + uint256 requiredGasLimit, + string calldata message +) external returns (uint256 messageID) {} +``` + +`MyExampleCrossChainMessenger` also needs to implement `ITeleporterReceiver` by adding the method `receiveTeleporterMessage` that receives the cross-chain messages from Teleporter. + +```solidity +// Receive a new message from another chain. +function receiveTeleporterMessage( + bytes32 originChainID, + address originSenderAddress, + bytes calldata message +) external {} +``` + +Now it's time to implement the methods, starting with `sendMessage`. First, import OpenZeppelin's `IERC20` contract, then in `sendMessage` check whether `feeAmount` is greater than zero. If it is, transfer and approve the amount of IERC20 asset at `feeTokenAddress` to the Teleporter Messenger saved as a state variable. Relayer fees are an optional way to incentive relayers to deliver a Teleporter message to its destination. They are not strictly necessary, and may be omitted if a relayer is willing to relay messages with no fee, such as with a self-hosted relayer. + +```solidity +// For non-zero fee amounts, transfer the fee into the control of this contract first, and then +// allow the Teleporter contract to spend it. +if (feeAmount > 0) { + IERC20 feeToken = IERC20(feeTokenAddress); + require( + feeToken.transferFrom(msg.sender, address(this), feeAmount), + "Failed to transfer fee amount" + ); + require( + feeToken.approve(address(teleporterMessenger), feeAmount), + "Failed to approve fee amount" + ); +} +``` + +Next, add the call to the `TeleporterMessenger` contract with the message data to be executed when delivered to the destination address. In `sendMessage`, form a `TeleporterMessageInput` and call `sendCrossChainMessage` on the `TeleporterMessenger` instance to start the cross chain messaging process. + +> `allowedRelayerAddresses` is empty in this example, meaning any relayer can try to deliver this cross chain message. Specific relayer addresses can be specified to ensure only those relayers can deliver the message. +> The `message` must be ABI encoded so that it can be properly decoded on the receiving end. + +```solidity +return + teleporterMessenger.sendCrossChainMessage( + TeleporterMessageInput({ + destinationChainID: destinationChainID, + destinationAddress: destinationAddress, + feeInfo: TeleporterFeeInfo({ + feeTokenAddress: feeTokenAddress, + amount: feeAmount + }), + requiredGasLimit: requiredGasLimit, + allowedRelayerAddresses: new address[](0), + message: abi.encode(message) + }) + ); +``` + +With the sending side complete, the next step is to implement `ITeleporterReceiver.receiveTeleporterMessage`. The receiver in this example will just receive the arbitrary string data, and check that the message is sent through Teleporter. + +```solidity +// Receive a new message from another chain. +function receiveTeleporterMessage( + bytes32 originChainID, + address originSenderAddress, + bytes calldata message +) external { + // Only the Teleporter receiver can deliver a message. + require(msg.sender == address(teleporterMessenger), "Unauthorized."); + + // do something with message. + return true; +} +``` + +The base of sending and receiving messages cross chain is complete. `MyExampleCrossChainMessenger` can now be expanded with functionality that saves the received messages, and allows users to query for the latest message received from a specified chain. + +### Step 4: Storing the Message + +Start by defining the `struct` for how to save our messages. It saves the string message itself and the address of the sender. + +A map will also be added where the key is the `originChainID`, and the value is the latest `message` sent from that chain. + +```solidity +// Messages sent to this contract. +struct Message { + address sender; + string message; +} + +mapping(bytes32 originChainID => Message message) private _messages; +``` + +Next, update `receiveTeleporterMessage` to save the message into our mapping after we receive and verify that it's sent from Teleporter. ABI decode the `message` bytes into a string. + +```solidity +// Receive a new message from another chain. +function receiveTeleporterMessage( + bytes32 originChainID, + address originSenderAddress, + bytes calldata message +) external { + // Only the Teleporter receiver can deliver a message. + require(msg.sender == address(teleporterMessenger), "Unauthorized."); + + // Store the message. + messages[originChainID] = Message(originSenderAddress, abi.decode(message, (string))); +} +``` + +Next, add a function called `getCurrentMessage` that allows users or contracts to easily query our contract for the latest message sent by a specified chain. + +```solidity +// Check the current message from another chain. +function getCurrentMessage( + bytes32 originChainID +) external view returns (address, string memory) { + Message memory messageInfo = messages[originChainID]; + return (messageInfo.sender, messageInfo.message); +} +``` + +There we have it, a simple cross chain messenger built on top of Teleporter! Full example [here](./ExampleMessenger/ExampleCrossChainMessenger.sol). + +### Step 5: Testing + +For testing, `scripts/local/test.sh` sets up a local Avalanche network with three subnets deployed with Teleporter, and a relayer to deliver Teleporter messages. To add an integration test simply add a new test script under `integration-tests`. An integration test for `ExampleCrossChainMessenger` is already included (`scripts/local/integration_tests/example_messenger.sh`), which performs the following steps: + +1. Deploys the [ExampleERC20](../Mocks/ExampleERC20.sol) token to subnet A. +2. Deploys `ExampleCrossChainMessenger` to both subnets A and B. +3. Approves the cross-chain messenger on subnet A to spend ERC20 tokens from the default address. +4. Sends `"hello world"` from subnet A to subnet B's cross-chain messenger to receive. +5. Calls `getCurrentMessage` on subnet B to make sure the right message and sender are received. + +Running `./test.sh example_messenger` at the root of the repo should yield at the end of the test: + +```bash +test_runner | Raw result is: "0x5DB9A7629912EBF95876228C24A848de0bfB43A9 +test_runner | hello world!" +test_runner | The latest message from chain ID GoTmTVw77eGauaL17e1xPrtWEa72SQnvf9G8ackU6KZVGVYpz was: +test_runner | Message Sender: 0x5DB9A7629912EBF95876228C24A848de0bfB43A9 +test_runner | Message: "hello world!" +test_runner | Successfully called getCurrentMessage. +test_runner | Done running test example_messenger. +test_runner | +test_runner exited with code 0 +``` diff --git a/contracts/src/CrossChainApplications/README.md b/contracts/src/CrossChainApplications/README.md index 9caec5b35..05eb0c759 100644 --- a/contracts/src/CrossChainApplications/README.md +++ b/contracts/src/CrossChainApplications/README.md @@ -2,216 +2,8 @@ This directory includes cross-chain applications that are built on top of the [Teleporter protocol](../Teleporter/README.md). -- [Teleporter Cross Chain Applications](#teleporter-cross-chain-applications) - - [Applications](#applications) - - [Get Started](#get-started) - - [Step 1: Create Initial Contract](#step-1-create-initial-contract) - - [Step 2: Integrating Teleporter Messenger](#step-2-integrating-teleporter-messenger) - - [Step 3: Send and Receive](#step-3-send-and-receive) - - [Step 4: Storing the Message](#step-4-storing-the-message) - - [Step 5: Testing](#step-5-testing) - - ## Applications - `ERC20Bridge` allows cross chain bridging of erc20 assets. More details found [here](./ERC20Bridge/README.md) - `ExampleMessenger` a simple cross chain messenger that demonstrates Teleporter application sending arbitrary string data. - `VerifiedBlockHash` publishes the latest block hash of one chain to a destination chain that receives the hash and verifies the sender. Includes `BlockHashPublisher` and `BlockHashReceiver`. More details found [here](./VerifiedBlockHash/README.md) - -## Getting started with an example application - -This section walks through how to build an example cross-chain application on top of the Teleporter protocol, recreating the `ExampleCrossChainMessenger` contract that sends arbitrary string data from one chain to another. Note that this tutorial is meant for education purposes only. The resulting code is not intended for use in production environments. - -### Step 1: Create Initial Contract - -Create a new file called `MyExampleCrossChainMessenger.sol` in the directory that will hold the application. - -At the top of the file define the Solidity version to work with, and import the necessary types and interfaces. - -```solidity -pragma solidity 0.8.18; - -import {ITeleporterMessenger, TeleporterMessageInput, TeleporterFeeInfo} from "../../Teleporter/ITeleporterMessenger.sol"; -import {ITeleporterReceiver} from "../../Teleporter/ITeleporterReceiver.sol"; -``` - -Next, define the initial empty contract. - -```solidity -contract MyExampleCrossChainMessenger {} -``` - -### Step 2: Integrating Teleporter Messenger - -Now that the initial empty `MyExampleCrossChainMessenger` is defined, it's time to integrate the `ITeleporterMessenger` that will provide the functionality to deliver cross chain messages. - -Create a state variable of `ITeleporterMessenger` type called `teleporterMessenger`. Then create a constructor for our contract that takes in an address where the Teleporter Messenger would be deployed on this chain, and set our state variable with it. - -```solidity -contract ExampleCrossChainMessenger { - ITeleporterMessenger public immutable teleporterMessenger; - - constructor(address teleporterMessengerAddress) { - teleporterMessenger = ITeleporterMessenger(teleporterMessengerAddress); - } -} -``` - -### Step 3: Send and Receive - -Now that `MyExampleCrossChainMessenger` has an instantiation of `ITeleporterMessenger`, the next step is to add in functionality of sending and receiving arbitrary string data between chains. - -To start, create the function declarations for `sendMessage`, which will send string data cross-chain to the specified destination address' receiver. This function allows callers to specify the destination chain ID, destination address to send to, relayer fees, required gas limit for message execution on destination address, and the actual message data. - -```solidity -// Send a new message to another chain. -function sendMessage( - bytes32 destinationChainID, - address destinationAddress, - address feeTokenAddress, - uint256 feeAmount, - uint256 requiredGasLimit, - string calldata message -) external returns (uint256 messageID) {} -``` - -`MyExampleCrossChainMessenger` also needs to implement `ITeleporterReceiver` by adding the method `receiveTeleporterMessage` that receives the cross-chain messages from Teleporter. - -```solidity -// Receive a new message from another chain. -function receiveTeleporterMessage( - bytes32 originChainID, - address originSenderAddress, - bytes calldata message -) external {} -``` - -Now it's time to implement the methods, starting with `sendMessage`. First, import OpenZeppelin's `IERC20` contract, then in `sendMessage` check whether `feeAmount` is greater than zero. If it is, transfer and approve the amount of IERC20 asset at `feeTokenAddress` to the Teleporter Messenger saved as a state variable. Relayer fees are an optional way to incentive relayers to deliver a Teleporter message to its destination. They are not strictly necessary, and may be omitted if a relayer is willing to relay messages with no fee, such as with a self-hosted relayer. - -```solidity -// For non-zero fee amounts, transfer the fee into the control of this contract first, and then -// allow the Teleporter contract to spend it. -if (feeAmount > 0) { - IERC20 feeToken = IERC20(feeTokenAddress); - require( - feeToken.transferFrom(msg.sender, address(this), feeAmount), - "Failed to transfer fee amount" - ); - require( - feeToken.approve(address(teleporterMessenger), feeAmount), - "Failed to approve fee amount" - ); -} -``` - -Next, add the call to the `TeleporterMessenger` contract with the message data to be executed when delivered to the destination address. In `sendMessage`, form a `TeleporterMessageInput` and call `sendCrossChainMessage` on the `TeleporterMessenger` instance to start the cross chain messaging process. - -> `allowedRelayerAddresses` is empty in this example, meaning any relayer can try to deliver this cross chain message. Specific relayer addresses can be specified to ensure only those relayers can deliver the message. -> The `message` must be ABI encoded so that it can be properly decoded on the receiving end. - -```solidity -return - teleporterMessenger.sendCrossChainMessage( - TeleporterMessageInput({ - destinationChainID: destinationChainID, - destinationAddress: destinationAddress, - feeInfo: TeleporterFeeInfo({ - feeTokenAddress: feeTokenAddress, - amount: feeAmount - }), - requiredGasLimit: requiredGasLimit, - allowedRelayerAddresses: new address[](0), - message: abi.encode(message) - }) - ); -``` - -With the sending side complete, the next step is to implement `ITeleporterReceiver.receiveTeleporterMessage`. The receiver in this example will just receive the arbitrary string data, and check that the message is sent through Teleporter. - -```solidity -// Receive a new message from another chain. -function receiveTeleporterMessage( - bytes32 originChainID, - address originSenderAddress, - bytes calldata message -) external { - // Only the Teleporter receiver can deliver a message. - require(msg.sender == address(teleporterMessenger), "Unauthorized."); - - // do something with message. - return true; -} -``` - -The base of sending and receiving messages cross chain is complete. `MyExampleCrossChainMessenger` can now be expanded with functionality that saves the received messages, and allows users to query for the latest message received from a specified chain. - -### Step 4: Storing the Message - -Start by defining the `struct` for how to save our messages. It saves the string message itself and the address of the sender. - -A map will also be added where the key is the `originChainID`, and the value is the latest `message` sent from that chain. - -```solidity -// Messages sent to this contract. -struct Message { - address sender; - string message; -} - -mapping(bytes32 originChainID => Message message) private _messages; -``` - -Next, update `receiveTeleporterMessage` to save the message into our mapping after we receive and verify that it's sent from Teleporter. ABI decode the `message` bytes into a string. - -```solidity -// Receive a new message from another chain. -function receiveTeleporterMessage( - bytes32 originChainID, - address originSenderAddress, - bytes calldata message -) external { - // Only the Teleporter receiver can deliver a message. - require(msg.sender == address(teleporterMessenger), "Unauthorized."); - - // Store the message. - messages[originChainID] = Message(originSenderAddress, abi.decode(message, (string))); -} -``` - -Next, add a function called `getCurrentMessage` that allows users or contracts to easily query our contract for the latest message sent by a specified chain. - -```solidity -// Check the current message from another chain. -function getCurrentMessage( - bytes32 originChainID -) external view returns (address, string memory) { - Message memory messageInfo = messages[originChainID]; - return (messageInfo.sender, messageInfo.message); -} -``` - -There we have it, a simple cross chain messenger built on top of Teleporter! Full example [here](./ExampleMessenger/ExampleCrossChainMessenger.sol). - -### Step 5: Testing - -For testing, `scripts/local/test.sh` sets up a local Avalanche network with three subnets deployed with Teleporter, and a relayer to deliver Teleporter messages. To add an integration test simply add a new test script under `integration-tests`. An integration test for `ExampleCrossChainMessenger` is already included (`scripts/local/integration_tests/example_messenger.sh`), which performs the following steps: - -1. Deploys the [ExampleERC20](../Mocks/ExampleERC20.sol) token to subnet A. -2. Deploys `ExampleCrossChainMessenger` to both subnets A and B. -3. Approves the cross-chain messenger on subnet A to spend ERC20 tokens from the default address. -4. Sends `"hello world"` from subnet A to subnet B's cross-chain messenger to receive. -5. Calls `getCurrentMessage` on subnet B to make sure the right message and sender are received. - -Running `./test.sh example_messenger` at the root of the repo should yield at the end of the test: - -```bash -test_runner | Raw result is: "0x5DB9A7629912EBF95876228C24A848de0bfB43A9 -test_runner | hello world!" -test_runner | The latest message from chain ID GoTmTVw77eGauaL17e1xPrtWEa72SQnvf9G8ackU6KZVGVYpz was: -test_runner | Message Sender: 0x5DB9A7629912EBF95876228C24A848de0bfB43A9 -test_runner | Message: "hello world!" -test_runner | Successfully called getCurrentMessage. -test_runner | Done running test example_messenger. -test_runner | -test_runner exited with code 0 -``` From 19dd4d61ed6603c09de7c58d87457a4a37763b60 Mon Sep 17 00:00:00 2001 From: cam-schultz <78878559+cam-schultz@users.noreply.github.com> Date: Mon, 27 Nov 2023 11:31:39 -0600 Subject: [PATCH 02/10] Update contracts/src/CrossChainApplications/GETTING_STARTED.md Co-authored-by: Meaghan FitzGerald Signed-off-by: cam-schultz <78878559+cam-schultz@users.noreply.github.com> --- contracts/src/CrossChainApplications/GETTING_STARTED.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/contracts/src/CrossChainApplications/GETTING_STARTED.md b/contracts/src/CrossChainApplications/GETTING_STARTED.md index 274eff99d..6e1484117 100644 --- a/contracts/src/CrossChainApplications/GETTING_STARTED.md +++ b/contracts/src/CrossChainApplications/GETTING_STARTED.md @@ -1,4 +1,4 @@ -# Getting Started with an Example Application +# Getting Started with an Example Teleporter Application This section walks through how to build an example cross-chain application on top of the Teleporter protocol, recreating the `ExampleCrossChainMessenger` contract that sends arbitrary string data from one chain to another. Note that this tutorial is meant for education purposes only. The resulting code is not intended for use in production environments. From 74df9f7fd714ca9e6b994ca83153c8a53f76342b Mon Sep 17 00:00:00 2001 From: cam-schultz <78878559+cam-schultz@users.noreply.github.com> Date: Mon, 27 Nov 2023 11:31:58 -0600 Subject: [PATCH 03/10] Update contracts/src/CrossChainApplications/GETTING_STARTED.md Co-authored-by: Meaghan FitzGerald Signed-off-by: cam-schultz <78878559+cam-schultz@users.noreply.github.com> --- contracts/src/CrossChainApplications/GETTING_STARTED.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/contracts/src/CrossChainApplications/GETTING_STARTED.md b/contracts/src/CrossChainApplications/GETTING_STARTED.md index 6e1484117..fdbb9d467 100644 --- a/contracts/src/CrossChainApplications/GETTING_STARTED.md +++ b/contracts/src/CrossChainApplications/GETTING_STARTED.md @@ -2,7 +2,7 @@ This section walks through how to build an example cross-chain application on top of the Teleporter protocol, recreating the `ExampleCrossChainMessenger` contract that sends arbitrary string data from one chain to another. Note that this tutorial is meant for education purposes only. The resulting code is not intended for use in production environments. -### Step 1: Create Initial Contract +## Step 1: Create Initial Contract Create a new file called `MyExampleCrossChainMessenger.sol` in the directory that will hold the application. From 240a4757bbf4efe361e52e09d67b91cf807dfe16 Mon Sep 17 00:00:00 2001 From: cam-schultz <78878559+cam-schultz@users.noreply.github.com> Date: Mon, 27 Nov 2023 11:32:04 -0600 Subject: [PATCH 04/10] Update contracts/src/CrossChainApplications/GETTING_STARTED.md Co-authored-by: Meaghan FitzGerald Signed-off-by: cam-schultz <78878559+cam-schultz@users.noreply.github.com> --- contracts/src/CrossChainApplications/GETTING_STARTED.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/contracts/src/CrossChainApplications/GETTING_STARTED.md b/contracts/src/CrossChainApplications/GETTING_STARTED.md index fdbb9d467..eb219c584 100644 --- a/contracts/src/CrossChainApplications/GETTING_STARTED.md +++ b/contracts/src/CrossChainApplications/GETTING_STARTED.md @@ -21,7 +21,7 @@ Next, define the initial empty contract. contract MyExampleCrossChainMessenger {} ``` -### Step 2: Integrating Teleporter Messenger +## Step 2: Integrating Teleporter Messenger Now that the initial empty `MyExampleCrossChainMessenger` is defined, it's time to integrate the `ITeleporterMessenger` that will provide the functionality to deliver cross chain messages. From 94b636840b3f29ef92c347af9345e789bf22de52 Mon Sep 17 00:00:00 2001 From: cam-schultz <78878559+cam-schultz@users.noreply.github.com> Date: Mon, 27 Nov 2023 11:32:10 -0600 Subject: [PATCH 05/10] Update contracts/src/CrossChainApplications/GETTING_STARTED.md Co-authored-by: Meaghan FitzGerald Signed-off-by: cam-schultz <78878559+cam-schultz@users.noreply.github.com> --- contracts/src/CrossChainApplications/GETTING_STARTED.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/contracts/src/CrossChainApplications/GETTING_STARTED.md b/contracts/src/CrossChainApplications/GETTING_STARTED.md index eb219c584..629bb293b 100644 --- a/contracts/src/CrossChainApplications/GETTING_STARTED.md +++ b/contracts/src/CrossChainApplications/GETTING_STARTED.md @@ -37,7 +37,7 @@ contract ExampleCrossChainMessenger { } ``` -### Step 3: Send and Receive +## Step 3: Send and Receive Now that `MyExampleCrossChainMessenger` has an instantiation of `ITeleporterMessenger`, the next step is to add in functionality of sending and receiving arbitrary string data between chains. From a788cc7f1ee89b98e88b34ac6d53e42f027335ae Mon Sep 17 00:00:00 2001 From: cam-schultz <78878559+cam-schultz@users.noreply.github.com> Date: Mon, 27 Nov 2023 11:32:15 -0600 Subject: [PATCH 06/10] Update contracts/src/CrossChainApplications/GETTING_STARTED.md Co-authored-by: Meaghan FitzGerald Signed-off-by: cam-schultz <78878559+cam-schultz@users.noreply.github.com> --- contracts/src/CrossChainApplications/GETTING_STARTED.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/contracts/src/CrossChainApplications/GETTING_STARTED.md b/contracts/src/CrossChainApplications/GETTING_STARTED.md index 629bb293b..96d76b44b 100644 --- a/contracts/src/CrossChainApplications/GETTING_STARTED.md +++ b/contracts/src/CrossChainApplications/GETTING_STARTED.md @@ -125,7 +125,7 @@ function receiveTeleporterMessage( The base of sending and receiving messages cross chain is complete. `MyExampleCrossChainMessenger` can now be expanded with functionality that saves the received messages, and allows users to query for the latest message received from a specified chain. -### Step 4: Storing the Message +## Step 4: Storing the Message Start by defining the `struct` for how to save our messages. It saves the string message itself and the address of the sender. From ee7f264d69a6508e94d47ef5f0006102a8f8644a Mon Sep 17 00:00:00 2001 From: cam-schultz <78878559+cam-schultz@users.noreply.github.com> Date: Mon, 27 Nov 2023 11:32:22 -0600 Subject: [PATCH 07/10] Update contracts/src/CrossChainApplications/GETTING_STARTED.md Co-authored-by: Meaghan FitzGerald Signed-off-by: cam-schultz <78878559+cam-schultz@users.noreply.github.com> --- contracts/src/CrossChainApplications/GETTING_STARTED.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/contracts/src/CrossChainApplications/GETTING_STARTED.md b/contracts/src/CrossChainApplications/GETTING_STARTED.md index 96d76b44b..9e81c05c7 100644 --- a/contracts/src/CrossChainApplications/GETTING_STARTED.md +++ b/contracts/src/CrossChainApplications/GETTING_STARTED.md @@ -172,7 +172,7 @@ function getCurrentMessage( There we have it, a simple cross chain messenger built on top of Teleporter! Full example [here](./ExampleMessenger/ExampleCrossChainMessenger.sol). -### Step 5: Testing +## Step 5: Testing For testing, `scripts/local/test.sh` sets up a local Avalanche network with three subnets deployed with Teleporter, and a relayer to deliver Teleporter messages. To add an integration test simply add a new test script under `integration-tests`. An integration test for `ExampleCrossChainMessenger` is already included (`scripts/local/integration_tests/example_messenger.sh`), which performs the following steps: From a8806ec92382f74832b5a51585983a36de7e2117 Mon Sep 17 00:00:00 2001 From: cam-schultz Date: Mon, 27 Nov 2023 20:22:59 +0000 Subject: [PATCH 08/10] cleanup --- .../CrossChainApplications/GETTING_STARTED.md | 43 +++++++++++++------ 1 file changed, 30 insertions(+), 13 deletions(-) diff --git a/contracts/src/CrossChainApplications/GETTING_STARTED.md b/contracts/src/CrossChainApplications/GETTING_STARTED.md index 9e81c05c7..7fa6a80b6 100644 --- a/contracts/src/CrossChainApplications/GETTING_STARTED.md +++ b/contracts/src/CrossChainApplications/GETTING_STARTED.md @@ -66,24 +66,41 @@ function receiveTeleporterMessage( ) external {} ``` -Now it's time to implement the methods, starting with `sendMessage`. First, import OpenZeppelin's `IERC20` contract, then in `sendMessage` check whether `feeAmount` is greater than zero. If it is, transfer and approve the amount of IERC20 asset at `feeTokenAddress` to the Teleporter Messenger saved as a state variable. Relayer fees are an optional way to incentive relayers to deliver a Teleporter message to its destination. They are not strictly necessary, and may be omitted if a relayer is willing to relay messages with no fee, such as with a self-hosted relayer. +Now it's time to implement the methods, starting with `sendMessage`. First, add the import for OpenZeppelin's `IERC20` contract to the top of your contract. ```solidity -// For non-zero fee amounts, transfer the fee into the control of this contract first, and then -// allow the Teleporter contract to spend it. -if (feeAmount > 0) { - IERC20 feeToken = IERC20(feeTokenAddress); - require( - feeToken.transferFrom(msg.sender, address(this), feeAmount), - "Failed to transfer fee amount" - ); - require( - feeToken.approve(address(teleporterMessenger), feeAmount), - "Failed to approve fee amount" - ); +import {IERC20} from "@openzeppelin/contracts/token/ERC20/IERC20.sol"; +``` + +Then in `sendMessage` check whether `feeAmount` is greater than zero. If it is, transfer and approve the amount of IERC20 asset at `feeTokenAddress` to the Teleporter Messenger saved as a state variable. + +```solidity +function sendMessage( + bytes32 destinationChainID, + address destinationAddress, + address feeTokenAddress, + uint256 feeAmount, + uint256 requiredGasLimit, + string calldata message +) external returns (uint256 messageID) { + // For non-zero fee amounts, first transfer the fee into the control of this contract, + // then allow the Teleporter contract to spend it. + if (feeAmount > 0) { + IERC20 feeToken = IERC20(feeTokenAddress); + require( + feeToken.transferFrom(msg.sender, address(this), feeAmount), + "Failed to transfer fee amount" + ); + require( + feeToken.approve(address(teleporterMessenger), feeAmount), + "Failed to approve fee amount" + ); + } } ``` +Note: Relayer fees are an optional way to incentive relayers to deliver a Teleporter message to its destination. They are not strictly necessary, and may be omitted if a relayer is willing to relay messages with no fee, such as with a self-hosted relayer. + Next, add the call to the `TeleporterMessenger` contract with the message data to be executed when delivered to the destination address. In `sendMessage`, form a `TeleporterMessageInput` and call `sendCrossChainMessage` on the `TeleporterMessenger` instance to start the cross chain messaging process. > `allowedRelayerAddresses` is empty in this example, meaning any relayer can try to deliver this cross chain message. Specific relayer addresses can be specified to ensure only those relayers can deliver the message. From dfb04c4fb5ab68c0cb6a0bd85765e3c4e709d211 Mon Sep 17 00:00:00 2001 From: cam-schultz Date: Thu, 30 Nov 2023 15:49:09 +0000 Subject: [PATCH 09/10] rephrase --- .../src/CrossChainApplications/ERC20Bridge/ERC20Bridge.sol | 2 +- .../ExampleMessenger/ExampleCrossChainMessenger.sol | 2 +- contracts/src/CrossChainApplications/GETTING_STARTED.md | 6 +++--- 3 files changed, 5 insertions(+), 5 deletions(-) diff --git a/contracts/src/CrossChainApplications/ERC20Bridge/ERC20Bridge.sol b/contracts/src/CrossChainApplications/ERC20Bridge/ERC20Bridge.sol index 0cba1ebad..9a2ed44d1 100644 --- a/contracts/src/CrossChainApplications/ERC20Bridge/ERC20Bridge.sol +++ b/contracts/src/CrossChainApplications/ERC20Bridge/ERC20Bridge.sol @@ -201,7 +201,7 @@ contract ERC20Bridge is ITeleporterMessenger teleporterMessenger = teleporterRegistry .getLatestTeleporter(); - // For non-zero fee amounts, transfer the fee into the control of this contract first, and then + // For non-zero fee amounts, first transfer the fee to this contract, and then // allow the Teleporter contract to spend it. uint256 adjustedFeeAmount = 0; if (messageFeeAmount > 0) { diff --git a/contracts/src/CrossChainApplications/ExampleMessenger/ExampleCrossChainMessenger.sol b/contracts/src/CrossChainApplications/ExampleMessenger/ExampleCrossChainMessenger.sol index b04e9c675..d459cdcb2 100644 --- a/contracts/src/CrossChainApplications/ExampleMessenger/ExampleCrossChainMessenger.sol +++ b/contracts/src/CrossChainApplications/ExampleMessenger/ExampleCrossChainMessenger.sol @@ -86,7 +86,7 @@ contract ExampleCrossChainMessenger is ) external nonReentrant returns (uint256) { ITeleporterMessenger teleporterMessenger = teleporterRegistry .getLatestTeleporter(); - // For non-zero fee amounts, transfer the fee into the control of this contract first, and then + // For non-zero fee amounts, first transfer the fee to this contract, and then // allow the Teleporter contract to spend it. uint256 adjustedFeeAmount = 0; if (feeAmount > 0) { diff --git a/contracts/src/CrossChainApplications/GETTING_STARTED.md b/contracts/src/CrossChainApplications/GETTING_STARTED.md index bbbb2ed6a..f04a0be9b 100644 --- a/contracts/src/CrossChainApplications/GETTING_STARTED.md +++ b/contracts/src/CrossChainApplications/GETTING_STARTED.md @@ -41,7 +41,7 @@ contract ExampleCrossChainMessenger { Now that `MyExampleCrossChainMessenger` has an instantiation of `ITeleporterMessenger`, the next step is to add in functionality of sending and receiving arbitrary string data between chains. -To start, create the function declarations for `sendMessage`, which will send string data cross-chain to the specified destination address' receiver. This function allows callers to specify the destination chain ID, destination address to send to, relayer fees, required gas limit for message execution on destination address, and the actual message data. +To start, create the function declarations for `sendMessage`, which will send string data cross-chain to the specified destination address' receiver. This function allows callers to specify the destination chain ID, destination address to send to, relayer fees, required gas limit for message execution at the destination address' `receiveTeleporterMessage` function, and the actual message data. ```solidity // Send a new message to another chain. @@ -83,8 +83,8 @@ function sendMessage( uint256 requiredGasLimit, string calldata message ) external returns (uint256 messageID) { - // For non-zero fee amounts, first transfer the fee into the control of this contract, - // then allow the Teleporter contract to spend it. + // For non-zero fee amounts, first transfer the fee to this contract, and then + // allow the Teleporter contract to spend it. if (feeAmount > 0) { IERC20 feeToken = IERC20(feeTokenAddress); require( From ecd38ea2325b59cd6256caff84cdec14d83111fc Mon Sep 17 00:00:00 2001 From: cam-schultz Date: Thu, 30 Nov 2023 15:53:34 +0000 Subject: [PATCH 10/10] update go bindings --- .../ERC20Bridge/ERC20Bridge/ERC20Bridge.go | 2 +- .../ExampleCrossChainMessenger/ExampleCrossChainMessenger.go | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/abi-bindings/go/CrossChainApplications/ERC20Bridge/ERC20Bridge/ERC20Bridge.go b/abi-bindings/go/CrossChainApplications/ERC20Bridge/ERC20Bridge/ERC20Bridge.go index 90e746726..0b540aa4b 100644 --- a/abi-bindings/go/CrossChainApplications/ERC20Bridge/ERC20Bridge/ERC20Bridge.go +++ b/abi-bindings/go/CrossChainApplications/ERC20Bridge/ERC20Bridge/ERC20Bridge.go @@ -32,7 +32,7 @@ var ( // ERC20BridgeMetaData contains all meta data concerning the ERC20Bridge contract. var ERC20BridgeMetaData = &bind.MetaData{ ABI: "[{\"inputs\":[{\"internalType\":\"address\",\"name\":\"teleporterRegistryAddress\",\"type\":\"address\"}],\"stateMutability\":\"nonpayable\",\"type\":\"constructor\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"tokenContractAddress\",\"type\":\"address\"},{\"indexed\":true,\"internalType\":\"bytes32\",\"name\":\"destinationBlockchainID\",\"type\":\"bytes32\"},{\"indexed\":true,\"internalType\":\"uint256\",\"name\":\"teleporterMessageID\",\"type\":\"uint256\"},{\"indexed\":false,\"internalType\":\"address\",\"name\":\"destinationBridgeAddress\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"address\",\"name\":\"recipient\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"uint256\",\"name\":\"amount\",\"type\":\"uint256\"}],\"name\":\"BridgeTokens\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"bytes32\",\"name\":\"nativeBlockchainID\",\"type\":\"bytes32\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"nativeBridgeAddress\",\"type\":\"address\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"nativeContractAddress\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"address\",\"name\":\"bridgeTokenAddress\",\"type\":\"address\"}],\"name\":\"CreateBridgeToken\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"uint256\",\"name\":\"oldMinTeleporterVersion\",\"type\":\"uint256\"},{\"indexed\":true,\"internalType\":\"uint256\",\"name\":\"newMinTeleporterVersion\",\"type\":\"uint256\"}],\"name\":\"MinTeleporterVersionUpdated\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"contractAddress\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"address\",\"name\":\"recipient\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"uint256\",\"name\":\"amount\",\"type\":\"uint256\"}],\"name\":\"MintBridgeTokens\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"previousOwner\",\"type\":\"address\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"newOwner\",\"type\":\"address\"}],\"name\":\"OwnershipTransferred\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"bytes32\",\"name\":\"destinationBlockchainID\",\"type\":\"bytes32\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"destinationBridgeAddress\",\"type\":\"address\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"nativeContractAddress\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"uint256\",\"name\":\"teleporterMessageID\",\"type\":\"uint256\"}],\"name\":\"SubmitCreateBridgeToken\",\"type\":\"event\"},{\"inputs\":[],\"name\":\"CREATE_BRIDGE_TOKENS_REQUIRED_GAS\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"MINT_BRIDGE_TOKENS_REQUIRED_GAS\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"TRANSFER_BRIDGE_TOKENS_REQUIRED_GAS\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"WARP_PRECOMPILE_ADDRESS\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"bytes32\",\"name\":\"destinationBlockchainID\",\"type\":\"bytes32\"},{\"internalType\":\"address\",\"name\":\"destinationBridgeAddress\",\"type\":\"address\"},{\"internalType\":\"address\",\"name\":\"tokenContractAddress\",\"type\":\"address\"},{\"internalType\":\"address\",\"name\":\"recipient\",\"type\":\"address\"},{\"internalType\":\"uint256\",\"name\":\"totalAmount\",\"type\":\"uint256\"},{\"internalType\":\"uint256\",\"name\":\"primaryFeeAmount\",\"type\":\"uint256\"},{\"internalType\":\"uint256\",\"name\":\"secondaryFeeAmount\",\"type\":\"uint256\"}],\"name\":\"bridgeTokens\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"bytes32\",\"name\":\"destinationBlockchainID\",\"type\":\"bytes32\"},{\"internalType\":\"address\",\"name\":\"destinationBridgeAddress\",\"type\":\"address\"},{\"internalType\":\"address\",\"name\":\"nativeTokenContract\",\"type\":\"address\"}],\"name\":\"bridgedBalances\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"balance\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"currentBlockchainID\",\"outputs\":[{\"internalType\":\"bytes32\",\"name\":\"\",\"type\":\"bytes32\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"nativeContractAddress\",\"type\":\"address\"},{\"internalType\":\"string\",\"name\":\"nativeName\",\"type\":\"string\"},{\"internalType\":\"string\",\"name\":\"nativeSymbol\",\"type\":\"string\"},{\"internalType\":\"uint8\",\"name\":\"nativeDecimals\",\"type\":\"uint8\"}],\"name\":\"encodeCreateBridgeTokenData\",\"outputs\":[{\"internalType\":\"bytes\",\"name\":\"\",\"type\":\"bytes\"}],\"stateMutability\":\"pure\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"nativeContractAddress\",\"type\":\"address\"},{\"internalType\":\"address\",\"name\":\"recipient\",\"type\":\"address\"},{\"internalType\":\"uint256\",\"name\":\"bridgeAmount\",\"type\":\"uint256\"}],\"name\":\"encodeMintBridgeTokensData\",\"outputs\":[{\"internalType\":\"bytes\",\"name\":\"\",\"type\":\"bytes\"}],\"stateMutability\":\"pure\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"bytes32\",\"name\":\"destinationBlockchainID\",\"type\":\"bytes32\"},{\"internalType\":\"address\",\"name\":\"destinationBridgeAddress\",\"type\":\"address\"},{\"internalType\":\"address\",\"name\":\"nativeContractAddress\",\"type\":\"address\"},{\"internalType\":\"address\",\"name\":\"recipient\",\"type\":\"address\"},{\"internalType\":\"uint256\",\"name\":\"amount\",\"type\":\"uint256\"},{\"internalType\":\"uint256\",\"name\":\"feeAmount\",\"type\":\"uint256\"}],\"name\":\"encodeTransferBridgeTokensData\",\"outputs\":[{\"internalType\":\"bytes\",\"name\":\"\",\"type\":\"bytes\"}],\"stateMutability\":\"pure\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"minTeleporterVersion\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"bytes32\",\"name\":\"nativeBlockchainID\",\"type\":\"bytes32\"},{\"internalType\":\"address\",\"name\":\"nativeBridgeAddress\",\"type\":\"address\"},{\"internalType\":\"address\",\"name\":\"nativeTokenAddress\",\"type\":\"address\"}],\"name\":\"nativeToWrappedTokens\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"bridgeTokenAddress\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"owner\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"bytes32\",\"name\":\"nativeBlockchainID\",\"type\":\"bytes32\"},{\"internalType\":\"address\",\"name\":\"nativeBridgeAddress\",\"type\":\"address\"},{\"internalType\":\"bytes\",\"name\":\"message\",\"type\":\"bytes\"}],\"name\":\"receiveTeleporterMessage\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"renounceOwnership\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"bytes32\",\"name\":\"destinationBlockchainID\",\"type\":\"bytes32\"},{\"internalType\":\"address\",\"name\":\"destinationBridgeAddress\",\"type\":\"address\"},{\"internalType\":\"contractERC20\",\"name\":\"nativeToken\",\"type\":\"address\"},{\"internalType\":\"address\",\"name\":\"messageFeeAsset\",\"type\":\"address\"},{\"internalType\":\"uint256\",\"name\":\"messageFeeAmount\",\"type\":\"uint256\"}],\"name\":\"submitCreateBridgeToken\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"bytes32\",\"name\":\"destinationBlockchainID\",\"type\":\"bytes32\"},{\"internalType\":\"address\",\"name\":\"destinationBridgeAddress\",\"type\":\"address\"},{\"internalType\":\"address\",\"name\":\"nativeTokenContract\",\"type\":\"address\"}],\"name\":\"submittedBridgeTokenCreations\",\"outputs\":[{\"internalType\":\"bool\",\"name\":\"tokenCreationSubmitted\",\"type\":\"bool\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"teleporterRegistry\",\"outputs\":[{\"internalType\":\"contractTeleporterRegistry\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"newOwner\",\"type\":\"address\"}],\"name\":\"transferOwnership\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"updateMinTeleporterVersion\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"bridgeToken\",\"type\":\"address\"}],\"name\":\"wrappedTokenContracts\",\"outputs\":[{\"internalType\":\"bool\",\"name\":\"bridgeTokenExists\",\"type\":\"bool\"}],\"stateMutability\":\"view\",\"type\":\"function\"}]", - Bin: "0x60c06040523480156200001157600080fd5b506040516200408c3803806200408c833981016040819052620000349162000212565b600160005580806001600160a01b038116620000bc5760405162461bcd60e51b815260206004820152603760248201527f54656c65706f727465725570677261646561626c653a207a65726f2074656c6560448201527f706f727465722072656769737472792061646472657373000000000000000000606482015260840160405180910390fd5b6001600160a01b03811660808190526040805163301fd1f560e21b8152905163c07f47d4916004808201926020929091908290030181865afa15801562000107573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906200012d919062000244565b600155506200013c33620001c0565b507302000000000000000000000000000000000000056001600160a01b0316634213cf786040518163ffffffff1660e01b8152600401602060405180830381865afa15801562000190573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190620001b6919062000244565b60a052506200025e565b600280546001600160a01b038381166001600160a01b0319831681179093556040519116919082907f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e090600090a35050565b6000602082840312156200022557600080fd5b81516001600160a01b03811681146200023d57600080fd5b9392505050565b6000602082840312156200025757600080fd5b5051919050565b60805160a051613dd0620002bc600039600081816101c7015281816109cb015281816117ba0152611e8001526000818161015c015281816104620152818161087d01528181610c8b015281816112d901526117fe0152613dd06000f3fe60806040523480156200001157600080fd5b5060043610620001515760003560e01c80638343f66111620000c7578063b9e55da11162000086578063b9e55da11462000329578063c60da612146200035d578063c63d22071462000374578063c868efaa146200038b578063e49cc55314620003a2578063f2fde38b14620003ac57600080fd5b80638343f66114620002885780638c56fcf014620002d05780638da5cb5b14620002e75780639bd9abc014620002f9578063b6109d9d146200031f57600080fd5b80636b47cd9a11620001145780636b47cd9a14620002405780636c7e40d1146200024b578063715018a6146200026457806374971856146200026e5780637a465fd9146200027d57600080fd5b80631a7f5bec1462000156578063367e9584146200019b5780634950d2d014620001c15780635f217bcc14620001f8578063654355681462000203575b600080fd5b6200017e7f000000000000000000000000000000000000000000000000000000000000000081565b6040516001600160a01b0390911681526020015b60405180910390f35b620001b2620001ac36600462002292565b620003c3565b6040516200019291906200237a565b620001e97f000000000000000000000000000000000000000000000000000000000000000081565b60405190815260200162000192565b620001e9621e848081565b6200017e620002143660046200238f565b60066020908152600093845260408085208252928452828420905282529020546001600160a01b031681565b620001e9620493e081565b620002626200025c366004620023d6565b62000422565b005b62000262620007f7565b6200017e6005600160991b0181565b620001e962030d4081565b620002bf620002993660046200238f565b600360209081526000938452604080852082529284528284209052825290205460ff1681565b604051901515815260200162000192565b620001b2620002e136600462002438565b6200080f565b6002546001600160a01b03166200017e565b620002bf6200030a3660046200247e565b60056020526000908152604090205460ff1681565b620002626200086a565b620001e96200033a3660046200238f565b600460209081526000938452604080852082529284528284209052825290205481565b620001b26200036e3660046200249e565b6200093f565b62000262620003853660046200250a565b620009bf565b620002626200039c3660046200257f565b62000c73565b620001e960015481565b62000262620003bd3660046200247e565b62000ee8565b6060600085858585604051602001620003e094939291906200260f565b60405160208183030381529060405290506000816040516020016200040792919062002674565b6040516020818303038152906040529150505b949350505050565b6200042c62000f64565b6001600160a01b0384166200045e5760405162461bcd60e51b81526004016200045590620026ae565b60405180910390fd5b60007f00000000000000000000000000000000000000000000000000000000000000006001600160a01b031663d820e64f6040518163ffffffff1660e01b8152600401602060405180830381865afa158015620004bf573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190620004e59190620026fa565b9050600082156200051457620004fc848462000fbf565b9050620005146001600160a01b038516838362001135565b60006200065286876001600160a01b03166306fdde036040518163ffffffff1660e01b8152600401600060405180830381865afa1580156200055a573d6000803e3d6000fd5b505050506040513d6000823e601f3d908101601f1916820160405262000584919081019062002766565b886001600160a01b03166395d89b416040518163ffffffff1660e01b8152600401600060405180830381865afa158015620005c3573d6000803e3d6000fd5b505050506040513d6000823e601f3d908101601f19168201604052620005ed919081019062002766565b896001600160a01b031663313ce5676040518163ffffffff1660e01b8152600401602060405180830381865afa1580156200062c573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190620001ac91906200279f565b90506000836001600160a01b031663624488506040518060c001604052808c81526020018b6001600160a01b0316815260200160405180604001604052808b6001600160a01b03168152602001888152508152602001621e84808152602001600067ffffffffffffffff811115620006ce57620006ce620021a0565b604051908082528060200260200182016040528015620006f8578160200160208202803683370190505b508152602001858152506040518263ffffffff1660e01b815260040162000720919062002805565b6020604051808303816000875af115801562000740573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019062000766919062002887565b60008a81526003602090815260408083206001600160a01b03808e16808652918452828520908d16808652935292819020805460ff1916600117905551929350918b907f110b902745a3d7d6b66732479f01de654a3bc6e501be7c8ba2c3a6f9868cb53990620007d99086815260200190565b60405180910390a450505050620007f06001600055565b5050505050565b6200080162001227565b6200080d600062001283565b565b606060008484846040516020016200082a93929190620028a1565b60405160208183030381529060405290506001816040516020016200085192919062002674565b6040516020818303038152906040529150509392505050565b6200087462001227565b600060015490507f00000000000000000000000000000000000000000000000000000000000000006001600160a01b031663c07f47d46040518163ffffffff1660e01b8152600401602060405180830381865afa158015620008da573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019062000900919062002887565b60018190558110156200093c5760015460405182907fa9a7ef57e41f05b4c15480842f5f0c27edfcbb553fed281f7c4068452cc1c02d90600090a35b50565b60408051602081018890526001600160a01b0387811682840152868116606080840191909152908616608083015260a0820185905260c08083018590528351808403909101815260e083019093529190620009a39060029083906101000162002674565b6040516020818303038152906040529150509695505050505050565b620009c962000f64565b7f0000000000000000000000000000000000000000000000000000000000000000870362000a0b5760405162461bcd60e51b81526004016200045590620028c5565b6001600160a01b03841662000a345760405162461bcd60e51b815260040162000455906200290d565b6001600160a01b03861662000a5d5760405162461bcd60e51b81526004016200045590620026ae565b6001600160a01b03851660009081526005602052604090205460ff161562000b485762000a8b818362002966565b831162000aea5760405162461bcd60e51b815260206004820152602660248201527f45524332304272696467653a20696e73756666696369656e7420746f74616c20604482015265185b5bdd5b9d60d21b606482015260840162000455565b62000b426040518060e00160405280898152602001886001600160a01b03168152602001876001600160a01b03168152602001866001600160a01b0316815260200185815260200184815260200183815250620012d5565b62000c5f565b60008781526003602090815260408083206001600160a01b03808b168552908352818420908916845290915290205460ff1662000bda5760405162461bcd60e51b815260206004820152602960248201527f45524332304272696467653a20696e76616c69642062726964676520746f6b656044820152686e206164647265737360b81b606482015260840162000455565b600062000be8868562000fbf565b905082811162000c4d5760405162461bcd60e51b815260206004820152602960248201527f45524332304272696467653a20696e73756666696369656e742061646a757374604482015268195908185b5bdd5b9d60ba1b606482015260840162000455565b62000c5d8888888885886200173c565b505b62000c6a6001600055565b50505050505050565b60015460405163260f846760e11b81523360048201527f00000000000000000000000000000000000000000000000000000000000000006001600160a01b031690634c1f08ce90602401602060405180830381865afa15801562000cdb573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019062000d01919062002887565b101562000d6a5760405162461bcd60e51b815260206004820152603060248201527f54656c65706f727465725570677261646561626c653a20696e76616c6964207460448201526f32b632b837b93a32b91039b2b73232b960811b606482015260840162000455565b60008062000d7b838501856200297c565b9092509050600082600281111562000d975762000d976200265e565b0362000ddb576000806000808480602001905181019062000db99190620029ea565b935093509350935062000dd18a8a8686868662001a73565b5050505062000ee0565b600182600281111562000df25762000df26200265e565b0362000e315760008060008380602001905181019062000e13919062002a74565b92509250925062000e28898985858562001be2565b50505062000ee0565b600282600281111562000e485762000e486200265e565b0362000e97576000806000806000808680602001905181019062000e6d919062002abc565b95509550955095509550955062000e8b8c8c88888888888862001d5c565b50505050505062000ee0565b60405162461bcd60e51b815260206004820152601b60248201527f45524332304272696467653a20696e76616c696420616374696f6e0000000000604482015260640162000455565b505050505050565b62000ef262001227565b6001600160a01b03811662000f595760405162461bcd60e51b815260206004820152602660248201527f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160448201526564647265737360d01b606482015260840162000455565b6200093c8162001283565b60026000540362000fb85760405162461bcd60e51b815260206004820152601f60248201527f5265656e7472616e637947756172643a207265656e7472616e742063616c6c00604482015260640162000455565b6002600055565b6040516370a0823160e01b815230600482015260009081906001600160a01b038516906370a0823190602401602060405180830381865afa15801562001009573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906200102f919062002887565b9050620010486001600160a01b03851633308662001f15565b6040516370a0823160e01b81523060048201526000906001600160a01b038616906370a0823190602401602060405180830381865afa15801562001090573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190620010b6919062002887565b90508181116200111e5760405162461bcd60e51b815260206004820152602c60248201527f5361666545524332305472616e7366657246726f6d3a2062616c616e6365206e60448201526b1bdd081a5b98dc99585cd95960a21b606482015260840162000455565b6200112a828262002b2c565b925050505b92915050565b604051636eb1769f60e11b81523060048201526001600160a01b038381166024830152600091839186169063dd62ed3e90604401602060405180830381865afa15801562001187573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190620011ad919062002887565b620011b9919062002966565b6040516001600160a01b0385166024820152604481018290529091506200122190859063095ea7b360e01b906064015b60408051601f198184030181529190526020810180516001600160e01b03166001600160e01b03199093169290921790915262001f39565b50505050565b6002546001600160a01b031633146200080d5760405162461bcd60e51b815260206004820181905260248201527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e6572604482015260640162000455565b600280546001600160a01b038381166001600160a01b0319831681179093556040519116919082907f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e090600090a35050565b60007f00000000000000000000000000000000000000000000000000000000000000006001600160a01b031663d820e64f6040518163ffffffff1660e01b8152600401602060405180830381865afa15801562001336573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906200135c9190620026fa565b90506000808360a0015111156200139f576200138183604001518460a0015162000fbf565b60408401519091506200139f906001600160a01b0316838362001135565b60008360a001518460800151620013b7919062002b2c565b604085810151905163079cc67960e41b815233600482015260248101839052919250906001600160a01b038216906379cc679090604401600060405180830381600087803b1580156200140957600080fd5b505af11580156200141e573d6000803e3d6000fd5b505050506000816001600160a01b031663f72539686040518163ffffffff1660e01b8152600401602060405180830381865afa15801562001463573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019062001489919062002887565b90506000826001600160a01b0316631a0b79bf6040518163ffffffff1660e01b8152600401602060405180830381865afa158015620014cc573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190620014f29190620026fa565b9050818760000151036200153857806001600160a01b031687602001516001600160a01b031614620015385760405162461bcd60e51b8152600401620004559062002b42565b6000620015be88600001518960200151866001600160a01b03166374d32ad46040518163ffffffff1660e01b8152600401602060405180830381865afa15801562001587573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190620015ad9190620026fa565b8b60600151898d60c001516200093f565b90506000876001600160a01b031663624488506040518060c00160405280878152602001866001600160a01b0316815260200160405180604001604052808e604001516001600160a01b031681526020018c8152508152602001620493e08152602001600067ffffffffffffffff8111156200163e576200163e620021a0565b60405190808252806020026020018201604052801562001668578160200160208202803683370190505b508152602001858152506040518263ffffffff1660e01b815260040162001690919062002805565b6020604051808303816000875af1158015620016b0573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190620016d6919062002887565b90508089600001518a604001516001600160a01b03167f97935c4470efae40c8440c3abfe968a5512232dd375cc974e712f487c2b99c318c602001518d606001518b6040516200172993929190620028a1565b60405180910390a4505050505050505050565b6001600160a01b03841660009081526005602052604090205460ff1615620017b85760405162461bcd60e51b815260206004820152602860248201527f45524332304272696467653a2063616e6e6f742062726964676520777261707060448201526732b2103a37b5b2b760c11b606482015260840162000455565b7f00000000000000000000000000000000000000000000000000000000000000008603620017fa5760405162461bcd60e51b81526004016200045590620028c5565b60007f00000000000000000000000000000000000000000000000000000000000000006001600160a01b031663d820e64f6040518163ffffffff1660e01b8152600401602060405180830381865afa1580156200185b573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190620018819190620026fa565b90508115620018a057620018a06001600160a01b038616828462001135565b6000620018ae838562002b2c565b60008981526004602090815260408083206001600160a01b03808d168552908352818420908b168452909152812080549293508392909190620018f390849062002966565b9091555060009050620019088787846200080f565b90506000836001600160a01b031663624488506040518060c001604052808d81526020018c6001600160a01b0316815260200160405180604001604052808d6001600160a01b031681526020018a815250815260200162030d408152602001600067ffffffffffffffff811115620019845762001984620021a0565b604051908082528060200260200182016040528015620019ae578160200160208202803683370190505b508152602001858152506040518263ffffffff1660e01b8152600401620019d6919062002805565b6020604051808303816000875af1158015620019f6573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019062001a1c919062002887565b9050808a896001600160a01b03167f97935c4470efae40c8440c3abfe968a5512232dd375cc974e712f487c2b99c318c8b8860405162001a5f93929190620028a1565b60405180910390a450505050505050505050565b60008681526006602090815260408083206001600160a01b038981168552908352818420888216855290925290912054161562001b045760405162461bcd60e51b815260206004820152602860248201527f45524332304272696467653a2062726964676520746f6b656e20616c72656164604482015267792065786973747360c01b606482015260840162000455565b600086868686868660405162001b1a906200217c565b62001b2b9695949392919062002b91565b604051809103906000f08015801562001b48573d6000803e3d6000fd5b506001600160a01b038181166000818152600560209081526040808320805460ff191660011790558c8352600682528083208c8616808552908352818420958c168085529583529281902080546001600160a01b031916851790555192835293945091928a917fe1c61a845f79534e11924517ddbedc668d0c20e467eafb4d3bd2858e2815f3b5910160405180910390a450505050505050565b62001bec62000f64565b6001600160a01b03821662001c155760405162461bcd60e51b815260040162000455906200290d565b60008581526006602090815260408083206001600160a01b038089168552908352818420878216855290925290912054168062001ca65760405162461bcd60e51b815260206004820152602860248201527f45524332304272696467653a2062726964676520746f6b656e20646f6573206e6044820152671bdd08195e1a5cdd60c21b606482015260840162000455565b6040516340c10f1960e01b81526001600160a01b038481166004830152602482018490528216906340c10f1990604401600060405180830381600087803b15801562001cf157600080fd5b505af115801562001d06573d6000803e3d6000fd5b5050604080516001600160a01b03878116825260208201879052851693507fc0767f158f0d5394b598489a51ed607cd55a8be2dcef113ba1626efcf4c6395492500160405180910390a250620007f06001600055565b62001d6662000f64565b6001600160a01b03831662001d8f5760405162461bcd60e51b815260040162000455906200290d565b6001600160a01b03851662001db85760405162461bcd60e51b81526004016200045590620026ae565b60008881526004602090815260408083206001600160a01b03808c16855290835281842090881684529091529020548281101562001e435760405162461bcd60e51b815260206004820152602160248201527f45524332304272696467653a20696e73756666696369656e742062616c616e636044820152606560f81b606482015260840162000455565b62001e4f838262002b2c565b60008a81526004602090815260408083206001600160a01b03808e168552908352818420908a1684529091529020557f0000000000000000000000000000000000000000000000000000000000000000870362001eee576001600160a01b038616301462001ed15760405162461bcd60e51b8152600401620004559062002b42565b62001ee76001600160a01b038616858562002017565b5062001f00565b62001efe8787878787876200173c565b505b62001f0b6001600055565b5050505050505050565b62001221846323b872dd60e01b858585604051602401620011e993929190620028a1565b600062001f90826040518060400160405280602081526020017f5361666545524332303a206c6f772d6c6576656c2063616c6c206661696c6564815250856001600160a01b0316620020499092919063ffffffff16565b80519091501562002012578080602001905181019062001fb1919062002bf0565b620020125760405162461bcd60e51b815260206004820152602a60248201527f5361666545524332303a204552433230206f7065726174696f6e20646964206e6044820152691bdd081cdd58d8d9595960b21b606482015260840162000455565b505050565b6040516001600160a01b0383166024820152604481018290526200201290849063a9059cbb60e01b90606401620011e9565b60606200041a848460008585600080866001600160a01b0316858760405162002073919062002c14565b60006040518083038185875af1925050503d8060008114620020b2576040519150601f19603f3d011682016040523d82523d6000602084013e620020b7565b606091505b5091509150620020ca87838387620020d5565b979650505050505050565b606083156200214957825160000362002141576001600160a01b0385163b620021415760405162461bcd60e51b815260206004820152601d60248201527f416464726573733a2063616c6c20746f206e6f6e2d636f6e7472616374000000604482015260640162000455565b50816200041a565b6200041a8383815115620021605781518083602001fd5b8060405162461bcd60e51b81526004016200045591906200237a565b6111688062002c3383390190565b6001600160a01b03811681146200093c57600080fd5b634e487b7160e01b600052604160045260246000fd5b604051601f8201601f1916810167ffffffffffffffff81118282101715620021e257620021e2620021a0565b604052919050565b600067ffffffffffffffff821115620022075762002207620021a0565b50601f01601f191660200190565b60006200222c6200222684620021ea565b620021b6565b90508281528383830111156200224157600080fd5b828260208301376000602084830101529392505050565b600082601f8301126200226a57600080fd5b6200227b8383356020850162002215565b9392505050565b60ff811681146200093c57600080fd5b60008060008060808587031215620022a957600080fd5b8435620022b6816200218a565b9350602085013567ffffffffffffffff80821115620022d457600080fd5b620022e28883890162002258565b94506040870135915080821115620022f957600080fd5b50620023088782880162002258565b92505060608501356200231b8162002282565b939692955090935050565b60005b838110156200234357818101518382015260200162002329565b50506000910152565b600081518084526200236681602086016020860162002326565b601f01601f19169290920160200192915050565b6020815260006200227b60208301846200234c565b600080600060608486031215620023a557600080fd5b833592506020840135620023b9816200218a565b91506040840135620023cb816200218a565b809150509250925092565b600080600080600060a08688031215620023ef57600080fd5b85359450602086013562002403816200218a565b9350604086013562002415816200218a565b9250606086013562002427816200218a565b949793965091946080013592915050565b6000806000606084860312156200244e57600080fd5b83356200245b816200218a565b925060208401356200246d816200218a565b929592945050506040919091013590565b6000602082840312156200249157600080fd5b81356200227b816200218a565b60008060008060008060c08789031215620024b857600080fd5b863595506020870135620024cc816200218a565b94506040870135620024de816200218a565b93506060870135620024f0816200218a565b9598949750929560808101359460a0909101359350915050565b600080600080600080600060e0888a0312156200252657600080fd5b8735965060208801356200253a816200218a565b955060408801356200254c816200218a565b945060608801356200255e816200218a565b9699959850939660808101359560a0820135955060c0909101359350915050565b600080600080606085870312156200259657600080fd5b843593506020850135620025aa816200218a565b9250604085013567ffffffffffffffff80821115620025c857600080fd5b818701915087601f830112620025dd57600080fd5b813581811115620025ed57600080fd5b8860208285010111156200260057600080fd5b95989497505060200194505050565b6001600160a01b038516815260806020820181905260009062002635908301866200234c565b82810360408401526200264981866200234c565b91505060ff8316606083015295945050505050565b634e487b7160e01b600052602160045260246000fd5b6000600384106200269557634e487b7160e01b600052602160045260246000fd5b838252604060208301526200041a60408301846200234c565b6020808252602c908201527f45524332304272696467653a207a65726f2064657374696e6174696f6e20627260408201526b69646765206164647265737360a01b606082015260800190565b6000602082840312156200270d57600080fd5b81516200227b816200218a565b600082601f8301126200272c57600080fd5b81516200273d6200222682620021ea565b8181528460208386010111156200275357600080fd5b6200041a82602083016020870162002326565b6000602082840312156200277957600080fd5b815167ffffffffffffffff8111156200279157600080fd5b6200041a848285016200271a565b600060208284031215620027b257600080fd5b81516200227b8162002282565b600081518084526020808501945080840160005b83811015620027fa5781516001600160a01b031687529582019590820190600101620027d3565b509495945050505050565b60208152815160208201526000602083015160018060a01b03808216604085015260408501519150808251166060850152506020810151608084015250606083015160a0830152608083015160e060c084015262002868610100840182620027bf565b905060a0840151601f198483030160e08501526200112a82826200234c565b6000602082840312156200289a57600080fd5b5051919050565b6001600160a01b039384168152919092166020820152604081019190915260600190565b60208082526028908201527f45524332304272696467653a2063616e6e6f742062726964676520746f20736160408201526736b29031b430b4b760c11b606082015260800190565b60208082526023908201527f45524332304272696467653a207a65726f20726563697069656e74206164647260408201526265737360e81b606082015260800190565b634e487b7160e01b600052601160045260246000fd5b808201808211156200112f576200112f62002950565b600080604083850312156200299057600080fd5b823560038110620029a057600080fd5b9150602083013567ffffffffffffffff811115620029bd57600080fd5b8301601f81018513620029cf57600080fd5b620029e08582356020840162002215565b9150509250929050565b6000806000806080858703121562002a0157600080fd5b845162002a0e816200218a565b602086015190945067ffffffffffffffff8082111562002a2d57600080fd5b62002a3b888389016200271a565b9450604087015191508082111562002a5257600080fd5b5062002a61878288016200271a565b92505060608501516200231b8162002282565b60008060006060848603121562002a8a57600080fd5b835162002a97816200218a565b602085015190935062002aaa816200218a565b80925050604084015190509250925092565b60008060008060008060c0878903121562002ad657600080fd5b86519550602087015162002aea816200218a565b604088015190955062002afd816200218a565b606088015190945062002b10816200218a565b809350506080870151915060a087015190509295509295509295565b818103818111156200112f576200112f62002950565b6020808252602f908201527f45524332304272696467653a20696e76616c69642064657374696e6174696f6e60408201526e20627269646765206164647265737360881b606082015260800190565b8681526001600160a01b0386811660208301528516604082015260c06060820181905260009062002bc5908301866200234c565b828103608084015262002bd981866200234c565b91505060ff831660a0830152979650505050505050565b60006020828403121562002c0357600080fd5b815180151581146200227b57600080fd5b6000825162002c2881846020870162002326565b919091019291505056fe6101206040523480156200001257600080fd5b506040516200116838038062001168833981016040819052620000359162000292565b82826003620000458382620003d5565b506004620000548282620003d5565b50879150620000b690505760405162461bcd60e51b815260206004820152602160248201527f427269646765546f6b656e3a207a65726f20736f7572636520636861696e20696044820152601960fa1b60648201526084015b60405180910390fd5b6001600160a01b0385166200011e5760405162461bcd60e51b815260206004820152602760248201527f427269646765546f6b656e3a207a65726f20736f7572636520627269646765206044820152666164647265737360c81b6064820152608401620000ad565b6001600160a01b038416620001855760405162461bcd60e51b815260206004820152602660248201527f427269646765546f6b656e3a207a65726f20736f75726365206173736574206160448201526564647265737360d01b6064820152608401620000ad565b3360805260a09590955250506001600160a01b0391821660c0521660e05260ff1661010052620004a1565b80516001600160a01b0381168114620001c857600080fd5b919050565b634e487b7160e01b600052604160045260246000fd5b600082601f830112620001f557600080fd5b81516001600160401b0380821115620002125762000212620001cd565b604051601f8301601f19908116603f011681019082821181831017156200023d576200023d620001cd565b816040528381526020925086838588010111156200025a57600080fd5b600091505b838210156200027e57858201830151818301840152908201906200025f565b600093810190920192909252949350505050565b60008060008060008060c08789031215620002ac57600080fd5b86519550620002be60208801620001b0565b9450620002ce60408801620001b0565b60608801519094506001600160401b0380821115620002ec57600080fd5b620002fa8a838b01620001e3565b945060808901519150808211156200031157600080fd5b506200032089828a01620001e3565b92505060a087015160ff811681146200033857600080fd5b809150509295509295509295565b600181811c908216806200035b57607f821691505b6020821081036200037c57634e487b7160e01b600052602260045260246000fd5b50919050565b601f821115620003d057600081815260208120601f850160051c81016020861015620003ab5750805b601f850160051c820191505b81811015620003cc57828155600101620003b7565b5050505b505050565b81516001600160401b03811115620003f157620003f1620001cd565b620004098162000402845462000346565b8462000382565b602080601f831160018114620004415760008415620004285750858301515b600019600386901b1c1916600185901b178555620003cc565b600085815260208120601f198616915b82811015620004725788860151825594840194600190910190840162000451565b5085821015620004915787850151600019600388901b60f8161c191681555b5050505050600190811b01905550565b60805160a05160c05160e05161010051610c7b620004ed60003960006101c70152600061025a01526000610173015260006102fc0152600081816102c2015261041b0152610c7b6000f3fe608060405234801561001057600080fd5b50600436106101165760003560e01c806370a08231116100a2578063a457c2d711610071578063a457c2d714610297578063a9059cbb146102aa578063cd596583146102bd578063dd62ed3e146102e4578063f7253968146102f757600080fd5b806370a082311461022c57806374d32ad41461025557806379cc67901461027c57806395d89b411461028f57600080fd5b806323b872dd116100e957806323b872dd146101ad578063313ce567146101c057806339509351146101f157806340c10f191461020457806342966c681461021957600080fd5b806306fdde031461011b578063095ea7b31461013957806318160ddd1461015c5780631a0b79bf1461016e575b600080fd5b61012361031e565b6040516101309190610aac565b60405180910390f35b61014c610147366004610b16565b6103b0565b6040519015158152602001610130565b6002545b604051908152602001610130565b6101957f000000000000000000000000000000000000000000000000000000000000000081565b6040516001600160a01b039091168152602001610130565b61014c6101bb366004610b40565b6103ca565b60405160ff7f0000000000000000000000000000000000000000000000000000000000000000168152602001610130565b61014c6101ff366004610b16565b6103ee565b610217610212366004610b16565b610410565b005b610217610227366004610b7c565b61049b565b61016061023a366004610b95565b6001600160a01b031660009081526020819052604090205490565b6101957f000000000000000000000000000000000000000000000000000000000000000081565b61021761028a366004610b16565b6104a8565b6101236104bd565b61014c6102a5366004610b16565b6104cc565b61014c6102b8366004610b16565b610547565b6101957f000000000000000000000000000000000000000000000000000000000000000081565b6101606102f2366004610bb7565b610555565b6101607f000000000000000000000000000000000000000000000000000000000000000081565b60606003805461032d90610bea565b80601f016020809104026020016040519081016040528092919081815260200182805461035990610bea565b80156103a65780601f1061037b576101008083540402835291602001916103a6565b820191906000526020600020905b81548152906001019060200180831161038957829003601f168201915b5050505050905090565b6000336103be818585610580565b60019150505b92915050565b6000336103d88582856106a5565b6103e385858561071f565b506001949350505050565b6000336103be8185856104018383610555565b61040b9190610c24565b610580565b336001600160a01b037f0000000000000000000000000000000000000000000000000000000000000000161461048d5760405162461bcd60e51b815260206004820152601960248201527f427269646765546f6b656e3a20756e617574686f72697a65640000000000000060448201526064015b60405180910390fd5b61049782826108c3565b5050565b6104a53382610982565b50565b6104b38233836106a5565b6104978282610982565b60606004805461032d90610bea565b600033816104da8286610555565b90508381101561053a5760405162461bcd60e51b815260206004820152602560248201527f45524332303a2064656372656173656420616c6c6f77616e63652062656c6f77604482015264207a65726f60d81b6064820152608401610484565b6103e38286868403610580565b6000336103be81858561071f565b6001600160a01b03918216600090815260016020908152604080832093909416825291909152205490565b6001600160a01b0383166105e25760405162461bcd60e51b8152602060048201526024808201527f45524332303a20617070726f76652066726f6d20746865207a65726f206164646044820152637265737360e01b6064820152608401610484565b6001600160a01b0382166106435760405162461bcd60e51b815260206004820152602260248201527f45524332303a20617070726f766520746f20746865207a65726f206164647265604482015261737360f01b6064820152608401610484565b6001600160a01b0383811660008181526001602090815260408083209487168084529482529182902085905590518481527f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b92591015b60405180910390a3505050565b60006106b18484610555565b90506000198114610719578181101561070c5760405162461bcd60e51b815260206004820152601d60248201527f45524332303a20696e73756666696369656e7420616c6c6f77616e63650000006044820152606401610484565b6107198484848403610580565b50505050565b6001600160a01b0383166107835760405162461bcd60e51b815260206004820152602560248201527f45524332303a207472616e736665722066726f6d20746865207a65726f206164604482015264647265737360d81b6064820152608401610484565b6001600160a01b0382166107e55760405162461bcd60e51b815260206004820152602360248201527f45524332303a207472616e7366657220746f20746865207a65726f206164647260448201526265737360e81b6064820152608401610484565b6001600160a01b0383166000908152602081905260409020548181101561085d5760405162461bcd60e51b815260206004820152602660248201527f45524332303a207472616e7366657220616d6f756e7420657863656564732062604482015265616c616e636560d01b6064820152608401610484565b6001600160a01b03848116600081815260208181526040808320878703905593871680835291849020805487019055925185815290927fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef910160405180910390a3610719565b6001600160a01b0382166109195760405162461bcd60e51b815260206004820152601f60248201527f45524332303a206d696e7420746f20746865207a65726f2061646472657373006044820152606401610484565b806002600082825461092b9190610c24565b90915550506001600160a01b038216600081815260208181526040808320805486019055518481527fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef910160405180910390a35050565b6001600160a01b0382166109e25760405162461bcd60e51b815260206004820152602160248201527f45524332303a206275726e2066726f6d20746865207a65726f206164647265736044820152607360f81b6064820152608401610484565b6001600160a01b03821660009081526020819052604090205481811015610a565760405162461bcd60e51b815260206004820152602260248201527f45524332303a206275726e20616d6f756e7420657863656564732062616c616e604482015261636560f01b6064820152608401610484565b6001600160a01b0383166000818152602081815260408083208686039055600280548790039055518581529192917fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef9101610698565b600060208083528351808285015260005b81811015610ad957858101830151858201604001528201610abd565b506000604082860101526040601f19601f8301168501019250505092915050565b80356001600160a01b0381168114610b1157600080fd5b919050565b60008060408385031215610b2957600080fd5b610b3283610afa565b946020939093013593505050565b600080600060608486031215610b5557600080fd5b610b5e84610afa565b9250610b6c60208501610afa565b9150604084013590509250925092565b600060208284031215610b8e57600080fd5b5035919050565b600060208284031215610ba757600080fd5b610bb082610afa565b9392505050565b60008060408385031215610bca57600080fd5b610bd383610afa565b9150610be160208401610afa565b90509250929050565b600181811c90821680610bfe57607f821691505b602082108103610c1e57634e487b7160e01b600052602260045260246000fd5b50919050565b808201808211156103c457634e487b7160e01b600052601160045260246000fdfea26469706673582212208a8e82a679ec260481bb5d10cf7933d8213beeeb9291c42d2ad6b12aa8eb16e264736f6c63430008120033a2646970667358221220121dc09bb98b9c7a249ffe9338950943f8e04992d339304462397f25c5f7a2ed64736f6c63430008120033", + Bin: "0x60c06040523480156200001157600080fd5b506040516200408c3803806200408c833981016040819052620000349162000212565b600160005580806001600160a01b038116620000bc5760405162461bcd60e51b815260206004820152603760248201527f54656c65706f727465725570677261646561626c653a207a65726f2074656c6560448201527f706f727465722072656769737472792061646472657373000000000000000000606482015260840160405180910390fd5b6001600160a01b03811660808190526040805163301fd1f560e21b8152905163c07f47d4916004808201926020929091908290030181865afa15801562000107573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906200012d919062000244565b600155506200013c33620001c0565b507302000000000000000000000000000000000000056001600160a01b0316634213cf786040518163ffffffff1660e01b8152600401602060405180830381865afa15801562000190573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190620001b6919062000244565b60a052506200025e565b600280546001600160a01b038381166001600160a01b0319831681179093556040519116919082907f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e090600090a35050565b6000602082840312156200022557600080fd5b81516001600160a01b03811681146200023d57600080fd5b9392505050565b6000602082840312156200025757600080fd5b5051919050565b60805160a051613dd0620002bc600039600081816101c7015281816109cb015281816117ba0152611e8001526000818161015c015281816104620152818161087d01528181610c8b015281816112d901526117fe0152613dd06000f3fe60806040523480156200001157600080fd5b5060043610620001515760003560e01c80638343f66111620000c7578063b9e55da11162000086578063b9e55da11462000329578063c60da612146200035d578063c63d22071462000374578063c868efaa146200038b578063e49cc55314620003a2578063f2fde38b14620003ac57600080fd5b80638343f66114620002885780638c56fcf014620002d05780638da5cb5b14620002e75780639bd9abc014620002f9578063b6109d9d146200031f57600080fd5b80636b47cd9a11620001145780636b47cd9a14620002405780636c7e40d1146200024b578063715018a6146200026457806374971856146200026e5780637a465fd9146200027d57600080fd5b80631a7f5bec1462000156578063367e9584146200019b5780634950d2d014620001c15780635f217bcc14620001f8578063654355681462000203575b600080fd5b6200017e7f000000000000000000000000000000000000000000000000000000000000000081565b6040516001600160a01b0390911681526020015b60405180910390f35b620001b2620001ac36600462002292565b620003c3565b6040516200019291906200237a565b620001e97f000000000000000000000000000000000000000000000000000000000000000081565b60405190815260200162000192565b620001e9621e848081565b6200017e620002143660046200238f565b60066020908152600093845260408085208252928452828420905282529020546001600160a01b031681565b620001e9620493e081565b620002626200025c366004620023d6565b62000422565b005b62000262620007f7565b6200017e6005600160991b0181565b620001e962030d4081565b620002bf620002993660046200238f565b600360209081526000938452604080852082529284528284209052825290205460ff1681565b604051901515815260200162000192565b620001b2620002e136600462002438565b6200080f565b6002546001600160a01b03166200017e565b620002bf6200030a3660046200247e565b60056020526000908152604090205460ff1681565b620002626200086a565b620001e96200033a3660046200238f565b600460209081526000938452604080852082529284528284209052825290205481565b620001b26200036e3660046200249e565b6200093f565b62000262620003853660046200250a565b620009bf565b620002626200039c3660046200257f565b62000c73565b620001e960015481565b62000262620003bd3660046200247e565b62000ee8565b6060600085858585604051602001620003e094939291906200260f565b60405160208183030381529060405290506000816040516020016200040792919062002674565b6040516020818303038152906040529150505b949350505050565b6200042c62000f64565b6001600160a01b0384166200045e5760405162461bcd60e51b81526004016200045590620026ae565b60405180910390fd5b60007f00000000000000000000000000000000000000000000000000000000000000006001600160a01b031663d820e64f6040518163ffffffff1660e01b8152600401602060405180830381865afa158015620004bf573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190620004e59190620026fa565b9050600082156200051457620004fc848462000fbf565b9050620005146001600160a01b038516838362001135565b60006200065286876001600160a01b03166306fdde036040518163ffffffff1660e01b8152600401600060405180830381865afa1580156200055a573d6000803e3d6000fd5b505050506040513d6000823e601f3d908101601f1916820160405262000584919081019062002766565b886001600160a01b03166395d89b416040518163ffffffff1660e01b8152600401600060405180830381865afa158015620005c3573d6000803e3d6000fd5b505050506040513d6000823e601f3d908101601f19168201604052620005ed919081019062002766565b896001600160a01b031663313ce5676040518163ffffffff1660e01b8152600401602060405180830381865afa1580156200062c573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190620001ac91906200279f565b90506000836001600160a01b031663624488506040518060c001604052808c81526020018b6001600160a01b0316815260200160405180604001604052808b6001600160a01b03168152602001888152508152602001621e84808152602001600067ffffffffffffffff811115620006ce57620006ce620021a0565b604051908082528060200260200182016040528015620006f8578160200160208202803683370190505b508152602001858152506040518263ffffffff1660e01b815260040162000720919062002805565b6020604051808303816000875af115801562000740573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019062000766919062002887565b60008a81526003602090815260408083206001600160a01b03808e16808652918452828520908d16808652935292819020805460ff1916600117905551929350918b907f110b902745a3d7d6b66732479f01de654a3bc6e501be7c8ba2c3a6f9868cb53990620007d99086815260200190565b60405180910390a450505050620007f06001600055565b5050505050565b6200080162001227565b6200080d600062001283565b565b606060008484846040516020016200082a93929190620028a1565b60405160208183030381529060405290506001816040516020016200085192919062002674565b6040516020818303038152906040529150509392505050565b6200087462001227565b600060015490507f00000000000000000000000000000000000000000000000000000000000000006001600160a01b031663c07f47d46040518163ffffffff1660e01b8152600401602060405180830381865afa158015620008da573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019062000900919062002887565b60018190558110156200093c5760015460405182907fa9a7ef57e41f05b4c15480842f5f0c27edfcbb553fed281f7c4068452cc1c02d90600090a35b50565b60408051602081018890526001600160a01b0387811682840152868116606080840191909152908616608083015260a0820185905260c08083018590528351808403909101815260e083019093529190620009a39060029083906101000162002674565b6040516020818303038152906040529150509695505050505050565b620009c962000f64565b7f0000000000000000000000000000000000000000000000000000000000000000870362000a0b5760405162461bcd60e51b81526004016200045590620028c5565b6001600160a01b03841662000a345760405162461bcd60e51b815260040162000455906200290d565b6001600160a01b03861662000a5d5760405162461bcd60e51b81526004016200045590620026ae565b6001600160a01b03851660009081526005602052604090205460ff161562000b485762000a8b818362002966565b831162000aea5760405162461bcd60e51b815260206004820152602660248201527f45524332304272696467653a20696e73756666696369656e7420746f74616c20604482015265185b5bdd5b9d60d21b606482015260840162000455565b62000b426040518060e00160405280898152602001886001600160a01b03168152602001876001600160a01b03168152602001866001600160a01b0316815260200185815260200184815260200183815250620012d5565b62000c5f565b60008781526003602090815260408083206001600160a01b03808b168552908352818420908916845290915290205460ff1662000bda5760405162461bcd60e51b815260206004820152602960248201527f45524332304272696467653a20696e76616c69642062726964676520746f6b656044820152686e206164647265737360b81b606482015260840162000455565b600062000be8868562000fbf565b905082811162000c4d5760405162461bcd60e51b815260206004820152602960248201527f45524332304272696467653a20696e73756666696369656e742061646a757374604482015268195908185b5bdd5b9d60ba1b606482015260840162000455565b62000c5d8888888885886200173c565b505b62000c6a6001600055565b50505050505050565b60015460405163260f846760e11b81523360048201527f00000000000000000000000000000000000000000000000000000000000000006001600160a01b031690634c1f08ce90602401602060405180830381865afa15801562000cdb573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019062000d01919062002887565b101562000d6a5760405162461bcd60e51b815260206004820152603060248201527f54656c65706f727465725570677261646561626c653a20696e76616c6964207460448201526f32b632b837b93a32b91039b2b73232b960811b606482015260840162000455565b60008062000d7b838501856200297c565b9092509050600082600281111562000d975762000d976200265e565b0362000ddb576000806000808480602001905181019062000db99190620029ea565b935093509350935062000dd18a8a8686868662001a73565b5050505062000ee0565b600182600281111562000df25762000df26200265e565b0362000e315760008060008380602001905181019062000e13919062002a74565b92509250925062000e28898985858562001be2565b50505062000ee0565b600282600281111562000e485762000e486200265e565b0362000e97576000806000806000808680602001905181019062000e6d919062002abc565b95509550955095509550955062000e8b8c8c88888888888862001d5c565b50505050505062000ee0565b60405162461bcd60e51b815260206004820152601b60248201527f45524332304272696467653a20696e76616c696420616374696f6e0000000000604482015260640162000455565b505050505050565b62000ef262001227565b6001600160a01b03811662000f595760405162461bcd60e51b815260206004820152602660248201527f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160448201526564647265737360d01b606482015260840162000455565b6200093c8162001283565b60026000540362000fb85760405162461bcd60e51b815260206004820152601f60248201527f5265656e7472616e637947756172643a207265656e7472616e742063616c6c00604482015260640162000455565b6002600055565b6040516370a0823160e01b815230600482015260009081906001600160a01b038516906370a0823190602401602060405180830381865afa15801562001009573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906200102f919062002887565b9050620010486001600160a01b03851633308662001f15565b6040516370a0823160e01b81523060048201526000906001600160a01b038616906370a0823190602401602060405180830381865afa15801562001090573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190620010b6919062002887565b90508181116200111e5760405162461bcd60e51b815260206004820152602c60248201527f5361666545524332305472616e7366657246726f6d3a2062616c616e6365206e60448201526b1bdd081a5b98dc99585cd95960a21b606482015260840162000455565b6200112a828262002b2c565b925050505b92915050565b604051636eb1769f60e11b81523060048201526001600160a01b038381166024830152600091839186169063dd62ed3e90604401602060405180830381865afa15801562001187573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190620011ad919062002887565b620011b9919062002966565b6040516001600160a01b0385166024820152604481018290529091506200122190859063095ea7b360e01b906064015b60408051601f198184030181529190526020810180516001600160e01b03166001600160e01b03199093169290921790915262001f39565b50505050565b6002546001600160a01b031633146200080d5760405162461bcd60e51b815260206004820181905260248201527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e6572604482015260640162000455565b600280546001600160a01b038381166001600160a01b0319831681179093556040519116919082907f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e090600090a35050565b60007f00000000000000000000000000000000000000000000000000000000000000006001600160a01b031663d820e64f6040518163ffffffff1660e01b8152600401602060405180830381865afa15801562001336573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906200135c9190620026fa565b90506000808360a0015111156200139f576200138183604001518460a0015162000fbf565b60408401519091506200139f906001600160a01b0316838362001135565b60008360a001518460800151620013b7919062002b2c565b604085810151905163079cc67960e41b815233600482015260248101839052919250906001600160a01b038216906379cc679090604401600060405180830381600087803b1580156200140957600080fd5b505af11580156200141e573d6000803e3d6000fd5b505050506000816001600160a01b031663f72539686040518163ffffffff1660e01b8152600401602060405180830381865afa15801562001463573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019062001489919062002887565b90506000826001600160a01b0316631a0b79bf6040518163ffffffff1660e01b8152600401602060405180830381865afa158015620014cc573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190620014f29190620026fa565b9050818760000151036200153857806001600160a01b031687602001516001600160a01b031614620015385760405162461bcd60e51b8152600401620004559062002b42565b6000620015be88600001518960200151866001600160a01b03166374d32ad46040518163ffffffff1660e01b8152600401602060405180830381865afa15801562001587573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190620015ad9190620026fa565b8b60600151898d60c001516200093f565b90506000876001600160a01b031663624488506040518060c00160405280878152602001866001600160a01b0316815260200160405180604001604052808e604001516001600160a01b031681526020018c8152508152602001620493e08152602001600067ffffffffffffffff8111156200163e576200163e620021a0565b60405190808252806020026020018201604052801562001668578160200160208202803683370190505b508152602001858152506040518263ffffffff1660e01b815260040162001690919062002805565b6020604051808303816000875af1158015620016b0573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190620016d6919062002887565b90508089600001518a604001516001600160a01b03167f97935c4470efae40c8440c3abfe968a5512232dd375cc974e712f487c2b99c318c602001518d606001518b6040516200172993929190620028a1565b60405180910390a4505050505050505050565b6001600160a01b03841660009081526005602052604090205460ff1615620017b85760405162461bcd60e51b815260206004820152602860248201527f45524332304272696467653a2063616e6e6f742062726964676520777261707060448201526732b2103a37b5b2b760c11b606482015260840162000455565b7f00000000000000000000000000000000000000000000000000000000000000008603620017fa5760405162461bcd60e51b81526004016200045590620028c5565b60007f00000000000000000000000000000000000000000000000000000000000000006001600160a01b031663d820e64f6040518163ffffffff1660e01b8152600401602060405180830381865afa1580156200185b573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190620018819190620026fa565b90508115620018a057620018a06001600160a01b038616828462001135565b6000620018ae838562002b2c565b60008981526004602090815260408083206001600160a01b03808d168552908352818420908b168452909152812080549293508392909190620018f390849062002966565b9091555060009050620019088787846200080f565b90506000836001600160a01b031663624488506040518060c001604052808d81526020018c6001600160a01b0316815260200160405180604001604052808d6001600160a01b031681526020018a815250815260200162030d408152602001600067ffffffffffffffff811115620019845762001984620021a0565b604051908082528060200260200182016040528015620019ae578160200160208202803683370190505b508152602001858152506040518263ffffffff1660e01b8152600401620019d6919062002805565b6020604051808303816000875af1158015620019f6573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019062001a1c919062002887565b9050808a896001600160a01b03167f97935c4470efae40c8440c3abfe968a5512232dd375cc974e712f487c2b99c318c8b8860405162001a5f93929190620028a1565b60405180910390a450505050505050505050565b60008681526006602090815260408083206001600160a01b038981168552908352818420888216855290925290912054161562001b045760405162461bcd60e51b815260206004820152602860248201527f45524332304272696467653a2062726964676520746f6b656e20616c72656164604482015267792065786973747360c01b606482015260840162000455565b600086868686868660405162001b1a906200217c565b62001b2b9695949392919062002b91565b604051809103906000f08015801562001b48573d6000803e3d6000fd5b506001600160a01b038181166000818152600560209081526040808320805460ff191660011790558c8352600682528083208c8616808552908352818420958c168085529583529281902080546001600160a01b031916851790555192835293945091928a917fe1c61a845f79534e11924517ddbedc668d0c20e467eafb4d3bd2858e2815f3b5910160405180910390a450505050505050565b62001bec62000f64565b6001600160a01b03821662001c155760405162461bcd60e51b815260040162000455906200290d565b60008581526006602090815260408083206001600160a01b038089168552908352818420878216855290925290912054168062001ca65760405162461bcd60e51b815260206004820152602860248201527f45524332304272696467653a2062726964676520746f6b656e20646f6573206e6044820152671bdd08195e1a5cdd60c21b606482015260840162000455565b6040516340c10f1960e01b81526001600160a01b038481166004830152602482018490528216906340c10f1990604401600060405180830381600087803b15801562001cf157600080fd5b505af115801562001d06573d6000803e3d6000fd5b5050604080516001600160a01b03878116825260208201879052851693507fc0767f158f0d5394b598489a51ed607cd55a8be2dcef113ba1626efcf4c6395492500160405180910390a250620007f06001600055565b62001d6662000f64565b6001600160a01b03831662001d8f5760405162461bcd60e51b815260040162000455906200290d565b6001600160a01b03851662001db85760405162461bcd60e51b81526004016200045590620026ae565b60008881526004602090815260408083206001600160a01b03808c16855290835281842090881684529091529020548281101562001e435760405162461bcd60e51b815260206004820152602160248201527f45524332304272696467653a20696e73756666696369656e742062616c616e636044820152606560f81b606482015260840162000455565b62001e4f838262002b2c565b60008a81526004602090815260408083206001600160a01b03808e168552908352818420908a1684529091529020557f0000000000000000000000000000000000000000000000000000000000000000870362001eee576001600160a01b038616301462001ed15760405162461bcd60e51b8152600401620004559062002b42565b62001ee76001600160a01b038616858562002017565b5062001f00565b62001efe8787878787876200173c565b505b62001f0b6001600055565b5050505050505050565b62001221846323b872dd60e01b858585604051602401620011e993929190620028a1565b600062001f90826040518060400160405280602081526020017f5361666545524332303a206c6f772d6c6576656c2063616c6c206661696c6564815250856001600160a01b0316620020499092919063ffffffff16565b80519091501562002012578080602001905181019062001fb1919062002bf0565b620020125760405162461bcd60e51b815260206004820152602a60248201527f5361666545524332303a204552433230206f7065726174696f6e20646964206e6044820152691bdd081cdd58d8d9595960b21b606482015260840162000455565b505050565b6040516001600160a01b0383166024820152604481018290526200201290849063a9059cbb60e01b90606401620011e9565b60606200041a848460008585600080866001600160a01b0316858760405162002073919062002c14565b60006040518083038185875af1925050503d8060008114620020b2576040519150601f19603f3d011682016040523d82523d6000602084013e620020b7565b606091505b5091509150620020ca87838387620020d5565b979650505050505050565b606083156200214957825160000362002141576001600160a01b0385163b620021415760405162461bcd60e51b815260206004820152601d60248201527f416464726573733a2063616c6c20746f206e6f6e2d636f6e7472616374000000604482015260640162000455565b50816200041a565b6200041a8383815115620021605781518083602001fd5b8060405162461bcd60e51b81526004016200045591906200237a565b6111688062002c3383390190565b6001600160a01b03811681146200093c57600080fd5b634e487b7160e01b600052604160045260246000fd5b604051601f8201601f1916810167ffffffffffffffff81118282101715620021e257620021e2620021a0565b604052919050565b600067ffffffffffffffff821115620022075762002207620021a0565b50601f01601f191660200190565b60006200222c6200222684620021ea565b620021b6565b90508281528383830111156200224157600080fd5b828260208301376000602084830101529392505050565b600082601f8301126200226a57600080fd5b6200227b8383356020850162002215565b9392505050565b60ff811681146200093c57600080fd5b60008060008060808587031215620022a957600080fd5b8435620022b6816200218a565b9350602085013567ffffffffffffffff80821115620022d457600080fd5b620022e28883890162002258565b94506040870135915080821115620022f957600080fd5b50620023088782880162002258565b92505060608501356200231b8162002282565b939692955090935050565b60005b838110156200234357818101518382015260200162002329565b50506000910152565b600081518084526200236681602086016020860162002326565b601f01601f19169290920160200192915050565b6020815260006200227b60208301846200234c565b600080600060608486031215620023a557600080fd5b833592506020840135620023b9816200218a565b91506040840135620023cb816200218a565b809150509250925092565b600080600080600060a08688031215620023ef57600080fd5b85359450602086013562002403816200218a565b9350604086013562002415816200218a565b9250606086013562002427816200218a565b949793965091946080013592915050565b6000806000606084860312156200244e57600080fd5b83356200245b816200218a565b925060208401356200246d816200218a565b929592945050506040919091013590565b6000602082840312156200249157600080fd5b81356200227b816200218a565b60008060008060008060c08789031215620024b857600080fd5b863595506020870135620024cc816200218a565b94506040870135620024de816200218a565b93506060870135620024f0816200218a565b9598949750929560808101359460a0909101359350915050565b600080600080600080600060e0888a0312156200252657600080fd5b8735965060208801356200253a816200218a565b955060408801356200254c816200218a565b945060608801356200255e816200218a565b9699959850939660808101359560a0820135955060c0909101359350915050565b600080600080606085870312156200259657600080fd5b843593506020850135620025aa816200218a565b9250604085013567ffffffffffffffff80821115620025c857600080fd5b818701915087601f830112620025dd57600080fd5b813581811115620025ed57600080fd5b8860208285010111156200260057600080fd5b95989497505060200194505050565b6001600160a01b038516815260806020820181905260009062002635908301866200234c565b82810360408401526200264981866200234c565b91505060ff8316606083015295945050505050565b634e487b7160e01b600052602160045260246000fd5b6000600384106200269557634e487b7160e01b600052602160045260246000fd5b838252604060208301526200041a60408301846200234c565b6020808252602c908201527f45524332304272696467653a207a65726f2064657374696e6174696f6e20627260408201526b69646765206164647265737360a01b606082015260800190565b6000602082840312156200270d57600080fd5b81516200227b816200218a565b600082601f8301126200272c57600080fd5b81516200273d6200222682620021ea565b8181528460208386010111156200275357600080fd5b6200041a82602083016020870162002326565b6000602082840312156200277957600080fd5b815167ffffffffffffffff8111156200279157600080fd5b6200041a848285016200271a565b600060208284031215620027b257600080fd5b81516200227b8162002282565b600081518084526020808501945080840160005b83811015620027fa5781516001600160a01b031687529582019590820190600101620027d3565b509495945050505050565b60208152815160208201526000602083015160018060a01b03808216604085015260408501519150808251166060850152506020810151608084015250606083015160a0830152608083015160e060c084015262002868610100840182620027bf565b905060a0840151601f198483030160e08501526200112a82826200234c565b6000602082840312156200289a57600080fd5b5051919050565b6001600160a01b039384168152919092166020820152604081019190915260600190565b60208082526028908201527f45524332304272696467653a2063616e6e6f742062726964676520746f20736160408201526736b29031b430b4b760c11b606082015260800190565b60208082526023908201527f45524332304272696467653a207a65726f20726563697069656e74206164647260408201526265737360e81b606082015260800190565b634e487b7160e01b600052601160045260246000fd5b808201808211156200112f576200112f62002950565b600080604083850312156200299057600080fd5b823560038110620029a057600080fd5b9150602083013567ffffffffffffffff811115620029bd57600080fd5b8301601f81018513620029cf57600080fd5b620029e08582356020840162002215565b9150509250929050565b6000806000806080858703121562002a0157600080fd5b845162002a0e816200218a565b602086015190945067ffffffffffffffff8082111562002a2d57600080fd5b62002a3b888389016200271a565b9450604087015191508082111562002a5257600080fd5b5062002a61878288016200271a565b92505060608501516200231b8162002282565b60008060006060848603121562002a8a57600080fd5b835162002a97816200218a565b602085015190935062002aaa816200218a565b80925050604084015190509250925092565b60008060008060008060c0878903121562002ad657600080fd5b86519550602087015162002aea816200218a565b604088015190955062002afd816200218a565b606088015190945062002b10816200218a565b809350506080870151915060a087015190509295509295509295565b818103818111156200112f576200112f62002950565b6020808252602f908201527f45524332304272696467653a20696e76616c69642064657374696e6174696f6e60408201526e20627269646765206164647265737360881b606082015260800190565b8681526001600160a01b0386811660208301528516604082015260c06060820181905260009062002bc5908301866200234c565b828103608084015262002bd981866200234c565b91505060ff831660a0830152979650505050505050565b60006020828403121562002c0357600080fd5b815180151581146200227b57600080fd5b6000825162002c2881846020870162002326565b919091019291505056fe6101206040523480156200001257600080fd5b506040516200116838038062001168833981016040819052620000359162000292565b82826003620000458382620003d5565b506004620000548282620003d5565b50879150620000b690505760405162461bcd60e51b815260206004820152602160248201527f427269646765546f6b656e3a207a65726f20736f7572636520636861696e20696044820152601960fa1b60648201526084015b60405180910390fd5b6001600160a01b0385166200011e5760405162461bcd60e51b815260206004820152602760248201527f427269646765546f6b656e3a207a65726f20736f7572636520627269646765206044820152666164647265737360c81b6064820152608401620000ad565b6001600160a01b038416620001855760405162461bcd60e51b815260206004820152602660248201527f427269646765546f6b656e3a207a65726f20736f75726365206173736574206160448201526564647265737360d01b6064820152608401620000ad565b3360805260a09590955250506001600160a01b0391821660c0521660e05260ff1661010052620004a1565b80516001600160a01b0381168114620001c857600080fd5b919050565b634e487b7160e01b600052604160045260246000fd5b600082601f830112620001f557600080fd5b81516001600160401b0380821115620002125762000212620001cd565b604051601f8301601f19908116603f011681019082821181831017156200023d576200023d620001cd565b816040528381526020925086838588010111156200025a57600080fd5b600091505b838210156200027e57858201830151818301840152908201906200025f565b600093810190920192909252949350505050565b60008060008060008060c08789031215620002ac57600080fd5b86519550620002be60208801620001b0565b9450620002ce60408801620001b0565b60608801519094506001600160401b0380821115620002ec57600080fd5b620002fa8a838b01620001e3565b945060808901519150808211156200031157600080fd5b506200032089828a01620001e3565b92505060a087015160ff811681146200033857600080fd5b809150509295509295509295565b600181811c908216806200035b57607f821691505b6020821081036200037c57634e487b7160e01b600052602260045260246000fd5b50919050565b601f821115620003d057600081815260208120601f850160051c81016020861015620003ab5750805b601f850160051c820191505b81811015620003cc57828155600101620003b7565b5050505b505050565b81516001600160401b03811115620003f157620003f1620001cd565b620004098162000402845462000346565b8462000382565b602080601f831160018114620004415760008415620004285750858301515b600019600386901b1c1916600185901b178555620003cc565b600085815260208120601f198616915b82811015620004725788860151825594840194600190910190840162000451565b5085821015620004915787850151600019600388901b60f8161c191681555b5050505050600190811b01905550565b60805160a05160c05160e05161010051610c7b620004ed60003960006101c70152600061025a01526000610173015260006102fc0152600081816102c2015261041b0152610c7b6000f3fe608060405234801561001057600080fd5b50600436106101165760003560e01c806370a08231116100a2578063a457c2d711610071578063a457c2d714610297578063a9059cbb146102aa578063cd596583146102bd578063dd62ed3e146102e4578063f7253968146102f757600080fd5b806370a082311461022c57806374d32ad41461025557806379cc67901461027c57806395d89b411461028f57600080fd5b806323b872dd116100e957806323b872dd146101ad578063313ce567146101c057806339509351146101f157806340c10f191461020457806342966c681461021957600080fd5b806306fdde031461011b578063095ea7b31461013957806318160ddd1461015c5780631a0b79bf1461016e575b600080fd5b61012361031e565b6040516101309190610aac565b60405180910390f35b61014c610147366004610b16565b6103b0565b6040519015158152602001610130565b6002545b604051908152602001610130565b6101957f000000000000000000000000000000000000000000000000000000000000000081565b6040516001600160a01b039091168152602001610130565b61014c6101bb366004610b40565b6103ca565b60405160ff7f0000000000000000000000000000000000000000000000000000000000000000168152602001610130565b61014c6101ff366004610b16565b6103ee565b610217610212366004610b16565b610410565b005b610217610227366004610b7c565b61049b565b61016061023a366004610b95565b6001600160a01b031660009081526020819052604090205490565b6101957f000000000000000000000000000000000000000000000000000000000000000081565b61021761028a366004610b16565b6104a8565b6101236104bd565b61014c6102a5366004610b16565b6104cc565b61014c6102b8366004610b16565b610547565b6101957f000000000000000000000000000000000000000000000000000000000000000081565b6101606102f2366004610bb7565b610555565b6101607f000000000000000000000000000000000000000000000000000000000000000081565b60606003805461032d90610bea565b80601f016020809104026020016040519081016040528092919081815260200182805461035990610bea565b80156103a65780601f1061037b576101008083540402835291602001916103a6565b820191906000526020600020905b81548152906001019060200180831161038957829003601f168201915b5050505050905090565b6000336103be818585610580565b60019150505b92915050565b6000336103d88582856106a5565b6103e385858561071f565b506001949350505050565b6000336103be8185856104018383610555565b61040b9190610c24565b610580565b336001600160a01b037f0000000000000000000000000000000000000000000000000000000000000000161461048d5760405162461bcd60e51b815260206004820152601960248201527f427269646765546f6b656e3a20756e617574686f72697a65640000000000000060448201526064015b60405180910390fd5b61049782826108c3565b5050565b6104a53382610982565b50565b6104b38233836106a5565b6104978282610982565b60606004805461032d90610bea565b600033816104da8286610555565b90508381101561053a5760405162461bcd60e51b815260206004820152602560248201527f45524332303a2064656372656173656420616c6c6f77616e63652062656c6f77604482015264207a65726f60d81b6064820152608401610484565b6103e38286868403610580565b6000336103be81858561071f565b6001600160a01b03918216600090815260016020908152604080832093909416825291909152205490565b6001600160a01b0383166105e25760405162461bcd60e51b8152602060048201526024808201527f45524332303a20617070726f76652066726f6d20746865207a65726f206164646044820152637265737360e01b6064820152608401610484565b6001600160a01b0382166106435760405162461bcd60e51b815260206004820152602260248201527f45524332303a20617070726f766520746f20746865207a65726f206164647265604482015261737360f01b6064820152608401610484565b6001600160a01b0383811660008181526001602090815260408083209487168084529482529182902085905590518481527f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b92591015b60405180910390a3505050565b60006106b18484610555565b90506000198114610719578181101561070c5760405162461bcd60e51b815260206004820152601d60248201527f45524332303a20696e73756666696369656e7420616c6c6f77616e63650000006044820152606401610484565b6107198484848403610580565b50505050565b6001600160a01b0383166107835760405162461bcd60e51b815260206004820152602560248201527f45524332303a207472616e736665722066726f6d20746865207a65726f206164604482015264647265737360d81b6064820152608401610484565b6001600160a01b0382166107e55760405162461bcd60e51b815260206004820152602360248201527f45524332303a207472616e7366657220746f20746865207a65726f206164647260448201526265737360e81b6064820152608401610484565b6001600160a01b0383166000908152602081905260409020548181101561085d5760405162461bcd60e51b815260206004820152602660248201527f45524332303a207472616e7366657220616d6f756e7420657863656564732062604482015265616c616e636560d01b6064820152608401610484565b6001600160a01b03848116600081815260208181526040808320878703905593871680835291849020805487019055925185815290927fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef910160405180910390a3610719565b6001600160a01b0382166109195760405162461bcd60e51b815260206004820152601f60248201527f45524332303a206d696e7420746f20746865207a65726f2061646472657373006044820152606401610484565b806002600082825461092b9190610c24565b90915550506001600160a01b038216600081815260208181526040808320805486019055518481527fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef910160405180910390a35050565b6001600160a01b0382166109e25760405162461bcd60e51b815260206004820152602160248201527f45524332303a206275726e2066726f6d20746865207a65726f206164647265736044820152607360f81b6064820152608401610484565b6001600160a01b03821660009081526020819052604090205481811015610a565760405162461bcd60e51b815260206004820152602260248201527f45524332303a206275726e20616d6f756e7420657863656564732062616c616e604482015261636560f01b6064820152608401610484565b6001600160a01b0383166000818152602081815260408083208686039055600280548790039055518581529192917fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef9101610698565b600060208083528351808285015260005b81811015610ad957858101830151858201604001528201610abd565b506000604082860101526040601f19601f8301168501019250505092915050565b80356001600160a01b0381168114610b1157600080fd5b919050565b60008060408385031215610b2957600080fd5b610b3283610afa565b946020939093013593505050565b600080600060608486031215610b5557600080fd5b610b5e84610afa565b9250610b6c60208501610afa565b9150604084013590509250925092565b600060208284031215610b8e57600080fd5b5035919050565b600060208284031215610ba757600080fd5b610bb082610afa565b9392505050565b60008060408385031215610bca57600080fd5b610bd383610afa565b9150610be160208401610afa565b90509250929050565b600181811c90821680610bfe57607f821691505b602082108103610c1e57634e487b7160e01b600052602260045260246000fd5b50919050565b808201808211156103c457634e487b7160e01b600052601160045260246000fdfea26469706673582212208a8e82a679ec260481bb5d10cf7933d8213beeeb9291c42d2ad6b12aa8eb16e264736f6c63430008120033a26469706673582212200154a4130f205f5650af65dc28d67856563d7ace97ac7837c10fce0fae8a0d7564736f6c63430008120033", } // ERC20BridgeABI is the input ABI used to generate the binding from. diff --git a/abi-bindings/go/CrossChainApplications/ExampleMessenger/ExampleCrossChainMessenger/ExampleCrossChainMessenger.go b/abi-bindings/go/CrossChainApplications/ExampleMessenger/ExampleCrossChainMessenger/ExampleCrossChainMessenger.go index 170554a96..730343efe 100644 --- a/abi-bindings/go/CrossChainApplications/ExampleMessenger/ExampleCrossChainMessenger/ExampleCrossChainMessenger.go +++ b/abi-bindings/go/CrossChainApplications/ExampleMessenger/ExampleCrossChainMessenger/ExampleCrossChainMessenger.go @@ -32,7 +32,7 @@ var ( // ExampleCrossChainMessengerMetaData contains all meta data concerning the ExampleCrossChainMessenger contract. var ExampleCrossChainMessengerMetaData = &bind.MetaData{ ABI: "[{\"inputs\":[{\"internalType\":\"address\",\"name\":\"teleporterRegistryAddress\",\"type\":\"address\"}],\"stateMutability\":\"nonpayable\",\"type\":\"constructor\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"uint256\",\"name\":\"oldMinTeleporterVersion\",\"type\":\"uint256\"},{\"indexed\":true,\"internalType\":\"uint256\",\"name\":\"newMinTeleporterVersion\",\"type\":\"uint256\"}],\"name\":\"MinTeleporterVersionUpdated\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"address\",\"name\":\"previousOwner\",\"type\":\"address\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"newOwner\",\"type\":\"address\"}],\"name\":\"OwnershipTransferred\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"bytes32\",\"name\":\"originBlockchainID\",\"type\":\"bytes32\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"originSenderAddress\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"string\",\"name\":\"message\",\"type\":\"string\"}],\"name\":\"ReceiveMessage\",\"type\":\"event\"},{\"anonymous\":false,\"inputs\":[{\"indexed\":true,\"internalType\":\"bytes32\",\"name\":\"destinationBlockchainID\",\"type\":\"bytes32\"},{\"indexed\":true,\"internalType\":\"address\",\"name\":\"destinationAddress\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"address\",\"name\":\"feeTokenAddress\",\"type\":\"address\"},{\"indexed\":false,\"internalType\":\"uint256\",\"name\":\"feeAmount\",\"type\":\"uint256\"},{\"indexed\":false,\"internalType\":\"uint256\",\"name\":\"requiredGasLimit\",\"type\":\"uint256\"},{\"indexed\":false,\"internalType\":\"string\",\"name\":\"message\",\"type\":\"string\"}],\"name\":\"SendMessage\",\"type\":\"event\"},{\"inputs\":[{\"internalType\":\"bytes32\",\"name\":\"originBlockchainID\",\"type\":\"bytes32\"}],\"name\":\"getCurrentMessage\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"},{\"internalType\":\"string\",\"name\":\"\",\"type\":\"string\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"minTeleporterVersion\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"owner\",\"outputs\":[{\"internalType\":\"address\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"bytes32\",\"name\":\"originBlockchainID\",\"type\":\"bytes32\"},{\"internalType\":\"address\",\"name\":\"originSenderAddress\",\"type\":\"address\"},{\"internalType\":\"bytes\",\"name\":\"message\",\"type\":\"bytes\"}],\"name\":\"receiveTeleporterMessage\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"renounceOwnership\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"bytes32\",\"name\":\"destinationBlockchainID\",\"type\":\"bytes32\"},{\"internalType\":\"address\",\"name\":\"destinationAddress\",\"type\":\"address\"},{\"internalType\":\"address\",\"name\":\"feeTokenAddress\",\"type\":\"address\"},{\"internalType\":\"uint256\",\"name\":\"feeAmount\",\"type\":\"uint256\"},{\"internalType\":\"uint256\",\"name\":\"requiredGasLimit\",\"type\":\"uint256\"},{\"internalType\":\"string\",\"name\":\"message\",\"type\":\"string\"}],\"name\":\"sendMessage\",\"outputs\":[{\"internalType\":\"uint256\",\"name\":\"\",\"type\":\"uint256\"}],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"teleporterRegistry\",\"outputs\":[{\"internalType\":\"contractTeleporterRegistry\",\"name\":\"\",\"type\":\"address\"}],\"stateMutability\":\"view\",\"type\":\"function\"},{\"inputs\":[{\"internalType\":\"address\",\"name\":\"newOwner\",\"type\":\"address\"}],\"name\":\"transferOwnership\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"},{\"inputs\":[],\"name\":\"updateMinTeleporterVersion\",\"outputs\":[],\"stateMutability\":\"nonpayable\",\"type\":\"function\"}]", - Bin: "0x60a06040523480156200001157600080fd5b50604051620015aa380380620015aa833981016040819052620000349162000196565b600160005580806001600160a01b038116620000bc5760405162461bcd60e51b815260206004820152603760248201527f54656c65706f727465725570677261646561626c653a207a65726f2074656c6560448201527f706f727465722072656769737472792061646472657373000000000000000000606482015260840160405180910390fd5b6001600160a01b03811660808190526040805163301fd1f560e21b8152905163c07f47d4916004808201926020929091908290030181865afa15801562000107573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906200012d9190620001c8565b600155506200013c3362000144565b5050620001e2565b600280546001600160a01b038381166001600160a01b0319831681179093556040519116919082907f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e090600090a35050565b600060208284031215620001a957600080fd5b81516001600160a01b0381168114620001c157600080fd5b9392505050565b600060208284031215620001db57600080fd5b5051919050565b6080516113986200021260003960008181609d0152818161026d01528181610343015261055701526113986000f3fe608060405234801561001057600080fd5b50600436106100935760003560e01c8063b6109d9d11610066578063b6109d9d14610118578063c868efaa14610120578063e49cc55314610133578063f2fde38b1461014a578063f63d09d71461015d57600080fd5b80631a7f5bec14610098578063715018a6146100dc5780638da5cb5b146100e6578063b33fead4146100f7575b600080fd5b6100bf7f000000000000000000000000000000000000000000000000000000000000000081565b6040516001600160a01b0390911681526020015b60405180910390f35b6100e4610170565b005b6002546001600160a01b03166100bf565b61010a610105366004610d72565b610184565b6040516100d3929190610ddb565b6100e461025c565b6100e461012e366004610e5d565b61032b565b61013c60015481565b6040519081526020016100d3565b6100e4610158366004610eb9565b6104d3565b61013c61016b366004610edd565b610549565b610178610789565b61018260006107e3565b565b6000818152600360209081526040808320815180830190925280546001600160a01b0316825260018101805460609486949392908401916101c490610f63565b80601f01602080910402602001604051908101604052809291908181526020018280546101f090610f63565b801561023d5780601f106102125761010080835404028352916020019161023d565b820191906000526020600020905b81548152906001019060200180831161022057829003601f168201915b5050505050815250509050806000015181602001519250925050915091565b610264610789565b600060015490507f00000000000000000000000000000000000000000000000000000000000000006001600160a01b031663c07f47d46040518163ffffffff1660e01b8152600401602060405180830381865afa1580156102c9573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906102ed9190610f9d565b60018190558110156103285760015460405182907fa9a7ef57e41f05b4c15480842f5f0c27edfcbb553fed281f7c4068452cc1c02d90600090a35b50565b60015460405163260f846760e11b81523360048201527f00000000000000000000000000000000000000000000000000000000000000006001600160a01b031690634c1f08ce90602401602060405180830381865afa158015610392573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906103b69190610f9d565b10156104225760405162461bcd60e51b815260206004820152603060248201527f54656c65706f727465725570677261646561626c653a20696e76616c6964207460448201526f32b632b837b93a32b91039b2b73232b960811b60648201526084015b60405180910390fd5b600061043082840184610fcc565b6040805180820182526001600160a01b038781168252602080830185815260008b81526003909252939020825181546001600160a01b0319169216919091178155915192935091600182019061048690826110cb565b50905050836001600160a01b0316857f1f5c800b5f2b573929a7948f82a199c2a212851b53a6c5bd703ece23999d24aa836040516104c4919061118b565b60405180910390a35050505050565b6104db610789565b6001600160a01b0381166105405760405162461bcd60e51b815260206004820152602660248201527f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160448201526564647265737360d01b6064820152608401610419565b610328816107e3565b6000610553610835565b60007f00000000000000000000000000000000000000000000000000000000000000006001600160a01b031663d820e64f6040518163ffffffff1660e01b8152600401602060405180830381865afa1580156105b3573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906105d7919061119e565b905060008615610601576105eb888861088e565b90506106016001600160a01b03891683836109f8565b886001600160a01b03168a7fa06eff1edd0c66b8dc96d086dda7ba263edf88d7417e6cb15073b5e7bff8a8ca8a848a8a8a6040516106439594939291906111e4565b60405180910390a3816001600160a01b031663624488506040518060c001604052808d81526020018c6001600160a01b0316815260200160405180604001604052808d6001600160a01b03168152602001868152508152602001898152602001600067ffffffffffffffff8111156106bd576106bd610fb6565b6040519080825280602002602001820160405280156106e6578160200160208202803683370190505b50815260200188886040516020016106ff929190611212565b6040516020818303038152906040528152506040518263ffffffff1660e01b815260040161072d919061126a565b6020604051808303816000875af115801561074c573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906107709190610f9d565b9250505061077e6001600055565b979650505050505050565b6002546001600160a01b031633146101825760405162461bcd60e51b815260206004820181905260248201527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e65726044820152606401610419565b600280546001600160a01b038381166001600160a01b0319831681179093556040519116919082907f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e090600090a35050565b6002600054036108875760405162461bcd60e51b815260206004820152601f60248201527f5265656e7472616e637947756172643a207265656e7472616e742063616c6c006044820152606401610419565b6002600055565b6040516370a0823160e01b815230600482015260009081906001600160a01b038516906370a0823190602401602060405180830381865afa1580156108d7573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906108fb9190610f9d565b90506109126001600160a01b038516333086610ae3565b6040516370a0823160e01b81523060048201526000906001600160a01b038616906370a0823190602401602060405180830381865afa158015610959573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061097d9190610f9d565b90508181116109e35760405162461bcd60e51b815260206004820152602c60248201527f5361666545524332305472616e7366657246726f6d3a2062616c616e6365206e60448201526b1bdd081a5b98dc99585cd95960a21b6064820152608401610419565b6109ed82826112fe565b925050505b92915050565b604051636eb1769f60e11b81523060048201526001600160a01b038381166024830152600091839186169063dd62ed3e90604401602060405180830381865afa158015610a49573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610a6d9190610f9d565b610a779190611311565b6040516001600160a01b038516602482015260448101829052909150610add90859063095ea7b360e01b906064015b60408051601f198184030181529190526020810180516001600160e01b03166001600160e01b031990931692909217909152610b1b565b50505050565b6040516001600160a01b0380851660248301528316604482015260648101829052610add9085906323b872dd60e01b90608401610aa6565b6000610b70826040518060400160405280602081526020017f5361666545524332303a206c6f772d6c6576656c2063616c6c206661696c6564815250856001600160a01b0316610bf29092919063ffffffff16565b805190915015610bed5780806020019051810190610b8e9190611324565b610bed5760405162461bcd60e51b815260206004820152602a60248201527f5361666545524332303a204552433230206f7065726174696f6e20646964206e6044820152691bdd081cdd58d8d9595960b21b6064820152608401610419565b505050565b6060610c018484600085610c09565b949350505050565b606082471015610c6a5760405162461bcd60e51b815260206004820152602660248201527f416464726573733a20696e73756666696369656e742062616c616e636520666f6044820152651c8818d85b1b60d21b6064820152608401610419565b600080866001600160a01b03168587604051610c869190611346565b60006040518083038185875af1925050503d8060008114610cc3576040519150601f19603f3d011682016040523d82523d6000602084013e610cc8565b606091505b509150915061077e8783838760608315610d43578251600003610d3c576001600160a01b0385163b610d3c5760405162461bcd60e51b815260206004820152601d60248201527f416464726573733a2063616c6c20746f206e6f6e2d636f6e74726163740000006044820152606401610419565b5081610c01565b610c018383815115610d585781518083602001fd5b8060405162461bcd60e51b8152600401610419919061118b565b600060208284031215610d8457600080fd5b5035919050565b60005b83811015610da6578181015183820152602001610d8e565b50506000910152565b60008151808452610dc7816020860160208601610d8b565b601f01601f19169290920160200192915050565b6001600160a01b0383168152604060208201819052600090610c0190830184610daf565b6001600160a01b038116811461032857600080fd5b60008083601f840112610e2657600080fd5b50813567ffffffffffffffff811115610e3e57600080fd5b602083019150836020828501011115610e5657600080fd5b9250929050565b60008060008060608587031215610e7357600080fd5b843593506020850135610e8581610dff565b9250604085013567ffffffffffffffff811115610ea157600080fd5b610ead87828801610e14565b95989497509550505050565b600060208284031215610ecb57600080fd5b8135610ed681610dff565b9392505050565b600080600080600080600060c0888a031215610ef857600080fd5b873596506020880135610f0a81610dff565b95506040880135610f1a81610dff565b9450606088013593506080880135925060a088013567ffffffffffffffff811115610f4457600080fd5b610f508a828b01610e14565b989b979a50959850939692959293505050565b600181811c90821680610f7757607f821691505b602082108103610f9757634e487b7160e01b600052602260045260246000fd5b50919050565b600060208284031215610faf57600080fd5b5051919050565b634e487b7160e01b600052604160045260246000fd5b600060208284031215610fde57600080fd5b813567ffffffffffffffff80821115610ff657600080fd5b818401915084601f83011261100a57600080fd5b81358181111561101c5761101c610fb6565b604051601f8201601f19908116603f0116810190838211818310171561104457611044610fb6565b8160405282815287602084870101111561105d57600080fd5b826020860160208301376000928101602001929092525095945050505050565b601f821115610bed57600081815260208120601f850160051c810160208610156110a45750805b601f850160051c820191505b818110156110c3578281556001016110b0565b505050505050565b815167ffffffffffffffff8111156110e5576110e5610fb6565b6110f9816110f38454610f63565b8461107d565b602080601f83116001811461112e57600084156111165750858301515b600019600386901b1c1916600185901b1785556110c3565b600085815260208120601f198616915b8281101561115d5788860151825594840194600190910190840161113e565b508582101561117b5787850151600019600388901b60f8161c191681555b5050505050600190811b01905550565b602081526000610ed66020830184610daf565b6000602082840312156111b057600080fd5b8151610ed681610dff565b81835281816020850137506000828201602090810191909152601f909101601f19169091010190565b60018060a01b038616815284602082015283604082015260806060820152600061077e6080830184866111bb565b602081526000610c016020830184866111bb565b600081518084526020808501945080840160005b8381101561125f5781516001600160a01b03168752958201959082019060010161123a565b509495945050505050565b60208152815160208201526000602083015160018060a01b03808216604085015260408501519150808251166060850152506020810151608084015250606083015160a0830152608083015160e060c08401526112cb610100840182611226565b905060a0840151601f198483030160e08501526109ed8282610daf565b634e487b7160e01b600052601160045260246000fd5b818103818111156109f2576109f26112e8565b808201808211156109f2576109f26112e8565b60006020828403121561133657600080fd5b81518015158114610ed657600080fd5b60008251611358818460208701610d8b565b919091019291505056fea26469706673582212205c31234a02169e7dc025213f34fae2b92a6a54b9182943ddfb2798902b0327e464736f6c63430008120033", + Bin: "0x60a06040523480156200001157600080fd5b50604051620015aa380380620015aa833981016040819052620000349162000196565b600160005580806001600160a01b038116620000bc5760405162461bcd60e51b815260206004820152603760248201527f54656c65706f727465725570677261646561626c653a207a65726f2074656c6560448201527f706f727465722072656769737472792061646472657373000000000000000000606482015260840160405180910390fd5b6001600160a01b03811660808190526040805163301fd1f560e21b8152905163c07f47d4916004808201926020929091908290030181865afa15801562000107573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906200012d9190620001c8565b600155506200013c3362000144565b5050620001e2565b600280546001600160a01b038381166001600160a01b0319831681179093556040519116919082907f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e090600090a35050565b600060208284031215620001a957600080fd5b81516001600160a01b0381168114620001c157600080fd5b9392505050565b600060208284031215620001db57600080fd5b5051919050565b6080516113986200021260003960008181609d0152818161026d01528181610343015261055701526113986000f3fe608060405234801561001057600080fd5b50600436106100935760003560e01c8063b6109d9d11610066578063b6109d9d14610118578063c868efaa14610120578063e49cc55314610133578063f2fde38b1461014a578063f63d09d71461015d57600080fd5b80631a7f5bec14610098578063715018a6146100dc5780638da5cb5b146100e6578063b33fead4146100f7575b600080fd5b6100bf7f000000000000000000000000000000000000000000000000000000000000000081565b6040516001600160a01b0390911681526020015b60405180910390f35b6100e4610170565b005b6002546001600160a01b03166100bf565b61010a610105366004610d72565b610184565b6040516100d3929190610ddb565b6100e461025c565b6100e461012e366004610e5d565b61032b565b61013c60015481565b6040519081526020016100d3565b6100e4610158366004610eb9565b6104d3565b61013c61016b366004610edd565b610549565b610178610789565b61018260006107e3565b565b6000818152600360209081526040808320815180830190925280546001600160a01b0316825260018101805460609486949392908401916101c490610f63565b80601f01602080910402602001604051908101604052809291908181526020018280546101f090610f63565b801561023d5780601f106102125761010080835404028352916020019161023d565b820191906000526020600020905b81548152906001019060200180831161022057829003601f168201915b5050505050815250509050806000015181602001519250925050915091565b610264610789565b600060015490507f00000000000000000000000000000000000000000000000000000000000000006001600160a01b031663c07f47d46040518163ffffffff1660e01b8152600401602060405180830381865afa1580156102c9573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906102ed9190610f9d565b60018190558110156103285760015460405182907fa9a7ef57e41f05b4c15480842f5f0c27edfcbb553fed281f7c4068452cc1c02d90600090a35b50565b60015460405163260f846760e11b81523360048201527f00000000000000000000000000000000000000000000000000000000000000006001600160a01b031690634c1f08ce90602401602060405180830381865afa158015610392573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906103b69190610f9d565b10156104225760405162461bcd60e51b815260206004820152603060248201527f54656c65706f727465725570677261646561626c653a20696e76616c6964207460448201526f32b632b837b93a32b91039b2b73232b960811b60648201526084015b60405180910390fd5b600061043082840184610fcc565b6040805180820182526001600160a01b038781168252602080830185815260008b81526003909252939020825181546001600160a01b0319169216919091178155915192935091600182019061048690826110cb565b50905050836001600160a01b0316857f1f5c800b5f2b573929a7948f82a199c2a212851b53a6c5bd703ece23999d24aa836040516104c4919061118b565b60405180910390a35050505050565b6104db610789565b6001600160a01b0381166105405760405162461bcd60e51b815260206004820152602660248201527f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160448201526564647265737360d01b6064820152608401610419565b610328816107e3565b6000610553610835565b60007f00000000000000000000000000000000000000000000000000000000000000006001600160a01b031663d820e64f6040518163ffffffff1660e01b8152600401602060405180830381865afa1580156105b3573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906105d7919061119e565b905060008615610601576105eb888861088e565b90506106016001600160a01b03891683836109f8565b886001600160a01b03168a7fa06eff1edd0c66b8dc96d086dda7ba263edf88d7417e6cb15073b5e7bff8a8ca8a848a8a8a6040516106439594939291906111e4565b60405180910390a3816001600160a01b031663624488506040518060c001604052808d81526020018c6001600160a01b0316815260200160405180604001604052808d6001600160a01b03168152602001868152508152602001898152602001600067ffffffffffffffff8111156106bd576106bd610fb6565b6040519080825280602002602001820160405280156106e6578160200160208202803683370190505b50815260200188886040516020016106ff929190611212565b6040516020818303038152906040528152506040518263ffffffff1660e01b815260040161072d919061126a565b6020604051808303816000875af115801561074c573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906107709190610f9d565b9250505061077e6001600055565b979650505050505050565b6002546001600160a01b031633146101825760405162461bcd60e51b815260206004820181905260248201527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e65726044820152606401610419565b600280546001600160a01b038381166001600160a01b0319831681179093556040519116919082907f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e090600090a35050565b6002600054036108875760405162461bcd60e51b815260206004820152601f60248201527f5265656e7472616e637947756172643a207265656e7472616e742063616c6c006044820152606401610419565b6002600055565b6040516370a0823160e01b815230600482015260009081906001600160a01b038516906370a0823190602401602060405180830381865afa1580156108d7573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906108fb9190610f9d565b90506109126001600160a01b038516333086610ae3565b6040516370a0823160e01b81523060048201526000906001600160a01b038616906370a0823190602401602060405180830381865afa158015610959573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061097d9190610f9d565b90508181116109e35760405162461bcd60e51b815260206004820152602c60248201527f5361666545524332305472616e7366657246726f6d3a2062616c616e6365206e60448201526b1bdd081a5b98dc99585cd95960a21b6064820152608401610419565b6109ed82826112fe565b925050505b92915050565b604051636eb1769f60e11b81523060048201526001600160a01b038381166024830152600091839186169063dd62ed3e90604401602060405180830381865afa158015610a49573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610a6d9190610f9d565b610a779190611311565b6040516001600160a01b038516602482015260448101829052909150610add90859063095ea7b360e01b906064015b60408051601f198184030181529190526020810180516001600160e01b03166001600160e01b031990931692909217909152610b1b565b50505050565b6040516001600160a01b0380851660248301528316604482015260648101829052610add9085906323b872dd60e01b90608401610aa6565b6000610b70826040518060400160405280602081526020017f5361666545524332303a206c6f772d6c6576656c2063616c6c206661696c6564815250856001600160a01b0316610bf29092919063ffffffff16565b805190915015610bed5780806020019051810190610b8e9190611324565b610bed5760405162461bcd60e51b815260206004820152602a60248201527f5361666545524332303a204552433230206f7065726174696f6e20646964206e6044820152691bdd081cdd58d8d9595960b21b6064820152608401610419565b505050565b6060610c018484600085610c09565b949350505050565b606082471015610c6a5760405162461bcd60e51b815260206004820152602660248201527f416464726573733a20696e73756666696369656e742062616c616e636520666f6044820152651c8818d85b1b60d21b6064820152608401610419565b600080866001600160a01b03168587604051610c869190611346565b60006040518083038185875af1925050503d8060008114610cc3576040519150601f19603f3d011682016040523d82523d6000602084013e610cc8565b606091505b509150915061077e8783838760608315610d43578251600003610d3c576001600160a01b0385163b610d3c5760405162461bcd60e51b815260206004820152601d60248201527f416464726573733a2063616c6c20746f206e6f6e2d636f6e74726163740000006044820152606401610419565b5081610c01565b610c018383815115610d585781518083602001fd5b8060405162461bcd60e51b8152600401610419919061118b565b600060208284031215610d8457600080fd5b5035919050565b60005b83811015610da6578181015183820152602001610d8e565b50506000910152565b60008151808452610dc7816020860160208601610d8b565b601f01601f19169290920160200192915050565b6001600160a01b0383168152604060208201819052600090610c0190830184610daf565b6001600160a01b038116811461032857600080fd5b60008083601f840112610e2657600080fd5b50813567ffffffffffffffff811115610e3e57600080fd5b602083019150836020828501011115610e5657600080fd5b9250929050565b60008060008060608587031215610e7357600080fd5b843593506020850135610e8581610dff565b9250604085013567ffffffffffffffff811115610ea157600080fd5b610ead87828801610e14565b95989497509550505050565b600060208284031215610ecb57600080fd5b8135610ed681610dff565b9392505050565b600080600080600080600060c0888a031215610ef857600080fd5b873596506020880135610f0a81610dff565b95506040880135610f1a81610dff565b9450606088013593506080880135925060a088013567ffffffffffffffff811115610f4457600080fd5b610f508a828b01610e14565b989b979a50959850939692959293505050565b600181811c90821680610f7757607f821691505b602082108103610f9757634e487b7160e01b600052602260045260246000fd5b50919050565b600060208284031215610faf57600080fd5b5051919050565b634e487b7160e01b600052604160045260246000fd5b600060208284031215610fde57600080fd5b813567ffffffffffffffff80821115610ff657600080fd5b818401915084601f83011261100a57600080fd5b81358181111561101c5761101c610fb6565b604051601f8201601f19908116603f0116810190838211818310171561104457611044610fb6565b8160405282815287602084870101111561105d57600080fd5b826020860160208301376000928101602001929092525095945050505050565b601f821115610bed57600081815260208120601f850160051c810160208610156110a45750805b601f850160051c820191505b818110156110c3578281556001016110b0565b505050505050565b815167ffffffffffffffff8111156110e5576110e5610fb6565b6110f9816110f38454610f63565b8461107d565b602080601f83116001811461112e57600084156111165750858301515b600019600386901b1c1916600185901b1785556110c3565b600085815260208120601f198616915b8281101561115d5788860151825594840194600190910190840161113e565b508582101561117b5787850151600019600388901b60f8161c191681555b5050505050600190811b01905550565b602081526000610ed66020830184610daf565b6000602082840312156111b057600080fd5b8151610ed681610dff565b81835281816020850137506000828201602090810191909152601f909101601f19169091010190565b60018060a01b038616815284602082015283604082015260806060820152600061077e6080830184866111bb565b602081526000610c016020830184866111bb565b600081518084526020808501945080840160005b8381101561125f5781516001600160a01b03168752958201959082019060010161123a565b509495945050505050565b60208152815160208201526000602083015160018060a01b03808216604085015260408501519150808251166060850152506020810151608084015250606083015160a0830152608083015160e060c08401526112cb610100840182611226565b905060a0840151601f198483030160e08501526109ed8282610daf565b634e487b7160e01b600052601160045260246000fd5b818103818111156109f2576109f26112e8565b808201808211156109f2576109f26112e8565b60006020828403121561133657600080fd5b81518015158114610ed657600080fd5b60008251611358818460208701610d8b565b919091019291505056fea26469706673582212200ac3abd1656ec36fe93e285d17b1522d243bab43567aa1d1ae54840806b6eb8d64736f6c63430008120033", } // ExampleCrossChainMessengerABI is the input ABI used to generate the binding from.