Skip to content

Commit 2fceb3a

Browse files
authored
Merge pull request #16634 from argotorg/ssa-improve-shuffling
SSA: Improve shuffling
2 parents e6bfd0f + 7fc062d commit 2fceb3a

6 files changed

Lines changed: 49 additions & 17 deletions

File tree

libyul/backends/evm/ssa/StackShuffler.h

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -580,6 +580,21 @@ class StackShuffler
580580
}
581581
}
582582
}
583+
// If there were no other swapping opportunities, try fixing at least the top before we start pushing
584+
// more stuff on stack
585+
if (!_state.isArgsCompatible(stackTop, stackTop))
586+
for (StackOffset offset: _state.stackArgsRange())
587+
if (
588+
offset != stackTop &&
589+
_stack[offset] != _stack[stackTop] && // don't swap identical values (no-op)
590+
_stack.isValidSwapTarget(offset) &&
591+
!_state.isArgsCompatible(offset, offset) &&
592+
_state.isArgsCompatible(offset, stackTop)
593+
)
594+
{
595+
_stack.swap(offset);
596+
return {ShuffleHelperResult::Status::StackModified};
597+
}
583598
}
584599

585600
// dup up whatever is missing

test/libsolidity/semanticTests/externalContracts/deposit_contract.sol

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -185,8 +185,8 @@ contract DepositContract is IDepositContract, ERC165 {
185185
// gas legacy code: 1438800
186186
// gas legacyOptimized: 848699
187187
// gas legacyOptimized code: 878200
188-
// gas ssaCFGOptimized: 809592
189-
// gas ssaCFGOptimized code: 569200
188+
// gas ssaCFGOptimized: 809403
189+
// gas ssaCFGOptimized code: 568200
190190
// supportsInterface(bytes4): 0x0 -> 0
191191
// supportsInterface(bytes4): 0xffffffff00000000000000000000000000000000000000000000000000000000 -> false # defined to be false by ERC-165 #
192192
// supportsInterface(bytes4): 0x01ffc9a700000000000000000000000000000000000000000000000000000000 -> true # ERC-165 id #
@@ -195,28 +195,28 @@ contract DepositContract is IDepositContract, ERC165 {
195195
// gas irOptimized: 109178
196196
// gas legacy: 142741
197197
// gas legacyOptimized: 117558
198-
// gas ssaCFGOptimized: 109748
198+
// gas ssaCFGOptimized: 109652
199199
// get_deposit_count() -> 0x20, 8, 0 # TODO: check balance and logs after each deposit #
200200
// deposit(bytes,bytes,bytes,bytes32), 32 ether: 0 -> FAILURE # Empty input #
201201
// get_deposit_root() -> 0xd70a234731285c6804c2a4f56711ddb8c82c99740f207854891028af34e27e5e
202202
// gas irOptimized: 109178
203203
// gas legacy: 142741
204204
// gas legacyOptimized: 117558
205-
// gas ssaCFGOptimized: 109748
205+
// gas ssaCFGOptimized: 109652
206206
// get_deposit_count() -> 0x20, 8, 0
207207
// deposit(bytes,bytes,bytes,bytes32), 1 ether: 0x80, 0xe0, 0x120, 0xaa4a8d0b7d9077248630f1a4701ae9764e42271d7f22b7838778411857fd349e, 0x30, 0x933ad9491b62059dd065b560d256d8957a8c402cc6e8d8ee7290ae11e8f73292, 0x67a8811c397529dac52ae1342ba58c9500000000000000000000000000000000, 0x20, 0x00f50428677c60f997aadeab24aabf7fceaef491c96a52b463ae91f95611cf71, 0x60, 0xa29d01cc8c6296a8150e515b5995390ef841dc18948aa3e79be6d7c1851b4cbb, 0x5d6ff49fa70b9c782399506a22a85193151b9b691245cebafd2063012443c132, 0x4b6c36debaedefb7b2d71b0503ffdc00150aaffd42e63358238ec888901738b8 -> # txhash: 0x7085c586686d666e8bb6e9477a0f0b09565b2060a11f1c4209d3a52295033832 #
208208
// ~ emit DepositEvent(bytes,bytes,bytes,bytes,bytes): 0xa0, 0x0100, 0x0140, 0x0180, 0x0200, 0x30, 0x933ad9491b62059dd065b560d256d8957a8c402cc6e8d8ee7290ae11e8f73292, 0x67a8811c397529dac52ae1342ba58c9500000000000000000000000000000000, 0x20, 0xf50428677c60f997aadeab24aabf7fceaef491c96a52b463ae91f95611cf71, 0x08, 0xca9a3b00000000000000000000000000000000000000000000000000000000, 0x60, 0xa29d01cc8c6296a8150e515b5995390ef841dc18948aa3e79be6d7c1851b4cbb, 0x5d6ff49fa70b9c782399506a22a85193151b9b691245cebafd2063012443c132, 0x4b6c36debaedefb7b2d71b0503ffdc00150aaffd42e63358238ec888901738b8, 0x08, 0x00
209209
// get_deposit_root() -> 0x2089653123d9c721215120b6db6738ba273bbc5228ac093b1f983badcdc8a438
210210
// gas irOptimized: 109174
211211
// gas legacy: 142750
212212
// gas legacyOptimized: 117570
213-
// gas ssaCFGOptimized: 109741
213+
// gas ssaCFGOptimized: 109645
214214
// get_deposit_count() -> 0x20, 8, 0x0100000000000000000000000000000000000000000000000000000000000000
215215
// deposit(bytes,bytes,bytes,bytes32), 32 ether: 0x80, 0xe0, 0x120, 0xdbd986dc85ceb382708cf90a3500f500f0a393c5ece76963ac3ed72eccd2c301, 0x30, 0xb2ce0f79f90e7b3a113ca5783c65756f96c4b4673c2b5c1eb4efc22280259441, 0x06d601211e8866dc5b50dc48a244dd7c00000000000000000000000000000000, 0x20, 0x00344b6c73f71b11c56aba0d01b7d8ad83559f209d0a4101a515f6ad54c89771, 0x60, 0x945caaf82d18e78c033927d51f452ebcd76524497b91d7a11219cb3db6a1d369, 0x7595fc095ce489e46b2ef129591f2f6d079be4faaf345a02c5eb133c072e7c56, 0x0c6c3617eee66b4b878165c502357d49485326bc6b31bc96873f308c8f19c09d -> # txhash: 0x404d8e109822ce448e68f45216c12cb051b784d068fbe98317ab8e50c58304ac #
216216
// ~ emit DepositEvent(bytes,bytes,bytes,bytes,bytes): 0xa0, 0x0100, 0x0140, 0x0180, 0x0200, 0x30, 0xb2ce0f79f90e7b3a113ca5783c65756f96c4b4673c2b5c1eb4efc22280259441, 0x06d601211e8866dc5b50dc48a244dd7c00000000000000000000000000000000, 0x20, 0x344b6c73f71b11c56aba0d01b7d8ad83559f209d0a4101a515f6ad54c89771, 0x08, 0x40597307000000000000000000000000000000000000000000000000000000, 0x60, 0x945caaf82d18e78c033927d51f452ebcd76524497b91d7a11219cb3db6a1d369, 0x7595fc095ce489e46b2ef129591f2f6d079be4faaf345a02c5eb133c072e7c56, 0x0c6c3617eee66b4b878165c502357d49485326bc6b31bc96873f308c8f19c09d, 0x08, 0x0100000000000000000000000000000000000000000000000000000000000000
217217
// get_deposit_root() -> 0x40255975859377d912c53aa853245ebd939bdd2b33a28e084babdcc1ed8238ee
218218
// gas irOptimized: 109174
219219
// gas legacy: 142750
220220
// gas legacyOptimized: 117570
221-
// gas ssaCFGOptimized: 109741
221+
// gas ssaCFGOptimized: 109645
222222
// get_deposit_count() -> 0x20, 8, 0x0200000000000000000000000000000000000000000000000000000000000000
Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
// Grow the stack and shuffle value to the correct places. Should be doable with 3 swaps, 3 dups and 1 push
2+
initial: [v2, lit2, v3, v1]
3+
targetStackTop: [v2, lit1, v2, lit2, v2, lit1, v1, v3]
4+
// ----
5+
// | 0 1 2 3 4 5 6 7
6+
// +--------------------------------------------------------
7+
// (initial)| v2 lit2 v3 v1
8+
// SWAP2| v2 v1 v3 lit2
9+
// DUP4| v2 v1 v3 lit2 v2
10+
// PUSH lit1| v2 v1 v3 lit2 v2 lit1
11+
// DUP1| v2 v1 v3 lit2 v2 lit1 lit1
12+
// SWAP5| v2 lit1 v3 lit2 v2 lit1 v1
13+
// DUP3| v2 lit1 v3 lit2 v2 lit1 v1 v2
14+
// SWAP5| v2 lit1 v2 lit2 v2 lit1 v1 v3
15+
// +--------------------------------------------------------
16+
// (target)| v2 lit1 v2 lit2 v2 lit1 v1 v3
17+
// Status: Admissible

test/libyul/ssa/stackShuffler/satisfy_tail_requirements.stack

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -8,9 +8,9 @@ targetStackSize: 17
88
// +------------------------------------------------- +----------------------------------------------------------------------
99
// (initial)| v2 v3 v4 v5 v6 v7 v8 | v9 v10
1010
// SWAP8| v10 v3 v4 v5 v6 v7 v8 | v9 v2
11-
// PUSH lit3| v10 v3 v4 v5 v6 v7 v8 | v9 v2 lit3
12-
// SWAP2| v10 v3 v4 v5 v6 v7 v8 | lit3 v2 v9
13-
// SWAP1| v10 v3 v4 v5 v6 v7 v8 | lit3 v9 v2
11+
// SWAP1| v10 v3 v4 v5 v6 v7 v8 | v2 v9
12+
// PUSH lit3| v10 v3 v4 v5 v6 v7 v8 | v2 v9 lit3
13+
// SWAP2| v10 v3 v4 v5 v6 v7 v8 | lit3 v9 v2
1414
// DUP4| v10 v3 v4 v5 v6 v7 v8 | lit3 v9 v2 v8
1515
// SWAP1| v10 v3 v4 v5 v6 v7 v8 | lit3 v9 v8 v2
1616
// DUP6| v10 v3 v4 v5 v6 v7 v8 | lit3 v9 v8 v2 v7

test/libyul/ssa/stackShuffler/spill_to_pop_deep_junk.stack

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -31,9 +31,9 @@ targetStackTop: [v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v1
3131
// SWAP15| v1 v2 * v3 v5 v6 v7 v8 v9 v10 v11 v12 v13 v14 v15 v16 v17
3232
// SWAP13| v1 v2 * v17 v5 v6 v7 v8 v9 v10 v11 v12 v13 v14 v15 v16 v3
3333
// SWAP14| v1 v2 v3 v17 v5 v6 v7 v8 v9 v10 v11 v12 v13 v14 v15 v16 *
34-
// PUSH v4| v1 v2 v3 v17 v5 v6 v7 v8 v9 v10 v11 v12 v13 v14 v15 v16 * v4
35-
// SWAP14| v1 v2 v3 v4 v5 v6 v7 v8 v9 v10 v11 v12 v13 v14 v15 v16 * v17
36-
// SWAP1| v1 v2 v3 v4 v5 v6 v7 v8 v9 v10 v11 v12 v13 v14 v15 v16 v17 *
34+
// SWAP13| v1 v2 v3 * v5 v6 v7 v8 v9 v10 v11 v12 v13 v14 v15 v16 v17
35+
// PUSH v4| v1 v2 v3 * v5 v6 v7 v8 v9 v10 v11 v12 v13 v14 v15 v16 v17 v4
36+
// SWAP14| v1 v2 v3 v4 v5 v6 v7 v8 v9 v10 v11 v12 v13 v14 v15 v16 v17 *
3737
// PUSH v18| v1 v2 v3 v4 v5 v6 v7 v8 v9 v10 v11 v12 v13 v14 v15 v16 v17 * v18
3838
// SWAP1| v1 v2 v3 v4 v5 v6 v7 v8 v9 v10 v11 v12 v13 v14 v15 v16 v17 v18 *
3939
// PUSH v19| v1 v2 v3 v4 v5 v6 v7 v8 v9 v10 v11 v12 v13 v14 v15 v16 v17 v18 * v19

test/libyul/ssa/stackShuffler/spilled_to_pop_deep_junk.stack

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -30,11 +30,11 @@ targetStackTop: [v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v1
3030
// POP| * v18 v19 v3 v5 v6 v7 v8 v9 v10 v11 v12 v13 v14 v15 v16 v17
3131
// SWAP13| * v18 v19 v17 v5 v6 v7 v8 v9 v10 v11 v12 v13 v14 v15 v16 v3
3232
// SWAP14| * v18 v3 v17 v5 v6 v7 v8 v9 v10 v11 v12 v13 v14 v15 v16 v19
33-
// PUSH v1| * v18 v3 v17 v5 v6 v7 v8 v9 v10 v11 v12 v13 v14 v15 v16 v19 v1
34-
// POP| * v18 v3 v17 v5 v6 v7 v8 v9 v10 v11 v12 v13 v14 v15 v16 v19
35-
// PUSH v1| * v18 v3 v17 v5 v6 v7 v8 v9 v10 v11 v12 v13 v14 v15 v16 v19 v1
36-
// POP| * v18 v3 v17 v5 v6 v7 v8 v9 v10 v11 v12 v13 v14 v15 v16 v19
37-
// PUSH v1| * v18 v3 v17 v5 v6 v7 v8 v9 v10 v11 v12 v13 v14 v15 v16 v19 v1
33+
// SWAP13| * v18 v3 v19 v5 v6 v7 v8 v9 v10 v11 v12 v13 v14 v15 v16 v17
34+
// PUSH v1| * v18 v3 v19 v5 v6 v7 v8 v9 v10 v11 v12 v13 v14 v15 v16 v17 v1
35+
// POP| * v18 v3 v19 v5 v6 v7 v8 v9 v10 v11 v12 v13 v14 v15 v16 v17
36+
// PUSH v1| * v18 v3 v19 v5 v6 v7 v8 v9 v10 v11 v12 v13 v14 v15 v16 v17 v1
37+
// POP| * v18 v3 v19 v5 v6 v7 v8 v9 v10 v11 v12 v13 v14 v15 v16 v17
3838
// ...|
3939
// +-------------------------------------------------------------------------------------------------------------------------------------------- +-------
4040
// (target)| v1 v2 v3 v4 v5 v6 v7 v8 v9 v10 v11 v12 v13 v14 v15 v16 v17 v18 v19 v20 |

0 commit comments

Comments
 (0)