diff options
author | Derek Schuff <dschuff@chromium.org> | 2017-07-21 08:46:23 -0700 |
---|---|---|
committer | GitHub <noreply@github.com> | 2017-07-21 08:46:23 -0700 |
commit | ab8dbae1d1a27e4de24fd9ee09d45785a414922d (patch) | |
tree | ac337117d973464a16d597fc7a5c29550a93a489 /src/passes/DeadCodeElimination.cpp | |
parent | da680fdbcb7eaad1c692369c7c826fc02b00c877 (diff) | |
download | binaryen-ab8dbae1d1a27e4de24fd9ee09d45785a414922d.tar.gz binaryen-ab8dbae1d1a27e4de24fd9ee09d45785a414922d.tar.bz2 binaryen-ab8dbae1d1a27e4de24fd9ee09d45785a414922d.zip |
Optimizer support for atomic instructions (#1094)
* Teach EffectAnalyzer not to reorder atomics wrt other memory operations.
* Teach EffectAnalyzer not to reorder host operations with memory operations
* Teach various passes about the operands of AtomicRMW and AtomicCmpxchg
* Factor out some functions in DeadCodeElimination and MergeBlocks
Diffstat (limited to 'src/passes/DeadCodeElimination.cpp')
-rw-r--r-- | src/passes/DeadCodeElimination.cpp | 98 |
1 files changed, 38 insertions, 60 deletions
diff --git a/src/passes/DeadCodeElimination.cpp b/src/passes/DeadCodeElimination.cpp index 321bc0f9a..5017569aa 100644 --- a/src/passes/DeadCodeElimination.cpp +++ b/src/passes/DeadCodeElimination.cpp @@ -28,6 +28,7 @@ // have no side effects. // +#include <vector> #include <wasm.h> #include <pass.h> #include <wasm-builder.h> @@ -321,84 +322,62 @@ struct DeadCodeElimination : public WalkerPass<PostWalker<DeadCodeElimination>> } } - void visitSetLocal(SetLocal* curr) { - if (isUnreachable(curr->value)) { - replaceCurrent(curr->value); + // Append the reachable operands of the current node to a block, and replace + // it with the block + void blockifyReachableOperands(std::vector<Expression*>&& list, WasmType type) { + for (size_t i = 0; i < list.size(); ++i) { + auto* elem = list[i]; + if (isUnreachable(elem)) { + auto* replacement = elem; + if (i > 0) { + auto* block = getModule()->allocator.alloc<Block>(); + for (size_t j = 0; j < i; ++j) { + block->list.push_back(drop(list[j])); + } + block->list.push_back(list[i]); + block->finalize(type); + replacement = block; + } + replaceCurrent(replacement); + return; + } } } + void visitSetLocal(SetLocal* curr) { + blockifyReachableOperands({ curr->value }, curr->type); + } + void visitLoad(Load* curr) { - if (isUnreachable(curr->ptr)) { - replaceCurrent(curr->ptr); - } + blockifyReachableOperands({ curr->ptr}, curr->type); } void visitStore(Store* curr) { - if (isUnreachable(curr->ptr)) { - replaceCurrent(curr->ptr); - return; - } - if (isUnreachable(curr->value)) { - auto* block = getModule()->allocator.alloc<Block>(); - block->list.resize(2); - block->list[0] = drop(curr->ptr); - block->list[1] = curr->value; - block->finalize(curr->type); - replaceCurrent(block); - } + blockifyReachableOperands({ curr->ptr, curr->value }, curr->type); + } + + void visitAtomicRMW(AtomicRMW* curr) { + blockifyReachableOperands({ curr->ptr, curr->value }, curr->type); + } + + void visitAtomicCmpxchg(AtomicCmpxchg* curr) { + blockifyReachableOperands({ curr->ptr, curr->expected, curr->replacement }, curr->type); } void visitUnary(Unary* curr) { - if (isUnreachable(curr->value)) { - replaceCurrent(curr->value); - } + blockifyReachableOperands({ curr->value }, curr->type); } void visitBinary(Binary* curr) { - if (isUnreachable(curr->left)) { - replaceCurrent(curr->left); - return; - } - if (isUnreachable(curr->right)) { - auto* block = getModule()->allocator.alloc<Block>(); - block->list.resize(2); - block->list[0] = drop(curr->left); - block->list[1] = curr->right; - block->finalize(curr->type); - replaceCurrent(block); - } + blockifyReachableOperands({ curr->left, curr->right}, curr->type); } void visitSelect(Select* curr) { - if (isUnreachable(curr->ifTrue)) { - replaceCurrent(curr->ifTrue); - return; - } - if (isUnreachable(curr->ifFalse)) { - auto* block = getModule()->allocator.alloc<Block>(); - block->list.resize(2); - block->list[0] = drop(curr->ifTrue); - block->list[1] = curr->ifFalse; - block->finalize(curr->type); - replaceCurrent(block); - return; - } - if (isUnreachable(curr->condition)) { - auto* block = getModule()->allocator.alloc<Block>(); - block->list.resize(3); - block->list[0] = drop(curr->ifTrue); - block->list[1] = drop(curr->ifFalse); - block->list[2] = curr->condition; - block->finalize(curr->type); - replaceCurrent(block); - return; - } + blockifyReachableOperands({ curr->ifTrue, curr->ifFalse, curr->condition}, curr->type); } void visitDrop(Drop* curr) { - if (isUnreachable(curr->value)) { - replaceCurrent(curr->value); - } + blockifyReachableOperands({ curr->value }, curr->type); } void visitHost(Host* curr) { @@ -415,4 +394,3 @@ Pass *createDeadCodeEliminationPass() { } } // namespace wasm - |