Commit 63c71b69 authored by Maurelian's avatar Maurelian

contracts-bedrock: Add Superchain Config immutable to OptimismPortal

parent bd5f1d81
...@@ -156,6 +156,7 @@ library ChainAssertions { ...@@ -156,6 +156,7 @@ library ChainAssertions {
require(portal.guardian() == _cfg.portalGuardian()); require(portal.guardian() == _cfg.portalGuardian());
require(address(portal.SYSTEM_CONFIG()) == _contracts.SystemConfig); require(address(portal.SYSTEM_CONFIG()) == _contracts.SystemConfig);
require(address(portal.systemConfig()) == _contracts.SystemConfig); require(address(portal.systemConfig()) == _contracts.SystemConfig);
require(address(portal.superchainConfig()) == address(_contracts.SuperchainConfig));
require(portal.paused() == _isPaused); require(portal.paused() == _isPaused);
} }
...@@ -181,16 +182,16 @@ library ChainAssertions { ...@@ -181,16 +182,16 @@ library ChainAssertions {
} }
/// @notice Asserts that the SuperchainConfig is setup correctly /// @notice Asserts that the SuperchainConfig is setup correctly
function checkSuperchainConfig(Types.ContractSet memory _contracts, DeployConfig _cfg) internal view { function checkSuperchainConfig(
SuperchainConfig superchainConfig = SuperchainConfig(_contracts.SuperchainConfig); Types.ContractSet memory _proxies,
require(superchainConfig.guardian() == _cfg.portalGuardian()); DeployConfig _cfg,
require(superchainConfig.paused() == false); bool _isPaused
} )
internal
/// @notice Asserts that the SuperchainConfig is setup correctly view
function checkSuperchainConfig(Types.ContractSet memory _proxies, DeployConfig _cfg) internal view { {
SuperchainConfig superchainConfig = SuperchainConfig(_proxies.SuperchainConfig); SuperchainConfig superchainConfig = SuperchainConfig(_proxies.SuperchainConfig);
require(superchainConfig.guardian() == _cfg.portalGuardian()); require(superchainConfig.guardian() == _cfg.portalGuardian());
require(superchainConfig.paused() == false); require(superchainConfig.paused() == _isPaused);
} }
} }
...@@ -504,12 +504,14 @@ contract Deploy is Deployer { ...@@ -504,12 +504,14 @@ contract Deploy is Deployer {
L2OutputOracle l2OutputOracle = L2OutputOracle(mustGetAddress("L2OutputOracleProxy")); L2OutputOracle l2OutputOracle = L2OutputOracle(mustGetAddress("L2OutputOracleProxy"));
SystemConfig systemConfig = SystemConfig(mustGetAddress("SystemConfigProxy")); SystemConfig systemConfig = SystemConfig(mustGetAddress("SystemConfigProxy"));
SuperchainConfig superchainConfig = SuperchainConfig(mustGetAddress("SuperchainConfigProxy"));
OptimismPortal portal = new OptimismPortal{ salt: _implSalt() }({ OptimismPortal portal = new OptimismPortal{ salt: _implSalt() }({
_l2Oracle: l2OutputOracle, _l2Oracle: l2OutputOracle,
_guardian: guardian, _guardian: guardian,
_paused: true, _paused: true,
_systemConfig: systemConfig _systemConfig: systemConfig,
_superchainConfig: superchainConfig
}); });
save("OptimismPortal", address(portal)); save("OptimismPortal", address(portal));
...@@ -520,7 +522,7 @@ contract Deploy is Deployer { ...@@ -520,7 +522,7 @@ contract Deploy is Deployer {
// are always proxies. // are always proxies.
Types.ContractSet memory contracts = _proxiesUnstrict(); Types.ContractSet memory contracts = _proxiesUnstrict();
contracts.OptimismPortal = address(portal); contracts.OptimismPortal = address(portal);
ChainAssertions.checkOptimismPortal({ _contracts: contracts, _cfg: cfg, _isPaused: true }); ChainAssertions.checkOptimismPortal({ _contracts: contracts, _cfg: cfg, _isPaused: false });
require(loadInitializedSlot("OptimismPortal", false) == 1, "OptimismPortal is not initialized"); require(loadInitializedSlot("OptimismPortal", false) == 1, "OptimismPortal is not initialized");
...@@ -736,7 +738,7 @@ contract Deploy is Deployer { ...@@ -736,7 +738,7 @@ contract Deploy is Deployer {
_innerCallData: abi.encodeCall(SuperchainConfig.initialize, (cfg.portalGuardian())) _innerCallData: abi.encodeCall(SuperchainConfig.initialize, (cfg.portalGuardian()))
}); });
ChainAssertions.checkSuperchainConfig(_proxiesUnstrict(), cfg); ChainAssertions.checkSuperchainConfig({ _proxies: _proxiesUnstrict(), _cfg: cfg, _isPaused: false });
} }
/// @notice Initialize the DisputeGameFactory /// @notice Initialize the DisputeGameFactory
...@@ -939,7 +941,7 @@ contract Deploy is Deployer { ...@@ -939,7 +941,7 @@ contract Deploy is Deployer {
_upgradeAndCallViaSafe({ _upgradeAndCallViaSafe({
_proxy: payable(optimismPortalProxy), _proxy: payable(optimismPortalProxy),
_implementation: optimismPortal, _implementation: optimismPortal,
_innerCallData: abi.encodeCall(OptimismPortal.initialize, (false)) _innerCallData: abi.encodeCall(OptimismPortal.initialize, ())
}); });
OptimismPortal portal = OptimismPortal(payable(optimismPortalProxy)); OptimismPortal portal = OptimismPortal(payable(optimismPortalProxy));
......
...@@ -5,6 +5,7 @@ import { Initializable } from "@openzeppelin/contracts/proxy/utils/Initializable ...@@ -5,6 +5,7 @@ import { Initializable } from "@openzeppelin/contracts/proxy/utils/Initializable
import { SafeCall } from "src/libraries/SafeCall.sol"; import { SafeCall } from "src/libraries/SafeCall.sol";
import { L2OutputOracle } from "src/L1/L2OutputOracle.sol"; import { L2OutputOracle } from "src/L1/L2OutputOracle.sol";
import { SystemConfig } from "src/L1/SystemConfig.sol"; import { SystemConfig } from "src/L1/SystemConfig.sol";
import { SuperchainConfig } from "src/L1/SuperchainConfig.sol";
import { Constants } from "src/libraries/Constants.sol"; import { Constants } from "src/libraries/Constants.sol";
import { Types } from "src/libraries/Types.sol"; import { Types } from "src/libraries/Types.sol";
import { Hashing } from "src/libraries/Hashing.sol"; import { Hashing } from "src/libraries/Hashing.sol";
...@@ -51,6 +52,9 @@ contract OptimismPortal is Initializable, ResourceMetering, ISemver { ...@@ -51,6 +52,9 @@ contract OptimismPortal is Initializable, ResourceMetering, ISemver {
/// @custom:legacy /// @custom:legacy
address public immutable GUARDIAN; address public immutable GUARDIAN;
/// @notice The address of the Superchain Config contract.
SuperchainConfig internal immutable SUPERCHAIN_CONFIG;
/// @notice Address of the L2 account which initiated a withdrawal in this transaction. /// @notice Address of the L2 account which initiated a withdrawal in this transaction.
/// If the of this variable is the default L2 sender address, then we are NOT inside of /// If the of this variable is the default L2 sender address, then we are NOT inside of
/// a call to finalizeWithdrawalTransaction. /// a call to finalizeWithdrawalTransaction.
...@@ -62,10 +66,13 @@ contract OptimismPortal is Initializable, ResourceMetering, ISemver { ...@@ -62,10 +66,13 @@ contract OptimismPortal is Initializable, ResourceMetering, ISemver {
/// @notice A mapping of withdrawal hashes to `ProvenWithdrawal` data. /// @notice A mapping of withdrawal hashes to `ProvenWithdrawal` data.
mapping(bytes32 => ProvenWithdrawal) public provenWithdrawals; mapping(bytes32 => ProvenWithdrawal) public provenWithdrawals;
/// @notice Determines if cross domain messaging is paused. /// @custom:legacy
/// When set to true, withdrawals are paused. /// @custom:spacer paused
/// This may be removed in the future. /// @notice Spacer for backwards compatibility.
bool public paused; bool public spacer_53_0_1;
/// @notice The address of the Superchain Config contract.
SuperchainConfig public superchainConfig;
/// @notice Emitted when a transaction is deposited from L1 to L2. /// @notice Emitted when a transaction is deposited from L1 to L2.
/// The parameters of this event are read by the rollup node and used to derive deposit /// The parameters of this event are read by the rollup node and used to derive deposit
...@@ -97,7 +104,7 @@ contract OptimismPortal is Initializable, ResourceMetering, ISemver { ...@@ -97,7 +104,7 @@ contract OptimismPortal is Initializable, ResourceMetering, ISemver {
/// @notice Reverts when paused. /// @notice Reverts when paused.
modifier whenNotPaused() { modifier whenNotPaused() {
require(paused == false, "OptimismPortal: paused"); require(paused() == false, "OptimismPortal: paused");
_; _;
} }
...@@ -107,20 +114,19 @@ contract OptimismPortal is Initializable, ResourceMetering, ISemver { ...@@ -107,20 +114,19 @@ contract OptimismPortal is Initializable, ResourceMetering, ISemver {
/// @notice Constructs the OptimismPortal contract. /// @notice Constructs the OptimismPortal contract.
/// @param _l2Oracle Address of the L2OutputOracle contract. /// @param _l2Oracle Address of the L2OutputOracle contract.
/// @param _guardian Address that can pause withdrawals.
/// @param _paused Sets the contract's pausability state.
/// @param _systemConfig Address of the SystemConfig contract. /// @param _systemConfig Address of the SystemConfig contract.
constructor(L2OutputOracle _l2Oracle, address _guardian, bool _paused, SystemConfig _systemConfig) { /// @param _superchainConfig Address of the SuperchainConfig contract.
constructor(L2OutputOracle _l2Oracle, SystemConfig _systemConfig, SuperchainConfig _superchainConfig) {
L2_ORACLE = _l2Oracle; L2_ORACLE = _l2Oracle;
GUARDIAN = _guardian;
SYSTEM_CONFIG = _systemConfig; SYSTEM_CONFIG = _systemConfig;
initialize(_paused); SUPERCHAIN_CONFIG = _superchainConfig;
GUARDIAN = _superchainConfig.guardian();
initialize();
} }
/// @notice Initializer. /// @notice Initializer.
function initialize(bool _paused) public initializer { function initialize() public initializer {
l2Sender = Constants.DEFAULT_L2_SENDER; l2Sender = Constants.DEFAULT_L2_SENDER;
paused = _paused;
__ResourceMetering_init(); __ResourceMetering_init();
} }
...@@ -136,24 +142,23 @@ contract OptimismPortal is Initializable, ResourceMetering, ISemver { ...@@ -136,24 +142,23 @@ contract OptimismPortal is Initializable, ResourceMetering, ISemver {
return SYSTEM_CONFIG; return SYSTEM_CONFIG;
} }
/// @notice Getter function for the address of the L2OutputOracle on this chain. /// @notice Getter function for the address of the L2OutputOracle on this chain. This will be removed in the
/// future, use `SuperchainConfig.guardian()` instead.
/// @notice Address of the L2OutputOracle on this chain. /// @notice Address of the L2OutputOracle on this chain.
/// @custom:legacy
function guardian() public view returns (address) { function guardian() public view returns (address) {
return GUARDIAN; return SUPERCHAIN_CONFIG.guardian();
} }
/// @notice Pauses withdrawals. /// @notice Getter function for the address of the SuperchainConfig on this chain.
function pause() external { /// @return SuperchainConfig Address of the SuperchainConfig on this chain.
require(msg.sender == GUARDIAN, "OptimismPortal: only guardian can pause"); function superchainConfig() public view returns (SuperchainConfig) {
paused = true; return SUPERCHAIN_CONFIG;
emit Paused(msg.sender);
} }
/// @notice Unpauses withdrawals. /// @notice Getter for the current paused status.
function unpause() external { function paused() public view returns (bool paused_) {
require(msg.sender == GUARDIAN, "OptimismPortal: only guardian can unpause"); paused_ = SUPERCHAIN_CONFIG.paused();
paused = false;
emit Unpaused(msg.sender);
} }
/// @notice Computes the minimum gas limit for a deposit. /// @notice Computes the minimum gas limit for a deposit.
......
...@@ -63,7 +63,7 @@ contract Initializer_Test is Bridge_Initializer { ...@@ -63,7 +63,7 @@ contract Initializer_Test is Bridge_Initializer {
contracts.push( contracts.push(
InitializeableContract({ InitializeableContract({
target: address(optimismPortal), target: address(optimismPortal),
initCalldata: abi.encodeCall(optimismPortal.initialize, (false)), initCalldata: abi.encodeCall(optimismPortal.initialize, ()),
initializedSlotVal: deploy.loadInitializedSlot("OptimismPortal", true) initializedSlotVal: deploy.loadInitializedSlot("OptimismPortal", true)
}) })
); );
......
...@@ -21,9 +21,6 @@ import { SystemConfig } from "src/L1/SystemConfig.sol"; ...@@ -21,9 +21,6 @@ import { SystemConfig } from "src/L1/SystemConfig.sol";
import { OptimismPortal } from "src/L1/OptimismPortal.sol"; import { OptimismPortal } from "src/L1/OptimismPortal.sol";
contract OptimismPortal_Test is CommonTest { contract OptimismPortal_Test is CommonTest {
event Paused(address);
event Unpaused(address);
address depositor; address depositor;
function setUp() public override { function setUp() public override {
...@@ -49,11 +46,11 @@ contract OptimismPortal_Test is CommonTest { ...@@ -49,11 +46,11 @@ contract OptimismPortal_Test is CommonTest {
assertEq(optimismPortal.paused(), false); assertEq(optimismPortal.paused(), false);
vm.expectEmit(address(optimismPortal)); vm.expectEmit(address(superchainConfig));
emit Paused(guardian); emit Paused("identifier");
vm.prank(guardian); vm.prank(guardian);
optimismPortal.pause(); superchainConfig.pause("identifier");
assertEq(optimismPortal.paused(), true); assertEq(optimismPortal.paused(), true);
} }
...@@ -63,9 +60,9 @@ contract OptimismPortal_Test is CommonTest { ...@@ -63,9 +60,9 @@ contract OptimismPortal_Test is CommonTest {
assertEq(optimismPortal.paused(), false); assertEq(optimismPortal.paused(), false);
assertTrue(optimismPortal.GUARDIAN() != alice); assertTrue(optimismPortal.GUARDIAN() != alice);
vm.expectRevert("OptimismPortal: only guardian can pause"); vm.expectRevert("SuperchainConfig: only guardian can pause");
vm.prank(alice); vm.prank(alice);
optimismPortal.pause(); superchainConfig.pause("identifier");
assertEq(optimismPortal.paused(), false); assertEq(optimismPortal.paused(), false);
} }
...@@ -76,13 +73,13 @@ contract OptimismPortal_Test is CommonTest { ...@@ -76,13 +73,13 @@ contract OptimismPortal_Test is CommonTest {
address guardian = optimismPortal.GUARDIAN(); address guardian = optimismPortal.GUARDIAN();
vm.prank(guardian); vm.prank(guardian);
optimismPortal.pause(); superchainConfig.pause("identifier");
assertEq(optimismPortal.paused(), true); assertEq(optimismPortal.paused(), true);
vm.expectEmit(address(optimismPortal)); vm.expectEmit(address(superchainConfig));
emit Unpaused(guardian); emit Unpaused();
vm.prank(guardian); vm.prank(guardian);
optimismPortal.unpause(); superchainConfig.unpause();
assertEq(optimismPortal.paused(), false); assertEq(optimismPortal.paused(), false);
} }
...@@ -92,13 +89,13 @@ contract OptimismPortal_Test is CommonTest { ...@@ -92,13 +89,13 @@ contract OptimismPortal_Test is CommonTest {
address guardian = optimismPortal.GUARDIAN(); address guardian = optimismPortal.GUARDIAN();
vm.prank(guardian); vm.prank(guardian);
optimismPortal.pause(); superchainConfig.pause("identifier");
assertEq(optimismPortal.paused(), true); assertEq(optimismPortal.paused(), true);
assertTrue(optimismPortal.GUARDIAN() != alice); assertTrue(optimismPortal.GUARDIAN() != alice);
vm.expectRevert("OptimismPortal: only guardian can unpause"); vm.expectRevert("SuperchainConfig: only guardian can unpause");
vm.prank(alice); vm.prank(alice);
optimismPortal.unpause(); superchainConfig.unpause();
assertEq(optimismPortal.paused(), true); assertEq(optimismPortal.paused(), true);
} }
...@@ -383,7 +380,7 @@ contract OptimismPortal_FinalizeWithdrawal_Test is CommonTest { ...@@ -383,7 +380,7 @@ contract OptimismPortal_FinalizeWithdrawal_Test is CommonTest {
/// @dev Tests that `proveWithdrawalTransaction` reverts when paused. /// @dev Tests that `proveWithdrawalTransaction` reverts when paused.
function test_proveWithdrawalTransaction_paused_reverts() external { function test_proveWithdrawalTransaction_paused_reverts() external {
vm.prank(optimismPortal.GUARDIAN()); vm.prank(optimismPortal.GUARDIAN());
optimismPortal.pause(); superchainConfig.pause("identifier");
vm.expectRevert("OptimismPortal: paused"); vm.expectRevert("OptimismPortal: paused");
optimismPortal.proveWithdrawalTransaction({ optimismPortal.proveWithdrawalTransaction({
...@@ -535,7 +532,7 @@ contract OptimismPortal_FinalizeWithdrawal_Test is CommonTest { ...@@ -535,7 +532,7 @@ contract OptimismPortal_FinalizeWithdrawal_Test is CommonTest {
/// @dev Tests that `finalizeWithdrawalTransaction` reverts if the contract is paused. /// @dev Tests that `finalizeWithdrawalTransaction` reverts if the contract is paused.
function test_finalizeWithdrawalTransaction_paused_reverts() external { function test_finalizeWithdrawalTransaction_paused_reverts() external {
vm.prank(optimismPortal.GUARDIAN()); vm.prank(optimismPortal.GUARDIAN());
optimismPortal.pause(); superchainConfig.pause("identifier");
vm.expectRevert("OptimismPortal: paused"); vm.expectRevert("OptimismPortal: paused");
optimismPortal.finalizeWithdrawalTransaction(_defaultTx); optimismPortal.finalizeWithdrawalTransaction(_defaultTx);
...@@ -899,14 +896,14 @@ contract OptimismPortalUpgradeable_Test is CommonTest { ...@@ -899,14 +896,14 @@ contract OptimismPortalUpgradeable_Test is CommonTest {
/// @dev Tests that the proxy cannot be initialized twice. /// @dev Tests that the proxy cannot be initialized twice.
function test_initialize_cannotInitProxy_reverts() external { function test_initialize_cannotInitProxy_reverts() external {
vm.expectRevert("Initializable: contract is already initialized"); vm.expectRevert("Initializable: contract is already initialized");
optimismPortal.initialize({ _paused: false }); optimismPortal.initialize();
} }
/// @dev Tests that the implementation cannot be initialized twice. /// @dev Tests that the implementation cannot be initialized twice.
function test_initialize_cannotInitImpl_reverts() external { function test_initialize_cannotInitImpl_reverts() external {
address opImpl = deploy.mustGetAddress("OptimismPortal"); address opImpl = deploy.mustGetAddress("OptimismPortal");
vm.expectRevert("Initializable: contract is already initialized"); vm.expectRevert("Initializable: contract is already initialized");
OptimismPortal(payable(opImpl)).initialize({ _paused: false }); OptimismPortal(payable(opImpl)).initialize();
} }
/// @dev Tests that the proxy can be upgraded. /// @dev Tests that the proxy can be upgraded.
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment