// SPDX-License-Identifier: UNLICENSED pragma solidity =0.8.18; import "../../SomaAccessControl/utils/AccessibleUpgradeable.sol"; import "./ISeizableSecurity.sol"; /** * @notice Implementation of the {ISeizableSecurity} interface. */ abstract contract SeizableSecurity is ISeizableSecurity, AccessibleUpgradeable { /** * @notice Initializer for extended contracts. */ function __SeizableSecurity_init() internal { __ERC165_init_unchained(); __Context_init_unchained(); __SomaContract_init_unchained(); __Accessible_init_unchained(); __Multicall_init_unchained(); __Pausable_init_unchained(); __SeizableSecurity_init_unchained(); } /** * @notice Unchained initializer. */ function __SeizableSecurity_init_unchained() internal onlyInitializing { LOCAL_SEIZE_ROLE = keccak256(abi.encodePacked(address(this), GLOBAL_SEIZE_ROLE)); } /** * @notice Returns the GLOBAL_SEIZE_ROLE. */ bytes32 public constant GLOBAL_SEIZE_ROLE = keccak256("SeizableSecurity.SEIZE_ROLE"); /** * @notice Returns the LOCAL_SEIZE_ROLE. */ bytes32 public LOCAL_SEIZE_ROLE; /** * @notice True if a seize is in progress, else False. */ bool internal seizeInProgress; /** * @notice Modifier to update seize in progress state. */ modifier enableSeizing() { seizeInProgress = true; _; seizeInProgress = false; } /** * @notice Modifier to restrict a function caller to an account with the GLOBAL_SEIZE_ROLE or LOCAL_SEIZE_ROLE. */ modifier onlySeizeRole() { address sender = _msgSender(); require( hasRole(LOCAL_SEIZE_ROLE, sender) || hasRole(GLOBAL_SEIZE_ROLE, sender), "SeizableSecurity: UNAUTHORIZED" ); _; } /** * @notice Checks if SeizableSecurity inherits a given contract interface. * @dev See {IERC165-supportsInterface}. */ function supportsInterface(bytes4 interfaceId) public view virtual override returns (bool) { return interfaceId == type(ISeizableSecurity).interfaceId || super.supportsInterface(interfaceId); } /** * @inheritdoc ISeizableSecurity */ function seize(address tokenHolder, uint256 amount) public override enableSeizing onlySeizeRole { address seizeTo = SOMA.seizeTo(); _seize(tokenHolder, seizeTo, amount); emit Seized(_msgSender(), tokenHolder, seizeTo, amount); } function _seize(address from, address to, uint256 amount) internal virtual; uint256[50] private __gap; }