Skip to content

Commit

Permalink
start ts migration
Browse files Browse the repository at this point in the history
  • Loading branch information
invocamanman committed Jan 25, 2024
1 parent eda2d5c commit 00d6ea8
Show file tree
Hide file tree
Showing 33 changed files with 15,897 additions and 19,362 deletions.
3 changes: 2 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -17,4 +17,5 @@ deploy_parameters.json
deployments
upgrade_parameters.json
docker/gethData/
*.ignore/
*.ignore/
typechain-types/
5 changes: 1 addition & 4 deletions contracts/v2/PolygonRollupManager.sol
Original file line number Diff line number Diff line change
Expand Up @@ -3,21 +3,18 @@
pragma solidity 0.8.20;

import "./interfaces/IPolygonRollupManager.sol";
import "@openzeppelin/contracts-upgradeable/proxy/utils/Initializable.sol";
import "../interfaces/IPolygonZkEVMGlobalExitRoot.sol";
import "../interfaces/IPolygonZkEVMBridge.sol";
import "./interfaces/IPolygonRollupBase.sol";
import "../lib/EmergencyManager.sol";
import "@openzeppelin/contracts-upgradeable/token/ERC20/utils/SafeERC20Upgradeable.sol";
import "@openzeppelin/contracts-upgradeable/access/OwnableUpgradeable.sol";
import "@openzeppelin/contracts-upgradeable/proxy/utils/Initializable.sol";
import "@openzeppelin/contracts/proxy/transparent/TransparentUpgradeableProxy.sol";
import "./lib/PolygonAccessControlUpgradeable.sol";
import "../interfaces/IVerifierRollup.sol";
import "./consensus/zkEVM/PolygonZkEVMV2Upgraded.sol";

// review check contract slots!
// Update OZ libs, new transaparent proxy is cheaper, but admin immutable
// review Update OZ libs, new transaparent proxy is cheaper, but admin immutable
/**
* Contract responsible for managing the exit roots across multiple Rollups
*/
Expand Down
67 changes: 67 additions & 0 deletions contracts/v2/mocks/PolygonRollupManagerMock.sol
Original file line number Diff line number Diff line change
@@ -0,0 +1,67 @@
// SPDX-License-Identifier: AGPL-3.0
pragma solidity 0.8.20;
import "../PolygonRollupManager.sol";

/**
* PolygonRollupManager mock
*/
contract PolygonRollupManagerMock is PolygonRollupManager {
/**
* @param _globalExitRootManager Global exit root manager address
* @param _pol MATIC token address
* @param _bridgeAddress Bridge address
*/
constructor(
IPolygonZkEVMGlobalExitRoot _globalExitRootManager,
IERC20Upgradeable _pol,
IPolygonZkEVMBridge _bridgeAddress
) PolygonRollupManager(_globalExitRootManager, _pol, _bridgeAddress) {}

function initializeMock(
address _trustedAggregator,
uint64 _pendingStateTimeout,
uint64 _trustedAggregatorTimeout,
address admin,
address timelock,
address emergencyCouncil
) external initializer {
trustedAggregator = _trustedAggregator;
pendingStateTimeout = _pendingStateTimeout;
trustedAggregatorTimeout = _trustedAggregatorTimeout;

// Constant deployment variables
_batchFee = 0.1 ether; // 0.1 Matic
verifyBatchTimeTarget = 30 minutes;
multiplierBatchFee = 1002;

// Initialize OZ contracts
__AccessControl_init();

// setup roles

// Timelock roles
_setupRole(DEFAULT_ADMIN_ROLE, timelock);
_setupRole(_ADD_ROLLUP_TYPE_ROLE, timelock);
_setupRole(_ADD_EXISTING_ROLLUP_ROLE, timelock);

// Even this role can only update to an already added verifier/consensus
// Could break the compatibility of them, changing the virtual state
// review
_setupRole(_UPDATE_ROLLUP_ROLE, timelock);

// Admin roles
_setupRole(_OBSOLETE_ROLLUP_TYPE_ROLE, admin);
_setupRole(_CREATE_ROLLUP_ROLE, admin);
_setupRole(_STOP_EMERGENCY_ROLE, admin);
_setupRole(_TRUSTED_AGGREGATOR_ROLE, admin);
_setupRole(_TWEAK_PARAMETERS_ROLE, admin);

// review Could be another address?¿
_setupRole(_SET_FEE_ROLE, admin);

// Emergency council roles
_setRoleAdmin(_EMERGENCY_COUNCIL_ROLE, _EMERGENCY_COUNCIL_ADMIN);
_setupRole(_EMERGENCY_COUNCIL_ROLE, emergencyCouncil);
_setupRole(_EMERGENCY_COUNCIL_ADMIN, emergencyCouncil);
}
}
26 changes: 13 additions & 13 deletions deployment/0_createGenesisMainnet.js
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,7 @@ async function main() {
// Constant variables
const attemptsDeployProxy = 20;
const networkIDL2 = 1;
const zkevmAddressL2 = ethers.constants.AddressZero;
const zkevmAddressL2 = ethers.ZeroAddress;

const timelockAddress = mainnetMultisig;
const initialZkEVMDeployerOwner = mainnetInitialZkEVMDeployerOwner;
Expand Down Expand Up @@ -190,8 +190,8 @@ async function main() {
const bridgeProxyInfo = await getAddressInfo(proxyBridgeAddress);

// Override admin and implementation slots:
bridgeProxyInfo.storage[_ADMIN_SLOT] = ethers.utils.hexZeroPad(mainnetProxyAdminAddress, 32);
bridgeProxyInfo.storage[_IMPLEMENTATION_SLOT] = ethers.utils.hexZeroPad(mainnetZkEVMBridgeImplementationAddress, 32);
bridgeProxyInfo.storage[_ADMIN_SLOT] = ethers.hexZeroPad(mainnetProxyAdminAddress, 32);
bridgeProxyInfo.storage[_IMPLEMENTATION_SLOT] = ethers.hexZeroPad(mainnetZkEVMBridgeImplementationAddress, 32);

// update proxy storage
genesis.push({
Expand Down Expand Up @@ -219,8 +219,8 @@ async function main() {
const proxyGlobalExitRootL2Info = await getAddressInfo(polygonZkEVMGlobalExitRootL2.address);

// Override admin and implementation slots:
proxyGlobalExitRootL2Info.storage[_ADMIN_SLOT] = ethers.utils.hexZeroPad(mainnetProxyAdminAddress, 32);
proxyGlobalExitRootL2Info.storage[_IMPLEMENTATION_SLOT] = ethers.utils.hexZeroPad(mainnetGlobalExitRootL2ImplementationAddress, 32);
proxyGlobalExitRootL2Info.storage[_ADMIN_SLOT] = ethers.hexZeroPad(mainnetProxyAdminAddress, 32);
proxyGlobalExitRootL2Info.storage[_IMPLEMENTATION_SLOT] = ethers.hexZeroPad(mainnetGlobalExitRootL2ImplementationAddress, 32);

genesis.push({
contractName: 'PolygonZkEVMGlobalExitRootL2 proxy',
Expand All @@ -242,26 +242,26 @@ async function main() {
* bytes32 public constant CANCELLER_ROLE = keccak256("CANCELLER_ROLE");
*/
const timelockRolesHash = [
ethers.utils.id('TIMELOCK_ADMIN_ROLE'),
ethers.utils.id('PROPOSER_ROLE'),
ethers.utils.id('EXECUTOR_ROLE'),
ethers.utils.id('CANCELLER_ROLE'),
ethers.id('TIMELOCK_ADMIN_ROLE'),
ethers.id('PROPOSER_ROLE'),
ethers.id('EXECUTOR_ROLE'),
ethers.id('CANCELLER_ROLE'),
];

for (let i = 0; i < timelockRolesHash.length; i++) {
const rolesMappingStoragePositionStruct = 0;
const storagePosition = ethers.utils.solidityKeccak256(['uint256', 'uint256'], [timelockRolesHash[i], rolesMappingStoragePositionStruct]);
const storagePosition = ethers.solidityPackedKeccak256(['uint256', 'uint256'], [timelockRolesHash[i], rolesMappingStoragePositionStruct]);

// check timelock address manager, and timelock address itself
const addressArray = [timelockAddress, timelockContract.address];
for (let j = 0; j < addressArray.length; j++) {
const storagePositionRole = ethers.utils.solidityKeccak256(['uint256', 'uint256'], [addressArray[j], storagePosition]);
const storagePositionRole = ethers.solidityPackedKeccak256(['uint256', 'uint256'], [addressArray[j], storagePosition]);
const valueRole = await ethers.provider.getStorageAt(timelockContract.address, storagePositionRole);
if (valueRole !== '0x0000000000000000000000000000000000000000000000000000000000000000') {
timelockInfo.storage[storagePositionRole] = valueRole;
}
}
const roleAdminSlot = ethers.utils.hexZeroPad((ethers.BigNumber.from(storagePosition).add(1)).toHexString(), 32);
const roleAdminSlot = ethers.hexZeroPad((ethers.BigNumber.from(storagePosition).add(1)).toHexString(), 32);
const valueRoleAdminSlot = await ethers.provider.getStorageAt(timelockContract.address, roleAdminSlot);
if (valueRoleAdminSlot !== '0x0000000000000000000000000000000000000000000000000000000000000000') {
timelockInfo.storage[roleAdminSlot] = valueRoleAdminSlot;
Expand Down Expand Up @@ -326,7 +326,7 @@ async function getAddressInfo(address) {
for (let i = 0; i < 120; i++) {
const storageValue = await ethers.provider.getStorageAt(address, i);
if (storageValue !== '0x0000000000000000000000000000000000000000000000000000000000000000') {
storage[ethers.utils.hexZeroPad(ethers.utils.hexlify(i), 32)] = storageValue;
storage[ethers.hexZeroPad(ethers.hexlify(i), 32)] = storageValue;
}
}

Expand Down
22 changes: 11 additions & 11 deletions deployment/1_createGenesis.js
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ async function main() {
const attemptsDeployProxy = 20;
const networkIDL2 = 1;
const globalExitRootL2Address = '0xa40d5f56745a118d0906a34e69aec8c0db1cb8fa';
const zkevmAddressL2 = ethers.constants.AddressZero;
const zkevmAddressL2 = ethers.ZeroAddress;
const maxUint256 = ethers.BigNumber.from('0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff').toString();

let balanceBrige;
Expand Down Expand Up @@ -296,8 +296,8 @@ async function main() {
// Bridge proxy
const bridgeProxyInfo = await getAddressInfo(proxyBridgeAddress);
// Override admin and implementation slots:
bridgeProxyInfo.storage[_ADMIN_SLOT] = ethers.utils.hexZeroPad(proxyAdminAddress, 32);
bridgeProxyInfo.storage[_IMPLEMENTATION_SLOT] = ethers.utils.hexZeroPad(finalBridgeImplAddress, 32);
bridgeProxyInfo.storage[_ADMIN_SLOT] = ethers.hexZeroPad(proxyAdminAddress, 32);
bridgeProxyInfo.storage[_IMPLEMENTATION_SLOT] = ethers.hexZeroPad(finalBridgeImplAddress, 32);

genesis.push({
contractName: 'PolygonZkEVMBridge proxy',
Expand Down Expand Up @@ -342,26 +342,26 @@ async function main() {
* bytes32 public constant CANCELLER_ROLE = keccak256("CANCELLER_ROLE");
*/
const timelockRolesHash = [
ethers.utils.id('TIMELOCK_ADMIN_ROLE'),
ethers.utils.id('PROPOSER_ROLE'),
ethers.utils.id('EXECUTOR_ROLE'),
ethers.utils.id('CANCELLER_ROLE'),
ethers.id('TIMELOCK_ADMIN_ROLE'),
ethers.id('PROPOSER_ROLE'),
ethers.id('EXECUTOR_ROLE'),
ethers.id('CANCELLER_ROLE'),
];

for (let i = 0; i < timelockRolesHash.length; i++) {
const rolesMappingStoragePositionStruct = 0;
const storagePosition = ethers.utils.solidityKeccak256(['uint256', 'uint256'], [timelockRolesHash[i], rolesMappingStoragePositionStruct]);
const storagePosition = ethers.solidityPackedKeccak256(['uint256', 'uint256'], [timelockRolesHash[i], rolesMappingStoragePositionStruct]);

// check timelock address manager, and timelock address itself
const addressArray = [timelockAddress, timelockContract.address];
for (let j = 0; j < addressArray.length; j++) {
const storagePositionRole = ethers.utils.solidityKeccak256(['uint256', 'uint256'], [addressArray[j], storagePosition]);
const storagePositionRole = ethers.solidityPackedKeccak256(['uint256', 'uint256'], [addressArray[j], storagePosition]);
const valueRole = await ethers.provider.getStorageAt(timelockContract.address, storagePositionRole);
if (valueRole !== '0x0000000000000000000000000000000000000000000000000000000000000000') {
timelockInfo.storage[storagePositionRole] = valueRole;
}
}
const roleAdminSlot = ethers.utils.hexZeroPad((ethers.BigNumber.from(storagePosition).add(1)).toHexString(), 32);
const roleAdminSlot = ethers.hexZeroPad((ethers.BigNumber.from(storagePosition).add(1)).toHexString(), 32);
const valueRoleAdminSlot = await ethers.provider.getStorageAt(timelockContract.address, roleAdminSlot);
if (valueRoleAdminSlot !== '0x0000000000000000000000000000000000000000000000000000000000000000') {
timelockInfo.storage[roleAdminSlot] = valueRoleAdminSlot;
Expand Down Expand Up @@ -439,7 +439,7 @@ async function getAddressInfo(address) {
for (let i = 0; i < 120; i++) {
const storageValue = await ethers.provider.getStorageAt(address, i);
if (storageValue !== '0x0000000000000000000000000000000000000000000000000000000000000000') {
storage[ethers.utils.hexZeroPad(ethers.utils.hexlify(i), 32)] = storageValue;
storage[ethers.hexZeroPad(ethers.hexlify(i), 32)] = storageValue;
}
}

Expand Down
6 changes: 3 additions & 3 deletions deployment/2_deployPolygonZKEVMDeployer.js
Original file line number Diff line number Diff line change
Expand Up @@ -19,8 +19,8 @@ async function main() {
if (deployParameters.maxPriorityFeePerGas && deployParameters.maxFeePerGas) {
console.log(`Hardcoded gas used: MaxPriority${deployParameters.maxPriorityFeePerGas} gwei, MaxFee${deployParameters.maxFeePerGas} gwei`);
const FEE_DATA = {
maxFeePerGas: ethers.utils.parseUnits(deployParameters.maxFeePerGas, 'gwei'),
maxPriorityFeePerGas: ethers.utils.parseUnits(deployParameters.maxPriorityFeePerGas, 'gwei'),
maxFeePerGas: ethers.parseUnits(deployParameters.maxFeePerGas, 'gwei'),
maxPriorityFeePerGas: ethers.parseUnits(deployParameters.maxPriorityFeePerGas, 'gwei'),
};
currentProvider.getFeeData = async () => FEE_DATA;
} else {
Expand Down Expand Up @@ -58,7 +58,7 @@ async function main() {

// Deploy PolygonZkEVMDeployer if is not deployed already using keyless deployment
const [zkEVMDeployerContract, keylessDeployer] = await deployPolygonZkEVMDeployer(initialZkEVMDeployerOwner, deployer);
if (keylessDeployer === ethers.constants.AddressZero) {
if (keylessDeployer === ethers.ZeroAddress) {
console.log('#######################\n');
console.log('polygonZkEVMDeployer already deployed on: ', zkEVMDeployerContract.address);
} else {
Expand Down
8 changes: 4 additions & 4 deletions deployment/3_deployContracts.js
Original file line number Diff line number Diff line change
Expand Up @@ -90,8 +90,8 @@ async function main() {
if (deployParameters.maxPriorityFeePerGas && deployParameters.maxFeePerGas) {
console.log(`Hardcoded gas used: MaxPriority${deployParameters.maxPriorityFeePerGas} gwei, MaxFee${deployParameters.maxFeePerGas} gwei`);
const FEE_DATA = {
maxFeePerGas: ethers.utils.parseUnits(deployParameters.maxFeePerGas, 'gwei'),
maxPriorityFeePerGas: ethers.utils.parseUnits(deployParameters.maxPriorityFeePerGas, 'gwei'),
maxFeePerGas: ethers.parseUnits(deployParameters.maxFeePerGas, 'gwei'),
maxPriorityFeePerGas: ethers.parseUnits(deployParameters.maxPriorityFeePerGas, 'gwei'),
};
currentProvider.getFeeData = async () => FEE_DATA;
} else {
Expand Down Expand Up @@ -232,8 +232,8 @@ async function main() {
fs.writeFileSync(pathOngoingDeploymentJson, JSON.stringify(ongoingDeployment, null, 1));

// Contracts are not deployed, normal deployment
precalculateGLobalExitRootAddress = ethers.utils.getContractAddress({ from: deployer.address, nonce: nonceProxyGlobalExitRoot });
precalculateZkevmAddress = ethers.utils.getContractAddress({ from: deployer.address, nonce: nonceProxyZkevm });
precalculateGLobalExitRootAddress = ethers.getContractAddress({ from: deployer.address, nonce: nonceProxyGlobalExitRoot });
precalculateZkevmAddress = ethers.getContractAddress({ from: deployer.address, nonce: nonceProxyZkevm });
}

const dataCallProxy = polygonZkEVMBridgeFactory.interface.encodeFunctionData(
Expand Down
18 changes: 9 additions & 9 deletions deployment/helpers/deployment-helpers.js
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ async function deployPolygonZkEVMDeployer(deployerAddress, signer) {
)).data;

const gasLimit = ethers.BigNumber.from(1000000); // Put 1 Million, aprox 650k are necessary
const gasPrice = ethers.BigNumber.from(ethers.utils.parseUnits(gasPriceKeylessDeployment, 'gwei'));
const gasPrice = ethers.BigNumber.from(ethers.parseUnits(gasPriceKeylessDeployment, 'gwei'));
const to = '0x'; // bc deployment transaction, "to" is "0x"
const tx = {
to,
Expand All @@ -29,16 +29,16 @@ async function deployPolygonZkEVMDeployer(deployerAddress, signer) {
r: '0x5ca1ab1e0', // Equals 0x00000000000000000000000000000000000000000000000000000005ca1ab1e0
s: '0x5ca1ab1e', // Equals 0x000000000000000000000000000000000000000000000000000000005ca1ab1e
};
const serializedTransaction = ethers.utils.serializeTransaction(tx, signature);
const resultTransaction = ethers.utils.parseTransaction(serializedTransaction);
const serializedTransaction = ethers.serializeTransaction(tx, signature);
const resultTransaction = ethers.parseTransaction(serializedTransaction);
const totalEther = gasLimit.mul(gasPrice); // 0.1 ether

// Check if it's already deployed
const zkEVMDeployerAddress = ethers.utils.getContractAddress(resultTransaction);
const zkEVMDeployerAddress = ethers.getContractAddress(resultTransaction);
if (await signer.provider.getCode(zkEVMDeployerAddress) !== '0x') {
const zkEVMDeployerContract = PolgonZKEVMDeployerFactory.attach(zkEVMDeployerAddress);
expect(await zkEVMDeployerContract.owner()).to.be.equal(signer.address);
return [zkEVMDeployerContract, ethers.constants.AddressZero];
return [zkEVMDeployerContract, ethers.ZeroAddress];
}

// Fund keyless deployment
Expand All @@ -58,10 +58,10 @@ async function deployPolygonZkEVMDeployer(deployerAddress, signer) {

async function create2Deployment(polgonZKEVMDeployerContract, salt, deployTransaction, dataCall, deployer, hardcodedGasLimit) {
// Encode deploy transaction
const hashInitCode = ethers.utils.solidityKeccak256(['bytes'], [deployTransaction]);
const hashInitCode = ethers.solidityPackedKeccak256(['bytes'], [deployTransaction]);

// Precalculate create2 address
const precalculatedAddressDeployed = ethers.utils.getCreate2Address(polgonZKEVMDeployerContract.address, salt, hashInitCode);
const precalculatedAddressDeployed = ethers.getCreate2Address(polgonZKEVMDeployerContract.address, salt, hashInitCode);
const amount = 0;

if (await deployer.provider.getCode(precalculatedAddressDeployed) !== '0x') {
Expand Down Expand Up @@ -101,10 +101,10 @@ async function create2Deployment(polgonZKEVMDeployerContract, salt, deployTransa

function getCreate2Address(polgonZKEVMDeployerContract, salt, deployTransaction) {
// Encode deploy transaction
const hashInitCode = ethers.utils.solidityKeccak256(['bytes'], [deployTransaction]);
const hashInitCode = ethers.solidityPackedKeccak256(['bytes'], [deployTransaction]);

// Precalculate create2 address
return ethers.utils.getCreate2Address(polgonZKEVMDeployerContract.address, salt, hashInitCode);
return ethers.getCreate2Address(polgonZKEVMDeployerContract.address, salt, hashInitCode);
}

module.exports = {
Expand Down
6 changes: 3 additions & 3 deletions deployment/testnet/prepareGasToken.js
Original file line number Diff line number Diff line change
Expand Up @@ -17,8 +17,8 @@ async function main() {
if (deployParameters.maxPriorityFeePerGas && deployParameters.maxFeePerGas) {
console.log(`Hardcoded gas used: MaxPriority${deployParameters.maxPriorityFeePerGas} gwei, MaxFee${deployParameters.maxFeePerGas} gwei`);
const FEE_DATA = {
maxFeePerGas: ethers.utils.parseUnits(deployParameters.maxFeePerGas, 'gwei'),
maxPriorityFeePerGas: ethers.utils.parseUnits(deployParameters.maxPriorityFeePerGas, 'gwei'),
maxFeePerGas: ethers.parseUnits(deployParameters.maxFeePerGas, 'gwei'),
maxPriorityFeePerGas: ethers.parseUnits(deployParameters.maxPriorityFeePerGas, 'gwei'),
};
currentProvider.getFeeData = async () => FEE_DATA;
} else {
Expand Down Expand Up @@ -52,7 +52,7 @@ async function main() {
*/
const gasTokenName = 'Gas Token';
const gasTokenSymbol = 'GT';
const gasTokenInitialBalance = ethers.utils.parseEther('20000000');
const gasTokenInitialBalance = ethers.parseEther('20000000');

const gasTokenFactory = await ethers.getContractFactory('ERC20PermitMock', deployer);
const gasTokenContract = await gasTokenFactory.deploy(
Expand Down
Loading

0 comments on commit 00d6ea8

Please sign in to comment.