@across-protocol/contracts 3.0.17 → 3.0.19
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +2 -0
- package/artifacts/build-info/9cb910e5bb5dd730cd01af84a0fb0466.json +1 -0
- package/artifacts/contracts/Ink_SpokePool.sol/Ink_SpokePool.dbg.json +4 -0
- package/artifacts/contracts/Ink_SpokePool.sol/Ink_SpokePool.json +2316 -0
- package/contracts/Ink_SpokePool.sol +72 -0
- package/dist/deploy/consts.js +8 -2
- package/dist/deployments/deployments.json +7 -1
- package/dist/hardhat.config.js +17 -0
- package/dist/scripts/svm/addressToPublicKey.d.ts +1 -0
- package/dist/scripts/svm/addressToPublicKey.js +20 -0
- package/dist/scripts/svm/bridgeLiabilityToHubPool.d.ts +25 -0
- package/dist/scripts/svm/bridgeLiabilityToHubPool.js +221 -0
- package/dist/scripts/svm/closeRelayerPdas.js +8 -9
- package/dist/scripts/svm/enableRoute.js +7 -1
- package/dist/scripts/svm/executeRebalanceToHubPool.d.ts +29 -0
- package/dist/scripts/svm/executeRebalanceToHubPool.js +345 -0
- package/dist/scripts/svm/executeRebalanceToSpokePool.d.ts +1 -0
- package/dist/scripts/svm/executeRebalanceToSpokePool.js +240 -0
- package/dist/scripts/svm/fakeFillWithRandomDistribution.js +6 -7
- package/dist/scripts/svm/initialize.js +2 -2
- package/dist/scripts/svm/proposeRebalanceToHubPool.d.ts +27 -0
- package/dist/scripts/svm/proposeRebalanceToHubPool.js +117 -0
- package/dist/scripts/svm/proposeRebalanceToSpokePool.d.ts +1 -0
- package/dist/scripts/svm/proposeRebalanceToSpokePool.js +97 -0
- package/dist/scripts/svm/publicKeyToAddress.d.ts +1 -0
- package/dist/scripts/svm/publicKeyToAddress.js +20 -0
- package/dist/scripts/svm/queryDeposits.js +3 -2
- package/dist/scripts/svm/queryFills.js +12 -14
- package/dist/scripts/svm/queryRoute.js +7 -1
- package/dist/scripts/svm/queryState.js +1 -0
- package/dist/scripts/svm/remoteHubPoolPauseDeposits.d.ts +1 -0
- package/dist/scripts/svm/remoteHubPoolPauseDeposits.js +191 -0
- package/dist/scripts/svm/remoteHubPoolSetDepositRoute.js +16 -29
- package/dist/scripts/svm/remotePauseDeposits.js +21 -27
- package/dist/scripts/svm/simpleDeposit.js +7 -1
- package/dist/scripts/svm/simpleFakeRelayerRepayment.js +3 -3
- package/dist/scripts/svm/simpleFill.js +6 -6
- package/dist/scripts/svm/utils/constants.d.ts +4 -0
- package/dist/scripts/svm/utils/constants.js +8 -1
- package/dist/scripts/svm/utils/helpers.d.ts +33 -0
- package/dist/scripts/svm/utils/helpers.js +60 -1
- package/dist/scripts/svm/utils/poolRebalanceTree.d.ts +22 -0
- package/dist/scripts/svm/utils/poolRebalanceTree.js +20 -0
- package/dist/src/svm/coders.d.ts +37 -0
- package/dist/src/svm/coders.js +250 -0
- package/dist/src/svm/conversionUtils.d.ts +22 -0
- package/dist/src/svm/conversionUtils.js +73 -0
- package/dist/src/svm/index.d.ts +6 -0
- package/dist/src/svm/index.js +22 -0
- package/dist/src/svm/instructionParamsUtils.d.ts +31 -0
- package/dist/src/svm/instructionParamsUtils.js +128 -0
- package/dist/src/svm/relayHashUtils.d.ts +30 -0
- package/dist/src/svm/relayHashUtils.js +209 -0
- package/dist/src/svm/solanaProgramUtils.d.ts +38 -0
- package/dist/src/svm/solanaProgramUtils.js +147 -0
- package/dist/src/svm/transactionUtils.d.ts +8 -0
- package/dist/src/svm/transactionUtils.js +55 -0
- package/dist/src/types/svm.d.ts +118 -0
- package/dist/src/types/svm.js +2 -0
- package/dist/target/types/svm_spoke.d.ts +47 -42
- package/dist/tasks/enableL1TokenAcrossEcosystem.js +3 -33
- package/dist/tasks/types.d.ts +2 -0
- package/dist/tasks/types.js +2 -0
- package/dist/tasks/utils.d.ts +12 -0
- package/dist/tasks/utils.js +34 -0
- package/dist/test/svm/MulticallHandler.js +2 -2
- package/dist/test/svm/SvmSpoke.Bundle.js +59 -60
- package/dist/test/svm/SvmSpoke.Deposit.js +23 -31
- package/dist/test/svm/SvmSpoke.Fill.AcrossPlus.js +16 -18
- package/dist/test/svm/SvmSpoke.Fill.js +38 -40
- package/dist/test/svm/SvmSpoke.HandleReceiveMessage.js +2 -2
- package/dist/test/svm/SvmSpoke.Ownership.js +11 -17
- package/dist/test/svm/SvmSpoke.RefundClaims.js +12 -11
- package/dist/test/svm/SvmSpoke.Routes.js +11 -7
- package/dist/test/svm/SvmSpoke.SlowFill.AcrossPlus.js +72 -16
- package/dist/test/svm/SvmSpoke.SlowFill.js +33 -28
- package/dist/test/svm/SvmSpoke.TokenBridge.js +15 -17
- package/dist/test/svm/SvmSpoke.common.d.ts +1 -49
- package/dist/test/svm/SvmSpoke.common.js +6 -5
- package/dist/test/svm/cctpHelpers.js +2 -2
- package/dist/test/svm/utils.d.ts +5 -67
- package/dist/test/svm/utils.js +10 -220
- package/dist/typechain/contracts/Ink_SpokePool.d.ts +1251 -0
- package/dist/typechain/contracts/Ink_SpokePool.js +2 -0
- package/dist/typechain/contracts/index.d.ts +1 -0
- package/dist/typechain/factories/contracts/Ink_SpokePool__factory.d.ts +1833 -0
- package/dist/typechain/factories/contracts/Ink_SpokePool__factory.js +2347 -0
- package/dist/typechain/factories/contracts/index.d.ts +1 -0
- package/dist/typechain/factories/contracts/index.js +3 -1
- package/dist/typechain/hardhat.d.ts +9 -0
- package/dist/typechain/index.d.ts +2 -0
- package/dist/typechain/index.js +5 -3
- package/package.json +2 -2
- package/dist/src/SvmUtils.d.ts +0 -50
- package/dist/src/SvmUtils.js +0 -415
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Script: Propose Root Bundle for USDC Rebalance to Hub Pool
|
|
3
|
+
*
|
|
4
|
+
* Submits a root bundle proposal on the Hub Pool to rebalance USDC from the Solana Spoke Pool to the Ethereum Hub Pool.
|
|
5
|
+
* After submission and the liveness period, the rebalance can be executed with `executeRebalanceToHubPool.ts`.
|
|
6
|
+
*
|
|
7
|
+
* Required Environment Variables:
|
|
8
|
+
* - TESTNET: (Optional) Set to "true" to use Sepolia; defaults to mainnet.
|
|
9
|
+
* - MNEMONIC: Wallet mnemonic to sign the Ethereum transaction.
|
|
10
|
+
* - HUB_POOL_ADDRESS: Ethereum address of the Hub Pool.
|
|
11
|
+
* - NODE_URL_1: Ethereum RPC URL for mainnet (ignored if TESTNET=true).
|
|
12
|
+
* - NODE_URL_11155111: Ethereum RPC URL for Sepolia (ignored if TESTNET=false).
|
|
13
|
+
*
|
|
14
|
+
* Required Argument:
|
|
15
|
+
* - `--netSendAmount`: The unscaled amount of USDC to rebalance. (e.g., for USDC with 6 decimals, 1 = 0.000001 USDC).
|
|
16
|
+
*
|
|
17
|
+
* Example Usage:
|
|
18
|
+
* TESTNET=true \
|
|
19
|
+
* NODE_URL_11155111=$NODE_URL_11155111 \
|
|
20
|
+
* MNEMONIC=$MNEMONIC \
|
|
21
|
+
* HUB_POOL_ADDRESS=$HUB_POOL_ADDRESS \
|
|
22
|
+
* anchor run proposeRebalanceToHubPool -- --netSendAmount 7
|
|
23
|
+
*
|
|
24
|
+
* Note:
|
|
25
|
+
* Ensure the required environment variables are set before running this script.
|
|
26
|
+
*/
|
|
27
|
+
export {};
|
|
@@ -0,0 +1,117 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
/**
|
|
3
|
+
* Script: Propose Root Bundle for USDC Rebalance to Hub Pool
|
|
4
|
+
*
|
|
5
|
+
* Submits a root bundle proposal on the Hub Pool to rebalance USDC from the Solana Spoke Pool to the Ethereum Hub Pool.
|
|
6
|
+
* After submission and the liveness period, the rebalance can be executed with `executeRebalanceToHubPool.ts`.
|
|
7
|
+
*
|
|
8
|
+
* Required Environment Variables:
|
|
9
|
+
* - TESTNET: (Optional) Set to "true" to use Sepolia; defaults to mainnet.
|
|
10
|
+
* - MNEMONIC: Wallet mnemonic to sign the Ethereum transaction.
|
|
11
|
+
* - HUB_POOL_ADDRESS: Ethereum address of the Hub Pool.
|
|
12
|
+
* - NODE_URL_1: Ethereum RPC URL for mainnet (ignored if TESTNET=true).
|
|
13
|
+
* - NODE_URL_11155111: Ethereum RPC URL for Sepolia (ignored if TESTNET=false).
|
|
14
|
+
*
|
|
15
|
+
* Required Argument:
|
|
16
|
+
* - `--netSendAmount`: The unscaled amount of USDC to rebalance. (e.g., for USDC with 6 decimals, 1 = 0.000001 USDC).
|
|
17
|
+
*
|
|
18
|
+
* Example Usage:
|
|
19
|
+
* TESTNET=true \
|
|
20
|
+
* NODE_URL_11155111=$NODE_URL_11155111 \
|
|
21
|
+
* MNEMONIC=$MNEMONIC \
|
|
22
|
+
* HUB_POOL_ADDRESS=$HUB_POOL_ADDRESS \
|
|
23
|
+
* anchor run proposeRebalanceToHubPool -- --netSendAmount 7
|
|
24
|
+
*
|
|
25
|
+
* Note:
|
|
26
|
+
* Ensure the required environment variables are set before running this script.
|
|
27
|
+
*/
|
|
28
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
29
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
30
|
+
};
|
|
31
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
32
|
+
const web3_js_1 = require("@solana/web3.js");
|
|
33
|
+
const common_1 = require("@uma/common");
|
|
34
|
+
const ethers_1 = require("ethers");
|
|
35
|
+
const yargs_1 = __importDefault(require("yargs"));
|
|
36
|
+
const helpers_1 = require("yargs/helpers");
|
|
37
|
+
const typechain_1 = require("../../typechain");
|
|
38
|
+
const constants_1 = require("../../utils/constants");
|
|
39
|
+
const constants_2 = require("./utils/constants");
|
|
40
|
+
const helpers_2 = require("./utils/helpers");
|
|
41
|
+
// Set up Ethereum provider and signer.
|
|
42
|
+
const nodeURL = process.env.TESTNET === "true" ? (0, common_1.getNodeUrl)("sepolia", true) : (0, common_1.getNodeUrl)("mainnet", true);
|
|
43
|
+
const ethersProvider = new ethers_1.ethers.providers.JsonRpcProvider(nodeURL);
|
|
44
|
+
const ethersSigner = ethers_1.ethers.Wallet.fromMnemonic((0, helpers_2.requireEnv)("MNEMONIC")).connect(ethersProvider);
|
|
45
|
+
// Get the HubPool contract instance.
|
|
46
|
+
const hubPoolAddress = ethers_1.ethers.utils.getAddress((0, helpers_2.requireEnv)("HUB_POOL_ADDRESS"));
|
|
47
|
+
const hubPool = typechain_1.HubPool__factory.connect(hubPoolAddress, ethersProvider);
|
|
48
|
+
// Parse arguments.
|
|
49
|
+
const argv = (0, yargs_1.default)((0, helpers_1.hideBin)(process.argv)).option("netSendAmount", {
|
|
50
|
+
type: "string",
|
|
51
|
+
demandOption: true,
|
|
52
|
+
describe: "Net send amount to Hub Pool from Solana Spoke Pool",
|
|
53
|
+
}).argv;
|
|
54
|
+
async function proposeRebalanceToHubPool() {
|
|
55
|
+
const resolvedArgv = await argv;
|
|
56
|
+
const netSendAmount = ethers_1.BigNumber.from(resolvedArgv.netSendAmount);
|
|
57
|
+
// Resolve chain IDs and USDC address.
|
|
58
|
+
const evmChainId = (await ethersProvider.getNetwork()).chainId;
|
|
59
|
+
if (evmChainId !== constants_1.CHAIN_IDs.MAINNET && evmChainId !== constants_1.CHAIN_IDs.SEPOLIA) {
|
|
60
|
+
throw new Error("Unsupported EVM chain ID");
|
|
61
|
+
}
|
|
62
|
+
// If evmChainId is mainnet, use mainnet solana cluster. Otherwise, use devnet.
|
|
63
|
+
const solanaCluster = evmChainId === constants_1.CHAIN_IDs.MAINNET ? "mainnet" : "devnet";
|
|
64
|
+
const solanaChainId = (0, helpers_2.getSolanaChainId)(solanaCluster);
|
|
65
|
+
const svmUsdc = evmChainId === constants_1.CHAIN_IDs.MAINNET ? constants_2.SOLANA_USDC_MAINNET : constants_2.SOLANA_USDC_DEVNET;
|
|
66
|
+
// Check there are no active proposals.
|
|
67
|
+
const currentRootBundleProposal = await hubPool.callStatic.rootBundleProposal();
|
|
68
|
+
if (currentRootBundleProposal.unclaimedPoolRebalanceLeafCount !== 0) {
|
|
69
|
+
throw new Error("Proposal has unclaimed leaves");
|
|
70
|
+
}
|
|
71
|
+
// Ensure bond token balance and approval is sufficient.
|
|
72
|
+
const bondTokenAddress = await hubPool.callStatic.bondToken();
|
|
73
|
+
const bondAmount = await hubPool.callStatic.bondAmount();
|
|
74
|
+
const bondToken = typechain_1.BondToken__factory.connect(bondTokenAddress, ethersProvider);
|
|
75
|
+
const bondBalance = await bondToken.callStatic.balanceOf(ethersSigner.address);
|
|
76
|
+
if (bondBalance.lt(bondAmount)) {
|
|
77
|
+
const ethDeposit = bondAmount.sub(bondBalance);
|
|
78
|
+
console.log(`Depositing ${ethers_1.ethers.utils.formatUnits(ethDeposit.toString())} ETH into bond token:`);
|
|
79
|
+
const tx = await bondToken.connect(ethersSigner).deposit({ value: ethDeposit });
|
|
80
|
+
console.log(`✅ submitted tx hash: ${tx.hash}`);
|
|
81
|
+
await tx.wait();
|
|
82
|
+
console.log("✅ tx confirmed");
|
|
83
|
+
}
|
|
84
|
+
const allowance = await bondToken.callStatic.allowance(ethersSigner.address, hubPool.address);
|
|
85
|
+
if (allowance.lt(bondAmount)) {
|
|
86
|
+
console.log(`Approving ${ethers_1.ethers.utils.formatUnits(bondAmount.toString())} bond tokens for HubPool:`);
|
|
87
|
+
const tx = await bondToken.connect(ethersSigner).approve(hubPool.address, bondAmount);
|
|
88
|
+
console.log(`✅ submitted tx hash: ${tx.hash}`);
|
|
89
|
+
await tx.wait();
|
|
90
|
+
console.log("✅ tx confirmed");
|
|
91
|
+
}
|
|
92
|
+
// Construct an empty pool rebalance tree as we need to propose at least one leaf.
|
|
93
|
+
const { poolRebalanceTree } = (0, helpers_2.constructEmptyPoolRebalanceTree)(solanaChainId, 0);
|
|
94
|
+
// Relayer refund root Merkle tree.
|
|
95
|
+
const { merkleTree } = (0, helpers_2.constructSimpleRebalanceTreeToHubPool)(netSendAmount, solanaChainId, new web3_js_1.PublicKey(svmUsdc));
|
|
96
|
+
console.log("Proposing rebalance pool bundle to spoke...");
|
|
97
|
+
console.table([
|
|
98
|
+
{ Property: "isTestnet", Value: process.env.TESTNET === "true" },
|
|
99
|
+
{ Property: "originChainId", Value: evmChainId.toString() },
|
|
100
|
+
{ Property: "targetChainId", Value: solanaChainId.toString() },
|
|
101
|
+
{ Property: "hubPoolAddress", Value: hubPool.address },
|
|
102
|
+
{ Property: "netSendAmount (formatted)", Value: (0, helpers_2.formatUsdc)(netSendAmount) },
|
|
103
|
+
{ Property: "poolRebalanceRoot", Value: poolRebalanceTree.getHexRoot() },
|
|
104
|
+
{ Property: "relayerRefundRoot", Value: merkleTree.getHexRoot() },
|
|
105
|
+
]);
|
|
106
|
+
console.log("Submitting proposal...");
|
|
107
|
+
const tx = await hubPool.connect(ethersSigner).proposeRootBundle([0], // bundleEvaluationBlockNumbers, not checked in this script.
|
|
108
|
+
1, // poolRebalanceLeafCount, only one leaf in this script.
|
|
109
|
+
poolRebalanceTree.getHexRoot(), // poolRebalanceRoot.
|
|
110
|
+
merkleTree.getHexRoot(), // relayerRefundRoot.
|
|
111
|
+
ethers_1.ethers.constants.HashZero // slowRelayRoot.
|
|
112
|
+
);
|
|
113
|
+
await tx.wait();
|
|
114
|
+
console.log("✅ proposal submitted");
|
|
115
|
+
}
|
|
116
|
+
// Run the proposeRebalanceToHubPool function.
|
|
117
|
+
proposeRebalanceToHubPool();
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1,97 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
// This script proposes root bundle on HubPool that would rebalance tokens to Solana Spoke Pool once executed.
|
|
3
|
+
// Required environment:
|
|
4
|
+
// - TESTNET: (Optional) Set to "true" to use Sepolia; defaults to mainnet.
|
|
5
|
+
// - MNEMONIC: Wallet mnemonic to sign the Ethereum transaction.
|
|
6
|
+
// - HUB_POOL_ADDRESS: Hub Pool address
|
|
7
|
+
// - NODE_URL_1: Ethereum RPC URL for mainnet (ignored if TESTNET=true).
|
|
8
|
+
// - NODE_URL_11155111: Ethereum RPC URL for Sepolia (ignored if TESTNET=false).
|
|
9
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
10
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
11
|
+
};
|
|
12
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
13
|
+
// eslint-disable-next-line camelcase
|
|
14
|
+
const constants_1 = require("../../utils/constants");
|
|
15
|
+
const yargs_1 = __importDefault(require("yargs"));
|
|
16
|
+
const helpers_1 = require("yargs/helpers");
|
|
17
|
+
const ethers_1 = require("ethers");
|
|
18
|
+
const common_1 = require("@uma/common");
|
|
19
|
+
// eslint-disable-next-line camelcase
|
|
20
|
+
const typechain_1 = require("../../typechain");
|
|
21
|
+
const poolRebalanceTree_1 = require("./utils/poolRebalanceTree");
|
|
22
|
+
const helpers_2 = require("./utils/helpers");
|
|
23
|
+
// Set up Ethereum provider.
|
|
24
|
+
const nodeURL = process.env.TESTNET === "true" ? (0, common_1.getNodeUrl)("sepolia", true) : (0, common_1.getNodeUrl)("mainnet", true);
|
|
25
|
+
const ethersProvider = new ethers_1.ethers.providers.JsonRpcProvider(nodeURL);
|
|
26
|
+
const ethersSigner = ethers_1.ethers.Wallet.fromMnemonic((0, helpers_2.requireEnv)("MNEMONIC")).connect(ethersProvider);
|
|
27
|
+
// Get the HubPool contract instance.
|
|
28
|
+
const hubPoolAddress = ethers_1.ethers.utils.getAddress((0, helpers_2.requireEnv)("HUB_POOL_ADDRESS"));
|
|
29
|
+
const hubPool = typechain_1.HubPool__factory.connect(hubPoolAddress, ethersProvider);
|
|
30
|
+
// Parse arguments
|
|
31
|
+
const argv = (0, yargs_1.default)((0, helpers_1.hideBin)(process.argv)).option("netSendAmount", {
|
|
32
|
+
type: "string",
|
|
33
|
+
demandOption: true,
|
|
34
|
+
describe: "Net send amount to spoke",
|
|
35
|
+
}).argv;
|
|
36
|
+
async function proposeRebalanceToSpokePool() {
|
|
37
|
+
const resolvedArgv = await argv;
|
|
38
|
+
const netSendAmount = ethers_1.BigNumber.from(resolvedArgv.netSendAmount);
|
|
39
|
+
// Resolve chain IDs and USDC address.
|
|
40
|
+
const evmChainId = (await ethersProvider.getNetwork()).chainId;
|
|
41
|
+
if (evmChainId !== constants_1.CHAIN_IDs.MAINNET && evmChainId !== constants_1.CHAIN_IDs.SEPOLIA)
|
|
42
|
+
throw new Error("Unsupported EVM chain ID");
|
|
43
|
+
const solanaCluster = evmChainId === constants_1.CHAIN_IDs.MAINNET ? "mainnet" : "devnet";
|
|
44
|
+
const solanaChainId = (0, helpers_2.getSolanaChainId)(solanaCluster);
|
|
45
|
+
const l1TokenAddress = constants_1.TOKEN_SYMBOLS_MAP.USDC.addresses[evmChainId];
|
|
46
|
+
// Construct simple merkle tree for the pool rebalance.
|
|
47
|
+
const { poolRebalanceTree } = (0, poolRebalanceTree_1.constructSimpleRebalanceTree)(l1TokenAddress, netSendAmount, solanaChainId);
|
|
48
|
+
console.log("Proposing rebalance pool bundle to spoke...");
|
|
49
|
+
console.table([
|
|
50
|
+
{ Property: "originChainId", Value: evmChainId.toString() },
|
|
51
|
+
{ Property: "targetChainId", Value: solanaChainId.toString() },
|
|
52
|
+
{ Property: "hubPoolAddress", Value: hubPool.address },
|
|
53
|
+
{ Property: "l1TokenAddress", Value: l1TokenAddress },
|
|
54
|
+
{ Property: "netSendAmount", Value: netSendAmount.toString() },
|
|
55
|
+
{ Property: "poolRebalanceRoot", Value: poolRebalanceTree.getHexRoot() },
|
|
56
|
+
]);
|
|
57
|
+
// Check there are no active proposals.
|
|
58
|
+
const currentRootBundleProposal = await hubPool.callStatic.rootBundleProposal();
|
|
59
|
+
if (currentRootBundleProposal.unclaimedPoolRebalanceLeafCount !== 0)
|
|
60
|
+
throw new Error("Proposal has unclaimed leaves");
|
|
61
|
+
// Ensure bond token balance and approval is sufficient
|
|
62
|
+
const bondTokenAddress = await hubPool.callStatic.bondToken();
|
|
63
|
+
const bondAmount = await hubPool.callStatic.bondAmount();
|
|
64
|
+
const bondToken = typechain_1.BondToken__factory.connect(bondTokenAddress, ethersProvider);
|
|
65
|
+
const bondBalance = await bondToken.callStatic.balanceOf(ethersSigner.address);
|
|
66
|
+
if (bondBalance.lt(bondAmount)) {
|
|
67
|
+
const ethDeposit = bondAmount.sub(bondBalance);
|
|
68
|
+
console.log(`Depositing ${ethers_1.ethers.utils.formatUnits(ethDeposit.toString())} ETH into bond token:`);
|
|
69
|
+
// This will throw if the signer does not have enough ETH.
|
|
70
|
+
const tx = await bondToken.connect(ethersSigner).deposit({ value: bondAmount.sub(bondBalance) });
|
|
71
|
+
console.log(`✔️ submitted tx hash: ${tx.hash}`);
|
|
72
|
+
await tx.wait();
|
|
73
|
+
console.log(`✔️ tx confirmed`);
|
|
74
|
+
}
|
|
75
|
+
const allowance = await bondToken.callStatic.allowance(ethersSigner.address, hubPool.address);
|
|
76
|
+
if (allowance.lt(bondAmount)) {
|
|
77
|
+
console.log(`Approving ${ethers_1.ethers.utils.formatUnits(bondAmount.toString())} bond tokens for HubPool:`);
|
|
78
|
+
const tx = await bondToken.connect(ethersSigner).approve(hubPool.address, bondAmount);
|
|
79
|
+
console.log(`✔️ submitted tx hash: ${tx.hash}`);
|
|
80
|
+
await tx.wait();
|
|
81
|
+
console.log(`✔️ tx confirmed`);
|
|
82
|
+
}
|
|
83
|
+
// Propose the rebalance to the spoke pool.
|
|
84
|
+
console.log(`Proposing ${netSendAmount.toString()} rebalance to spoke pool:`);
|
|
85
|
+
const tx = await hubPool.connect(ethersSigner).proposeRootBundle([0], // bundleEvaluationBlockNumbers, not checked in this script.
|
|
86
|
+
1, // poolRebalanceLeafCount.
|
|
87
|
+
poolRebalanceTree.getHexRoot(), // poolRebalanceRoot. Generated from the merkle tree constructed before.
|
|
88
|
+
ethers_1.ethers.constants.HashZero, // relayerRefundRoot, not relevant for this script.
|
|
89
|
+
ethers_1.ethers.constants.HashZero // slowRelayRoot, not relevant for this test.
|
|
90
|
+
);
|
|
91
|
+
console.log(`✔️ submitted tx hash: ${tx.hash}`);
|
|
92
|
+
await tx.wait();
|
|
93
|
+
console.log(`✔️ tx confirmed`);
|
|
94
|
+
console.log("Rebalance proposal submitted successfully, to execute, run executeRebalanceToSpokePool script with the same netSendAmount after liveness period.");
|
|
95
|
+
}
|
|
96
|
+
// Run the proposeRebalanceToSpokePool function
|
|
97
|
+
proposeRebalanceToSpokePool();
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
const yargs_1 = __importDefault(require("yargs"));
|
|
7
|
+
const helpers_1 = require("yargs/helpers");
|
|
8
|
+
const svm_1 = require("../../src/svm");
|
|
9
|
+
const argv = (0, yargs_1.default)((0, helpers_1.hideBin)(process.argv)).option("publicKey", {
|
|
10
|
+
type: "string",
|
|
11
|
+
demandOption: true,
|
|
12
|
+
describe: "Public key to convert",
|
|
13
|
+
}).argv;
|
|
14
|
+
async function logEvmAddress() {
|
|
15
|
+
const publicKey = (await argv).publicKey;
|
|
16
|
+
const evmAddress = (0, svm_1.publicKeyToEvmAddress)(publicKey);
|
|
17
|
+
console.log("Public Key:", publicKey);
|
|
18
|
+
console.log("Associated Ethereum Address:", evmAddress);
|
|
19
|
+
}
|
|
20
|
+
logEvmAddress();
|
|
@@ -32,13 +32,14 @@ const anchor_1 = require("@coral-xyz/anchor");
|
|
|
32
32
|
const web3_js_1 = require("@solana/web3.js");
|
|
33
33
|
const yargs_1 = __importDefault(require("yargs"));
|
|
34
34
|
const helpers_1 = require("yargs/helpers");
|
|
35
|
-
const
|
|
35
|
+
const svm_1 = require("../../src/svm");
|
|
36
36
|
// Set up the provider
|
|
37
37
|
const provider = anchor_1.AnchorProvider.env();
|
|
38
38
|
anchor.setProvider(provider);
|
|
39
39
|
const idl = require("../../target/idl/svm_spoke.json");
|
|
40
40
|
const program = new anchor_1.Program(idl, provider);
|
|
41
41
|
const programId = program.programId;
|
|
42
|
+
console.log("SVM-Spoke Program ID:", programId.toString());
|
|
42
43
|
// Parse arguments
|
|
43
44
|
const argvPromise = (0, yargs_1.default)((0, helpers_1.hideBin)(process.argv)).option("seed", {
|
|
44
45
|
type: "string",
|
|
@@ -56,7 +57,7 @@ async function queryDeposits() {
|
|
|
56
57
|
{ Property: "statePda", Value: statePda.toString() },
|
|
57
58
|
]);
|
|
58
59
|
try {
|
|
59
|
-
const events = await (0,
|
|
60
|
+
const events = await (0, svm_1.readProgramEvents)(provider.connection, program);
|
|
60
61
|
const depositEvents = events.filter((event) => event.name === "v3FundsDeposited");
|
|
61
62
|
if (depositEvents.length === 0) {
|
|
62
63
|
console.log("No deposit events found for the given seed.");
|
|
@@ -32,7 +32,7 @@ const anchor_1 = require("@coral-xyz/anchor");
|
|
|
32
32
|
const web3_js_1 = require("@solana/web3.js");
|
|
33
33
|
const yargs_1 = __importDefault(require("yargs"));
|
|
34
34
|
const helpers_1 = require("yargs/helpers");
|
|
35
|
-
const
|
|
35
|
+
const svm_1 = require("../../src/svm");
|
|
36
36
|
// Set up the provider
|
|
37
37
|
const provider = anchor_1.AnchorProvider.env();
|
|
38
38
|
anchor.setProvider(provider);
|
|
@@ -56,7 +56,7 @@ async function queryFills() {
|
|
|
56
56
|
{ Property: "statePda", Value: statePda.toString() },
|
|
57
57
|
]);
|
|
58
58
|
try {
|
|
59
|
-
const events = await (0,
|
|
59
|
+
const events = await (0, svm_1.readProgramEvents)(provider.connection, program);
|
|
60
60
|
const fillEvents = events.filter((event) => event.name === "filledV3Relay");
|
|
61
61
|
if (fillEvents.length === 0) {
|
|
62
62
|
console.log("No fill events found for the given seed.");
|
|
@@ -66,25 +66,23 @@ async function queryFills() {
|
|
|
66
66
|
fillEvents.forEach((event, index) => {
|
|
67
67
|
console.log(`Fill Event ${index + 1}:`);
|
|
68
68
|
console.table([
|
|
69
|
-
{ Property: "inputToken", Value:
|
|
70
|
-
{ Property: "outputToken", Value:
|
|
69
|
+
{ Property: "inputToken", Value: (0, svm_1.strPublicKey)(event.data.inputToken) },
|
|
70
|
+
{ Property: "outputToken", Value: (0, svm_1.strPublicKey)(event.data.outputToken) },
|
|
71
71
|
{ Property: "inputAmount", Value: event.data.inputAmount.toString() },
|
|
72
72
|
{ Property: "outputAmount", Value: event.data.outputAmount.toString() },
|
|
73
73
|
{ Property: "repaymentChainId", Value: event.data.repaymentChainId.toString() },
|
|
74
74
|
{ Property: "originChainId", Value: event.data.originChainId.toString() },
|
|
75
75
|
{ Property: "depositId", Value: event.data.depositId.toString() },
|
|
76
|
+
{ Property: "depositIdNum", Value: (0, svm_1.u8Array32ToInt)(event.data.depositId).toString() },
|
|
76
77
|
{ Property: "fillDeadline", Value: event.data.fillDeadline.toString() },
|
|
77
78
|
{ Property: "exclusivityDeadline", Value: event.data.exclusivityDeadline.toString() },
|
|
78
|
-
{ Property: "exclusiveRelayer", Value:
|
|
79
|
-
{ Property: "relayer", Value:
|
|
80
|
-
{ Property: "depositor", Value:
|
|
81
|
-
{ Property: "recipient", Value:
|
|
82
|
-
{ Property: "
|
|
83
|
-
{
|
|
84
|
-
|
|
85
|
-
Value: new web3_js_1.PublicKey(event.data.relayExecutionInfo.updatedRecipient).toString(),
|
|
86
|
-
},
|
|
87
|
-
{ Property: "updatedMessage", Value: event.data.relayExecutionInfo.updatedMessage.toString() },
|
|
79
|
+
{ Property: "exclusiveRelayer", Value: (0, svm_1.strPublicKey)(event.data.exclusiveRelayer) },
|
|
80
|
+
{ Property: "relayer", Value: (0, svm_1.strPublicKey)(event.data.relayer) },
|
|
81
|
+
{ Property: "depositor", Value: (0, svm_1.strPublicKey)(event.data.depositor) },
|
|
82
|
+
{ Property: "recipient", Value: (0, svm_1.strPublicKey)(event.data.recipient) },
|
|
83
|
+
{ Property: "messageHash", Value: event.data.messageHash.toString() },
|
|
84
|
+
{ Property: "updatedRecipient", Value: (0, svm_1.strPublicKey)(event.data.relayExecutionInfo.updatedRecipient) },
|
|
85
|
+
{ Property: "updatedMessageHash", Value: event.data.relayExecutionInfo.updatedMessageHash.toString() },
|
|
88
86
|
{ Property: "updatedOutputAmount", Value: event.data.relayExecutionInfo.updatedOutputAmount.toString() },
|
|
89
87
|
{ Property: "fillType", Value: event.data.relayExecutionInfo.fillType },
|
|
90
88
|
]);
|
|
@@ -39,6 +39,7 @@ anchor.setProvider(provider);
|
|
|
39
39
|
const idl = require("../../target/idl/svm_spoke.json");
|
|
40
40
|
const program = new anchor_1.Program(idl, provider);
|
|
41
41
|
const programId = program.programId;
|
|
42
|
+
console.log("SVM-Spoke Program ID:", programId.toString());
|
|
42
43
|
// Parse arguments
|
|
43
44
|
const argv = (0, yargs_1.default)((0, helpers_1.hideBin)(process.argv))
|
|
44
45
|
.option("seed", { type: "string", demandOption: true, describe: "Seed for the state account PDA" })
|
|
@@ -52,7 +53,12 @@ async function queryRoute() {
|
|
|
52
53
|
// Define the state account PDA
|
|
53
54
|
const [statePda, _] = web3_js_1.PublicKey.findProgramAddressSync([Buffer.from("state"), seed.toArrayLike(Buffer, "le", 8)], programId);
|
|
54
55
|
// Define the route account PDA
|
|
55
|
-
const [routePda] = web3_js_1.PublicKey.findProgramAddressSync([
|
|
56
|
+
const [routePda] = web3_js_1.PublicKey.findProgramAddressSync([
|
|
57
|
+
Buffer.from("route"),
|
|
58
|
+
Buffer.from(originToken),
|
|
59
|
+
seed.toArrayLike(Buffer, "le", 8),
|
|
60
|
+
chainId.toArrayLike(Buffer, "le", 8),
|
|
61
|
+
], programId);
|
|
56
62
|
// Compute the vault address
|
|
57
63
|
const vault = (0, spl_token_1.getAssociatedTokenAddressSync)(new web3_js_1.PublicKey(originToken), statePda, true, spl_token_1.TOKEN_PROGRAM_ID, spl_token_1.ASSOCIATED_TOKEN_PROGRAM_ID);
|
|
58
64
|
console.log("Querying route...");
|
|
@@ -38,6 +38,7 @@ anchor.setProvider(provider);
|
|
|
38
38
|
const idl = require("../../target/idl/svm_spoke.json");
|
|
39
39
|
const program = new anchor_1.Program(idl, provider);
|
|
40
40
|
const programId = program.programId;
|
|
41
|
+
console.log("SVM-Spoke Program ID:", programId.toString());
|
|
41
42
|
// Parse arguments
|
|
42
43
|
const argv = (0, yargs_1.default)((0, helpers_1.hideBin)(process.argv)).option("seed", {
|
|
43
44
|
type: "string",
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
import "dotenv/config";
|
|
@@ -0,0 +1,191 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
// This script bridges remote call to pause deposits on Solana Spoke Pool. Required environment:
|
|
3
|
+
// - NODE_URL_${CHAIN_ID}: Ethereum RPC URL (must point to the Mainnet or Sepolia depending on Solana cluster).
|
|
4
|
+
// - MNEMONIC: Mnemonic of the wallet that will sign the sending transaction on Ethereum
|
|
5
|
+
// - HUB_POOL_ADDRESS: Hub Pool address
|
|
6
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
7
|
+
if (k2 === undefined) k2 = k;
|
|
8
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
9
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
10
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
11
|
+
}
|
|
12
|
+
Object.defineProperty(o, k2, desc);
|
|
13
|
+
}) : (function(o, m, k, k2) {
|
|
14
|
+
if (k2 === undefined) k2 = k;
|
|
15
|
+
o[k2] = m[k];
|
|
16
|
+
}));
|
|
17
|
+
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
18
|
+
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
19
|
+
}) : function(o, v) {
|
|
20
|
+
o["default"] = v;
|
|
21
|
+
});
|
|
22
|
+
var __importStar = (this && this.__importStar) || function (mod) {
|
|
23
|
+
if (mod && mod.__esModule) return mod;
|
|
24
|
+
var result = {};
|
|
25
|
+
if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
|
|
26
|
+
__setModuleDefault(result, mod);
|
|
27
|
+
return result;
|
|
28
|
+
};
|
|
29
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
30
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
31
|
+
};
|
|
32
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
33
|
+
const anchor = __importStar(require("@coral-xyz/anchor"));
|
|
34
|
+
const anchor_1 = require("@coral-xyz/anchor");
|
|
35
|
+
const web3_js_1 = require("@solana/web3.js");
|
|
36
|
+
require("dotenv/config");
|
|
37
|
+
const ethers_1 = require("ethers");
|
|
38
|
+
const yargs_1 = __importDefault(require("yargs"));
|
|
39
|
+
const helpers_1 = require("yargs/helpers");
|
|
40
|
+
const common_1 = require("@uma/common");
|
|
41
|
+
const cctpHelpers_1 = require("../../test/svm/cctpHelpers");
|
|
42
|
+
const typechain_1 = require("../../typechain");
|
|
43
|
+
const constants_1 = require("./utils/constants");
|
|
44
|
+
const helpers_2 = require("./utils/helpers");
|
|
45
|
+
// Set up Solana provider.
|
|
46
|
+
const provider = anchor_1.AnchorProvider.env();
|
|
47
|
+
anchor.setProvider(provider);
|
|
48
|
+
// Parse arguments
|
|
49
|
+
const argv = (0, yargs_1.default)((0, helpers_1.hideBin)(process.argv))
|
|
50
|
+
.option("chainId", { type: "string", demandOption: true, describe: "Chain ID" })
|
|
51
|
+
.option("pause", { type: "boolean", demandOption: true, describe: "Pause deposits" })
|
|
52
|
+
.option("resumeRemoteTx", { type: "string", demandOption: false, describe: "Resume receiving remote tx" }).argv;
|
|
53
|
+
async function remoteHubPoolPauseDeposit() {
|
|
54
|
+
const resolvedArgv = await argv;
|
|
55
|
+
const chainId = resolvedArgv.chainId;
|
|
56
|
+
const seed = new anchor_1.BN(0);
|
|
57
|
+
const resumeRemoteTx = resolvedArgv.resumeRemoteTx;
|
|
58
|
+
const pause = resolvedArgv.pause;
|
|
59
|
+
// Set up Ethereum provider and signer.
|
|
60
|
+
const isDevnet = (0, helpers_2.isSolanaDevnet)(provider);
|
|
61
|
+
const nodeURL = isDevnet ? (0, common_1.getNodeUrl)("sepolia", true) : (0, common_1.getNodeUrl)("mainnet", true);
|
|
62
|
+
const ethersProvider = new ethers_1.ethers.providers.JsonRpcProvider(nodeURL);
|
|
63
|
+
const ethersSigner = ethers_1.ethers.Wallet.fromMnemonic((0, helpers_2.requireEnv)("MNEMONIC")).connect(ethersProvider);
|
|
64
|
+
const hubPoolAddress = (0, helpers_2.requireEnv)("HUB_POOL_ADDRESS");
|
|
65
|
+
// CCTP domains.
|
|
66
|
+
const remoteDomain = 0; // Ethereum
|
|
67
|
+
// Get Solana programs and accounts.
|
|
68
|
+
const svmSpokeIdl = require("../../target/idl/svm_spoke.json");
|
|
69
|
+
const svmSpokeProgram = new anchor_1.Program(svmSpokeIdl, provider);
|
|
70
|
+
const [statePda, _] = web3_js_1.PublicKey.findProgramAddressSync([Buffer.from("state"), seed.toArrayLike(Buffer, "le", 8)], svmSpokeProgram.programId);
|
|
71
|
+
const messageTransmitterIdl = require("../../target/idl/message_transmitter.json");
|
|
72
|
+
const messageTransmitterProgram = new anchor_1.Program(messageTransmitterIdl, provider);
|
|
73
|
+
const [messageTransmitterState] = web3_js_1.PublicKey.findProgramAddressSync([Buffer.from("message_transmitter")], messageTransmitterProgram.programId);
|
|
74
|
+
const [authorityPda] = web3_js_1.PublicKey.findProgramAddressSync([Buffer.from("message_transmitter_authority"), svmSpokeProgram.programId.toBuffer()], messageTransmitterProgram.programId);
|
|
75
|
+
const [selfAuthority] = web3_js_1.PublicKey.findProgramAddressSync([Buffer.from("self_authority")], svmSpokeProgram.programId);
|
|
76
|
+
const [eventAuthority] = web3_js_1.PublicKey.findProgramAddressSync([Buffer.from("__event_authority")], svmSpokeProgram.programId);
|
|
77
|
+
const irisApiUrl = isDevnet ? constants_1.CIRCLE_IRIS_API_URL_DEVNET : constants_1.CIRCLE_IRIS_API_URL_MAINNET;
|
|
78
|
+
const hubPool = typechain_1.HubPool__factory.connect(hubPoolAddress, ethersProvider);
|
|
79
|
+
const spokePoolIface = new ethers_1.ethers.utils.Interface(["function pauseDeposits(bool pause)"]);
|
|
80
|
+
console.log("Remotely configuring deposit route...");
|
|
81
|
+
console.table([
|
|
82
|
+
{ Property: "seed", Value: seed.toString() },
|
|
83
|
+
{ Property: "chainId", Value: chainId.toString() },
|
|
84
|
+
{ Property: "pause", Value: pause },
|
|
85
|
+
{ Property: "svmSpokeProgramProgramId", Value: svmSpokeProgram.programId.toString() },
|
|
86
|
+
{ Property: "providerPublicKey", Value: provider.wallet.publicKey.toString() },
|
|
87
|
+
{ Property: "statePda", Value: statePda.toString() },
|
|
88
|
+
{ Property: "messageTransmitterProgramId", Value: messageTransmitterProgram.programId.toString() },
|
|
89
|
+
{ Property: "messageTransmitterState", Value: messageTransmitterState.toString() },
|
|
90
|
+
{ Property: "authorityPda", Value: authorityPda.toString() },
|
|
91
|
+
{ Property: "selfAuthority", Value: selfAuthority.toString() },
|
|
92
|
+
{ Property: "eventAuthority", Value: eventAuthority.toString() },
|
|
93
|
+
{ Property: "remoteSender", Value: ethersSigner.address },
|
|
94
|
+
]);
|
|
95
|
+
// Send pauseDeposits call from Ethereum, unless resuming a remote transaction.
|
|
96
|
+
let remoteTxHash;
|
|
97
|
+
if (!resumeRemoteTx) {
|
|
98
|
+
console.log("Sending pauseDeposits message from HubPool...");
|
|
99
|
+
const calldata = spokePoolIface.encodeFunctionData("pauseDeposits", [pause]);
|
|
100
|
+
const tx = await hubPool.connect(ethersSigner).relaySpokePoolAdminFunction(chainId, calldata);
|
|
101
|
+
await tx.wait();
|
|
102
|
+
remoteTxHash = tx.hash;
|
|
103
|
+
console.log("Message sent on remote chain, tx", remoteTxHash);
|
|
104
|
+
}
|
|
105
|
+
else
|
|
106
|
+
remoteTxHash = resumeRemoteTx;
|
|
107
|
+
// Fetch attestation from CCTP attestation service.
|
|
108
|
+
const attestationResponse = await (0, cctpHelpers_1.getMessages)(remoteTxHash, remoteDomain, irisApiUrl);
|
|
109
|
+
const { attestation, message } = attestationResponse.messages[0];
|
|
110
|
+
console.log("CCTP attestation response:", attestationResponse.messages[0]);
|
|
111
|
+
// Accounts in CCTP message_transmitter receive_message instruction.
|
|
112
|
+
const nonce = (0, cctpHelpers_1.decodeMessageHeader)(Buffer.from(message.replace("0x", ""), "hex")).nonce;
|
|
113
|
+
const usedNonces = (await messageTransmitterProgram.methods
|
|
114
|
+
.getNoncePda({
|
|
115
|
+
nonce: new anchor_1.BN(nonce.toString()),
|
|
116
|
+
sourceDomain: remoteDomain,
|
|
117
|
+
})
|
|
118
|
+
.accounts({
|
|
119
|
+
messageTransmitter: messageTransmitterState,
|
|
120
|
+
})
|
|
121
|
+
.view());
|
|
122
|
+
const receiveMessageAccounts = {
|
|
123
|
+
payer: provider.wallet.publicKey,
|
|
124
|
+
caller: provider.wallet.publicKey,
|
|
125
|
+
authorityPda,
|
|
126
|
+
messageTransmitter: messageTransmitterState,
|
|
127
|
+
usedNonces,
|
|
128
|
+
receiver: svmSpokeProgram.programId,
|
|
129
|
+
systemProgram: anchor_1.web3.SystemProgram.programId,
|
|
130
|
+
};
|
|
131
|
+
// accountMetas list to pass to remaining accounts when receiving message via CCTP.
|
|
132
|
+
const remainingAccounts = [];
|
|
133
|
+
// state in HandleReceiveMessage accounts (used for remote domain and sender authentication).
|
|
134
|
+
remainingAccounts.push({
|
|
135
|
+
isSigner: false,
|
|
136
|
+
isWritable: false,
|
|
137
|
+
pubkey: statePda,
|
|
138
|
+
});
|
|
139
|
+
// self_authority in HandleReceiveMessage accounts, also signer in self-invoked CPIs.
|
|
140
|
+
remainingAccounts.push({
|
|
141
|
+
isSigner: false,
|
|
142
|
+
isWritable: false,
|
|
143
|
+
pubkey: selfAuthority,
|
|
144
|
+
});
|
|
145
|
+
// program in HandleReceiveMessage accounts.
|
|
146
|
+
remainingAccounts.push({
|
|
147
|
+
isSigner: false,
|
|
148
|
+
isWritable: false,
|
|
149
|
+
pubkey: svmSpokeProgram.programId,
|
|
150
|
+
});
|
|
151
|
+
// state
|
|
152
|
+
remainingAccounts.push({
|
|
153
|
+
isSigner: false,
|
|
154
|
+
isWritable: true,
|
|
155
|
+
pubkey: statePda,
|
|
156
|
+
});
|
|
157
|
+
// event_authority in self-invoked CPIs (appended by Anchor with event_cpi macro).
|
|
158
|
+
remainingAccounts.push({
|
|
159
|
+
isSigner: false,
|
|
160
|
+
isWritable: true,
|
|
161
|
+
pubkey: eventAuthority,
|
|
162
|
+
});
|
|
163
|
+
// program
|
|
164
|
+
remainingAccounts.push({
|
|
165
|
+
isSigner: false,
|
|
166
|
+
isWritable: true,
|
|
167
|
+
pubkey: svmSpokeProgram.programId,
|
|
168
|
+
});
|
|
169
|
+
// Receive remote message on Solana.
|
|
170
|
+
console.log("Receiving message on Solana...");
|
|
171
|
+
const receiveMessageTx = await messageTransmitterProgram.methods
|
|
172
|
+
.receiveMessage({
|
|
173
|
+
message: Buffer.from(message.replace("0x", ""), "hex"),
|
|
174
|
+
attestation: Buffer.from(attestation.replace("0x", ""), "hex"),
|
|
175
|
+
})
|
|
176
|
+
.accounts(receiveMessageAccounts)
|
|
177
|
+
.remainingAccounts(remainingAccounts)
|
|
178
|
+
.rpc();
|
|
179
|
+
console.log("\nReceived remote message");
|
|
180
|
+
console.log("Your transaction signature", receiveMessageTx);
|
|
181
|
+
let stateAccount = await svmSpokeProgram.account.state.fetch(statePda);
|
|
182
|
+
console.log("Updated deposit route state to: pausedDeposits =", stateAccount.pausedDeposits);
|
|
183
|
+
}
|
|
184
|
+
remoteHubPoolPauseDeposit()
|
|
185
|
+
.then(() => {
|
|
186
|
+
process.exit(0);
|
|
187
|
+
})
|
|
188
|
+
.catch((err) => {
|
|
189
|
+
console.error(err);
|
|
190
|
+
process.exit(1);
|
|
191
|
+
});
|