1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859 |
- //===--- BlockReadableOrder.h - Visit blocks in human readable order ------===//
- //
- // The LLVM Compiler Infrastructure
- //
- // This file is distributed under the University of Illinois Open Source
- // License. See LICENSE.TXT for details.
- //
- //===----------------------------------------------------------------------===//
- //
- // The SPIR-V spec requires code blocks to appear in an order satisfying the
- // dominator-tree direction (ie, dominator before the dominated). This is,
- // actually, easy to achieve: any pre-order CFG traversal algorithm will do it.
- // Because such algorithms visit a block only after traversing some path to it
- // from the root, they necessarily visit the block's immediate dominator first.
- //
- // But not every graph-traversal algorithm outputs blocks in an order that
- // appears logical to human readers. The problem is that unrelated branches may
- // be interspersed with each other, and merge blocks may come before some of the
- // branches being merged.
- //
- // A good, human-readable order of blocks may be achieved by performing
- // depth-first search but delaying continue and merge nodes until after all
- // their branches have been visited. This is implemented below by the
- // BlockReadableOrderVisitor.
- //
- //===----------------------------------------------------------------------===//
- #ifndef LLVM_CLANG_LIB_SPIRV_BLOCKREADABLEORDER_H
- #define LLVM_CLANG_LIB_SPIRV_BLOCKREADABLEORDER_H
- #include "clang/SPIRV/Structure.h"
- #include "llvm/ADT/DenseSet.h"
- namespace clang {
- namespace spirv {
- /// \brief A basic block visitor traversing basic blocks in a human readable
- /// order and calling a pre-set callback on each basic block.
- class BlockReadableOrderVisitor {
- public:
- explicit BlockReadableOrderVisitor(std::function<void(BasicBlock *)> cb)
- : callback(cb) {}
- /// \brief Recursively visits all blocks reachable from the given starting
- /// basic block in a depth-first manner and calls the callback passed-in
- /// during construction on each basic block.
- void visit(BasicBlock *block);
- private:
- std::function<void(BasicBlock *)> callback;
- llvm::DenseSet<BasicBlock *> doneBlocks; ///< Blocks already visited
- llvm::DenseSet<BasicBlock *> todoBlocks; ///< Blocks to be visited later
- };
- } // end namespace spirv
- } // end namespace clang
- #endif
|