Summary
The initialize() function in LLMOracleCoordinator lacks access control, allowing any user to call it before the legitimate owner.
This vulnerability enables attackers to hijack the contract by initializing it with their own parameters and gaining owner privileges.
Vulnerability Details
The initialize() function is used to set up the contract but lacks access controls:
function initialize(
address _oracleRegistry,
address _feeToken,
uint256 _platformFee,
uint256 _generationFee,
uint256 _validationFee
) public initializer {
__Ownable_init(msg.sender);
__LLMOracleManager_init(_platformFee, _generationFee, _validationFee);
registry = LLMOracleRegistry(_oracleRegistry);
feeToken = ERC20(_feeToken);
nextTaskId = 1;
}
Impact
Complete Contract Control:
Attacker becomes contract owner
Can control all owner-privileged functions
Can manipulate fees and withdrawals
Tools Used
Manual Review
Recommendations
Add access control to initialize:
contract LLMOracleCoordinator is LLMOracleTask, LLMOracleManager, UUPSUpgradeable {
address public immutable deployer;
constructor() {
_disableInitializers();
deployer = msg.sender;
}
function initialize(
address _oracleRegistry,
address _feeToken,
uint256 _platformFee,
uint256 _generationFee,
uint256 _validationFee
) public initializer {
require(msg.sender == deployer, "Not deployer");
__Ownable_init(msg.sender);
__LLMOracleManager_init(_platformFee, _generationFee, _validationFee);
registry = LLMOracleRegistry(_oracleRegistry);
feeToken = ERC20(_feeToken);
nextTaskId = 1;
}
}