DeFiLayer 1Layer 2
14,723 OP
View results
Submission Details
Severity: high
Invalid

Missing validation on proof in `verifyScrvusdByStateRoot` could lead to wrong price calculation

Title

Missing validation on proof in verifyScrvusdByStateRoot could lead to wrong price calculation

Summary

There is no check on validity of the timestamp (param[5]), which is used to update price.

Vulnerability Details

https://github.com/CodeHawks-Contests/2025-03-curve/blob/main/contracts/scrvusd/verifiers/ScrvusdVerifierV1.sol#L71-L80

In verifyScrvusdByStateRoot function of ScrvusdVerifierV1 contract, there is no check on validity of the timestamp (param[5]) which represents the last_profit_update.
When tampered by a malicious provider, it will result a significant error in _updatePrice function that's being called afterwards.
This is a discrepency compared to verifyScrvusdByBlockHash function where the timestamp is acquired from the block header itself.

/// @param _block_number Number of the block to use state root hash
/// @param _proof_rlp The state proof of the parameters
function verifyScrvusdByStateRoot(
uint256 _block_number,
bytes memory _proof_rlp
) external returns (uint256) {
bytes32 state_root = IBlockHashOracle(BLOCK_HASH_ORACLE).get_state_root(_block_number);
uint256[PARAM_CNT] memory params = _extractParametersFromProof(state_root, _proof_rlp);
// Use last_profit_update as the timestamp surrogate
>> return _updatePrice(params, params[5], _block_number);
}

Impact

Due to the possibility of proof manipulation, price can be sorted out wrongly and result in consequent errors in pool operations. Potential loss of funds are expected in case the malicious actors manage the proof in a way they can drain funds from the pool.

Recommendations

Update verifyScrvusdByStateRoot to get the timestamp from a trusted source rather than directly from the proof. Consider following the approach from verifyScrvusdByBlockHash function to get it from the block header.

Updates

Lead Judging Commences

0xnevi Lead Judge 2 months ago
Submission Judgement Published
Invalidated
Reason: Out of scope
Assigned finding tags:

[invalid] finding-missing-proof-content-validation

- See [here]([https://github.com/CodeHawks-Contests/2025-03-curve?tab=readme-ov-file#blockhash-oracle)](https://github.com/CodeHawks-Contests/2025-03-curve?tab=readme-ov-file#blockhash-oracle) on how it is used to verify storage variable - All state roots and proofs must be verified by the OOS `StateProofVerifier` inherited as `Verifier` (where the price values and params are extracted), so there is no proof that manipulating timestamp/inputs can affect a price update - It is assumed that the OOS prover will provide accurate data and the OOS verifier will verify the prices/max unlock time to be within an appropriate bound/values - There is a account existance check in L96 of `ScrvusdVerifierV1.sol`, in which the params for price updates are extracted from

Support

FAQs

Can't find an answer? Chat with us on Discord, Twitter or Linkedin.