@@ -26,27 +26,8 @@ abstract contract StdCheatsSafe {
26
26
string rpcUrl;
27
27
}
28
28
29
- struct Chains {
30
- Chain Anvil;
31
- Chain Hardhat;
32
- Chain Mainnet;
33
- Chain Goerli;
34
- Chain Sepolia;
35
- Chain Optimism;
36
- Chain OptimismGoerli;
37
- Chain ArbitrumOne;
38
- Chain ArbitrumOneGoerli;
39
- Chain ArbitrumNova;
40
- Chain Polygon;
41
- Chain PolygonMumbai;
42
- Chain Avalanche;
43
- Chain AvalancheFuji;
44
- Chain BnbSmartChain;
45
- Chain BnbSmartChainTestnet;
46
- Chain GnosisChain;
47
- }
48
-
49
- Chains stdChains;
29
+ // Maps from a chain's name (matching what's in the `foundry.toml` file) to chain data.
30
+ mapping (string => Chain) internal stdChains;
50
31
51
32
// Data structures to parse Transaction objects from the broadcast artifact
52
33
// that conform to EIP1559. The Raw structs is what is parsed from the JSON
@@ -227,63 +208,33 @@ abstract contract StdCheatsSafe {
227
208
228
209
function _constructor () private returns (uint256 ) {
229
210
// Initialize `stdChains` with the defaults.
230
- stdChains = Chains ({
231
- Anvil: Chain ("Anvil " , 31337 , "http://127.0.0.1:8545 " ),
232
- Hardhat: Chain ("Hardhat " , 31337 , "http://127.0.0.1:8545 " ),
233
- Mainnet: Chain ("Mainnet " , 1 , "https://api.mycryptoapi.com/eth " ),
234
- Goerli: Chain ("Goerli " , 5 , "https://goerli.infura.io/v3/84842078b09946638c03157f83405213 " ), // Default Infura key from ethers.js: https://github.com/ethers-io/ethers.js/blob/c80fcddf50a9023486e9f9acb1848aba4c19f7b6/packages/providers/src.ts/infura-provider.ts
235
- Sepolia: Chain ("Sepolia " , 11155111 , "https://rpc.sepolia.dev " ),
236
- Optimism: Chain ("Optimism " , 10 , "https://mainnet.optimism.io " ),
237
- OptimismGoerli: Chain ("OptimismGoerli " , 420 , "https://goerli.optimism.io " ),
238
- ArbitrumOne: Chain ("ArbitrumOne " , 42161 , "https://arb1.arbitrum.io/rpc " ),
239
- ArbitrumOneGoerli: Chain ("ArbitrumOneGoerli " , 421613 , "https://goerli-rollup.arbitrum.io/rpc " ),
240
- ArbitrumNova: Chain ("ArbitrumNova " , 42170 , "https://nova.arbitrum.io/rpc " ),
241
- Polygon: Chain ("Polygon " , 137 , "https://polygon-rpc.com " ),
242
- PolygonMumbai: Chain ("PolygonMumbai " , 80001 , "https://rpc-mumbai.matic.today " ),
243
- Avalanche: Chain ("Avalanche " , 43114 , "https://api.avax.network/ext/bc/C/rpc " ),
244
- AvalancheFuji: Chain ("AvalancheFuji " , 43113 , "https://api.avax-test.network/ext/bc/C/rpc " ),
245
- BnbSmartChain: Chain ("BnbSmartChain " , 56 , "https://bsc-dataseed1.binance.org " ),
246
- BnbSmartChainTestnet: Chain ("BnbSmartChainTestnet " , 97 , "https://data-seed-prebsc-1-s1.binance.org:8545 " ),
247
- GnosisChain: Chain ("GnosisChain " , 100 , "https://rpc.gnosischain.com " )
248
- });
211
+ stdChains["anvil " ] = Chain ("Anvil " , 31337 , "http://127.0.0.1:8545 " );
212
+ stdChains["hardhat " ] = Chain ("Hardhat " , 31337 , "http://127.0.0.1:8545 " );
213
+ stdChains["mainnet " ] = Chain ("Mainnet " , 1 , "https://api.mycryptoapi.com/eth " );
214
+ stdChains["goerli " ] = Chain ("Goerli " , 5 , "https://goerli.infura.io/v3/6770454bc6ea42c58aac12978531b93f " );
215
+ stdChains["sepolia " ] = Chain ("Sepolia " , 11155111 , "https://rpc.sepolia.dev " );
216
+ stdChains["optimism " ] = Chain ("Optimism " , 10 , "https://mainnet.optimism.io " );
217
+ stdChains["optimism_goerli " ] = Chain ("Optimism Goerli " , 420 , "https://goerli.optimism.io " );
218
+ stdChains["arbitrum_one " ] = Chain ("Arbitrum One " , 42161 , "https://arb1.arbitrum.io/rpc " );
219
+ stdChains["arbitrum_one_goerli " ] = Chain ("Arbitrum One Goerli " , 421613 , "https://goerli-rollup.arbitrum.io/rpc " );
220
+ stdChains["arbitrum_nova " ] = Chain ("Arbitrum Nova " , 42170 , "https://nova.arbitrum.io/rpc " );
221
+ stdChains["polygon " ] = Chain ("Polygon " , 137 , "https://polygon-rpc.com " );
222
+ stdChains["polygon_mumbai " ] = Chain ("Polygon Mumbai " , 80001 , "https://rpc-mumbai.matic.today " );
223
+ stdChains["avalanche " ] = Chain ("Avalanche " , 43114 , "https://api.avax.network/ext/bc/C/rpc " );
224
+ stdChains["avalanche_fuji " ] = Chain ("Avalanche Fuji " , 43113 , "https://api.avax-test.network/ext/bc/C/rpc " );
225
+ stdChains["bnb_smart_chain " ] = Chain ("BNB Smart Chain " , 56 , "https://bsc-dataseed1.binance.org " );
226
+ stdChains["bnb_smart_chain_testnet " ] = Chain ("BNB Smart Chain Testnet " , 97 , "https://data-seed-prebsc-1-s1.binance.org:8545 " );// forgefmt: disable-line
227
+ stdChains["gnosis_chain " ] = Chain ("Gnosis Chain " , 100 , "https://rpc.gnosischain.com " );
249
228
250
229
// Loop over RPC URLs in the config file to replace the default RPC URLs
251
- ( string [ 2 ][] memory rpcs ) = vm.rpcUrls ();
230
+ Vm.Rpc[] memory rpcs = vm.rpcUrlStructs ();
252
231
for (uint256 i = 0 ; i < rpcs.length ; i++ ) {
253
- (string memory name , string memory rpcUrl ) = (rpcs[i][0 ], rpcs[i][1 ]);
254
- // forgefmt: disable-start
255
- if (isEqual (name, "anvil " )) stdChains.Anvil.rpcUrl = rpcUrl;
256
- else if (isEqual (name, "hardhat " )) stdChains.Hardhat.rpcUrl = rpcUrl;
257
- else if (isEqual (name, "mainnet " )) stdChains.Mainnet.rpcUrl = rpcUrl;
258
- else if (isEqual (name, "goerli " )) stdChains.Goerli.rpcUrl = rpcUrl;
259
- else if (isEqual (name, "sepolia " )) stdChains.Sepolia.rpcUrl = rpcUrl;
260
- else if (isEqual (name, "optimism " )) stdChains.Optimism.rpcUrl = rpcUrl;
261
- else if (isEqual (name, "optimism_goerli " , "optimism-goerli " )) stdChains.OptimismGoerli.rpcUrl = rpcUrl;
262
- else if (isEqual (name, "arbitrum_one " , "arbitrum-one " )) stdChains.ArbitrumOne.rpcUrl = rpcUrl;
263
- else if (isEqual (name, "arbitrum_one_goerli " , "arbitrum-one-goerli " )) stdChains.ArbitrumOneGoerli.rpcUrl = rpcUrl;
264
- else if (isEqual (name, "arbitrum_nova " , "arbitrum-nova " )) stdChains.ArbitrumNova.rpcUrl = rpcUrl;
265
- else if (isEqual (name, "polygon " )) stdChains.Polygon.rpcUrl = rpcUrl;
266
- else if (isEqual (name, "polygon_mumbai " , "polygon-mumbai " )) stdChains.PolygonMumbai.rpcUrl = rpcUrl;
267
- else if (isEqual (name, "avalanche " )) stdChains.Avalanche.rpcUrl = rpcUrl;
268
- else if (isEqual (name, "avalanche_fuji " , "avalanche-fuji " )) stdChains.AvalancheFuji.rpcUrl = rpcUrl;
269
- else if (isEqual (name, "bnb_smart_chain " , "bnb-smart-chain " )) stdChains.BnbSmartChain.rpcUrl = rpcUrl;
270
- else if (isEqual (name, "bnb_smart_chain_testnet " , "bnb-smart-chain-testnet " )) stdChains.BnbSmartChainTestnet.rpcUrl = rpcUrl;
271
- else if (isEqual (name, "gnosis_chain " , "gnosis-chain " )) stdChains.GnosisChain.rpcUrl = rpcUrl;
272
- // forgefmt: disable-end
232
+ stdChains[rpcs[i].name].rpcUrl = rpcs[i].url;
273
233
}
274
234
return 0 ;
275
235
}
276
236
277
- function isEqual (string memory a , string memory b ) private pure returns (bool ) {
278
- return keccak256 (abi.encode (a)) == keccak256 (abi.encode (b));
279
- }
280
-
281
- function isEqual (string memory a , string memory b , string memory c ) private pure returns (bool ) {
282
- return
283
- keccak256 (abi.encode (a)) == keccak256 (abi.encode (b)) || keccak256 (abi.encode (a)) == keccak256 (abi.encode (c));
284
- }
285
-
286
- function assumeNoPrecompiles (address addr ) internal virtual {
237
+ function assumeNoPrecompiles (address addr ) internal view virtual {
287
238
// Assembly required since `block.chainid` was introduced in 0.8.0.
288
239
uint256 chainId;
289
240
assembly {
@@ -292,21 +243,21 @@ abstract contract StdCheatsSafe {
292
243
assumeNoPrecompiles (addr, chainId);
293
244
}
294
245
295
- function assumeNoPrecompiles (address addr , uint256 chainId ) internal virtual {
246
+ function assumeNoPrecompiles (address addr , uint256 chainId ) internal view virtual {
296
247
// Note: For some chains like Optimism these are technically predeploys (i.e. bytecode placed at a specific
297
248
// address), but the same rationale for excluding them applies so we include those too.
298
249
299
250
// These should be present on all EVM-compatible chains.
300
251
vm.assume (addr < address (0x1 ) || addr > address (0x9 ));
301
252
302
253
// forgefmt: disable-start
303
- if (chainId == stdChains.Optimism. chainId || chainId == stdChains.OptimismGoerli .chainId) {
254
+ if (chainId == stdChains[ " optimism " ]. chainId || chainId == stdChains[ " optimism_goerli " ] .chainId) {
304
255
// https://github.com/ethereum-optimism/optimism/blob/eaa371a0184b56b7ca6d9eb9cb0a2b78b2ccd864/op-bindings/predeploys/addresses.go#L6-L21
305
256
vm.assume (addr < address (0x4200000000000000000000000000000000000000 ) || addr > address (0x4200000000000000000000000000000000000800 ));
306
- } else if (chainId == stdChains.ArbitrumOne. chainId || chainId == stdChains.ArbitrumOneGoerli .chainId) {
257
+ } else if (chainId == stdChains[ " arbitrum_one " ]. chainId || chainId == stdChains[ " arbitrum_one_goerli " ] .chainId) {
307
258
// https://developer.arbitrum.io/useful-addresses#arbitrum-precompiles-l2-same-on-all-arb-chains
308
259
vm.assume (addr < address (0x0000000000000000000000000000000000000064 ) || addr > address (0x0000000000000000000000000000000000000068 ));
309
- } else if (chainId == stdChains.Avalanche. chainId || chainId == stdChains.AvalancheFuji .chainId) {
260
+ } else if (chainId == stdChains[ " avalanche " ]. chainId || chainId == stdChains[ " avalanche_fuji " ] .chainId) {
310
261
// https://github.com/ava-labs/subnet-evm/blob/47c03fd007ecaa6de2c52ea081596e0a88401f58/precompile/params.go#L18-L59
311
262
vm.assume (addr < address (0x0100000000000000000000000000000000000000 ) || addr > address (0x01000000000000000000000000000000000000ff ));
312
263
vm.assume (addr < address (0x0200000000000000000000000000000000000000 ) || addr > address (0x02000000000000000000000000000000000000FF ));
@@ -315,7 +266,12 @@ abstract contract StdCheatsSafe {
315
266
// forgefmt: disable-end
316
267
}
317
268
318
- function readEIP1559ScriptArtifact (string memory path ) internal virtual returns (EIP1559ScriptArtifact memory ) {
269
+ function readEIP1559ScriptArtifact (string memory path )
270
+ internal
271
+ view
272
+ virtual
273
+ returns (EIP1559ScriptArtifact memory )
274
+ {
319
275
string memory data = vm.readFile (path);
320
276
bytes memory parsedData = vm.parseJson (data);
321
277
RawEIP1559ScriptArtifact memory rawArtifact = abi.decode (parsedData, (RawEIP1559ScriptArtifact));
@@ -367,14 +323,14 @@ abstract contract StdCheatsSafe {
367
323
return txDetail;
368
324
}
369
325
370
- function readTx1559s (string memory path ) internal virtual returns (Tx1559[] memory ) {
326
+ function readTx1559s (string memory path ) internal view virtual returns (Tx1559[] memory ) {
371
327
string memory deployData = vm.readFile (path);
372
328
bytes memory parsedDeployData = vm.parseJson (deployData, ".transactions " );
373
329
RawTx1559[] memory rawTxs = abi.decode (parsedDeployData, (RawTx1559[]));
374
330
return rawToConvertedEIPTx1559s (rawTxs);
375
331
}
376
332
377
- function readTx1559 (string memory path , uint256 index ) internal virtual returns (Tx1559 memory ) {
333
+ function readTx1559 (string memory path , uint256 index ) internal view virtual returns (Tx1559 memory ) {
378
334
string memory deployData = vm.readFile (path);
379
335
string memory key = string (abi.encodePacked (".transactions[ " , vm.toString (index), "] " ));
380
336
bytes memory parsedDeployData = vm.parseJson (deployData, key);
@@ -383,14 +339,14 @@ abstract contract StdCheatsSafe {
383
339
}
384
340
385
341
// Analogous to readTransactions, but for receipts.
386
- function readReceipts (string memory path ) internal virtual returns (Receipt[] memory ) {
342
+ function readReceipts (string memory path ) internal view virtual returns (Receipt[] memory ) {
387
343
string memory deployData = vm.readFile (path);
388
344
bytes memory parsedDeployData = vm.parseJson (deployData, ".receipts " );
389
345
RawReceipt[] memory rawReceipts = abi.decode (parsedDeployData, (RawReceipt[]));
390
346
return rawToConvertedReceipts (rawReceipts);
391
347
}
392
348
393
- function readReceipt (string memory path , uint256 index ) internal virtual returns (Receipt memory ) {
349
+ function readReceipt (string memory path , uint256 index ) internal view virtual returns (Receipt memory ) {
394
350
string memory deployData = vm.readFile (path);
395
351
string memory key = string (abi.encodePacked (".receipts[ " , vm.toString (index), "] " ));
396
352
bytes memory parsedDeployData = vm.parseJson (deployData, key);
0 commit comments