In Solidity contracts, implementing an emergency stop feature is typically used to respond quickly to severe security issues or urgent maintenance needs by pausing the contract's execution. This feature is also known as the "Circuit Breaker".
Implementation Steps:
-
State Variable Addition First, define a state variable in the contract to control whether execution is paused. This variable is typically a
booltype.soliditycontract MyContract { bool private stopped = false; } -
Modifier Definition Next, define a modifier that checks if the contract is paused before executing affected functions.
soliditymodifier stopInEmergency { require(!stopped, "Contract is stopped in emergency"); _; } -
Control Functions Define one or more functions callable only by the contract owner to toggle the emergency state. This usually includes functions to activate and deactivate emergency mode.
solidityfunction toggleContractActive() public onlyOwner { stopped = !stopped; }Here,
onlyOwneris a modifier ensuring only the contract owner can call this function, preventing malicious users from triggering the emergency stop. -
Apply Modifiers Apply the defined modifier to critical functions (e.g., fund transfers or state updates). This ensures these functions cannot execute when the contract is paused.
solidityfunction transfer(address _to, uint _amount) public stopInEmergency { // Transfer logic }
Example
Here is a simple example demonstrating emergency stop implementation in a token contract:
solidity// SPDX-License-Identifier: MIT pragma solidity ^0.8.4; contract Token { mapping(address => uint) balances; bool private stopped = false; address public owner; constructor() { owner = msg.sender; } modifier onlyOwner { require(msg.sender == owner, "Not the owner"); _; } modifier stopInEmergency { require(!stopped, "Contract is stopped in emergency"); _; } function toggleContractActive() public onlyOwner { stopped = !stopped; } function deposit() public payable { balances[msg.sender] += msg.value; } function withdraw(uint _amount) public stopInEmergency { require(balances[msg.sender] >= _amount, "Insufficient funds"); payable(msg.sender).transfer(_amount); balances[msg.sender] -= _amount; } }
In this example, the withdraw function uses the stopInEmergency modifier, meaning withdrawal is blocked if the contract is paused (stopped is true). The contract owner controls the emergency state via toggleContractActive.
Summary
Adding an emergency stop feature enhances security and controllability when facing unforeseen issues. This is a crucial feature, especially for handling large funds or critical logic.