diff --git a/src/Vm.sol b/src/Vm.sol index aff0fb63f..d0712a4c9 100644 --- a/src/Vm.sol +++ b/src/Vm.sol @@ -48,6 +48,28 @@ interface VmSafe { Extcodecopy } + /// Forge execution contexts. + enum ForgeContext { + // Test group execution context (test, coverage or snapshot). + TestGroup, + // `forge test` execution context. + Test, + // `forge coverage` execution context. + Coverage, + // `forge snapshot` execution context. + Snapshot, + // Script group execution context (dry run, broadcast or resume). + ScriptGroup, + // `forge script` execution context. + ScriptDryRun, + // `forge script --broadcast` execution context. + ScriptBroadcast, + // `forge script --resume` execution context. + ScriptResume, + // Unknown `forge` execution context. + Unknown + } + /// An Ethereum log. Returned by `getRecordedLogs`. struct Log { // The topics of the log, including the signature, if any. @@ -207,6 +229,20 @@ interface VmSafe { bool reverted; } + /// Gas used. Returned by `lastCallGas`. + struct Gas { + // The gas limit of the call. + uint64 gasLimit; + // The total gas used. + uint64 gasTotalUsed; + // The amount of gas used for memory expansion. + uint64 gasMemoryUsed; + // The amount of gas refunded. + int64 gasRefunded; + // The amount of gas remaining. + uint64 gasRemaining; + } + // ======== Environment ======== /// Gets the environment variable `name` and parses it as `address`. @@ -356,6 +392,9 @@ interface VmSafe { /// Reverts if the variable was not found or could not be parsed. function envUint(string calldata name, string calldata delim) external view returns (uint256[] memory value); + /// Returns true if `forge` command was executed in given context. + function isContext(ForgeContext context) external view returns (bool isContext); + /// Sets environment variables. function setEnv(string calldata name, string calldata value) external; @@ -372,6 +411,12 @@ interface VmSafe { external returns (EthGetLogs[] memory logs); + /// Gets the current `block.blobbasefee`. + /// You should use this instead of `block.blobbasefee` if you use `vm.blobBaseFee`, as `block.blobbasefee` is assumed to be constant across a transaction, + /// and as a result will get optimized out by the compiler. + /// See https://github.com/foundry-rs/foundry/issues/6180 + function getBlobBaseFee() external view returns (uint256 blobBaseFee); + /// Gets the current `block.number`. /// You should use this instead of `block.number` if you use `vm.roll`, as `block.number` is assumed to be constant across a transaction, /// and as a result will get optimized out by the compiler. @@ -402,6 +447,9 @@ interface VmSafe { /// Gets all the recorded logs. function getRecordedLogs() external returns (Log[] memory logs); + /// Gets the gas used in the last call. + function lastCallGas() external view returns (Gas memory gas); + /// Loads a storage slot from an address. function load(address target, bytes32 slot) external view returns (bytes32 data); @@ -426,6 +474,17 @@ interface VmSafe { /// Signs `digest` with `privateKey` using the secp256k1 curve. function sign(uint256 privateKey, bytes32 digest) external pure returns (uint8 v, bytes32 r, bytes32 s); + /// Signs `digest` with signer provided to script using the secp256k1 curve. + /// If `--sender` is provided, the signer with provided address is used, otherwise, + /// if exactly one signer is provided to the script, that signer is used. + /// Raises error if signer passed through `--sender` does not match any unlocked signers or + /// if `--sender` is not provided and not exactly one signer is passed to the script. + function sign(bytes32 digest) external pure returns (uint8 v, bytes32 r, bytes32 s); + + /// Signs `digest` with signer provided to script using the secp256k1 curve. + /// Raises error if none of the signers passed into the script have provided address. + function sign(address signer, bytes32 digest) external pure returns (uint8 v, bytes32 r, bytes32 s); + /// Starts recording all map SSTOREs for later retrieval. function startMappingRecording() external; @@ -467,10 +526,12 @@ interface VmSafe { /// Given a path, query the file system to get information about a file, directory, etc. function fsMetadata(string calldata path) external view returns (FsMetadata memory metadata); - /// Gets the creation bytecode from an artifact file. Takes in the relative path to the json file. + /// Gets the creation bytecode from an artifact file. Takes in the relative path to the json file or the path to the + /// artifact in the form of :: where and parts are optional. function getCode(string calldata artifactPath) external view returns (bytes memory creationBytecode); - /// Gets the deployed bytecode from an artifact file. Takes in the relative path to the json file. + /// Gets the deployed bytecode from an artifact file. Takes in the relative path to the json file or the path to the + /// artifact in the form of :: where and parts are optional. function getDeployedCode(string calldata artifactPath) external view returns (bytes memory runtimeBytecode); /// Returns true if the path exists on disk and is pointing at a directory, else returns false. @@ -485,9 +546,15 @@ interface VmSafe { /// Prompts the user for a string value in the terminal. function prompt(string calldata promptText) external returns (string memory input); + /// Prompts the user for an address in the terminal. + function promptAddress(string calldata promptText) external returns (address); + /// Prompts the user for a hidden string value in the terminal. function promptSecret(string calldata promptText) external returns (string memory input); + /// Prompts the user for uint256 in the terminal. + function promptUint(string calldata promptText) external returns (uint256); + /// Reads the directory at the given path recursively, up to `maxDepth`. /// `maxDepth` defaults to 1, meaning only the direct children of the given directory will be returned. /// Follows symbolic links if `followLinks` is true. @@ -701,8 +768,11 @@ interface VmSafe { // ======== Scripting ======== - /// Using the address that calls the test contract, has the next call (at this call depth only) - /// create a transaction that can later be signed and sent onchain. + /// Has the next call (at this call depth only) create transactions that can later be signed and sent onchain. + /// Broadcasting address is determined by checking the following in order: + /// 1. If `--sender` argument was provided, that address is used. + /// 2. If exactly one signer (e.g. private key, hw wallet, keystore) is set when `forge broadcast` is invoked, that signer is used. + /// 3. Otherwise, default foundry sender (1804c8AB1F12E6bbf3894d4083f33e07309d1f38) is used. function broadcast() external; /// Has the next call (at this call depth only) create a transaction with the address provided @@ -713,8 +783,11 @@ interface VmSafe { /// provided as the sender that can later be signed and sent onchain. function broadcast(uint256 privateKey) external; - /// Using the address that calls the test contract, has all subsequent calls - /// (at this call depth only) create transactions that can later be signed and sent onchain. + /// Has all subsequent calls (at this call depth only) create transactions that can later be signed and sent onchain. + /// Broadcasting address is determined by checking the following in order: + /// 1. If `--sender` argument was provided, that address is used. + /// 2. If exactly one signer (e.g. private key, hw wallet, keystore) is set when `forge broadcast` is invoked, that signer is used. + /// 3. Otherwise, default foundry sender (1804c8AB1F12E6bbf3894d4083f33e07309d1f38) is used. function startBroadcast() external; /// Has all subsequent calls (at this call depth only) create transactions with the address @@ -730,6 +803,11 @@ interface VmSafe { // ======== String ======== + /// Returns the index of the first occurrence of a `key` in an `input` string. + /// Returns `NOT_FOUND` (i.e. `type(uint256).max`) if the `key` is not found. + /// Returns 0 in case of an empty `key`. + function indexOf(string calldata input, string memory key) external pure returns (uint256); + /// Parses the given `string` into an `address`. function parseAddress(string calldata stringifiedValue) external pure returns (address parsedValue); @@ -1391,6 +1469,9 @@ interface Vm is VmSafe { /// In forking mode, explicitly grant the given address cheatcode access. function allowCheatcodes(address account) external; + /// Sets `block.blobbasefee` + function blobBaseFee(uint256 newBlobBaseFee) external; + /// Sets `block.chainid`. function chainId(uint256 newChainId) external;