编译器
0.8.24+commit.e11b9ed9
文件 1 的 16:Address.sol
pragma solidity ^0.8.1;
library Address {
function isContract(address account) internal view returns (bool) {
return account.code.length > 0;
}
function sendValue(address payable recipient, uint256 amount) internal {
require(address(this).balance >= amount, "Address: insufficient balance");
(bool success, ) = recipient.call{value: amount}("");
require(success, "Address: unable to send value, recipient may have reverted");
}
function functionCall(address target, bytes memory data) internal returns (bytes memory) {
return functionCallWithValue(target, data, 0, "Address: low-level call failed");
}
function functionCall(
address target,
bytes memory data,
string memory errorMessage
) internal returns (bytes memory) {
return functionCallWithValue(target, data, 0, errorMessage);
}
function functionCallWithValue(address target, bytes memory data, uint256 value) internal returns (bytes memory) {
return functionCallWithValue(target, data, value, "Address: low-level call with value failed");
}
function functionCallWithValue(
address target,
bytes memory data,
uint256 value,
string memory errorMessage
) internal returns (bytes memory) {
require(address(this).balance >= value, "Address: insufficient balance for call");
(bool success, bytes memory returndata) = target.call{value: value}(data);
return verifyCallResultFromTarget(target, success, returndata, errorMessage);
}
function functionStaticCall(address target, bytes memory data) internal view returns (bytes memory) {
return functionStaticCall(target, data, "Address: low-level static call failed");
}
function functionStaticCall(
address target,
bytes memory data,
string memory errorMessage
) internal view returns (bytes memory) {
(bool success, bytes memory returndata) = target.staticcall(data);
return verifyCallResultFromTarget(target, success, returndata, errorMessage);
}
function functionDelegateCall(address target, bytes memory data) internal returns (bytes memory) {
return functionDelegateCall(target, data, "Address: low-level delegate call failed");
}
function functionDelegateCall(
address target,
bytes memory data,
string memory errorMessage
) internal returns (bytes memory) {
(bool success, bytes memory returndata) = target.delegatecall(data);
return verifyCallResultFromTarget(target, success, returndata, errorMessage);
}
function verifyCallResultFromTarget(
address target,
bool success,
bytes memory returndata,
string memory errorMessage
) internal view returns (bytes memory) {
if (success) {
if (returndata.length == 0) {
require(isContract(target), "Address: call to non-contract");
}
return returndata;
} else {
_revert(returndata, errorMessage);
}
}
function verifyCallResult(
bool success,
bytes memory returndata,
string memory errorMessage
) internal pure returns (bytes memory) {
if (success) {
return returndata;
} else {
_revert(returndata, errorMessage);
}
}
function _revert(bytes memory returndata, string memory errorMessage) private pure {
if (returndata.length > 0) {
assembly {
let returndata_size := mload(returndata)
revert(add(32, returndata), returndata_size)
}
} else {
revert(errorMessage);
}
}
}
文件 2 的 16:Context.sol
pragma solidity ^0.8.0;
abstract contract Context {
function _msgSender() internal view virtual returns (address) {
return msg.sender;
}
function _msgData() internal view virtual returns (bytes calldata) {
return msg.data;
}
}
文件 3 的 16:IAxelarGasService.sol
pragma solidity 0.8.24;
interface IAxelarGasService {
function payNativeGasForContractCall(
address sender,
string calldata destinationChain,
string calldata destinationAddress,
bytes calldata payload,
address refundAddress
) external payable;
}
文件 4 的 16:IAxelarGateway.sol
pragma solidity 0.8.24;
interface IAxelarGateway {
function callContract(
string calldata destinationChain,
string calldata contractAddress,
bytes calldata payload
) external;
function validateContractCall(
bytes32 commandId,
string calldata sourceChain,
string calldata sourceAddress,
bytes32 payloadHash
) external returns (bool);
}
文件 5 的 16:IBridge.sol
pragma solidity 0.8.24;
interface IBridge {
event SwapIn(
address indexed fromAddress,
address indexed toAddress,
address fromAssetAddress,
address toAssetAddress,
uint256 amountIn,
uint256 amountOut,
bytes encodedDepositData
);
event SwapOut(
address indexed fromAddress,
address indexed toAddress,
address fromAssetAddress,
address toAssetAddress,
uint256 amountIn,
uint256 amountOut,
bytes32 depositDataHash
);
event UpdateInternalCaller(address indexed sender, address caller, bool value);
function updateInternalCaller(address caller, bool value) external;
function updateWeth(address value) external;
function updateNetworkIdAndRouterAddress(bytes32 value) external;
function multicall(bytes[] calldata data) external returns (bytes[] memory results);
}
文件 6 的 16:IMagpieCCTPBridge.sol
pragma solidity 0.8.24;
import {IBridge} from "./IBridge.sol";
interface IMagpieCCTPBridge is IBridge {
function updateSwapFeeAddress(address value) external;
function updateTokenMessengerAddress(address value) external;
function updateMessageTransmitterAddress(address value) external;
function updateGatewayAddress(address value) external;
function updateGasReceiverAddress(address value) external;
function pause() external;
function unpause() external;
function execute(
bytes32 commandId,
string calldata sourceChain,
string calldata sourceAddress,
bytes calldata payload
) external;
}
文件 7 的 16:IMagpieRouterV3.sol
pragma solidity 0.8.24;
interface IMagpieRouterV3 {
event UpdateInternalCaller(address indexed sender, address caller, bool value);
function updateInternalCaller(address caller, bool value) external;
event UpdateBridge(address indexed sender, address caller, bool value);
function updateBridge(address caller, bool value) external;
function updateSwapFeeAddress(address value) external;
function pause() external;
function unpause() external;
event Swap(
address indexed fromAddress,
address indexed toAddress,
address fromAssetAddress,
address toAssetAddress,
uint256 amountIn,
uint256 amountOut
);
function multicall(bytes[] calldata data) external returns (bytes[] memory results);
function estimateSwapGas(bytes calldata swapArgs) external payable returns (uint256 amountOut, uint256 gasUsed);
function swapWithMagpieSignature(bytes calldata swapArgs) external payable returns (uint256 amountOut);
function swapWithUserSignature(bytes calldata swapArgs) external payable returns (uint256 amountOut);
function swapWithoutSignature(bytes calldata swapArgs) external payable returns (uint256 amountOut);
}
文件 8 的 16:IReceiver.sol
pragma solidity 0.8.24;
interface IReceiver {
function receiveMessage(bytes calldata message, bytes calldata signature) external returns (bool success);
}
文件 9 的 16:IWETH.sol
pragma solidity 0.8.24;
interface IWETH {
function deposit() external payable;
function transfer(address to, uint256 value) external returns (bool);
function withdraw(uint256) external;
}
文件 10 的 16:LibAsset.sol
pragma solidity 0.8.24;
import "../interfaces/IWETH.sol";
error AssetNotReceived();
error ApprovalFailed();
error TransferFromFailed();
error TransferFailed();
error FailedWrap();
error FailedUnwrap();
library LibAsset {
using LibAsset for address;
address constant NATIVE_ASSETID = address(0);
function isNative(address self) internal pure returns (bool) {
return self == NATIVE_ASSETID;
}
function wrap(address self, uint256 amount) internal {
uint256 ptr;
assembly {
ptr := mload(0x40)
mstore(0x40, add(ptr, 4))
mstore(ptr, 0xd0e30db000000000000000000000000000000000000000000000000000000000)
}
if (!execute(self, amount, ptr, 4, 0, 0)) {
revert FailedWrap();
}
}
function unwrap(address self, uint256 amount) internal {
uint256 ptr;
assembly {
ptr := mload(0x40)
mstore(0x40, add(ptr, 36))
mstore(ptr, 0x2e1a7d4d00000000000000000000000000000000000000000000000000000000)
mstore(add(ptr, 4), amount)
}
if (!execute(self, 0, ptr, 36, 0, 0)) {
revert FailedUnwrap();
}
}
function getBalance(address self) internal view returns (uint256) {
return getBalanceOf(self, address(this));
}
function getBalanceOf(address self, address targetAddress) internal view returns (uint256 amount) {
assembly {
switch self
case 0 {
amount := balance(targetAddress)
}
default {
let currentInputPtr := mload(0x40)
mstore(0x40, add(currentInputPtr, 68))
mstore(currentInputPtr, 0x70a0823100000000000000000000000000000000000000000000000000000000)
mstore(add(currentInputPtr, 4), targetAddress)
let currentOutputPtr := add(currentInputPtr, 36)
if iszero(staticcall(gas(), self, currentInputPtr, 36, currentOutputPtr, 32)) {
returndatacopy(0, 0, returndatasize())
revert(0, returndatasize())
}
amount := mload(currentOutputPtr)
}
}
}
function transferFrom(address self, address from, address to, uint256 amount) internal {
uint256 ptr;
assembly {
ptr := mload(0x40)
mstore(0x40, add(ptr, 100))
mstore(ptr, 0x23b872dd00000000000000000000000000000000000000000000000000000000)
mstore(add(ptr, 4), from)
mstore(add(ptr, 36), to)
mstore(add(ptr, 68), amount)
}
if (!execute(self, 0, ptr, 100, 0, 0)) {
revert TransferFromFailed();
}
}
function transfer(address self, address recipient, uint256 amount) internal {
if (self.isNative()) {
(bool success, ) = payable(recipient).call{value: amount}("");
if (!success) {
revert TransferFailed();
}
} else {
uint256 ptr;
assembly {
ptr := mload(0x40)
mstore(0x40, add(ptr, 68))
mstore(ptr, 0xa9059cbb00000000000000000000000000000000000000000000000000000000)
mstore(add(ptr, 4), recipient)
mstore(add(ptr, 36), amount)
}
if (!execute(self, 0, ptr, 68, 0, 0)) {
revert TransferFailed();
}
}
}
function approve(address self, address spender, uint256 amount) internal {
uint256 ptr;
assembly {
ptr := mload(0x40)
mstore(0x40, add(ptr, 68))
mstore(ptr, 0x095ea7b300000000000000000000000000000000000000000000000000000000)
mstore(add(ptr, 4), spender)
mstore(add(ptr, 36), amount)
}
if (!execute(self, 0, ptr, 68, 0, 0)) {
assembly {
mstore(add(ptr, 36), 0)
}
if (!execute(self, 0, ptr, 68, 0, 0)) {
revert ApprovalFailed();
}
assembly {
mstore(add(ptr, 36), amount)
}
if (!execute(self, 0, ptr, 68, 0, 0)) {
revert ApprovalFailed();
}
}
}
function permit(
address self,
address owner,
address spender,
uint256 amount,
uint256 deadline,
uint8 v,
bytes32 r,
bytes32 s
) internal {
assembly {
let ptr := mload(0x40)
mstore(0x40, add(ptr, 228))
mstore(ptr, 0xd505accf00000000000000000000000000000000000000000000000000000000)
mstore(add(ptr, 4), owner)
mstore(add(ptr, 36), spender)
mstore(add(ptr, 68), amount)
mstore(add(ptr, 100), deadline)
mstore(add(ptr, 132), v)
mstore(add(ptr, 164), r)
mstore(add(ptr, 196), s)
let success := call(gas(), self, 0, ptr, 228, 0, 0)
}
}
function isSuccessful(address target, bool success, bytes memory data) private view returns (bool result) {
if (success) {
if (data.length == 0) {
if (target.code.length > 0) {
result = true;
}
} else {
assembly {
result := mload(add(data, 32))
}
}
}
}
function execute(
address self,
uint256 currentNativeAmount,
uint256 currentInputPtr,
uint256 currentInputLength,
uint256 currentOutputPtr,
uint256 outputLength
) internal returns (bool result) {
assembly {
function isSuccessfulCall(targetAddress) -> isSuccessful {
switch iszero(returndatasize())
case 1 {
if gt(extcodesize(targetAddress), 0) {
isSuccessful := 1
}
}
case 0 {
returndatacopy(0, 0, 32)
isSuccessful := gt(mload(0), 0)
}
}
if iszero(
call(
gas(),
self,
currentNativeAmount,
currentInputPtr,
currentInputLength,
currentOutputPtr,
outputLength
)
) {
returndatacopy(0, 0, returndatasize())
revert(0, returndatasize())
}
result := isSuccessfulCall(self)
}
}
}
文件 11 的 16:LibBridge.sol
pragma solidity 0.8.24;
import {IMagpieRouterV3} from "../interfaces/IMagpieRouterV3.sol";
import {IBridge} from "../interfaces/IBridge.sol";
import {LibAsset} from "./LibAsset.sol";
import {LibRouter, SwapData} from "./LibRouter.sol";
struct DepositData {
address toAddress;
address fromAssetAddress;
address toAssetAddress;
uint256 amountOutMin;
uint256 swapFee;
uint256 amountIn;
uint16 networkId;
bytes32 senderAddress;
uint64 swapSequence;
}
error InvalidSwapData();
error InvalidSignature();
error InvalidToAddress();
error InvalidAmountIn();
error InvalidSwapFee();
error InvalidDepositAmount();
library LibBridge {
using LibAsset for address;
function getFee(SwapData memory swapData) internal view returns (uint256 bridgeFee) {
bridgeFee = swapData.fromAssetAddress.isNative()
? msg.value - (swapData.amountIn + swapData.swapFee + swapData.affiliateFee)
: msg.value;
}
function decodeDepositDataHash(bytes memory payload) internal pure returns (bytes32 depositDataHash) {
assembly {
depositDataHash := mload(add(payload, 32))
}
}
function encodeDepositDataHash(bytes32 depositDataHash) internal pure returns (bytes memory payload) {
payload = new bytes(32);
assembly {
mstore(add(payload, 32), depositDataHash)
}
}
function getDepositDataHash(
SwapData memory swapData,
uint16 recipientNetworkId,
address recipientAddress
) internal pure returns (bytes32 depositDataHash) {
assembly {
let depositDataPtr := mload(0x40)
mstore(0x40, add(depositDataPtr, 236))
mstore(depositDataPtr, mload(swapData))
mstore(add(depositDataPtr, 32), mload(add(swapData, 32)))
mstore(add(depositDataPtr, 64), mload(add(swapData, 64)))
mstore(add(depositDataPtr, 96), mload(add(swapData, 128)))
mstore(add(depositDataPtr, 128), mload(add(swapData, 160)))
mstore(add(depositDataPtr, 160), shl(240, recipientNetworkId))
mstore(add(depositDataPtr, 162), recipientAddress)
calldatacopy(add(depositDataPtr, 194), shr(240, calldataload(add(66, calldataload(36)))), 42)
depositDataHash := keccak256(depositDataPtr, 236)
}
}
function fillEncodedDepositData(
bytes memory encodedDepositData,
uint16 networkId,
uint64 swapSequence
) internal view {
assembly {
calldatacopy(add(encodedDepositData, 32), shr(240, calldataload(add(66, calldataload(36)))), 194)
mstore(add(encodedDepositData, 226), shl(240, networkId))
mstore(add(encodedDepositData, 228), address())
mstore(add(encodedDepositData, 260), shl(192, swapSequence))
}
}
function swap(address routerAddress, uint256 nativeAmount) private returns (uint256 amountOut, bool success) {
assembly {
let inputPtr := mload(0x40)
let inputLength := shr(240, calldataload(add(66, calldataload(36))))
let payloadLength := sub(inputLength, 68)
mstore(0x40, add(inputPtr, inputLength))
mstore(inputPtr, 0x158f689400000000000000000000000000000000000000000000000000000000)
mstore(add(inputPtr, 4), 32)
mstore(add(inputPtr, 36), payloadLength)
let outputPtr := mload(0x40)
mstore(0x40, add(outputPtr, 32))
calldatacopy(add(inputPtr, 68), 68, payloadLength)
success := call(gas(), routerAddress, nativeAmount, inputPtr, inputLength, outputPtr, 32)
if eq(success, 1) {
amountOut := mload(outputPtr)
}
}
}
function swapIn(
SwapData memory swapData,
bytes memory encodedDepositData,
address fromAddress,
address routerAddress,
address weth
) internal returns (uint256 amountOut) {
if (swapData.toAddress != address(this)) {
revert InvalidToAddress();
}
if (swapData.fromAssetAddress.isNative()) {
if (msg.value < (swapData.amountIn + swapData.swapFee + swapData.affiliateFee)) {
revert InvalidAmountIn();
}
}
if (swapData.fromAssetAddress.isNative() && swapData.toAssetAddress == weth) {
weth.wrap(swapData.amountIn);
amountOut = swapData.amountIn;
} else if (swapData.fromAssetAddress == weth && swapData.toAssetAddress.isNative()) {
swapData.fromAssetAddress.transferFrom(fromAddress, address(this), swapData.amountIn);
weth.unwrap(swapData.amountIn);
amountOut = swapData.amountIn;
} else if (swapData.fromAssetAddress == swapData.toAssetAddress) {
swapData.fromAssetAddress.transferFrom(fromAddress, address(this), swapData.amountIn);
amountOut = swapData.amountIn;
} else {
uint256 nativeAmount = 0;
if (swapData.fromAssetAddress.isNative()) {
nativeAmount = swapData.amountIn;
} else {
swapData.fromAssetAddress.transferFrom(fromAddress, address(this), swapData.amountIn);
swapData.fromAssetAddress.approve(routerAddress, swapData.amountIn);
}
bool success = false;
(amountOut, success) = swap(routerAddress, nativeAmount);
if (!success) {
assembly {
returndatacopy(0, 0, returndatasize())
revert(0, returndatasize())
}
}
}
emit IBridge.SwapIn(
fromAddress,
swapData.toAddress,
swapData.fromAssetAddress,
swapData.toAssetAddress,
swapData.amountIn + swapData.swapFee + swapData.affiliateFee,
amountOut,
encodedDepositData
);
}
function swapOut(
SwapData memory swapData,
uint256 depositAmount,
bytes32 depositDataHash,
address routerAddress,
address weth,
address swapFeeAddress
) internal returns (uint256 amountOut) {
if (depositAmount != swapData.amountIn + swapData.swapFee) {
revert InvalidDepositAmount();
}
if (swapData.swapFee > 0) {
swapData.fromAssetAddress.transfer(swapFeeAddress, swapData.swapFee);
}
if (swapData.amountIn > 0) {
if (swapData.fromAssetAddress == weth && swapData.toAssetAddress.isNative()) {
weth.unwrap(swapData.amountIn);
swapData.fromAssetAddress.transfer(swapData.toAddress, swapData.amountIn);
} else if (swapData.fromAssetAddress.isNative() && swapData.toAssetAddress == weth) {
weth.wrap(swapData.amountIn);
swapData.fromAssetAddress.transfer(swapData.toAddress, swapData.amountIn);
amountOut = swapData.amountIn;
} else if (swapData.fromAssetAddress == swapData.toAssetAddress) {
swapData.fromAssetAddress.transfer(swapData.toAddress, swapData.amountIn);
amountOut = swapData.amountIn;
} else {
uint256 nativeAmount = 0;
if (swapData.fromAssetAddress.isNative()) {
nativeAmount = swapData.amountIn;
} else {
swapData.fromAssetAddress.approve(routerAddress, swapData.amountIn);
}
bool success = false;
(amountOut, success) = swap(routerAddress, nativeAmount);
if (!success) {
if (!swapData.fromAssetAddress.isNative()) {
swapData.fromAssetAddress.approve(routerAddress, 0);
}
swapData.fromAssetAddress.transfer(swapData.toAddress, swapData.amountIn);
swapData.toAssetAddress = swapData.fromAssetAddress;
amountOut = swapData.amountIn;
}
}
}
emit IBridge.SwapOut(
msg.sender,
swapData.toAddress,
swapData.fromAssetAddress,
swapData.toAssetAddress,
swapData.amountIn + swapData.swapFee,
amountOut,
depositDataHash
);
}
}
文件 12 的 16:LibRouter.sol
pragma solidity 0.8.24;
import {LibAsset} from "../libraries/LibAsset.sol";
struct SwapData {
address toAddress;
address fromAssetAddress;
address toAssetAddress;
uint256 deadline;
uint256 amountOutMin;
uint256 swapFee;
uint256 amountIn;
bool hasPermit;
bool hasAffiliate;
address affiliateAddress;
uint256 affiliateFee;
}
error InvalidSignature();
error ExpiredTransaction();
library LibRouter {
using LibAsset for address;
function getData() internal view returns (SwapData memory swapData) {
assembly {
let deadline := shr(
shr(248, calldataload(132)),
calldataload(shr(240, calldataload(133)))
)
if lt(deadline, timestamp()) {
mstore(0, 0x931997cf00000000000000000000000000000000000000000000000000000000)
revert(0, 4)
}
mstore(swapData, shr(96, calldataload(72)))
mstore(add(swapData, 32), shr(96, calldataload(92)))
mstore(add(swapData, 64), shr(96, calldataload(112)))
mstore(add(swapData, 96), deadline)
mstore(
add(swapData, 128),
shr(
shr(248, calldataload(135)),
calldataload(shr(240, calldataload(136)))
)
)
mstore(
add(swapData, 160),
shr(
shr(248, calldataload(138)),
calldataload(shr(240, calldataload(139)))
)
)
mstore(
add(swapData, 192),
shr(
shr(248, calldataload(141)),
calldataload(shr(240, calldataload(142)))
)
)
let hasPermit := gt(shr(248, calldataload(209)), 0)
mstore(add(swapData, 224), hasPermit)
switch hasPermit
case 1 {
let hasAffiliate := shr(248, calldataload(277))
mstore(add(swapData, 256), hasAffiliate)
if eq(hasAffiliate, 1) {
mstore(add(swapData, 288), shr(96, calldataload(278)))
mstore(
add(swapData, 320),
shr(shr(248, calldataload(298)), calldataload(shr(240, calldataload(299))))
)
}
}
default {
let hasAffiliate := shr(248, calldataload(210))
mstore(add(swapData, 256), hasAffiliate)
if eq(hasAffiliate, 1) {
mstore(add(swapData, 288), shr(96, calldataload(211)))
mstore(
add(swapData, 320),
shr(shr(248, calldataload(231)), calldataload(shr(240, calldataload(232))))
)
}
}
}
}
function transferFees(SwapData memory swapData, address fromAddress, address swapFeeAddress) internal {
if (swapData.swapFee > 0) {
if (swapData.fromAssetAddress.isNative()) {
swapData.fromAssetAddress.transfer(swapFeeAddress, swapData.swapFee);
} else {
swapData.fromAssetAddress.transferFrom(fromAddress, swapFeeAddress, swapData.swapFee);
}
}
if (swapData.affiliateFee > 0) {
if (swapData.fromAssetAddress.isNative()) {
swapData.fromAssetAddress.transfer(swapData.affiliateAddress, swapData.affiliateFee);
} else {
swapData.fromAssetAddress.transferFrom(fromAddress, swapData.affiliateAddress, swapData.affiliateFee);
}
}
}
function permit(SwapData memory swapData, address fromAddress) internal {
uint8 v;
bytes32 r;
bytes32 s;
uint256 deadline;
assembly {
v := shr(248, calldataload(209))
r := calldataload(210)
s := calldataload(242)
deadline := shr(shr(248, calldataload(274)), calldataload(shr(240, calldataload(275))))
}
swapData.fromAssetAddress.permit(
fromAddress,
address(this),
swapData.amountIn + swapData.swapFee + swapData.affiliateFee,
deadline,
v,
r,
s
);
}
function recoverSigner(bytes32 hash, bytes32 r, bytes32 s, uint8 v) private pure returns (address signer) {
if (uint256(s) > 0x7FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF5D576E7357A4501DDFE92F46681B20A0) {
revert InvalidSignature();
}
if (v != 27 && v != 28) {
revert InvalidSignature();
}
signer = ecrecover(hash, v, r, s);
if (signer == address(0)) {
revert InvalidSignature();
}
}
function getDomainSeparator(bytes32 name, bytes32 version) private view returns (bytes32) {
uint256 chainId;
assembly {
chainId := chainid()
}
return
keccak256(
abi.encode(
0x8b73c3c69bb8fe3d512ecc4cf759cc79239f7b179b0ffacaa9a75d522b39400f,
name,
version,
chainId,
address(this)
)
);
}
function verifySignature(
bytes32 name,
bytes32 version,
SwapData memory swapData,
uint256 messagePtr,
uint256 messageLength,
bool useCaller,
uint8 internalCallersSlot
) internal view returns (address fromAddress) {
bytes32 domainSeparator = getDomainSeparator(name, version);
bytes32 digest;
bytes32 r;
bytes32 s;
uint8 v;
assembly {
mstore(add(messagePtr, 32), address())
mstore(add(messagePtr, 64), caller())
mstore(add(messagePtr, 96), mload(swapData))
mstore(add(messagePtr, 128), mload(add(swapData, 32)))
mstore(add(messagePtr, 160), mload(add(swapData, 64)))
mstore(add(messagePtr, 192), mload(add(swapData, 96)))
mstore(add(messagePtr, 224), mload(add(swapData, 128)))
mstore(add(messagePtr, 256), mload(add(swapData, 160)))
mstore(add(messagePtr, 288), mload(add(swapData, 192)))
if eq(mload(add(swapData, 256)), 1) {
mstore(add(messagePtr, 320), mload(add(swapData, 288)))
mstore(add(messagePtr, 352), mload(add(swapData, 320)))
}
let hash := keccak256(messagePtr, messageLength)
messagePtr := mload(0x40)
mstore(0x40, add(messagePtr, 66))
mstore(messagePtr, "\x19\x01")
mstore(add(messagePtr, 2), domainSeparator)
mstore(add(messagePtr, 34), hash)
digest := keccak256(messagePtr, 66)
r := calldataload(144)
s := calldataload(176)
v := shr(248, calldataload(208))
}
if (useCaller) {
address internalCaller = recoverSigner(digest, r, s, v);
assembly {
fromAddress := caller()
mstore(0, internalCaller)
mstore(0x20, internalCallersSlot)
if iszero(eq(sload(keccak256(0, 0x40)), 1)) {
mstore(0, 0x8baa579f00000000000000000000000000000000000000000000000000000000)
revert(0, 4)
}
}
} else {
fromAddress = recoverSigner(digest, r, s, v);
if (fromAddress == address(this)) {
revert InvalidSignature();
}
}
}
}
文件 13 的 16:MagpieCCTPBridge.sol
pragma solidity 0.8.24;
import {Ownable2Step} from "openzeppelin-solidity/contracts/access/Ownable2Step.sol";
import {Pausable} from "openzeppelin-solidity/contracts/security/Pausable.sol";
import {Address} from "openzeppelin-solidity/contracts/utils/Address.sol";
import {IMagpieCCTPBridge} from "./interfaces/IMagpieCCTPBridge.sol";
import {IAxelarGateway} from "./interfaces/axelar/IAxelarGateway.sol";
import {IAxelarGasService} from "./interfaces/axelar/IAxelarGasService.sol";
import {IReceiver} from "./interfaces/cctp/IReceiver.sol";
import {LibAsset} from "./libraries/LibAsset.sol";
import {LibBridge, DepositData, SwapData} from "./libraries/LibBridge.sol";
import {LibRouter, SwapData} from "./libraries/LibRouter.sol";
error InvalidCaller();
error ReentrancyError();
error DepositIsNotFound();
error InvalidAddress();
error NotApprovedByGateway();
error MintFailed();
error BurnFailed();
contract MagpieCCTPBridge is IMagpieCCTPBridge, Ownable2Step, Pausable {
using LibAsset for address;
mapping(address => bool) public internalCaller;
address public weth;
bytes32 public networkIdAndRouterAddress;
uint64 public swapSequence;
mapping(bytes32 => mapping(address => uint256)) public deposit;
address public swapFeeAddress;
address public tokenMessengerAddress;
address public messageTransmitterAddress;
address public gatewayAddress;
address public gasReceiverAddress;
modifier onlyInternalCaller() {
if (!internalCaller[msg.sender]) {
revert InvalidCaller();
}
_;
}
function updateInternalCaller(address caller, bool value) external onlyOwner {
internalCaller[caller] = value;
emit UpdateInternalCaller(msg.sender, caller, value);
}
function updateWeth(address value) external onlyOwner {
weth = value;
}
function updateNetworkIdAndRouterAddress(bytes32 value) external onlyOwner {
networkIdAndRouterAddress = value;
}
function updateSwapFeeAddress(address value) external onlyOwner {
swapFeeAddress = value;
}
function updateTokenMessengerAddress(address value) external onlyOwner {
tokenMessengerAddress = value;
}
function updateMessageTransmitterAddress(address value) external onlyOwner {
messageTransmitterAddress = value;
}
function updateGatewayAddress(address value) external onlyOwner {
gatewayAddress = value;
}
function updateGasReceiverAddress(address value) external onlyOwner {
gasReceiverAddress = value;
}
function pause() public onlyOwner whenNotPaused {
_pause();
}
function unpause() public onlyOwner whenPaused {
_unpause();
}
function swapInWithMagpieSignature(bytes calldata) external payable whenNotPaused returns (uint256 amountOut) {
SwapData memory swapData = LibRouter.getData();
amountOut = swapIn(swapData, true);
}
function swapInWithUserSignature(bytes calldata) external payable onlyInternalCaller returns (uint256 amountOut) {
SwapData memory swapData = LibRouter.getData();
if (swapData.fromAssetAddress.isNative()) {
revert InvalidAddress();
}
amountOut = swapIn(swapData, false);
}
function verifySignature(SwapData memory swapData, bool useCaller) private view returns (address) {
uint256 messagePtr;
bool hasAffiliate = swapData.hasAffiliate;
uint256 swapMessageLength = hasAffiliate ? 384 : 320;
uint256 messageLength = swapMessageLength + 320;
assembly {
messagePtr := mload(0x40)
mstore(0x40, add(messagePtr, messageLength))
switch hasAffiliate
case 1 {
mstore(messagePtr, 0x112d7d894fe0b136fbc52b80f6940fb79db28e03d78dd281e952df731f3e5ff1)
}
default {
mstore(messagePtr, 0x6d270d8b96a17d623996c9fcafb1b091927d68dcaab797c0f5dd271e918c2eeb)
}
let bridgeDataPosition := shr(240, calldataload(add(66, calldataload(36))))
let currentMessagePtr := add(messagePtr, swapMessageLength)
mstore(currentMessagePtr, calldataload(bridgeDataPosition))
currentMessagePtr := add(currentMessagePtr, 32)
mstore(currentMessagePtr, calldataload(add(bridgeDataPosition, 32)))
currentMessagePtr := add(currentMessagePtr, 32)
mstore(currentMessagePtr, calldataload(add(bridgeDataPosition, 64)))
currentMessagePtr := add(currentMessagePtr, 32)
mstore(currentMessagePtr, calldataload(add(bridgeDataPosition, 96)))
currentMessagePtr := add(currentMessagePtr, 32)
mstore(currentMessagePtr, calldataload(add(bridgeDataPosition, 128)))
currentMessagePtr := add(currentMessagePtr, 32)
mstore(currentMessagePtr, shr(240, calldataload(add(bridgeDataPosition, 160))))
currentMessagePtr := add(currentMessagePtr, 32)
mstore(currentMessagePtr, calldataload(add(bridgeDataPosition, 162)))
currentMessagePtr := add(currentMessagePtr, 32)
mstore(currentMessagePtr, shr(224, calldataload(add(bridgeDataPosition, 194))))
let bridgeAddressLength := shr(240, calldataload(add(bridgeDataPosition, 198)))
let bridgeAddressPtr := mload(0x40)
calldatacopy(bridgeAddressPtr, add(bridgeDataPosition, 200), bridgeAddressLength)
currentMessagePtr := add(currentMessagePtr, 32)
mstore(currentMessagePtr, keccak256(bridgeAddressPtr, bridgeAddressLength))
let bridgeChainLength := shr(240, calldataload(add(add(bridgeDataPosition, 200), bridgeAddressLength)))
let bridgeChainPtr := add(bridgeAddressPtr, bridgeAddressLength)
calldatacopy(bridgeChainPtr, add(add(bridgeDataPosition, 202), bridgeAddressLength), bridgeChainLength)
mstore(0x40, add(bridgeChainPtr, bridgeChainLength))
currentMessagePtr := add(currentMessagePtr, 32)
mstore(currentMessagePtr, keccak256(bridgeChainPtr, bridgeChainLength))
}
return
LibRouter.verifySignature(
0x31da2c74f8c27ef76897147f0ad12d949a674ee71cd159480d92be2858340871,
0xc89efdaa54c0f20c7adf612882df0950f5a951637e0307cdcb4c672f298b8bc6,
swapData,
messagePtr,
messageLength,
useCaller,
2
);
}
function swapIn(SwapData memory swapData, bool useCaller) private returns (uint256 amountOut) {
swapSequence++;
uint64 currentSwapSequence = swapSequence;
uint16 networkId;
address routerAddress;
assembly {
let currentNetworkIdAndRouterAddress := sload(networkIdAndRouterAddress.slot)
networkId := shr(240, currentNetworkIdAndRouterAddress)
routerAddress := shr(16, shl(16, currentNetworkIdAndRouterAddress))
}
address fromAddress = verifySignature(swapData, useCaller);
if (swapData.hasPermit) {
LibRouter.permit(swapData, fromAddress);
}
LibRouter.transferFees(swapData, fromAddress, swapData.swapFee == 0 ? address(0) : swapFeeAddress);
bytes memory encodedDepositData = new bytes(236);
LibBridge.fillEncodedDepositData(encodedDepositData, networkId, currentSwapSequence);
bytes32 depositDataHash = keccak256(encodedDepositData);
amountOut = LibBridge.swapIn(swapData, encodedDepositData, fromAddress, routerAddress, weth);
bridgeIn(LibBridge.getFee(swapData), fromAddress, swapData.toAssetAddress, amountOut, depositDataHash);
if (currentSwapSequence != swapSequence) {
revert ReentrancyError();
}
}
function bridgeIn(
uint256 transferFee,
address refundAddress,
address toAssetAddress,
uint256 amount,
bytes32 depositDataHash
) private {
toAssetAddress.approve(tokenMessengerAddress, amount);
uint256 ptr;
assembly {
let bridgeDataPosition := shr(240, calldataload(add(66, calldataload(36))))
ptr := mload(0x40)
mstore(0x40, add(ptr, 196))
mstore(ptr, 0xf856ddb600000000000000000000000000000000000000000000000000000000)
mstore(add(ptr, 4), amount)
mstore(add(ptr, 36), shr(224, calldataload(add(bridgeDataPosition, 194))))
mstore(add(ptr, 68), calldataload(add(bridgeDataPosition, 162)))
mstore(add(ptr, 100), toAssetAddress)
mstore(add(ptr, 132), calldataload(add(bridgeDataPosition, 162)))
}
if (!tokenMessengerAddress.execute(0, ptr, 164, ptr + 164, 32)) {
revert BurnFailed();
}
dataIn(transferFee, depositDataHash, amount, refundAddress);
}
function dataIn(uint256 transferFee, bytes32 depositDataHash, uint256 amount, address refundAddress) private {
bytes memory payload = new bytes(96);
string memory bridgeAddress;
string memory bridgeChain;
assembly {
let bridgeDataPosition := shr(240, calldataload(add(66, calldataload(36))))
let bridgeAddressLength := shr(240, calldataload(add(bridgeDataPosition, 198)))
bridgeAddress := mload(0x40)
mstore(bridgeAddress, bridgeAddressLength)
calldatacopy(add(bridgeAddress, 32), add(bridgeDataPosition, 200), bridgeAddressLength)
let bridgeChainLength := shr(240, calldataload(add(add(bridgeDataPosition, 200), bridgeAddressLength)))
bridgeChain := add(add(bridgeAddress, 32), bridgeAddressLength)
mstore(bridgeChain, bridgeChainLength)
calldatacopy(
add(bridgeChain, 32),
add(add(bridgeDataPosition, 202), bridgeAddressLength),
bridgeChainLength
)
mstore(0x40, add(add(bridgeChain, 32), bridgeChainLength))
mstore(add(payload, 32), depositDataHash)
mstore(add(payload, 64), amount)
mstore(add(payload, 96), calldataload(add(bridgeDataPosition, 32)))
}
IAxelarGasService(gasReceiverAddress).payNativeGasForContractCall{value: transferFee}(
address(this),
bridgeChain,
bridgeAddress,
payload,
refundAddress
);
IAxelarGateway(gatewayAddress).callContract(bridgeChain, bridgeAddress, payload);
}
event Deposit(bytes32 depositDataHash, uint256 amount);
function execute(
bytes32 commandId,
string calldata sourceChain,
string calldata sourceAddress,
bytes calldata payload
) external {
if (
!IAxelarGateway(gatewayAddress).validateContractCall(
commandId,
sourceChain,
sourceAddress,
keccak256(payload)
)
) {
revert NotApprovedByGateway();
}
addDeposit(payload);
}
function addDeposit(bytes memory payload) private {
bytes32 depositDataHash;
uint256 amount;
address assetAddress;
assembly {
depositDataHash := mload(add(payload, 32))
amount := mload(add(payload, 64))
assetAddress := mload(add(payload, 96))
}
deposit[depositDataHash][assetAddress] += amount;
emit Deposit(depositDataHash, amount);
}
function swapOut(bytes calldata) external onlyInternalCaller returns (uint256 amountOut) {
address routerAddress;
uint16 networkId;
assembly {
let currentNetworkIdAndRouterAddress := sload(networkIdAndRouterAddress.slot)
networkId := shr(240, currentNetworkIdAndRouterAddress)
routerAddress := shr(16, shl(16, currentNetworkIdAndRouterAddress))
}
SwapData memory swapData = LibRouter.getData();
bytes memory message;
bytes memory attestation;
uint256 messageAmount;
assembly {
let cctpBridgeDataPosition := add(shr(240, calldataload(add(66, calldataload(36)))), 42)
let messageLength := shr(240, calldataload(cctpBridgeDataPosition))
message := mload(0x40)
mstore(message, messageLength)
calldatacopy(add(message, 32), add(cctpBridgeDataPosition, 2), messageLength)
let attestationLength := shr(240, calldataload(add(add(cctpBridgeDataPosition, 2), messageLength)))
attestation := add(add(message, 32), messageLength)
mstore(attestation, attestationLength)
calldatacopy(add(attestation, 32), add(add(cctpBridgeDataPosition, 4), messageLength), attestationLength)
mstore(0x40, add(add(attestation, 32), attestationLength))
messageAmount := mload(add(message, 216))
}
if (!IReceiver(messageTransmitterAddress).receiveMessage(message, attestation)) {
revert MintFailed();
}
bytes32 depositDataHash = LibBridge.getDepositDataHash(swapData, networkId, address(this));
uint256 depositAmount = deposit[depositDataHash][swapData.fromAssetAddress];
if (depositAmount == 0 || messageAmount != depositAmount) {
revert DepositIsNotFound();
}
deposit[depositDataHash][swapData.fromAssetAddress] = 0;
amountOut = LibBridge.swapOut(swapData, depositAmount, depositDataHash, routerAddress, weth, swapFeeAddress);
}
function multicall(bytes[] calldata data) external onlyOwner returns (bytes[] memory results) {
results = new bytes[](data.length);
for (uint256 i = 0; i < data.length; i++) {
results[i] = Address.functionDelegateCall(address(this), data[i]);
}
return results;
}
receive() external payable {}
}
文件 14 的 16:Ownable.sol
pragma solidity ^0.8.0;
import "../utils/Context.sol";
abstract contract Ownable is Context {
address private _owner;
event OwnershipTransferred(address indexed previousOwner, address indexed newOwner);
constructor() {
_transferOwnership(_msgSender());
}
modifier onlyOwner() {
_checkOwner();
_;
}
function owner() public view virtual returns (address) {
return _owner;
}
function _checkOwner() internal view virtual {
require(owner() == _msgSender(), "Ownable: caller is not the owner");
}
function renounceOwnership() public virtual onlyOwner {
_transferOwnership(address(0));
}
function transferOwnership(address newOwner) public virtual onlyOwner {
require(newOwner != address(0), "Ownable: new owner is the zero address");
_transferOwnership(newOwner);
}
function _transferOwnership(address newOwner) internal virtual {
address oldOwner = _owner;
_owner = newOwner;
emit OwnershipTransferred(oldOwner, newOwner);
}
}
文件 15 的 16:Ownable2Step.sol
pragma solidity ^0.8.0;
import "./Ownable.sol";
abstract contract Ownable2Step is Ownable {
address private _pendingOwner;
event OwnershipTransferStarted(address indexed previousOwner, address indexed newOwner);
function pendingOwner() public view virtual returns (address) {
return _pendingOwner;
}
function transferOwnership(address newOwner) public virtual override onlyOwner {
_pendingOwner = newOwner;
emit OwnershipTransferStarted(owner(), newOwner);
}
function _transferOwnership(address newOwner) internal virtual override {
delete _pendingOwner;
super._transferOwnership(newOwner);
}
function acceptOwnership() public virtual {
address sender = _msgSender();
require(pendingOwner() == sender, "Ownable2Step: caller is not the new owner");
_transferOwnership(sender);
}
}
文件 16 的 16:Pausable.sol
pragma solidity ^0.8.0;
import "../utils/Context.sol";
abstract contract Pausable is Context {
event Paused(address account);
event Unpaused(address account);
bool private _paused;
constructor() {
_paused = false;
}
modifier whenNotPaused() {
_requireNotPaused();
_;
}
modifier whenPaused() {
_requirePaused();
_;
}
function paused() public view virtual returns (bool) {
return _paused;
}
function _requireNotPaused() internal view virtual {
require(!paused(), "Pausable: paused");
}
function _requirePaused() internal view virtual {
require(paused(), "Pausable: not paused");
}
function _pause() internal virtual whenNotPaused {
_paused = true;
emit Paused(_msgSender());
}
function _unpause() internal virtual whenPaused {
_paused = false;
emit Unpaused(_msgSender());
}
}
{
"compilationTarget": {
"contracts/MagpieCCTPBridge.sol": "MagpieCCTPBridge"
},
"evmVersion": "paris",
"libraries": {},
"metadata": {
"bytecodeHash": "ipfs",
"useLiteralContent": true
},
"optimizer": {
"enabled": true,
"runs": 200
},
"remappings": []
}
[{"inputs":[],"name":"ApprovalFailed","type":"error"},{"inputs":[],"name":"BurnFailed","type":"error"},{"inputs":[],"name":"DepositIsNotFound","type":"error"},{"inputs":[],"name":"FailedUnwrap","type":"error"},{"inputs":[],"name":"FailedWrap","type":"error"},{"inputs":[],"name":"InvalidAddress","type":"error"},{"inputs":[],"name":"InvalidAmountIn","type":"error"},{"inputs":[],"name":"InvalidCaller","type":"error"},{"inputs":[],"name":"InvalidDepositAmount","type":"error"},{"inputs":[],"name":"InvalidSignature","type":"error"},{"inputs":[],"name":"InvalidToAddress","type":"error"},{"inputs":[],"name":"MintFailed","type":"error"},{"inputs":[],"name":"NotApprovedByGateway","type":"error"},{"inputs":[],"name":"ReentrancyError","type":"error"},{"inputs":[],"name":"TransferFailed","type":"error"},{"inputs":[],"name":"TransferFromFailed","type":"error"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"bytes32","name":"depositDataHash","type":"bytes32"},{"indexed":false,"internalType":"uint256","name":"amount","type":"uint256"}],"name":"Deposit","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"previousOwner","type":"address"},{"indexed":true,"internalType":"address","name":"newOwner","type":"address"}],"name":"OwnershipTransferStarted","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":false,"internalType":"address","name":"account","type":"address"}],"name":"Paused","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"fromAddress","type":"address"},{"indexed":true,"internalType":"address","name":"toAddress","type":"address"},{"indexed":false,"internalType":"address","name":"fromAssetAddress","type":"address"},{"indexed":false,"internalType":"address","name":"toAssetAddress","type":"address"},{"indexed":false,"internalType":"uint256","name":"amountIn","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"amountOut","type":"uint256"},{"indexed":false,"internalType":"bytes","name":"encodedDepositData","type":"bytes"}],"name":"SwapIn","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"fromAddress","type":"address"},{"indexed":true,"internalType":"address","name":"toAddress","type":"address"},{"indexed":false,"internalType":"address","name":"fromAssetAddress","type":"address"},{"indexed":false,"internalType":"address","name":"toAssetAddress","type":"address"},{"indexed":false,"internalType":"uint256","name":"amountIn","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"amountOut","type":"uint256"},{"indexed":false,"internalType":"bytes32","name":"depositDataHash","type":"bytes32"}],"name":"SwapOut","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"account","type":"address"}],"name":"Unpaused","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"sender","type":"address"},{"indexed":false,"internalType":"address","name":"caller","type":"address"},{"indexed":false,"internalType":"bool","name":"value","type":"bool"}],"name":"UpdateInternalCaller","type":"event"},{"inputs":[],"name":"acceptOwnership","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"","type":"bytes32"},{"internalType":"address","name":"","type":"address"}],"name":"deposit","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes32","name":"commandId","type":"bytes32"},{"internalType":"string","name":"sourceChain","type":"string"},{"internalType":"string","name":"sourceAddress","type":"string"},{"internalType":"bytes","name":"payload","type":"bytes"}],"name":"execute","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"gasReceiverAddress","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"gatewayAddress","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"","type":"address"}],"name":"internalCaller","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"messageTransmitterAddress","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes[]","name":"data","type":"bytes[]"}],"name":"multicall","outputs":[{"internalType":"bytes[]","name":"results","type":"bytes[]"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"networkIdAndRouterAddress","outputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"owner","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"pause","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"paused","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"pendingOwner","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"renounceOwnership","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"swapFeeAddress","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes","name":"","type":"bytes"}],"name":"swapInWithMagpieSignature","outputs":[{"internalType":"uint256","name":"amountOut","type":"uint256"}],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"bytes","name":"","type":"bytes"}],"name":"swapInWithUserSignature","outputs":[{"internalType":"uint256","name":"amountOut","type":"uint256"}],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"bytes","name":"","type":"bytes"}],"name":"swapOut","outputs":[{"internalType":"uint256","name":"amountOut","type":"uint256"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"swapSequence","outputs":[{"internalType":"uint64","name":"","type":"uint64"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"tokenMessengerAddress","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"newOwner","type":"address"}],"name":"transferOwnership","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"unpause","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"value","type":"address"}],"name":"updateGasReceiverAddress","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"value","type":"address"}],"name":"updateGatewayAddress","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"caller","type":"address"},{"internalType":"bool","name":"value","type":"bool"}],"name":"updateInternalCaller","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"value","type":"address"}],"name":"updateMessageTransmitterAddress","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"value","type":"bytes32"}],"name":"updateNetworkIdAndRouterAddress","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"value","type":"address"}],"name":"updateSwapFeeAddress","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"value","type":"address"}],"name":"updateTokenMessengerAddress","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"value","type":"address"}],"name":"updateWeth","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"weth","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"stateMutability":"payable","type":"receive"}]