//===-- PostfixExpression.h -------------------------------------*- C++ -*-===// // // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. // See https://llvm.org/LICENSE.txt for license information. // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception // //===----------------------------------------------------------------------===// // // This file implements support for postfix expressions found in several symbol // file formats, and their conversion to DWARF. // //===----------------------------------------------------------------------===// #ifndef LLDB_SYMBOL_POSTFIXEXPRESSION_H #define LLDB_SYMBOL_POSTFIXEXPRESSION_H #include "llvm/ADT/StringRef.h" #include "llvm/Support/Allocator.h" #include "llvm/Support/Casting.h" #include <vector> namespace lldb_private { class Stream; namespace postfix { /// The base class for all nodes in the parsed postfix tree. class Node { … }; /// A node representing a binary expression. class BinaryOpNode : public Node { … }; /// A node representing the canonical frame address. class InitialValueNode: public Node { … }; /// A node representing an integer literal. class IntegerNode : public Node { … }; /// A node representing the value of a register with the given register number. /// The register kind (RegisterKind enum) used for the specifying the register /// number is implicit and assumed to be the same for all Register nodes in a /// given tree. class RegisterNode : public Node { … }; /// A node representing a symbolic reference to a named entity. This may be a /// register, which hasn't yet been resolved to a RegisterNode. class SymbolNode : public Node { … }; /// A node representing a unary operation. class UnaryOpNode : public Node { … }; /// A template class implementing a visitor pattern, but with a couple of /// twists: /// - It uses type switch instead of virtual double dispatch. This allows the // node classes to be vtable-free and trivially destructible. /// - The Visit functions get an extra Node *& parameter, which refers to the /// child pointer of the parent of the node we are currently visiting. This /// allows mutating algorithms, which replace the currently visited node with /// a different one. /// - The class is templatized on the return type of the Visit functions, which /// means it's possible to return values from them. template <typename ResultT = void> class Visitor { … }; /// A utility function for "resolving" SymbolNodes. It traverses a tree and /// calls the callback function for all SymbolNodes it encountered. The /// replacement function should return the node it wished to replace the current /// SymbolNode with (this can also be the original node), or nullptr in case of /// an error. The nodes returned by the callback are inspected and replaced /// recursively, *except* for the case when the function returns the exact same /// node as the input one. It returns true if all SymbolNodes were replaced /// successfully. bool ResolveSymbols(Node *&node, llvm::function_ref<Node *(SymbolNode &symbol)> replacer); template <typename T, typename... Args> inline T *MakeNode(llvm::BumpPtrAllocator &alloc, Args &&... args) { … } /// Parse the given postfix expression. The parsed nodes are placed into the /// provided allocator. Node *ParseOneExpression(llvm::StringRef expr, llvm::BumpPtrAllocator &alloc); std::vector<std::pair<llvm::StringRef, Node *>> ParseFPOProgram(llvm::StringRef prog, llvm::BumpPtrAllocator &alloc); /// Serialize the given expression tree as DWARF. The result is written into the /// given stream. The AST should not contain any SymbolNodes. If the expression /// contains InitialValueNodes, the generated expression will assume that their /// value will be provided as the top value of the initial evaluation stack (as /// is the case with the CFA value in register eh_unwind rules). void ToDWARF(Node &node, Stream &stream); } // namespace postfix } // namespace lldb_private #endif // LLDB_SYMBOL_POSTFIXEXPRESSION_H