Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Governor admin can set verifier address and verify params to a wrong or invalid address intentionally #181

Closed
code423n4 opened this issue Nov 7, 2022 · 5 comments
Labels
bug Something isn't working downgraded by judge Judge downgraded the risk level of this issue duplicate-239 QA (Quality Assurance) Assets are not at risk. State handling, function incorrect as to spec, issues with clarity, syntax sponsor disputed Sponsor cannot duplicate the issue, or otherwise disagrees this is an issue

Comments

@code423n4
Copy link
Contributor

Lines of code

https://github.com/code-423n4/2022-10-zksync/blob/456078b53a6d09636b84522ac8f3e8049e4e3af5/ethereum/contracts/zksync/facets/Governance.sol#L45
https://github.com/code-423n4/2022-10-zksync/blob/456078b53a6d09636b84522ac8f3e8049e4e3af5/ethereum/contracts/zksync/facets/Executor.sol#L231
https://github.com/code-423n4/2022-10-zksync/blob/456078b53a6d09636b84522ac8f3e8049e4e3af5/ethereum/contracts/zksync/facets/Executor.sol#L248
https://github.com/code-423n4/2022-10-zksync/blob/456078b53a6d09636b84522ac8f3e8049e4e3af5/ethereum/contracts/zksync/facets/Executor.sol#L260

Vulnerability details

Impact

Governor admin has the power to set the verifier address to whatever he wants.

If the admin set the verifier address to wrong or invalid address intentionally,

the validator cannot properly process the transaction and prove the transaction is processed.

Proof of Concept

The governor can set the verifier address and verify params to whatever he wants by calling this function:

/// @notice Change the address of the verifier smart contract
/// @param _newVerifier Verifier smart contract address
function setVerifier(Verifier _newVerifier) external onlyGovernor {
	Verifier oldVerifier = s.verifier;
	if (oldVerifier != _newVerifier) {
		s.verifier = _newVerifier;
		emit NewVerifier(address(oldVerifier), address(_newVerifier));
	}
}

/// @notice Change the verifier parameters
/// @param _newVerifierParams New parameters for the verifier
function setVerifierParams(VerifierParams calldata _newVerifierParams) external onlyGovernor {
	VerifierParams memory oldVerifierParams = s.verifierParams;

	s.verifierParams = _newVerifierParams;
	emit NewVerifierParams(oldVerifierParams, _newVerifierParams);
    }

For example, if the admin misbehave and set the verifier to address(0) or a random EOA account, the validator cannot properly prove the message by calling:

/// @notice Blocks commitment verification.
/// @notice Only verifies block commitments without any other processing
function proveBlocks(
	StoredBlockInfo calldata _prevBlock,
	StoredBlockInfo[] calldata _committedBlocks,
	ProofInput calldata _proof

note that the verifiy params is used in

// Save the variable from the storage to memory to save gas
VerifierParams memory verifierParams = s.verifierParams;

// Initialize the array, that will be used as public input to the ZKP
uint256[] memory proofPublicInput = new uint256[](committedBlocksLength);

// Check that the block passed by the validator is indeed the first unverified block
require(_hashStoredBlockInfo(_prevBlock) == s.storedBlockHashes[currentTotalBlocksVerified], "t1");

bytes32 prevBlockCommitment = _prevBlock.commitment;
for (uint256 i = 0; i < committedBlocksLength; i = i.uncheckedInc()) {
	require(
		_hashStoredBlockInfo(_committedBlocks[i]) ==
			s.storedBlockHashes[currentTotalBlocksVerified.uncheckedInc()],
		"o1"
	);

	bytes32 currentBlockCommitment = _committedBlocks[i].commitment;
	proofPublicInput[i] = _getBlockProofPublicInput(
		prevBlockCommitment,
		currentBlockCommitment,
		_proof,
		verifierParams
	);

	prevBlockCommitment = currentBlockCommitment;
	currentTotalBlocksVerified = currentTotalBlocksVerified.uncheckedInc();
}

and the verifier address is used in:

// #if DUMMY_VERIFIER == false
bool successVerifyProof = s.verifier.verify_serialized_proof(proofPublicInput, _proof.serializedProof);
require(successVerifyProof, "p"); // Proof verification fail

If this verification fails, Blocks commitment verification failed.

Tools Used

Manual Review

Recommended Mitigation Steps

We recommend the project add more parameter when admin setting the verifier to make sure that the verifier can verify dummy proof.

Also, we recommend the project use multsig wallet to safe guard to the admin address.

@code423n4 code423n4 added 2 (Med Risk) Assets not at direct risk, but function/availability of the protocol could be impacted or leak value bug Something isn't working labels Nov 7, 2022
code423n4 added a commit that referenced this issue Nov 7, 2022
@miladpiri
Copy link

This seems like self-attack, and does not show a clear vulnerability. So, invalid issue!

@c4-sponsor
Copy link

miladpiri marked the issue as sponsor disputed

@c4-sponsor c4-sponsor added the sponsor disputed Sponsor cannot duplicate the issue, or otherwise disagrees this is an issue label Nov 22, 2022
@c4-judge
Copy link
Contributor

c4-judge commented Dec 1, 2022

GalloDaSballo marked the issue as duplicate of #144

@GalloDaSballo
Copy link

L

@c4-judge c4-judge added QA (Quality Assurance) Assets are not at risk. State handling, function incorrect as to spec, issues with clarity, syntax downgraded by judge Judge downgraded the risk level of this issue duplicate-239 and removed 2 (Med Risk) Assets not at direct risk, but function/availability of the protocol could be impacted or leak value labels Dec 2, 2022
@c4-judge
Copy link
Contributor

c4-judge commented Dec 2, 2022

Duplicate of #239

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something isn't working downgraded by judge Judge downgraded the risk level of this issue duplicate-239 QA (Quality Assurance) Assets are not at risk. State handling, function incorrect as to spec, issues with clarity, syntax sponsor disputed Sponsor cannot duplicate the issue, or otherwise disagrees this is an issue
Projects
None yet
Development

No branches or pull requests

6 participants