@arbitrum/nitro-contracts 1.0.0-beta.5 → 1.0.0-beta.6

Sign up to get free protection for your applications and to get access to all the features.
Files changed (54) hide show
  1. package/package.json +2 -1
  2. package/src/bridge/Bridge.sol +127 -32
  3. package/src/bridge/IBridge.sol +40 -6
  4. package/src/bridge/{IMessageProvider.sol → IDelayedMessageProvider.sol} +2 -3
  5. package/src/bridge/IInbox.sol +23 -2
  6. package/src/bridge/IOwnable.sol +9 -0
  7. package/src/bridge/ISequencerInbox.sol +36 -9
  8. package/src/bridge/Inbox.sol +131 -45
  9. package/src/bridge/Outbox.sol +134 -31
  10. package/src/bridge/SequencerInbox.sol +159 -60
  11. package/src/challenge/ChallengeLib.sol +0 -2
  12. package/src/challenge/ChallengeManager.sol +4 -8
  13. package/src/challenge/IChallengeManager.sol +1 -1
  14. package/src/libraries/Error.sol +6 -0
  15. package/src/libraries/IGasRefunder.sol +12 -13
  16. package/src/libraries/MerkleLib.sol +11 -2
  17. package/src/libraries/MessageTypes.sol +1 -0
  18. package/src/mocks/BridgeStub.sol +67 -21
  19. package/src/mocks/InboxStub.sol +3 -9
  20. package/src/mocks/SequencerInboxStub.sol +10 -8
  21. package/src/mocks/Simple.sol +8 -0
  22. package/src/node-interface/NodeInterface.sol +32 -5
  23. package/src/osp/IOneStepProver.sol +1 -2
  24. package/src/osp/OneStepProver0.sol +1 -87
  25. package/src/osp/OneStepProverHostIo.sol +5 -6
  26. package/src/osp/OneStepProverMath.sol +37 -27
  27. package/src/osp/OneStepProverMemory.sol +3 -4
  28. package/src/precompiles/ArbAggregator.sol +23 -33
  29. package/src/precompiles/ArbBLS.sol +1 -43
  30. package/src/precompiles/ArbGasInfo.sol +1 -19
  31. package/src/precompiles/ArbOwner.sol +12 -15
  32. package/src/precompiles/ArbRetryableTx.sol +10 -1
  33. package/src/precompiles/ArbosActs.sol +9 -2
  34. package/src/rollup/BridgeCreator.sol +23 -28
  35. package/src/rollup/IRollupCore.sol +3 -3
  36. package/src/rollup/{IRollupEventBridge.sol → IRollupEventInbox.sol} +2 -2
  37. package/src/rollup/IRollupLogic.sol +21 -18
  38. package/src/rollup/RollupAdminLogic.sol +30 -34
  39. package/src/rollup/RollupCore.sol +15 -7
  40. package/src/rollup/RollupCreator.sol +21 -11
  41. package/src/rollup/{RollupEventBridge.sol → RollupEventInbox.sol} +10 -10
  42. package/src/rollup/RollupLib.sol +20 -5
  43. package/src/rollup/RollupUserLogic.sol +9 -18
  44. package/src/rollup/ValidatorWallet.sol +124 -8
  45. package/src/rollup/ValidatorWalletCreator.sol +11 -6
  46. package/src/state/Deserialize.sol +3 -22
  47. package/src/state/Instructions.sol +2 -10
  48. package/src/state/Machine.sol +0 -4
  49. package/src/state/ModuleMemory.sol +2 -1
  50. package/src/state/Value.sol +2 -3
  51. package/src/test-helpers/BridgeTester.sol +223 -0
  52. package/src/test-helpers/OutboxWithoutOptTester.sol +188 -0
  53. package/src/test-helpers/RollupMock.sol +21 -0
  54. package/src/state/PcStack.sol +0 -32
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@arbitrum/nitro-contracts",
3
- "version": "1.0.0-beta.5",
3
+ "version": "1.0.0-beta.6",
4
4
  "description": "Layer 2 precompiles and rollup for Arbitrum Nitro",
5
5
  "author": "Offchain Labs, Inc.",
6
6
  "license": "BUSL-1.1",
@@ -41,6 +41,7 @@
41
41
  "ethereum-waffle": "^3.4.0",
42
42
  "ethers": "^5.5.2",
43
43
  "hardhat-deploy": "^0.11.4",
44
+ "hardhat-gas-reporter": "^1.0.8",
44
45
  "prettier": "^2.5.1",
45
46
  "prettier-plugin-solidity": "^1.0.0-beta.19",
46
47
  "solhint": "^3.3.7",
@@ -4,21 +4,23 @@
4
4
 
5
5
  pragma solidity ^0.8.4;
6
6
 
7
- import "@openzeppelin/contracts-upgradeable/access/OwnableUpgradeable.sol";
7
+ import "@openzeppelin/contracts-upgradeable/proxy/utils/Initializable.sol";
8
8
  import "@openzeppelin/contracts-upgradeable/utils/AddressUpgradeable.sol";
9
9
 
10
10
  import "./IBridge.sol";
11
11
  import "./Messages.sol";
12
12
  import "../libraries/DelegateCallAware.sol";
13
13
 
14
+ import {L1MessageType_batchPostingReport} from "../libraries/MessageTypes.sol";
15
+
14
16
  /**
15
17
  * @title Staging ground for incoming and outgoing messages
16
- * @notice Holds the inbox accumulator for delayed messages, and is the ETH escrow
17
- * for value sent with these messages.
18
+ * @notice Holds the inbox accumulator for sequenced and delayed messages.
19
+ * It is also the ETH escrow for value sent with these messages.
18
20
  * Since the escrow is held here, this contract also contains a list of allowed
19
21
  * outboxes that can make calls from here and withdraw this escrow.
20
22
  */
21
- contract Bridge is OwnableUpgradeable, DelegateCallAware, IBridge {
23
+ contract Bridge is Initializable, DelegateCallAware, IBridge {
22
24
  using AddressUpgradeable for address;
23
25
 
24
26
  struct InOutInfo {
@@ -26,29 +28,109 @@ contract Bridge is OwnableUpgradeable, DelegateCallAware, IBridge {
26
28
  bool allowed;
27
29
  }
28
30
 
29
- mapping(address => InOutInfo) private allowedInboxesMap;
31
+ mapping(address => InOutInfo) private allowedDelayedInboxesMap;
30
32
  mapping(address => InOutInfo) private allowedOutboxesMap;
31
33
 
32
- address[] public allowedInboxList;
34
+ address[] public allowedDelayedInboxList;
33
35
  address[] public allowedOutboxList;
34
36
 
35
- address public override activeOutbox;
37
+ address private _activeOutbox;
36
38
 
37
39
  /// @dev Accumulator for delayed inbox messages; tail represents hash of the current state; each element represents the inclusion of a new message.
38
- bytes32[] public override inboxAccs;
40
+ bytes32[] public override delayedInboxAccs;
41
+
42
+ /// @dev Accumulator for sequencer inbox messages; tail represents hash of the current state; each element represents the inclusion of a new message.
43
+ bytes32[] public override sequencerInboxAccs;
44
+
45
+ IOwnable public override rollup;
46
+ address public sequencerInbox;
47
+
48
+ address private constant EMPTY_ACTIVEOUTBOX = address(type(uint160).max);
39
49
 
40
- function initialize() external initializer onlyDelegated {
41
- __Ownable_init();
50
+ function initialize(IOwnable rollup_) external initializer onlyDelegated {
51
+ _activeOutbox = EMPTY_ACTIVEOUTBOX;
52
+ rollup = rollup_;
42
53
  }
43
54
 
44
- function allowedInboxes(address inbox) external view override returns (bool) {
45
- return allowedInboxesMap[inbox].allowed;
55
+ modifier onlyRollupOrOwner() {
56
+ if (msg.sender != address(rollup)) {
57
+ address rollupOwner = rollup.owner();
58
+ if (msg.sender != rollupOwner) {
59
+ revert NotRollupOrOwner(msg.sender, address(rollup), rollupOwner);
60
+ }
61
+ }
62
+ _;
63
+ }
64
+
65
+ /// @dev returns the address of current active Outbox, or zero if no outbox is active
66
+ function activeOutbox() public view returns (address) {
67
+ address outbox = _activeOutbox;
68
+ // address zero is returned if no outbox is set, but the value used in storage
69
+ // is non-zero to save users some gas (as storage refunds are usually maxed out)
70
+ // EIP-1153 would help here.
71
+ // we don't return `EMPTY_ACTIVEOUTBOX` to avoid a breaking change on the current api
72
+ if (outbox == EMPTY_ACTIVEOUTBOX) return address(0);
73
+ return outbox;
74
+ }
75
+
76
+ function allowedDelayedInboxes(address inbox) external view override returns (bool) {
77
+ return allowedDelayedInboxesMap[inbox].allowed;
46
78
  }
47
79
 
48
80
  function allowedOutboxes(address outbox) external view override returns (bool) {
49
81
  return allowedOutboxesMap[outbox].allowed;
50
82
  }
51
83
 
84
+ modifier onlySequencerInbox() {
85
+ if (msg.sender != sequencerInbox) revert NotSequencerInbox(msg.sender);
86
+ _;
87
+ }
88
+
89
+ function enqueueSequencerMessage(bytes32 dataHash, uint256 afterDelayedMessagesRead)
90
+ external
91
+ override
92
+ onlySequencerInbox
93
+ returns (
94
+ uint256 seqMessageIndex,
95
+ bytes32 beforeAcc,
96
+ bytes32 delayedAcc,
97
+ bytes32 acc
98
+ )
99
+ {
100
+ seqMessageIndex = sequencerInboxAccs.length;
101
+ if (sequencerInboxAccs.length > 0) {
102
+ beforeAcc = sequencerInboxAccs[sequencerInboxAccs.length - 1];
103
+ }
104
+ if (afterDelayedMessagesRead > 0) {
105
+ delayedAcc = delayedInboxAccs[afterDelayedMessagesRead - 1];
106
+ }
107
+ acc = keccak256(abi.encodePacked(beforeAcc, dataHash, delayedAcc));
108
+ sequencerInboxAccs.push(acc);
109
+ }
110
+
111
+ /**
112
+ * @dev allows the sequencer inbox to submit a delayed message of the batchPostingReport type
113
+ * This is done through a separate function entrypoint instead of allowing the sequencer inbox
114
+ * to call `enqueueDelayedMessage` to avoid the gas overhead of an extra SLOAD in either
115
+ * every delayed inbox or every sequencer inbox call.
116
+ */
117
+ function submitBatchSpendingReport(address sender, bytes32 messageDataHash)
118
+ external
119
+ override
120
+ onlySequencerInbox
121
+ returns (uint256)
122
+ {
123
+ return
124
+ addMessageToDelayedAccumulator(
125
+ L1MessageType_batchPostingReport,
126
+ sender,
127
+ uint64(block.number),
128
+ uint64(block.timestamp), // solhint-disable-line not-rely-on-time,
129
+ block.basefee,
130
+ messageDataHash
131
+ );
132
+ }
133
+
52
134
  /**
53
135
  * @dev Enqueue a message in the delayed inbox accumulator.
54
136
  * These messages are later sequenced in the SequencerInbox, either by the sequencer as
@@ -59,9 +141,9 @@ contract Bridge is OwnableUpgradeable, DelegateCallAware, IBridge {
59
141
  address sender,
60
142
  bytes32 messageDataHash
61
143
  ) external payable override returns (uint256) {
62
- if (!allowedInboxesMap[msg.sender].allowed) revert NotInbox(msg.sender);
144
+ if (!allowedDelayedInboxesMap[msg.sender].allowed) revert NotDelayedInbox(msg.sender);
63
145
  return
64
- addMessageToAccumulator(
146
+ addMessageToDelayedAccumulator(
65
147
  kind,
66
148
  sender,
67
149
  uint64(block.number),
@@ -71,7 +153,7 @@ contract Bridge is OwnableUpgradeable, DelegateCallAware, IBridge {
71
153
  );
72
154
  }
73
155
 
74
- function addMessageToAccumulator(
156
+ function addMessageToDelayedAccumulator(
75
157
  uint8 kind,
76
158
  address sender,
77
159
  uint64 blockNumber,
@@ -79,7 +161,7 @@ contract Bridge is OwnableUpgradeable, DelegateCallAware, IBridge {
79
161
  uint256 baseFeeL1,
80
162
  bytes32 messageDataHash
81
163
  ) internal returns (uint256) {
82
- uint256 count = inboxAccs.length;
164
+ uint256 count = delayedInboxAccs.length;
83
165
  bytes32 messageHash = Messages.messageHash(
84
166
  kind,
85
167
  sender,
@@ -91,9 +173,9 @@ contract Bridge is OwnableUpgradeable, DelegateCallAware, IBridge {
91
173
  );
92
174
  bytes32 prevAcc = 0;
93
175
  if (count > 0) {
94
- prevAcc = inboxAccs[count - 1];
176
+ prevAcc = delayedInboxAccs[count - 1];
95
177
  }
96
- inboxAccs.push(Messages.accumulateInboxMessage(prevAcc, messageHash));
178
+ delayedInboxAccs.push(Messages.accumulateInboxMessage(prevAcc, messageHash));
97
179
  emit MessageDelivered(
98
180
  count,
99
181
  prevAcc,
@@ -114,37 +196,46 @@ contract Bridge is OwnableUpgradeable, DelegateCallAware, IBridge {
114
196
  ) external override returns (bool success, bytes memory returnData) {
115
197
  if (!allowedOutboxesMap[msg.sender].allowed) revert NotOutbox(msg.sender);
116
198
  if (data.length > 0 && !to.isContract()) revert NotContract(to);
117
- address prevOutbox = activeOutbox;
118
- activeOutbox = msg.sender;
199
+ address prevOutbox = _activeOutbox;
200
+ _activeOutbox = msg.sender;
119
201
  // We set and reset active outbox around external call so activeOutbox remains valid during call
120
202
 
121
203
  // We use a low level call here since we want to bubble up whether it succeeded or failed to the caller
122
204
  // rather than reverting on failure as well as allow contract and non-contract calls
123
205
  // solhint-disable-next-line avoid-low-level-calls
124
206
  (success, returnData) = to.call{value: value}(data);
125
- activeOutbox = prevOutbox;
207
+ _activeOutbox = prevOutbox;
126
208
  emit BridgeCallTriggered(msg.sender, to, value, data);
127
209
  }
128
210
 
129
- function setInbox(address inbox, bool enabled) external override onlyOwner {
130
- InOutInfo storage info = allowedInboxesMap[inbox];
211
+ function setSequencerInbox(address _sequencerInbox) external override onlyRollupOrOwner {
212
+ sequencerInbox = _sequencerInbox;
213
+ emit SequencerInboxUpdated(_sequencerInbox);
214
+ }
215
+
216
+ function setDelayedInbox(address inbox, bool enabled) external override onlyRollupOrOwner {
217
+ InOutInfo storage info = allowedDelayedInboxesMap[inbox];
131
218
  bool alreadyEnabled = info.allowed;
132
219
  emit InboxToggle(inbox, enabled);
133
220
  if ((alreadyEnabled && enabled) || (!alreadyEnabled && !enabled)) {
134
221
  return;
135
222
  }
136
223
  if (enabled) {
137
- allowedInboxesMap[inbox] = InOutInfo(allowedInboxList.length, true);
138
- allowedInboxList.push(inbox);
224
+ allowedDelayedInboxesMap[inbox] = InOutInfo(allowedDelayedInboxList.length, true);
225
+ allowedDelayedInboxList.push(inbox);
139
226
  } else {
140
- allowedInboxList[info.index] = allowedInboxList[allowedInboxList.length - 1];
141
- allowedInboxesMap[allowedInboxList[info.index]].index = info.index;
142
- allowedInboxList.pop();
143
- delete allowedInboxesMap[inbox];
227
+ allowedDelayedInboxList[info.index] = allowedDelayedInboxList[
228
+ allowedDelayedInboxList.length - 1
229
+ ];
230
+ allowedDelayedInboxesMap[allowedDelayedInboxList[info.index]].index = info.index;
231
+ allowedDelayedInboxList.pop();
232
+ delete allowedDelayedInboxesMap[inbox];
144
233
  }
145
234
  }
146
235
 
147
- function setOutbox(address outbox, bool enabled) external override onlyOwner {
236
+ function setOutbox(address outbox, bool enabled) external override onlyRollupOrOwner {
237
+ if (outbox == EMPTY_ACTIVEOUTBOX) revert InvalidOutboxSet(outbox);
238
+
148
239
  InOutInfo storage info = allowedOutboxesMap[outbox];
149
240
  bool alreadyEnabled = info.allowed;
150
241
  emit OutboxToggle(outbox, enabled);
@@ -162,7 +253,11 @@ contract Bridge is OwnableUpgradeable, DelegateCallAware, IBridge {
162
253
  }
163
254
  }
164
255
 
165
- function messageCount() external view override returns (uint256) {
166
- return inboxAccs.length;
256
+ function delayedMessageCount() external view override returns (uint256) {
257
+ return delayedInboxAccs.length;
258
+ }
259
+
260
+ function sequencerMessageCount() external view override returns (uint256) {
261
+ return sequencerInboxAccs.length;
167
262
  }
168
263
  }
@@ -4,16 +4,25 @@
4
4
 
5
5
  pragma solidity ^0.8.4;
6
6
 
7
- import {NotContract} from "../libraries/Error.sol";
7
+ import {NotContract, NotRollupOrOwner} from "../libraries/Error.sol";
8
+ import "./IOwnable.sol";
8
9
 
9
10
  /// @dev Thrown when an un-authorized address tries to access an only-inbox function
10
11
  /// @param sender The un-authorized sender
11
- error NotInbox(address sender);
12
+ error NotDelayedInbox(address sender);
13
+
14
+ /// @dev Thrown when an un-authorized address tries to access an only-sequencer-inbox function
15
+ /// @param sender The un-authorized sender
16
+ error NotSequencerInbox(address sender);
12
17
 
13
18
  /// @dev Thrown when an un-authorized address tries to access an only-outbox function
14
19
  /// @param sender The un-authorized sender
15
20
  error NotOutbox(address sender);
16
21
 
22
+ /// @dev the provided outbox address isn't valid
23
+ /// @param outbox address of outbox being set
24
+ error InvalidOutboxSet(address outbox);
25
+
17
26
  interface IBridge {
18
27
  event MessageDelivered(
19
28
  uint256 indexed messageIndex,
@@ -37,12 +46,27 @@ interface IBridge {
37
46
 
38
47
  event OutboxToggle(address indexed outbox, bool enabled);
39
48
 
49
+ event SequencerInboxUpdated(address newSequencerInbox);
50
+
40
51
  function enqueueDelayedMessage(
41
52
  uint8 kind,
42
53
  address sender,
43
54
  bytes32 messageDataHash
44
55
  ) external payable returns (uint256);
45
56
 
57
+ function enqueueSequencerMessage(bytes32 dataHash, uint256 afterDelayedMessagesRead)
58
+ external
59
+ returns (
60
+ uint256 seqMessageIndex,
61
+ bytes32 beforeAcc,
62
+ bytes32 delayedAcc,
63
+ bytes32 acc
64
+ );
65
+
66
+ function submitBatchSpendingReport(address batchPoster, bytes32 dataHash)
67
+ external
68
+ returns (uint256 msgNum);
69
+
46
70
  function executeCall(
47
71
  address to,
48
72
  uint256 value,
@@ -50,19 +74,29 @@ interface IBridge {
50
74
  ) external returns (bool success, bytes memory returnData);
51
75
 
52
76
  // These are only callable by the admin
53
- function setInbox(address inbox, bool enabled) external;
77
+ function setDelayedInbox(address inbox, bool enabled) external;
54
78
 
55
79
  function setOutbox(address inbox, bool enabled) external;
56
80
 
81
+ function setSequencerInbox(address _sequencerInbox) external;
82
+
57
83
  // View functions
58
84
 
85
+ function sequencerInbox() external view returns (address);
86
+
59
87
  function activeOutbox() external view returns (address);
60
88
 
61
- function allowedInboxes(address inbox) external view returns (bool);
89
+ function allowedDelayedInboxes(address inbox) external view returns (bool);
62
90
 
63
91
  function allowedOutboxes(address outbox) external view returns (bool);
64
92
 
65
- function inboxAccs(uint256 index) external view returns (bytes32);
93
+ function delayedInboxAccs(uint256 index) external view returns (bytes32);
94
+
95
+ function sequencerInboxAccs(uint256 index) external view returns (bytes32);
96
+
97
+ function delayedMessageCount() external view returns (uint256);
98
+
99
+ function sequencerMessageCount() external view returns (uint256);
66
100
 
67
- function messageCount() external view returns (uint256);
101
+ function rollup() external view returns (IOwnable);
68
102
  }
@@ -4,8 +4,7 @@
4
4
 
5
5
  pragma solidity ^0.8.0;
6
6
 
7
- interface IMessageProvider {
7
+ interface IDelayedMessageProvider {
8
+ /// @dev event emitted when a inbox message is added to the Bridge's delayed accumulator
8
9
  event InboxMessageDelivered(uint256 indexed messageNum, bytes data);
9
-
10
- event InboxMessageDeliveredFromOrigin(uint256 indexed messageNum);
11
10
  }
@@ -5,7 +5,7 @@
5
5
  pragma solidity ^0.8.4;
6
6
 
7
7
  import "./IBridge.sol";
8
- import "./IMessageProvider.sol";
8
+ import "./IDelayedMessageProvider.sol";
9
9
  import {AlreadyInit, NotOrigin, DataTooLarge} from "../libraries/Error.sol";
10
10
 
11
11
  /// @dev The contract is paused, so cannot be paused
@@ -23,7 +23,25 @@ error InsufficientValue(uint256 expected, uint256 actual);
23
23
  /// @dev submission cost provided isn't enough to create retryable ticket
24
24
  error InsufficientSubmissionCost(uint256 expected, uint256 actual);
25
25
 
26
- interface IInbox is IMessageProvider {
26
+ /// @dev address not allowed to interact with the given contract
27
+ error NotAllowedOrigin(address origin);
28
+
29
+ /// @dev used to convey retryable tx data in eth calls without requiring a tx trace
30
+ /// this follows a pattern similar to EIP-3668 where reverts surface call information
31
+ error RetryableData(
32
+ address from,
33
+ address to,
34
+ uint256 l2CallValue,
35
+ uint256 deposit,
36
+ uint256 maxSubmissionCost,
37
+ address excessFeeRefundAddress,
38
+ address callValueRefundAddress,
39
+ uint256 gasLimit,
40
+ uint256 maxFeePerGas,
41
+ bytes data
42
+ );
43
+
44
+ interface IInbox is IDelayedMessageProvider {
27
45
  function sendL2Message(bytes calldata messageData) external returns (uint256);
28
46
 
29
47
  function sendUnsignedTransaction(
@@ -58,6 +76,7 @@ interface IInbox is IMessageProvider {
58
76
  bytes calldata data
59
77
  ) external payable returns (uint256);
60
78
 
79
+ /// @dev Gas limit and maxFeePerGas should not be set to 1 as that is used to trigger the RetryableData error
61
80
  function createRetryableTicket(
62
81
  address to,
63
82
  uint256 arbTxCallValue,
@@ -69,6 +88,8 @@ interface IInbox is IMessageProvider {
69
88
  bytes calldata data
70
89
  ) external payable returns (uint256);
71
90
 
91
+ /// @notice TEMPORARILY DISABLED as exact mechanics are being worked out
92
+ /// @dev Gas limit and maxFeePerGas should not be set to 1 as that is used to trigger the RetryableData error
72
93
  function unsafeCreateRetryableTicket(
73
94
  address to,
74
95
  uint256 arbTxCallValue,
@@ -0,0 +1,9 @@
1
+ // Copyright 2021-2022, Offchain Labs, Inc.
2
+ // For license information, see https://github.com/nitro/blob/master/LICENSE
3
+ // SPDX-License-Identifier: BUSL-1.1
4
+
5
+ pragma solidity ^0.8.4;
6
+
7
+ interface IOwnable {
8
+ function owner() external view returns (address);
9
+ }
@@ -6,8 +6,9 @@ pragma solidity ^0.8.0;
6
6
 
7
7
  import "../libraries/IGasRefunder.sol";
8
8
  import {AlreadyInit, HadZeroInit, NotOrigin, DataTooLarge, NotRollup} from "../libraries/Error.sol";
9
+ import "./IDelayedMessageProvider.sol";
9
10
 
10
- interface ISequencerInbox {
11
+ interface ISequencerInbox is IDelayedMessageProvider {
11
12
  struct MaxTimeVariation {
12
13
  uint256 delayBlocks;
13
14
  uint256 futureBlocks;
@@ -38,18 +39,23 @@ interface ISequencerInbox {
38
39
  BatchDataLocation dataLocation
39
40
  );
40
41
 
42
+ event OwnerFunctionCalled(uint256 indexed id);
43
+
41
44
  /// @dev a separate event that emits batch data when this isn't easily accessible in the tx.input
42
45
  event SequencerBatchData(uint256 indexed batchSequenceNumber, bytes data);
43
46
 
47
+ /// @dev a valid keyset was added
48
+ event SetValidKeyset(bytes32 indexed keysetHash, bytes keysetBytes);
49
+
50
+ /// @dev a keyset was invalidated
51
+ event InvalidateKeyset(bytes32 indexed keysetHash);
52
+
44
53
  /// @dev Thrown when someone attempts to read fewer messages than have already been read
45
54
  error DelayedBackwards();
46
55
 
47
56
  /// @dev Thrown when someone attempts to read more messages than exist
48
57
  error DelayedTooFar();
49
58
 
50
- /// @dev Thrown if the length of the header plus the length of the batch overflows
51
- error DataLengthOverflow();
52
-
53
59
  /// @dev Force include can only read messages more blocks old than the delay period
54
60
  error ForceIncludeBlockTooSoon();
55
61
 
@@ -63,18 +69,20 @@ interface ISequencerInbox {
63
69
  error NotBatchPoster();
64
70
 
65
71
  /// @dev The sequence number provided to this message was inconsistent with the number of batches already included
66
- error BadSequencerNumber();
72
+ error BadSequencerNumber(uint256 stored, uint256 received);
67
73
 
68
74
  /// @dev The batch data has the inbox authenticated bit set, but the batch data was not authenticated by the inbox
69
75
  error DataNotAuthenticated();
70
76
 
71
- function inboxAccs(uint256 index) external view returns (bytes32);
77
+ /// @dev Tried to create an already valid Data Availability Service keyset
78
+ error AlreadyValidDASKeyset(bytes32);
72
79
 
73
- function batchCount() external view returns (uint256);
80
+ /// @dev Tried to use or invalidate an already invalid Data Availability Service keyset
81
+ error NoSuchKeyset(bytes32);
74
82
 
75
- function setMaxTimeVariation(MaxTimeVariation memory timeVariation) external;
83
+ function inboxAccs(uint256 index) external view returns (bytes32);
76
84
 
77
- function setIsBatchPoster(address addr, bool isBatchPoster_) external;
85
+ function batchCount() external view returns (uint256);
78
86
 
79
87
  function addSequencerL2Batch(
80
88
  uint256 sequenceNumber,
@@ -82,4 +90,23 @@ interface ISequencerInbox {
82
90
  uint256 afterDelayedMessagesRead,
83
91
  IGasRefunder gasRefunder
84
92
  ) external;
93
+
94
+ // Methods only callable by rollup owner
95
+
96
+ /**
97
+ * @notice Set max time variation from actual time for sequencer inbox
98
+ * @param timeVariation the maximum time variation parameters
99
+ */
100
+ function setMaxTimeVariation(MaxTimeVariation memory timeVariation) external;
101
+
102
+ /**
103
+ * @notice Updates whether an address is authorized to be a batch poster at the sequencer inbox
104
+ * @param addr the address
105
+ * @param isBatchPoster if the specified address should be authorized as a batch poster
106
+ */
107
+ function setIsBatchPoster(address addr, bool isBatchPoster) external;
108
+
109
+ function setValidKeyset(bytes calldata keysetBytes) external;
110
+
111
+ function invalidateKeysetHash(bytes32 ksHash) external;
85
112
  }