Skip to content

Commit 7062eaa

Browse files
Refactor BLSApkRegistry, update tests, and modify foundry config, finished addOrRemoveBlsRegisterWhitelist test (#3)
* Update env, fix imports, and unify SPDX licenses * Refactor BLSApkRegistry, update tests, and modify foundry config, finished addOrRemoveBlsRegisterWhitelist test
1 parent 7866fc0 commit 7062eaa

File tree

9 files changed

+153
-115
lines changed

9 files changed

+153
-115
lines changed

.env.example

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
SEPOLIA_RPC_URL=
2+
ETHERSCAN_API_KEY=
3+
PRIVATE_KEY=
4+
ACCOUNT_ADDRESS=

foundry.toml

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,17 @@
22
src = "src"
33
out = "out"
44
libs = ["lib"]
5-
solc = "^0.8.20"
5+
66
# See more config options https://github.com/foundry-rs/foundry/blob/master/crates/config/README.md#all-options
7+
solc = "0.8.22"
8+
# https://github.com/OpenZeppelin/openzeppelin-foundry-upgrades
9+
ffi = true
10+
ast = true
11+
build_info = true
12+
extra_output = ["storageLayout"]
713

14+
[rpc_endpoints]
15+
sepolia = "${SEPOLIA_RPC_URL}"
816

17+
[etherscan]
18+
sepolia = { key = "${ETHERSCAN_API_KEY}" }

script/deployFinalityRelayer.s.sol

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
// SPDX-License-Identifier: MIT
2-
pragma solidity ^0.8.12;
2+
pragma solidity ^0.8.20;
33

44
import "forge-std/Vm.sol";
55
import "@openzeppelin/contracts/proxy/transparent/ProxyAdmin.sol";

src/bls/BLSApkRegistry.sol

Lines changed: 76 additions & 78 deletions
Original file line numberDiff line numberDiff line change
@@ -11,8 +11,6 @@ import "../interfaces/IBLSApkRegistry.sol";
1111

1212
import "./BLSApkRegistryStorage.sol";
1313

14-
15-
1614
contract BLSApkRegistry is Initializable, OwnableUpgradeable, IBLSApkRegistry, BLSApkRegistryStorage, EIP712 {
1715
using BN254 for BN254.G1Point;
1816

@@ -28,43 +26,43 @@ contract BLSApkRegistry is Initializable, OwnableUpgradeable, IBLSApkRegistry, B
2826

2927
modifier onlyRelayerManager() {
3028
require(
31-
msg.sender == relayerManager,
32-
"BLSApkRegistry.onlyRelayerManager: caller is not the relayer manager address"
29+
msg.sender == relayerManager, "BLSApkRegistry.onlyRelayerManager: caller is not the relayer manager address"
3330
);
3431
_;
3532
}
3633

37-
constructor()
38-
EIP712("BLSApkRegistry", "v0.0.1")
39-
{
34+
constructor() EIP712("BLSApkRegistry", "v0.0.1") {
4035
_disableInitializers();
4136
}
4237

43-
function initialize(
44-
address _initialOwner,
45-
address _finalityRelayerManager,
46-
address _relayerManager
47-
) external initializer {
38+
function initialize(address _initialOwner, address _finalityRelayerManager, address _relayerManager)
39+
external
40+
initializer
41+
{
4842
_transferOwnership(_initialOwner);
4943
finalityRelayerManager = _finalityRelayerManager;
5044
relayerManager = _relayerManager;
5145
_initializeApk();
5246
}
5347

54-
function registerOperator(
55-
address operator
56-
) public onlyFinalityRelayerManager {
57-
(BN254.G1Point memory pubkey, ) = getRegisteredPubkey(operator);
48+
/**
49+
* @dev Registers an operator within the system.
50+
*
51+
* This function allows the Finality Relayer Manager to add an operator to the system.
52+
* The operator's public key is retrieved and used to update the associated proof (APK).
53+
*
54+
* @param operator The address of the operator to be registered.
55+
*/
56+
function registerOperator(address operator) public onlyFinalityRelayerManager {
57+
(BN254.G1Point memory pubkey,) = getRegisteredPubkey(operator);
5858

5959
_processApkUpdate(pubkey);
6060

6161
emit OperatorAdded(operator, operatorToPubkeyHash[operator]);
6262
}
6363

64-
function deregisterOperator(
65-
address operator
66-
) public onlyFinalityRelayerManager {
67-
(BN254.G1Point memory pubkey, ) = getRegisteredPubkey(operator);
64+
function deregisterOperator(address operator) public onlyFinalityRelayerManager {
65+
(BN254.G1Point memory pubkey,) = getRegisteredPubkey(operator);
6866

6967
_processApkUpdate(pubkey.negate());
7068
emit OperatorRemoved(operator, operatorToPubkeyHash[operator]);
@@ -82,10 +80,7 @@ contract BLSApkRegistry is Initializable, OwnableUpgradeable, IBLSApkRegistry, B
8280

8381
bytes32 pubkeyHash = BN254.hashG1Point(params.pubkeyG1);
8482

85-
require(
86-
pubkeyHash != ZERO_PK_HASH,
87-
"BLSApkRegistry.registerBLSPublicKey: cannot register zero pubkey"
88-
);
83+
require(pubkeyHash != ZERO_PK_HASH, "BLSApkRegistry.registerBLSPublicKey: cannot register zero pubkey");
8984
require(
9085
operatorToPubkeyHash[operator] == bytes32(0),
9186
"BLSApkRegistry.registerBLSPublicKey: operator already registered pubkey"
@@ -96,23 +91,30 @@ contract BLSApkRegistry is Initializable, OwnableUpgradeable, IBLSApkRegistry, B
9691
"BLSApkRegistry.registerBLSPublicKey: public key already registered"
9792
);
9893

99-
uint256 gamma = uint256(keccak256(abi.encodePacked(
100-
params.pubkeyRegistrationSignature.X,
101-
params.pubkeyRegistrationSignature.Y,
102-
params.pubkeyG1.X,
103-
params.pubkeyG1.Y,
104-
params.pubkeyG2.X,
105-
params.pubkeyG2.Y,
106-
pubkeyRegistrationMessageHash.X,
107-
pubkeyRegistrationMessageHash.Y
108-
))) % BN254.FR_MODULUS;
109-
110-
require(BN254.pairing(
111-
params.pubkeyRegistrationSignature.plus(params.pubkeyG1.scalar_mul(gamma)),
112-
BN254.negGeneratorG2(),
113-
pubkeyRegistrationMessageHash.plus(BN254.generatorG1().scalar_mul(gamma)),
114-
params.pubkeyG2
115-
), "BLSApkRegistry.registerBLSPublicKey: either the G1 signature is wrong, or G1 and G2 private key do not match");
94+
uint256 gamma = uint256(
95+
keccak256(
96+
abi.encodePacked(
97+
params.pubkeyRegistrationSignature.X,
98+
params.pubkeyRegistrationSignature.Y,
99+
params.pubkeyG1.X,
100+
params.pubkeyG1.Y,
101+
params.pubkeyG2.X,
102+
params.pubkeyG2.Y,
103+
pubkeyRegistrationMessageHash.X,
104+
pubkeyRegistrationMessageHash.Y
105+
)
106+
)
107+
) % BN254.FR_MODULUS;
108+
109+
require(
110+
BN254.pairing(
111+
params.pubkeyRegistrationSignature.plus(params.pubkeyG1.scalar_mul(gamma)),
112+
BN254.negGeneratorG2(),
113+
pubkeyRegistrationMessageHash.plus(BN254.generatorG1().scalar_mul(gamma)),
114+
params.pubkeyG2
115+
),
116+
"BLSApkRegistry.registerBLSPublicKey: either the G1 signature is wrong, or G1 and G2 private key do not match"
117+
);
116118

117119
operatorToPubkey[operator] = params.pubkeyG1;
118120
operatorToPubkeyHash[operator] = pubkeyHash;
@@ -123,12 +125,14 @@ contract BLSApkRegistry is Initializable, OwnableUpgradeable, IBLSApkRegistry, B
123125
return pubkeyHash;
124126
}
125127

126-
function checkSignatures(
127-
bytes32 msgHash,
128-
uint256 referenceBlockNumber,
129-
FinalityNonSignerAndSignature memory params
130-
) public view returns (StakeTotals memory, bytes32) {
131-
require(referenceBlockNumber < uint32(block.number), "BLSSignatureChecker.checkSignatures: invalid reference block");
128+
function checkSignatures(bytes32 msgHash, uint256 referenceBlockNumber, FinalityNonSignerAndSignature memory params)
129+
public
130+
view
131+
returns (StakeTotals memory, bytes32)
132+
{
133+
require(
134+
referenceBlockNumber < uint32(block.number), "BLSSignatureChecker.checkSignatures: invalid reference block"
135+
);
132136
BN254.G1Point memory signerApk = BN254.G1Point(0, 0);
133137
bytes32[] memory nonSignersPubkeyHashes;
134138
if (params.nonSignerPubkeys.length > 0) {
@@ -140,25 +144,21 @@ contract BLSApkRegistry is Initializable, OwnableUpgradeable, IBLSApkRegistry, B
140144
} else {
141145
signerApk = currentApk;
142146
}
143-
(bool pairingSuccessful, bool signatureIsValid) = trySignatureAndApkVerification(msgHash, signerApk, params.apkG2, params.sigma);
147+
(bool pairingSuccessful, bool signatureIsValid) =
148+
trySignatureAndApkVerification(msgHash, signerApk, params.apkG2, params.sigma);
144149
require(pairingSuccessful, "BLSSignatureChecker.checkSignatures: pairing precompile call failed");
145150
require(signatureIsValid, "BLSSignatureChecker.checkSignatures: signature is invalid");
146151

147152
bytes32 signatoryRecordHash = keccak256(abi.encodePacked(referenceBlockNumber, nonSignersPubkeyHashes));
148153

149-
StakeTotals memory stakeTotals = StakeTotals({
150-
totalBtcStaking: params.totalBtcStake,
151-
totalMantaStaking: params.totalMantaStake
152-
});
154+
StakeTotals memory stakeTotals =
155+
StakeTotals({totalBtcStaking: params.totalBtcStake, totalMantaStaking: params.totalMantaStake});
153156

154157
return (stakeTotals, signatoryRecordHash);
155158
}
156159

157160
function addOrRemoveBlsRegisterWhitelist(address register, bool isAdd) external onlyRelayerManager {
158-
require(
159-
register != address(0),
160-
"BLSApkRegistry.addOrRemoverBlsRegisterWhitelist: operator address is zero"
161-
);
161+
require(register != address(0), "BLSApkRegistry.addOrRemoverBlsRegisterWhitelist: operator address is zero");
162162
blsRegisterWhitelist[register] = isAdd;
163163
}
164164

@@ -167,8 +167,14 @@ contract BLSApkRegistry is Initializable, OwnableUpgradeable, IBLSApkRegistry, B
167167
BN254.G1Point memory apk,
168168
BN254.G2Point memory apkG2,
169169
BN254.G1Point memory sigma
170-
) public view returns(bool pairingSuccessful, bool siganatureIsValid) {
171-
uint256 gamma = uint256(keccak256(abi.encodePacked(msgHash, apk.X, apk.Y, apkG2.X[0], apkG2.X[1], apkG2.Y[0], apkG2.Y[1], sigma.X, sigma.Y))) % BN254.FR_MODULUS;
170+
) public view returns (bool pairingSuccessful, bool siganatureIsValid) {
171+
uint256 gamma = uint256(
172+
keccak256(
173+
abi.encodePacked(
174+
msgHash, apk.X, apk.Y, apkG2.X[0], apkG2.X[1], apkG2.Y[0], apkG2.Y[1], sigma.X, sigma.Y
175+
)
176+
)
177+
) % BN254.FR_MODULUS;
172178
(pairingSuccessful, siganatureIsValid) = BN254.safePairing(
173179
sigma.plus(apk.scalar_mul(gamma)),
174180
BN254.negGeneratorG2(),
@@ -194,42 +200,34 @@ contract BLSApkRegistry is Initializable, OwnableUpgradeable, IBLSApkRegistry, B
194200
lastUpdate.apkHash = newApkHash;
195201
} else {
196202
lastUpdate.nextUpdateBlockNumber = uint32(block.number);
197-
apkHistory.push(ApkUpdate({
198-
apkHash: newApkHash,
199-
updateBlockNumber: uint32(block.number),
200-
nextUpdateBlockNumber: 0
201-
}));
203+
apkHistory.push(
204+
ApkUpdate({apkHash: newApkHash, updateBlockNumber: uint32(block.number), nextUpdateBlockNumber: 0})
205+
);
202206
}
203207
}
204208

205209
function getRegisteredPubkey(address operator) public view returns (BN254.G1Point memory, bytes32) {
206210
BN254.G1Point memory pubkey = operatorToPubkey[operator];
207211
bytes32 pubkeyHash = operatorToPubkeyHash[operator];
208212

209-
require(
210-
pubkeyHash != bytes32(0),
211-
"BLSApkRegistry.getRegisteredPubkey: operator is not registered"
212-
);
213+
require(pubkeyHash != bytes32(0), "BLSApkRegistry.getRegisteredPubkey: operator is not registered");
213214

214215
return (pubkey, pubkeyHash);
215216
}
216217

217-
function pubkeyRegistrationMessageHash(address operator) public view returns (BN254.G1Point memory) {
218-
return BN254.hashToG1(
219-
_hashTypedDataV4(
220-
keccak256(abi.encode(PUBKEY_REGISTRATION_TYPEHASH, operator))
221-
)
222-
);
218+
function getPubkeyRegMessageHash(address operator) public view returns (BN254.G1Point memory) {
219+
return BN254.hashToG1(_hashTypedDataV4(keccak256(abi.encode(PUBKEY_REGISTRATION_TYPEHASH, operator))));
223220
}
224221

225222
function _initializeApk() internal {
226223
require(apkHistory.length == 0, "BLSApkRegistry.initializeApk: apk already exists");
227224

228-
apkHistory.push(ApkUpdate({
229-
apkHash: bytes24(0),
230-
updateBlockNumber: uint32(block.number),
231-
nextUpdateBlockNumber: 0
232-
}));
225+
apkHistory.push(
226+
ApkUpdate({apkHash: bytes24(0), updateBlockNumber: uint32(block.number), nextUpdateBlockNumber: 0})
227+
);
233228
}
234229

230+
function getPubkeyHash(address operator) public view returns (bytes32) {
231+
return operatorToPubkeyHash[operator];
232+
}
235233
}

src/bls/BLSApkRegistryStorage.sol

Lines changed: 3 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,9 @@
11
// SPDX-License-Identifier: MIT
22
pragma solidity ^0.8.20;
33

4-
import "@openzeppelin-upgrades/contracts/proxy/utils/Initializable.sol";
5-
6-
import "../libraries/BN254.sol";
7-
8-
import "../interfaces/IBLSApkRegistry.sol";
9-
import "../interfaces/IFinalityRelayerManager.sol";
4+
import {IBLSApkRegistry} from "../interfaces/IBLSApkRegistry.sol";
5+
import {BN254} from "../libraries/BN254.sol";
6+
import {Initializable} from "@openzeppelin-upgrades/contracts/proxy/utils/Initializable.sol";
107

118
abstract contract BLSApkRegistryStorage is Initializable, IBLSApkRegistry {
129
// Constants

src/interfaces/IBLSApkRegistry.sol

Lines changed: 8 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -29,21 +29,11 @@ interface IBLSApkRegistry {
2929
uint256 totalMantaStaking;
3030
}
3131

32-
event NewPubkeyRegistration(
33-
address indexed operator,
34-
BN254.G1Point pubkeyG1,
35-
BN254.G2Point pubkeyG2
36-
);
32+
event NewPubkeyRegistration(address indexed operator, BN254.G1Point pubkeyG1, BN254.G2Point pubkeyG2);
3733

38-
event OperatorAdded(
39-
address operator,
40-
bytes32 operatorId
41-
);
34+
event OperatorAdded(address operator, bytes32 operatorId);
4235

43-
event OperatorRemoved(
44-
address operator,
45-
bytes32 operatorId
46-
);
36+
event OperatorRemoved(address operator, bytes32 operatorId);
4737

4838
function registerOperator(address operator) external;
4939

@@ -55,17 +45,14 @@ interface IBLSApkRegistry {
5545
BN254.G1Point memory msgHash
5646
) external returns (bytes32);
5747

58-
function checkSignatures(
59-
bytes32 msgHash,
60-
uint256 referenceBlockNumber,
61-
FinalityNonSignerAndSignature memory params
62-
) external view returns (StakeTotals memory, bytes32);
63-
48+
function checkSignatures(bytes32 msgHash, uint256 referenceBlockNumber, FinalityNonSignerAndSignature memory params)
49+
external
50+
view
51+
returns (StakeTotals memory, bytes32);
6452

6553
function getRegisteredPubkey(address operator) external view returns (BN254.G1Point memory, bytes32);
6654

6755
function addOrRemoveBlsRegisterWhitelist(address operator, bool isAdd) external;
6856

69-
function pubkeyRegistrationMessageHash(address operator) external view returns (BN254.G1Point memory);
70-
57+
function getPubkeyRegMessageHash(address operator) external view returns (BN254.G1Point memory);
7158
}

src/utils/EmptyContract.sol

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
// SPDX-License-Identifier: UNLICENSED
1+
// SPDX-License-Identifier: MIT
22
pragma solidity ^0.8.20;
33

44
contract EmptyContract {

0 commit comments

Comments
 (0)