You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Copy file name to clipboardExpand all lines: contracts/utils/README.adoc
+3Lines changed: 3 additions & 0 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -49,6 +49,7 @@ Miscellaneous contracts and libraries containing utility functions you can use t
49
49
* {AbstractSigner}: Abstract contract for internal signature validation in smart contracts.
50
50
* {ERC7739}: An abstract contract to validate signatures following the rehashing scheme from `ERC7739Utils`.
51
51
* {ERC7739Utils}: Utilities library that implements a defensive rehashing mechanism to prevent replayability of smart contract signatures based on ERC-7739.
52
+
* {Time}: A library that provides helpers for manipulating time-related objects, including a `Delay` type.
52
53
53
54
[NOTE]
54
55
====
@@ -170,3 +171,5 @@ Ethereum contracts have no native concept of an interface, so applications must
Copy file name to clipboardExpand all lines: docs/modules/ROOT/pages/utilities.adoc
+78Lines changed: 78 additions & 0 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -405,3 +405,81 @@ contract L1Inbox {
405
405
----
406
406
407
407
IMPORTANT: After EIP-2935 activation, it takes 8,191 blocks to completely fill the history storage. Before that, only block hashes since the fork block will be available.
408
+
409
+
=== Time
410
+
411
+
The xref:api:utils.adoc#Time[`Time`] library provides helpers for manipulating time-related objects in a type-safe manner. It uses `uint48` for timepoints and `uint32` for durations, helping to reduce gas costs while providing adequate precision.
412
+
413
+
One of its key features is the `Delay` type, which represents a duration that can automatically change its value at a specified point in the future while maintaining delay guarantees. For example, when reducing a delay value (e.g., from 7 days to 1 day), the change only takes effect after the difference between the old and new delay (i.e. a 6 days) or a minimum setback period, preventing an attacker who gains admin access from immediately reducing security timeouts and executing sensitive operations. This is particularly useful for governance and security mechanisms where timelock periods need to be enforced.
414
+
415
+
Consider this example for using and safely updating Delays:
416
+
[source,solidity]
417
+
----
418
+
// SPDX-License-Identifier: MIT
419
+
pragma solidity ^0.8.27;
420
+
421
+
import {Time} from "contracts/utils/types/Time.sol";
422
+
423
+
contract MyDelayedContract {
424
+
using Time for *;
425
+
426
+
Time.Delay private _delay;
427
+
428
+
constructor() {
429
+
_delay = Time.toDelay(3 days);
430
+
}
431
+
432
+
function schedule(bytes32 operationId) external {
433
+
// Get the current `_delay` value, respecting any pending delay changes if they've taken effect
// Get complete delay details including pending changes
461
+
function getDelayDetails() external view returns (
462
+
uint32 currentValue, // The current delay value
463
+
uint32 pendingValue, // The pending delay value
464
+
uint48 effectTime // The timepoint when the pending delay change takes effect
465
+
) {
466
+
return _delay.getFull();
467
+
}
468
+
}
469
+
----
470
+
471
+
This pattern is used extensively in OpenZeppelin's xref:api:access.adoc#AccessManager[AccessManager] for implementing secure time-based access control. For example, when changing an admin delay:
472
+
473
+
[source,solidity]
474
+
----
475
+
// From AccessManager.sol
476
+
function _setTargetAdminDelay(address target, uint32 newDelay) internal virtual {
0 commit comments