Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -125,7 +125,7 @@ checkout-base-contracts-commit:
##
# Task Signer Tool
##
SIGNER_TOOL_COMMIT=194e3af584839bc9c1e900f96292e539aa783cd7
SIGNER_TOOL_COMMIT=cff3a601c6780e9fe7d303c58d59574dc1ba491b
SIGNER_TOOL_PATH=signer-tool

.PHONY: checkout-signer-tool
Expand Down
16 changes: 16 additions & 0 deletions sepolia/2025-12-22-update-bridge-alpha-config/.env
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
OP_COMMIT=d09c836f818c73ae139f60b717654c4e53712743
BASE_CONTRACTS_COMMIT=dcd8c98aa881e0ae4ebf872e0d91692a7bf94000
BRIDGE_COMMIT=39b6f53a1e2c623bef1dd2fc9626389784d32e4c

# DeployBridgeValidator config
L2_BRIDGE_VALIDATOR_PROXY=0xC05324843aca6C2b7446F15bdB17AF4599b761E6

# UpdateConfig config
OWNER_SAFE=0x5dfEB066334B67355A15dc9b67317fD2a2e1f77f
L1_PORTAL=0x49f53e41452C74589E85cA1677426Ba426459e85
L2_BRIDGE_PROXY=0x64567a9147fa89B1edc987e36Eb6f4b6db71656b
L2_BRIDGE_IMPL=0x636b7f211cB373bd8f6dC51AbDfeDe15a49b680f

SENDER=0xb2d9a52e76841279EF0372c534C539a4f68f8C0B

RECORD_STATE_DIFF=true
18 changes: 18 additions & 0 deletions sepolia/2025-12-22-update-bridge-alpha-config/FACILITATOR.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
# Facilitator Guide

Guide for facilitators after collecting signatures from signers.

### 1. Update repo:

```bash
cd contract-deployments
git pull
cd sepolia/2025-12-22-update-bridge-alpha-config
make deps
```

### 2. Execute update

```bash
SIGNATURES=AAABBBCCC make execute
```
36 changes: 36 additions & 0 deletions sepolia/2025-12-22-update-bridge-alpha-config/Makefile
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
include ../../Makefile
include ../.env
include .env

ifndef LEDGER_ACCOUNT
override LEDGER_ACCOUNT = 1
endif

RPC_URL=$(L1_RPC_URL)
SCRIPT_NAME=UpdateConfig

.PHONY: deps
deps:
forge install --no-git github.com/base/bridge@$(BRIDGE_COMMIT)

.PHONY: deploy
deploy:
forge script DeployBridgeUpdates --rpc-url $(L2_RPC_URL) \
--account testnet-admin --broadcast -vvvv

.PHONY: gen-validation
gen-validation: checkout-signer-tool run-script

.PHONY: run-script
run-script:
cd $(SIGNER_TOOL_PATH); \
npm ci; \
bun run scripts/genValidationFile.ts --rpc-url $(RPC_URL) \
--workdir .. --forge-cmd 'forge script --rpc-url $(RPC_URL) \
$(SCRIPT_NAME) --sig "sign(address[])" [] --sender $(SENDER)' --out ../validations/base-signer.json;

# Execute
.PHONY: execute
execute:
forge script --rpc-url $(RPC_URL) $(SCRIPT_NAME) \
--sig "run(bytes)" $(SIGNATURES) --ledger --hd-paths "m/44'/60'/$(LEDGER_ACCOUNT)'/0/0" --broadcast -vvvv
50 changes: 50 additions & 0 deletions sepolia/2025-12-22-update-bridge-alpha-config/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
# Update Base Bridge Alpha Validator Config

Status: READY TO SIGN

Deployment: [EXECUTED](https://sepolia.basescan.org/tx/0x03b7f6fb2777fdd874c22994d28d56cab6c7b4462feebee967219cfd460a4186)

## Description

Upgrades the `Bridge` contract for the testnet alpha deployment of [Base Bridge](https://github.com/base/bridge).

## Install dependencies

### 1. Update foundry

```bash
foundryup
```

### 2. Install Node.js if needed

First, check if you have node installed

```bash
node --version
```

If you do not see a version above or if it is older than v18.18, install

```bash
brew install node
```

## Sign Task

### 1. Update repo:

```bash
cd contract-deployments
git pull
```

### 2. Run the signing tool (NOTE: do not enter the task directory. Run this command from the project's root).

```bash
make sign-task
```

### 3. Open the UI at [http://localhost:3000](http://localhost:3000)

### 4. After signing, you can end the signer tool process with Ctrl + C
5 changes: 5 additions & 0 deletions sepolia/2025-12-22-update-bridge-alpha-config/addresses.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
{
"BridgeValidatorProxy": "0x14EDFe5b05CF5693336ABb1533a4Df0602A9ad3C",
"BridgeImpl": "0x636b7f211cB373bd8f6dC51AbDfeDe15a49b680f",
"RelayerOrchestratorProxy": "0x3201A59f42Eae46D5DAbd06dfC95a7Ba475bbfaE"
}
9 changes: 9 additions & 0 deletions sepolia/2025-12-22-update-bridge-alpha-config/config.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
{
"initialOwner": "0x5dfEB066334B67355A15dc9b67317fD2a2e1f77f",
"partnerValidators": "0x9614938Cb05C923298d3b3d72b127781c084681a",
"baseValidators": [
"0x0e9a877906EBc3b7098DA2404412BF0Ed1A5EFb4",
"0x6D0E9C04BD896608b7e10b87FB686E1Feba85510"
],
"partnerValidatorThreshold": 0
}
21 changes: 21 additions & 0 deletions sepolia/2025-12-22-update-bridge-alpha-config/foundry.toml
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
[profile.default]
src = 'src'
out = 'out'
libs = ['lib']
broadcast = 'records'
fs_permissions = [{ access = "read-write", path = "./" }]
optimizer = true
optimizer_runs = 999999
solc_version = "0.8.28"
via-ir = false
remappings = [
'@eth-optimism-bedrock/=lib/optimism/packages/contracts-bedrock/',
'@openzeppelin/contracts/=lib/openzeppelin-contracts/contracts',
'@openzeppelin/contracts-upgradeable/=lib/openzeppelin-contracts-upgradeable/contracts',
'@rari-capital/solmate/=lib/solmate/',
'@base-contracts/=lib/base-contracts',
'@solady/=lib/solady/src/',
'@lib-keccak=lib/lib-keccak/contracts/lib/'
]

# See more config options https://github.com/foundry-rs/foundry/tree/master/config

Large diffs are not rendered by default.

Original file line number Diff line number Diff line change
@@ -0,0 +1,117 @@
// SPDX-License-Identifier: MIT
pragma solidity 0.8.28;

import {Script} from "forge-std/Script.sol";
import {stdJson} from "forge-std/StdJson.sol";
import {LibString} from "solady/utils/LibString.sol";
import {ERC1967Factory} from "@solady/utils/ERC1967Factory.sol";
import {ERC1967FactoryConstants} from "@solady/utils/ERC1967FactoryConstants.sol";
import {AddressAliasHelper} from "@eth-optimism-bedrock/src/vendor/AddressAliasHelper.sol";

import {Bridge} from "bridge/Bridge.sol";
import {RelayerOrchestrator} from "bridge/periphery/RelayerOrchestrator.sol";
import {BridgeValidator} from "bridge/BridgeValidator.sol";
import {Pubkey} from "bridge/libraries/SVMLib.sol";

struct Cfg {
address erc1967Factory;
address initialOwner;
address partnerValidators;
address[] baseValidators;
uint256 partnerValidatorThreshold;
}

contract DeployBridgeUpdates is Script {
using stdJson for string;
using AddressAliasHelper for address;

string public cfgData;
Cfg public cfg;

address public immutable BRIDGE_PROXY;
address public immutable BRIDGE_VALIDATOR_PROXY;

constructor() {
BRIDGE_PROXY = vm.envAddress("L2_BRIDGE_PROXY");
BRIDGE_VALIDATOR_PROXY = vm.envAddress("L2_BRIDGE_VALIDATOR_PROXY");
}

function setUp() public {
cfgData = vm.readFile(string.concat(vm.projectRoot(), "/config.json"));

cfg.erc1967Factory = ERC1967FactoryConstants.ADDRESS;
cfg.initialOwner = _readAddressFromConfig("initialOwner").applyL1ToL2Alias();
cfg.partnerValidators = _readAddressFromConfig("partnerValidators");
cfg.baseValidators = _readAddressArrayFromConfig("baseValidators");
cfg.partnerValidatorThreshold = _readUintFromConfig("partnerValidatorThreshold");
}

function run() public {
address twinBeacon = Bridge(BRIDGE_PROXY).TWIN_BEACON();
address crossChainErc20Factory = Bridge(BRIDGE_PROXY).CROSS_CHAIN_ERC20_FACTORY();
Pubkey remoteBridge = Bridge(BRIDGE_PROXY).REMOTE_BRIDGE();
uint128 baseThreshold = BridgeValidator(BRIDGE_VALIDATOR_PROXY).getBaseThreshold();
uint256 baseSignerCount = BridgeValidator(BRIDGE_VALIDATOR_PROXY).getBaseValidatorCount();

require(baseSignerCount == cfg.baseValidators.length, "Precheck 00");

for (uint256 i; i < baseSignerCount; i++) {
require(BridgeValidator(BRIDGE_VALIDATOR_PROXY).isBaseValidator(cfg.baseValidators[i]), "Precheck 01");
}

vm.startBroadcast();
address bridgeValidatorImpl =
address(new BridgeValidator({bridgeAddress: BRIDGE_PROXY, partnerValidators: cfg.partnerValidators}));
address bridgeValidatorProxy = ERC1967Factory(cfg.erc1967Factory)
.deployAndCall({
implementation: bridgeValidatorImpl,
admin: cfg.initialOwner,
data: abi.encodeCall(
BridgeValidator.initialize, (cfg.baseValidators, baseThreshold, cfg.partnerValidatorThreshold)
)
});

address bridgeImpl = address(
new Bridge({
remoteBridge: remoteBridge,
twinBeacon: twinBeacon,
crossChainErc20Factory: crossChainErc20Factory,
bridgeValidator: bridgeValidatorProxy
})
);
address relayerOrchestratorProxy =
_deployRelayerOrchestrator({bridge: BRIDGE_PROXY, bridgeValidator: bridgeValidatorProxy});
vm.stopBroadcast();

_serializeAddress({key: "BridgeValidatorProxy", value: bridgeValidatorProxy});
_serializeAddress({key: "BridgeImpl", value: bridgeImpl});
_serializeAddress({key: "RelayerOrchestratorProxy", value: relayerOrchestratorProxy});
}

function _deployRelayerOrchestrator(address bridge, address bridgeValidator) private returns (address) {
address relayerOrchestratorImpl =
address(new RelayerOrchestrator({bridge: bridge, bridgeValidator: bridgeValidator}));

return
ERC1967Factory(cfg.erc1967Factory)
.deploy({implementation: relayerOrchestratorImpl, admin: cfg.initialOwner});
}

function _serializeAddress(string memory key, address value) private {
vm.writeJson({
json: LibString.toHexStringChecksummed(value), path: "addresses.json", valueKey: string.concat(".", key)
});
}

function _readUintFromConfig(string memory key) private view returns (uint256) {
return vm.parseJsonUint({json: cfgData, key: string.concat(".", key)});
}

function _readAddressArrayFromConfig(string memory key) private view returns (address[] memory) {
return vm.parseJsonAddressArray({json: cfgData, key: string.concat(".", key)});
}

function _readAddressFromConfig(string memory key) private view returns (address) {
return vm.parseJsonAddress({json: cfgData, key: string.concat(".", key)});
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
// SPDX-License-Identifier: MIT
pragma solidity 0.8.28;

import {Vm} from "forge-std/Vm.sol";
import {IMulticall3} from "forge-std/interfaces/IMulticall3.sol";
import {Simulation} from "@base-contracts/script/universal/Simulation.sol";
import {MultisigScript} from "@base-contracts/script/universal/MultisigScript.sol";
import {AddressAliasHelper} from "@eth-optimism-bedrock/src/vendor/AddressAliasHelper.sol";
import {ERC1967Factory} from "solady/utils/ERC1967Factory.sol";
import {ERC1967FactoryConstants} from "solady/utils/ERC1967FactoryConstants.sol";

interface IOptimismPortal2 {
function depositTransaction(address _to, uint256 _value, uint64 _gasLimit, bool _isCreation, bytes memory _data)
external
payable;
}

contract UpdateConfig is MultisigScript {
using AddressAliasHelper for address;

address public immutable OWNER_SAFE = vm.envAddress("OWNER_SAFE");
address public immutable L1_PORTAL = vm.envAddress("L1_PORTAL");
address public immutable L2_BRIDGE_PROXY = vm.envAddress("L2_BRIDGE_PROXY");
address public immutable L2_BRIDGE_IMPL = vm.envAddress("L2_BRIDGE_IMPL");

function _buildCalls() internal view override returns (IMulticall3.Call3Value[] memory) {
IMulticall3.Call3Value[] memory calls = new IMulticall3.Call3Value[](1);

address to = ERC1967FactoryConstants.ADDRESS;
uint256 value = 0;
uint64 gasLimit = 100_000;
bool isCreation = false;
bytes memory data = abi.encodeCall(ERC1967Factory.upgrade, (L2_BRIDGE_PROXY, L2_BRIDGE_IMPL));

calls[0] = IMulticall3.Call3Value({
target: L1_PORTAL,
allowFailure: false,
callData: abi.encodeCall(IOptimismPortal2.depositTransaction, (to, value, gasLimit, isCreation, data)),
value: value
});

return calls;
}

function _postCheck(Vm.AccountAccess[] memory, Simulation.Payload memory) internal view override {}

function _ownerSafe() internal view override returns (address) {
return OWNER_SAFE;
}
}
Loading
Loading