Skip to content

Commit

Permalink
Merge branch 'dev' into fix/request-id-validation
Browse files Browse the repository at this point in the history
  • Loading branch information
ashitakah authored Jul 26, 2024
2 parents 28628c3 + fbdedb5 commit 302ba38
Show file tree
Hide file tree
Showing 10 changed files with 271 additions and 129 deletions.
5 changes: 3 additions & 2 deletions solidity/contracts/extensions/BondEscalationAccounting.sol
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ contract BondEscalationAccounting is AccountingExtension, IBondEscalationAccount
mapping(bytes32 _disputeId => EscalationResult _result) public escalationResults;

/// @inheritdoc IBondEscalationAccounting
mapping(bytes32 _requestId => mapping(address _pledger => bool)) public pledgerClaimed;
mapping(bytes32 _requestId => mapping(address _pledger => bool _claimed)) public pledgerClaimed;

constructor(IOracle _oracle) AccountingExtension(_oracle) {}

Expand Down Expand Up @@ -84,7 +84,8 @@ contract BondEscalationAccounting is AccountingExtension, IBondEscalationAccount
uint256 _numberOfPledges;

if (_status == IOracle.DisputeStatus.NoResolution) {
_numberOfPledges = 1;
_numberOfPledges = _result.bondEscalationModule.pledgesForDispute(_requestId, _pledger)
+ _result.bondEscalationModule.pledgesAgainstDispute(_requestId, _pledger);
} else {
_numberOfPledges = _status == IOracle.DisputeStatus.Won
? _result.bondEscalationModule.pledgesForDispute(_requestId, _pledger)
Expand Down
17 changes: 15 additions & 2 deletions solidity/contracts/modules/dispute/CircuitResolverModule.sol
Original file line number Diff line number Diff line change
Expand Up @@ -94,12 +94,25 @@ contract CircuitResolverModule is Module, ICircuitResolverModule {
/// @inheritdoc IModule
function validateParameters(bytes calldata _encodedParameters)
external
pure
view
override(Module, IModule)
returns (bool _valid)
{
RequestParameters memory _params = decodeRequestData(_encodedParameters);
_valid = address(_params.accountingExtension) != address(0) && address(_params.bondToken) != address(0)
&& _params.bondSize != 0 && address(_params.verifier) != address(0) && _params.callData.length != 0;
&& _params.bondSize != 0 && _targetHasBytecode(_params.verifier) && _params.callData.length != 0;
}

/**
* @notice Checks if a target address has bytecode
* @param _target The address to check
* @return _hasBytecode Whether the target has bytecode or not
*/
function _targetHasBytecode(address _target) private view returns (bool _hasBytecode) {
uint256 _size;
assembly {
_size := extcodesize(_target)
}
_hasBytecode = _size > 0;
}
}
18 changes: 16 additions & 2 deletions solidity/contracts/modules/finality/CallbackModule.sol
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@ contract CallbackModule is Module, ICallbackModule {
address _finalizer
) external override(Module, ICallbackModule) onlyOracle {
RequestParameters memory _params = decodeRequestData(_request.finalityModuleData);

_params.target.call(_params.data);
emit Callback(_response.requestId, _params.target, _params.data);
emit RequestFinalized(_response.requestId, _response, _finalizer);
Expand All @@ -35,11 +36,24 @@ contract CallbackModule is Module, ICallbackModule {
/// @inheritdoc IModule
function validateParameters(bytes calldata _encodedParameters)
external
pure
view
override(Module, IModule)
returns (bool _valid)
{
RequestParameters memory _params = decodeRequestData(_encodedParameters);
_valid = address(_params.target) != address(0) && _params.data.length != 0;
_valid = _params.data.length != 0 && _targetHasBytecode(_params.target);
}

/**
* @notice Checks if a target address has bytecode
* @param _target The address to check
* @return _hasBytecode Whether the target has bytecode or not
*/
function _targetHasBytecode(address _target) private view returns (bool _hasBytecode) {
uint256 _size;
assembly {
_size := extcodesize(_target)
}
_hasBytecode = _size > 0;
}
}
17 changes: 15 additions & 2 deletions solidity/contracts/modules/finality/MultipleCallbacksModule.sol
Original file line number Diff line number Diff line change
Expand Up @@ -43,15 +43,15 @@ contract MultipleCallbacksModule is Module, IMultipleCallbacksModule {
/// @inheritdoc IModule
function validateParameters(bytes calldata _encodedParameters)
external
pure
view
override(Module, IModule)
returns (bool _valid)
{
RequestParameters memory _params = decodeRequestData(_encodedParameters);
_valid = true;

for (uint256 _i; _i < _params.targets.length; ++_i) {
if (_params.targets[_i] == address(0)) {
if (!_targetHasBytecode(_params.targets[_i])) {
_valid = false;
break;
}
Expand All @@ -64,4 +64,17 @@ contract MultipleCallbacksModule is Module, IMultipleCallbacksModule {
}
}
}

/**
* @notice Checks if a target address has bytecode
* @param _target The address to check
* @return _hasBytecode Whether the target has bytecode or not
*/
function _targetHasBytecode(address _target) private view returns (bool _hasBytecode) {
uint256 _size;
assembly {
_size := extcodesize(_target)
}
_hasBytecode = _size > 0;
}
}
2 changes: 1 addition & 1 deletion solidity/test/integration/IntegrationBase.sol
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@ import {TestConstants} from '../utils/TestConstants.sol';
// solhint-enable no-unused-import

contract IntegrationBase is DSTestPlus, TestConstants, Helpers {
uint256 public constant FORK_BLOCK = 100_000_000;
uint256 public constant FORK_BLOCK = 122_612_760;

uint256 internal _initialBalance = 100_000 ether;

Expand Down
57 changes: 57 additions & 0 deletions solidity/test/unit/modules/dispute/BondEscalationAccounting.t.sol
Original file line number Diff line number Diff line change
Expand Up @@ -533,4 +533,61 @@ contract BondEscalationAccounting_Unit_ClaimEscalationReward is BaseTest {
// Check: are the pledges updated?
assertEq(bondEscalationAccounting.pledges(_disputeId, token), 0);
}

function test_noResolution(
bytes32 _disputeId,
bytes32 _requestId,
uint256 _amount,
uint256 _pledgesAgainst,
uint256 _pledgesFor,
address _bondEscalationModule
) public assumeFuzzable(_bondEscalationModule) {
vm.assume(_amount > 0);
vm.assume(_pledgesAgainst > 0 && _pledgesAgainst < 10_000);
vm.assume(_pledgesFor > 0 && _pledgesFor < 10_000);

_amount = bound(_amount, 0, type(uint128).max / (_pledgesAgainst + _pledgesFor));

bondEscalationAccounting.forTest_setEscalationResult(
_disputeId, _requestId, token, _amount, IBondEscalationModule(_bondEscalationModule)
);

bondEscalationAccounting.forTest_setPledge(_disputeId, token, _amount * (_pledgesAgainst + _pledgesFor));

// Mock and expect to call the oracle getting the dispute status
_mockAndExpect(
address(oracle),
abi.encodeCall(IOracle.disputeStatus, (_disputeId)),
abi.encode(IOracle.DisputeStatus.NoResolution)
);

// Mock and expect to call the escalation module asking for pledges
_mockAndExpect(
_bondEscalationModule,
abi.encodeCall(IBondEscalationModule.pledgesAgainstDispute, (_requestId, pledger)),
abi.encode(_pledgesAgainst)
);

// Mock and expect the call to the escalation module asking for pledges
_mockAndExpect(
_bondEscalationModule,
abi.encodeCall(IBondEscalationModule.pledgesForDispute, (_requestId, pledger)),
abi.encode(_pledgesFor)
);

// Check: is the event emitted?
vm.expectEmit(true, true, true, true, address(bondEscalationAccounting));
emit EscalationRewardClaimed(_requestId, _disputeId, pledger, token, _amount * (_pledgesAgainst + _pledgesFor));

vm.prank(_bondEscalationModule);
bondEscalationAccounting.claimEscalationReward(_disputeId, pledger);

// Check: is the balance of the pledger properly updated?
assertEq(bondEscalationAccounting.balanceOf(pledger, token), _amount * (_pledgesAgainst + _pledgesFor));
// Check: is the reward marked as claimed for the pledger?
assertTrue(bondEscalationAccounting.pledgerClaimed(_requestId, pledger));

// Check: are the pledges updated?
assertEq(bondEscalationAccounting.pledges(_disputeId, token), 0);
}
}
10 changes: 9 additions & 1 deletion solidity/test/unit/modules/dispute/CircuitResolverModule.t.sol
Original file line number Diff line number Diff line change
Expand Up @@ -60,6 +60,14 @@ contract BaseTest is Test, Helpers {

circuitResolverModule = new ForTest_CircuitResolverModule(oracle);
}

function targetHasBytecode(address _target) public view returns (bool _hasBytecode) {
uint256 _size;
assembly {
_size := extcodesize(_target)
}
_hasBytecode = _size > 0;
}
}

contract CircuitResolverModule_Unit_ModuleData is BaseTest {
Expand Down Expand Up @@ -109,7 +117,7 @@ contract CircuitResolverModule_Unit_ModuleData is BaseTest {
function test_validateParameters(ICircuitResolverModule.RequestParameters calldata _params) public {
if (
address(_params.accountingExtension) == address(0) || address(_params.bondToken) == address(0)
|| _params.bondSize == 0 || address(_params.verifier) == address(0) || _params.callData.length == 0
|| _params.bondSize == 0 || !targetHasBytecode(_params.verifier) || _params.callData.length == 0
) {
assertFalse(circuitResolverModule.validateParameters(abi.encode(_params)));
} else {
Expand Down
11 changes: 10 additions & 1 deletion solidity/test/unit/modules/finality/CallbackModule.t.sol
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,14 @@ contract BaseTest is Test, Helpers {

callbackModule = new CallbackModule(oracle);
}

function targetHasBytecode(address _target) public view returns (bool _hasBytecode) {
uint256 _size;
assembly {
_size := extcodesize(_target)
}
_hasBytecode = _size > 0;
}
}

contract CallbackModule_Unit_ModuleData is BaseTest {
Expand Down Expand Up @@ -60,7 +68,7 @@ contract CallbackModule_Unit_ModuleData is BaseTest {
* @notice Test that the validateParameters function correctly checks the parameters
*/
function test_validateParameters(ICallbackModule.RequestParameters calldata _params) public {
if (address(_params.target) == address(0) || _params.data.length == 0) {
if (address(_params.target) == address(0) || _params.data.length == 0 || !targetHasBytecode(_params.target)) {
assertFalse(callbackModule.validateParameters(abi.encode(_params)));
} else {
assertTrue(callbackModule.validateParameters(abi.encode(_params)));
Expand All @@ -73,6 +81,7 @@ contract CallbackModule_Unit_FinalizeRequest is BaseTest {
* @notice Test that finalizeRequest emits events
*/
function test_emitsEvents(address _proposer, address _target, bytes calldata _data) public assumeFuzzable(_target) {
vm.etch(_target, '0xabcdef');
mockRequest.finalityModuleData = abi.encode(ICallbackModule.RequestParameters({target: _target, data: _data}));
mockResponse.requestId = _getId(mockRequest);

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,14 @@ contract BaseTest is Test, Helpers {

multipleCallbackModule = new MultipleCallbacksModule(oracle);
}

function targetHasBytecode(address _target) public view returns (bool _hasBytecode) {
uint256 _size;
assembly {
_size := extcodesize(_target)
}
_hasBytecode = _size > 0;
}
}

/**
Expand All @@ -50,7 +58,7 @@ contract MultipleCallbacksModule_Unit_ModuleData is BaseTest {
function test_validateParameters(IMultipleCallbacksModule.RequestParameters calldata _params) public {
bool _valid = true;
for (uint256 _i; _i < _params.targets.length; ++_i) {
if (_params.targets[_i] == address(0)) {
if (_params.targets[_i] == address(0) || !targetHasBytecode(_params.targets[_i])) {
_valid = false;
}
}
Expand Down
Loading

0 comments on commit 302ba38

Please sign in to comment.