Skip to content

Commit 7a1188f

Browse files
committed
feat(gateway): add and use feeForJuror param by governor
1 parent 1e0cbce commit 7a1188f

File tree

4 files changed

+84
-24
lines changed

4 files changed

+84
-24
lines changed

contracts/src/gateway/BaseForeignGateway.sol

Lines changed: 65 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -17,14 +17,15 @@ import "./interfaces/IHomeGateway.sol";
1717
import "./interfaces/IForeignGateway.sol";
1818

1919
abstract contract BaseForeignGateway is IL1Bridge, IForeignGateway {
20+
// The global default minimum number of jurors in a dispute.
21+
uint256 public constant MIN_JURORS = 3;
22+
2023
// @dev Note the disputeID needs to start from one as
2124
// the KlerosV1 proxy governor depends on this implementation.
2225
uint256 internal localDisputeID = 1;
2326

24-
// For now this is just a constant, but we'd probably need to
25-
// implement the same arbitrationCost calculation code we'll have
26-
// in the V2 court.
27-
uint256 internal internalArbitrationCost;
27+
// feeForJuror by subcourtID
28+
uint256[] internal feeForJuror;
2829

2930
struct DisputeData {
3031
uint256 id;
@@ -38,15 +39,26 @@ abstract contract BaseForeignGateway is IL1Bridge, IForeignGateway {
3839

3940
IHomeGateway public homeGateway;
4041
uint256 public chainID;
42+
address public governor;
4143

4244
modifier onlyFromL2() {
4345
onlyAuthorized();
4446
_;
4547
}
4648

47-
constructor(uint256 _arbitrationCost, IHomeGateway _homeGateway) {
48-
internalArbitrationCost = _arbitrationCost;
49+
modifier onlyByGovernor() {
50+
require(governor == msg.sender, "Access not allowed: Governor only.");
51+
_;
52+
}
53+
54+
constructor(
55+
address _governor,
56+
IHomeGateway _homeGateway,
57+
uint256[] memory _feeForJuror
58+
) {
59+
governor = _governor;
4960
homeGateway = _homeGateway;
61+
feeForJuror = _feeForJuror;
5062

5163
uint256 id;
5264
assembly {
@@ -55,9 +67,20 @@ abstract contract BaseForeignGateway is IL1Bridge, IForeignGateway {
5567
chainID = id;
5668
}
5769

70+
/** @dev Changes the `feeForJuror` property value of a specified subcourt.
71+
* @param _subcourtID The ID of the subcourt.
72+
* @param _feeForJuror The new value for the `feeForJuror` property value.
73+
*/
74+
function changeSubcourtJurorFee(uint96 _subcourtID, uint256 _feeForJuror) external onlyByGovernor {
75+
feeForJuror[_subcourtID] = _feeForJuror;
76+
}
77+
5878
function createDispute(uint256 _choices, bytes calldata _extraData) external payable returns (uint256 disputeID) {
5979
require(msg.value >= arbitrationCost(_extraData), "Not paid enough for arbitration");
6080

81+
(uint96 subcourtID, ) = extraDataToSubcourtIDMinJurors(_extraData);
82+
uint256 nbVotes = msg.value / feeForJuror[subcourtID];
83+
6184
disputeID = localDisputeID++;
6285
bytes32 disputeHash = keccak256(
6386
abi.encodePacked(
@@ -71,6 +94,7 @@ abstract contract BaseForeignGateway is IL1Bridge, IForeignGateway {
7194
)
7295
);
7396
disputeIDtoHash[disputeID] = disputeHash;
97+
7498
disputeHashtoDisputeData[disputeHash] = DisputeData({
7599
id: disputeID,
76100
arbitrable: msg.sender,
@@ -80,7 +104,13 @@ abstract contract BaseForeignGateway is IL1Bridge, IForeignGateway {
80104
});
81105

82106
bytes4 methodSelector = IHomeGateway.relayCreateDispute.selector;
83-
bytes memory data = abi.encodeWithSelector(methodSelector, disputeHash, _choices, _extraData);
107+
bytes memory data = abi.encodeWithSelector(
108+
methodSelector,
109+
disputeHash,
110+
_choices,
111+
_extraData,
112+
nbVotes * feeForJuror[subcourtID] // we calculate the min amount required for nbVotes
113+
);
84114

85115
// We only pay for the submissionPrice gas cost
86116
// which is minimum gas cost required for submitting a
@@ -100,16 +130,19 @@ abstract contract BaseForeignGateway is IL1Bridge, IForeignGateway {
100130
}
101131

102132
function arbitrationCost(bytes calldata _extraData) public view returns (uint256 cost) {
133+
(uint96 subcourtID, uint256 minJurors) = extraDataToSubcourtIDMinJurors(_extraData);
134+
103135
// Calculate the size of calldata that will be passed to the L2 bridge
104136
// as that is a factor for the bridging cost.
105137
// Calldata size of relayCreateDispute:
106-
// relayCreateDispute methodId +
107-
// (createDispute methodId + bytes32 disputeHash + uint256 _choices + bytes _extraData)
108-
// 4 + 4 + 32 + 32 + dynamic
109-
uint256 calldatasize = 82 + _extraData.length;
138+
// relayCreateDispute methodId + bytes32 disputeHash + uint256 _choices + bytes _extraData + uint256 _arbitrationCost)
139+
// 4 + 32 + 32 + dynamic + 32
140+
uint256 calldatasize = 100 + _extraData.length;
110141

111142
uint256 bridgeCost = getSubmissionPrice(calldatasize);
112-
return bridgeCost + internalArbitrationCost;
143+
uint256 arbCost = feeForJuror[subcourtID] * minJurors;
144+
145+
return bridgeCost + arbCost;
113146
}
114147

115148
/**
@@ -157,4 +190,24 @@ abstract contract BaseForeignGateway is IL1Bridge, IForeignGateway {
157190
function homeBridge(uint256 _disputeID) external view returns (address) {
158191
return address(homeGateway);
159192
}
193+
194+
function extraDataToSubcourtIDMinJurors(bytes memory _extraData)
195+
internal
196+
view
197+
returns (uint96 subcourtID, uint256 minJurors)
198+
{
199+
// Note that here we ignore DisputeKitID
200+
if (_extraData.length >= 64) {
201+
assembly {
202+
// solium-disable-line security/no-inline-assembly
203+
subcourtID := mload(add(_extraData, 0x20))
204+
minJurors := mload(add(_extraData, 0x40))
205+
}
206+
if (subcourtID >= feeForJuror.length) subcourtID = 0;
207+
if (minJurors == 0) minJurors = MIN_JURORS;
208+
} else {
209+
subcourtID = 0;
210+
minJurors = MIN_JURORS;
211+
}
212+
}
160213
}

contracts/src/gateway/BaseHomeGateway.sol

Lines changed: 13 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,7 @@ abstract contract BaseHomeGateway is IL2Bridge, IHomeGateway {
2727
struct RelayedData {
2828
uint256 choices;
2929
bytes extraData;
30-
uint256 numOfJurors;
30+
uint256 arbitrationCost;
3131
address forwarder;
3232
}
3333
mapping(bytes32 => RelayedData) public disputeHashtoRelayedData;
@@ -63,28 +63,33 @@ abstract contract BaseHomeGateway is IL2Bridge, IHomeGateway {
6363
}
6464

6565
/**
66-
* Relay the createDispute call from the foreign gateway to the arbitrator.
66+
* @dev Relay the createDispute call from the foreign gateway to the arbitrator.
67+
*
68+
* @param _disputeHash disputeHash
69+
* @param _choices number of ruling choices
70+
* @param _extraData extraData
71+
* @param _arbitrationCost We get the actual arbitrationCost paid by the
72+
* arbitrable here in case they paid more than the min arbitrationCost
6773
*/
6874
function relayCreateDispute(
6975
bytes32 _disputeHash,
7076
uint256 _choices,
7177
bytes calldata _extraData,
72-
uint256 _numOfJurors
78+
uint256 _arbitrationCost
7379
) external onlyFromL1 {
7480
RelayedData storage relayedData = disputeHashtoRelayedData[_disputeHash];
7581
relayedData.choices = _choices;
7682
relayedData.extraData = _extraData;
77-
relayedData.numOfJurors = _numOfJurors;
83+
relayedData.arbitrationCost = _arbitrationCost;
7884
}
7985

8086
function forwardCreateDispute(bytes32 _disputeHash) external payable {
8187
RelayedData storage relayedData = disputeHashtoRelayedData[_disputeHash];
88+
require(relayedData.forwarder == address(0), "Dispute already forwarded");
8289

83-
// TODO: Account for numOfJurors instead of just minJurors
84-
uint256 cost = arbitrator.arbitrationCost(relayedData.extraData);
85-
require(msg.value >= cost, "Not enough arbitration cost paid");
90+
require(msg.value >= relayedData.arbitrationCost, "Not enough arbitration cost paid");
8691

87-
uint256 disputeID = arbitrator.createDispute{value: cost}(relayedData.choices, relayedData.extraData);
92+
uint256 disputeID = arbitrator.createDispute{value: msg.value}(relayedData.choices, relayedData.extraData);
8893
disputeIDtoHash[disputeID] = _disputeHash;
8994
disputeHashtoID[_disputeHash] = disputeID;
9095
relayedData.forwarder = msg.sender;

contracts/src/gateway/arbitrum/EthereumGateway.sol

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,9 +9,10 @@ import "../BaseForeignGateway.sol";
99

1010
contract EthereumGateway is BaseForeignGateway, ArbL1Bridge {
1111
constructor(
12-
uint256 _arbitrationCost,
12+
address _governor,
1313
IHomeGateway _homeGateway,
14+
uint256[] memory _feeForJuror,
1415
address _l2Target,
1516
address _inbox
16-
) BaseForeignGateway(_arbitrationCost, _homeGateway) ArbL1Bridge(_l2Target, _inbox) {}
17+
) BaseForeignGateway(_governor, _homeGateway, _feeForJuror) ArbL1Bridge(_l2Target, _inbox) {}
1718
}

contracts/src/gateway/xdai/EthereumGateway.sol

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -10,9 +10,10 @@ import "../BaseForeignGateway.sol";
1010

1111
contract EthereumGateway is BaseForeignGateway, xDaiL1Bridge {
1212
constructor(
13-
uint256 _arbitrationCost,
13+
address _governor,
1414
IHomeGateway _homeGateway,
15+
uint256[] memory _feeForJuror,
1516
address _l2Target,
1617
IAMB _amb
17-
) BaseForeignGateway(_arbitrationCost, _homeGateway) xDaiL1Bridge(_l2Target, _amb) {}
18+
) BaseForeignGateway(_governor, _homeGateway, _feeForJuror) xDaiL1Bridge(_l2Target, _amb) {}
1819
}

0 commit comments

Comments
 (0)