@@ -15,39 +15,39 @@ import {Math} from "./math/Math.sol";
15
15
` ;
16
16
17
17
const sort = type => `\
18
- /**
19
- * @dev Sort an array of ${ type } (in memory) following the provided comparator function.
20
- *
21
- * This function does the sorting "in place", meaning that it overrides the input. The object is returned for
22
- * convenience, but that returned value can be discarded safely if the caller has a memory pointer to the array.
23
- *
24
- * NOTE: this function's cost is \`O(n · log(n))\` in average and \`O(n²)\` in the worst case, with n the length of the
25
- * array. Using it in view functions that are executed through \`eth_call\` is safe, but one should be very careful
26
- * when executing this as part of a transaction. If the array being sorted is too large, the sort operation may
27
- * consume more gas than is available in a block, leading to potential DoS.
28
- */
29
- function sort(
30
- ${ type } [] memory array,
31
- function(${ type } , ${ type } ) pure returns (bool) comp
32
- ) internal pure returns (${ type } [] memory) {
33
- ${
34
- type === 'bytes32'
35
- ? '_quickSort(_begin(array), _end(array), comp);'
36
- : 'sort(_castToBytes32Array(array), _castToBytes32Comp(comp));'
37
- }
38
- return array;
18
+ /**
19
+ * @dev Sort an array of ${ type } (in memory) following the provided comparator function.
20
+ *
21
+ * This function does the sorting "in place", meaning that it overrides the input. The object is returned for
22
+ * convenience, but that returned value can be discarded safely if the caller has a memory pointer to the array.
23
+ *
24
+ * NOTE: this function's cost is \`O(n · log(n))\` in average and \`O(n²)\` in the worst case, with n the length of the
25
+ * array. Using it in view functions that are executed through \`eth_call\` is safe, but one should be very careful
26
+ * when executing this as part of a transaction. If the array being sorted is too large, the sort operation may
27
+ * consume more gas than is available in a block, leading to potential DoS.
28
+ */
29
+ function sort(
30
+ ${ type } [] memory array,
31
+ function(${ type } , ${ type } ) pure returns (bool) comp
32
+ ) internal pure returns (${ type } [] memory) {
33
+ ${
34
+ type === 'bytes32'
35
+ ? '_quickSort(_begin(array), _end(array), comp);'
36
+ : 'sort(_castToBytes32Array(array), _castToBytes32Comp(comp));'
39
37
}
38
+ return array;
39
+ }
40
40
41
- /**
42
- * @dev Variant of {sort} that sorts an array of ${ type } in increasing order.
43
- */
44
- function sort(${ type } [] memory array) internal pure returns (${ type } [] memory) {
45
- ${ type === 'bytes32' ? 'sort(array, _defaultComp);' : 'sort(_castToBytes32Array(array), _defaultComp);' }
46
- return array;
47
- }
41
+ /**
42
+ * @dev Variant of {sort} that sorts an array of ${ type } in increasing order.
43
+ */
44
+ function sort(${ type } [] memory array) internal pure returns (${ type } [] memory) {
45
+ ${ type === 'bytes32' ? 'sort(array, _defaultComp);' : 'sort(_castToBytes32Array(array), _defaultComp);' }
46
+ return array;
47
+ }
48
48
` ;
49
49
50
- const quickSort = `
50
+ const quickSort = `\
51
51
/**
52
52
* @dev Performs a quick sort of a segment of memory. The segment sorted starts at \`begin\` (inclusive), and stops
53
53
* at end (exclusive). Sorting follows the \`comp\` comparator.
@@ -123,34 +123,34 @@ function _swap(uint256 ptr1, uint256 ptr2) private pure {
123
123
}
124
124
` ;
125
125
126
- const defaultComparator = `
127
- /// @dev Comparator for sorting arrays in increasing order.
128
- function _defaultComp(bytes32 a, bytes32 b) private pure returns (bool) {
129
- return a < b;
130
- }
126
+ const defaultComparator = `\
127
+ /// @dev Comparator for sorting arrays in increasing order.
128
+ function _defaultComp(bytes32 a, bytes32 b) private pure returns (bool) {
129
+ return a < b;
130
+ }
131
131
` ;
132
132
133
133
const castArray = type => `\
134
- /// @dev Helper: low level cast ${ type } memory array to uint256 memory array
135
- function _castToBytes32Array(${ type } [] memory input) private pure returns (bytes32[] memory output) {
136
- assembly {
137
- output := input
138
- }
134
+ /// @dev Helper: low level cast ${ type } memory array to uint256 memory array
135
+ function _castToBytes32Array(${ type } [] memory input) private pure returns (bytes32[] memory output) {
136
+ assembly {
137
+ output := input
139
138
}
139
+ }
140
140
` ;
141
141
142
142
const castComparator = type => `\
143
- /// @dev Helper: low level cast ${ type } comp function to bytes32 comp function
144
- function _castToBytes32Comp(
145
- function(${ type } , ${ type } ) pure returns (bool) input
146
- ) private pure returns (function(bytes32, bytes32) pure returns (bool) output) {
147
- assembly {
148
- output := input
149
- }
143
+ /// @dev Helper: low level cast ${ type } comp function to bytes32 comp function
144
+ function _castToBytes32Comp(
145
+ function(${ type } , ${ type } ) pure returns (bool) input
146
+ ) private pure returns (function(bytes32, bytes32) pure returns (bool) output) {
147
+ assembly {
148
+ output := input
150
149
}
150
+ }
151
151
` ;
152
152
153
- const search = `
153
+ const search = `\
154
154
/**
155
155
* @dev Searches a sorted \`array\` and returns the first index that contains
156
156
* a value greater or equal to \`element\`. If no such index exists (i.e. all
@@ -319,12 +319,12 @@ function upperBoundMemory(uint256[] memory array, uint256 element) internal pure
319
319
}
320
320
` ;
321
321
322
- const unsafeAccessStorage = type => `
322
+ const unsafeAccessStorage = type => `\
323
323
/**
324
- * @dev Access an array in an "unsafe" way. Skips solidity "index-out-of-range" check.
325
- *
326
- * WARNING: Only use if you are certain \`pos\` is lower than the array length.
327
- */
324
+ * @dev Access an array in an "unsafe" way. Skips solidity "index-out-of-range" check.
325
+ *
326
+ * WARNING: Only use if you are certain \`pos\` is lower than the array length.
327
+ */
328
328
function unsafeAccess(${ type } [] storage arr, uint256 pos) internal pure returns (StorageSlot.${ capitalize (
329
329
type ,
330
330
) } Slot storage) {
@@ -334,9 +334,10 @@ function unsafeAccess(${type}[] storage arr, uint256 pos) internal pure returns
334
334
slot := arr.slot
335
335
}
336
336
return slot.deriveArray().offset(pos).get${ capitalize ( type ) } Slot();
337
- }` ;
337
+ }
338
+ ` ;
338
339
339
- const unsafeAccessMemory = type => `
340
+ const unsafeAccessMemory = type => `\
340
341
/**
341
342
* @dev Access an array in an "unsafe" way. Skips solidity "index-out-of-range" check.
342
343
*
@@ -349,7 +350,7 @@ function unsafeMemoryAccess(${type}[] memory arr, uint256 pos) internal pure ret
349
350
}
350
351
` ;
351
352
352
- const unsafeSetLength = type => `
353
+ const unsafeSetLength = type => `\
353
354
/**
354
355
* @dev Helper to set the length of an dynamic array. Directly writing to \`.length\` is forbidden.
355
356
*
@@ -360,26 +361,32 @@ function unsafeSetLength(${type}[] storage array, uint256 len) internal {
360
361
assembly {
361
362
sstore(array.slot, len)
362
363
}
363
- }` ;
364
+ }
365
+ ` ;
364
366
365
367
// GENERATE
366
368
module . exports = format (
367
369
header . trimEnd ( ) ,
368
370
'library Arrays {' ,
369
- 'using SlotDerivation for bytes32;' ,
370
- 'using StorageSlot for bytes32;' ,
371
- // sorting, comparator, helpers and internal
372
- sort ( 'bytes32' ) ,
373
- TYPES . filter ( type => type !== 'bytes32' ) . map ( sort ) ,
374
- quickSort ,
375
- defaultComparator ,
376
- TYPES . filter ( type => type !== 'bytes32' ) . map ( castArray ) ,
377
- TYPES . filter ( type => type !== 'bytes32' ) . map ( castComparator ) ,
378
- // lookup
379
- search ,
380
- // unsafe (direct) storage and memory access
381
- TYPES . map ( unsafeAccessStorage ) ,
382
- TYPES . map ( unsafeAccessMemory ) ,
383
- TYPES . map ( unsafeSetLength ) ,
371
+ format (
372
+ [ ] . concat (
373
+ 'using SlotDerivation for bytes32;' ,
374
+ 'using StorageSlot for bytes32;' ,
375
+ '' ,
376
+ // sorting, comparator, helpers and internal
377
+ sort ( 'bytes32' ) ,
378
+ TYPES . filter ( type => type !== 'bytes32' ) . map ( sort ) ,
379
+ quickSort ,
380
+ defaultComparator ,
381
+ TYPES . filter ( type => type !== 'bytes32' ) . map ( castArray ) ,
382
+ TYPES . filter ( type => type !== 'bytes32' ) . map ( castComparator ) ,
383
+ // lookup
384
+ search ,
385
+ // unsafe (direct) storage and memory access
386
+ TYPES . map ( unsafeAccessStorage ) ,
387
+ TYPES . map ( unsafeAccessMemory ) ,
388
+ TYPES . map ( unsafeSetLength ) ,
389
+ ) ,
390
+ ) . trimEnd ( ) ,
384
391
'}' ,
385
392
) ;
0 commit comments