Home | History | Annotate | Line # | Download | only in Interp
      1 //===--- Function.h - Bytecode function for the VM --------------*- C++ -*-===//
      2 //
      3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
      4 // See https://llvm.org/LICENSE.txt for license information.
      5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
      6 //
      7 //===----------------------------------------------------------------------===//
      8 //
      9 // Defines the Function class which holds all bytecode function-specific data.
     10 //
     11 // The scope class which describes local variables is also defined here.
     12 //
     13 //===----------------------------------------------------------------------===//
     14 
     15 #ifndef LLVM_CLANG_AST_INTERP_FUNCTION_H
     16 #define LLVM_CLANG_AST_INTERP_FUNCTION_H
     17 
     18 #include "Pointer.h"
     19 #include "Source.h"
     20 #include "clang/AST/Decl.h"
     21 #include "llvm/Support/raw_ostream.h"
     22 
     23 namespace clang {
     24 namespace interp {
     25 class Program;
     26 class ByteCodeEmitter;
     27 enum PrimType : uint32_t;
     28 
     29 /// Describes a scope block.
     30 ///
     31 /// The block gathers all the descriptors of the locals defined in this block.
     32 class Scope {
     33 public:
     34   /// Information about a local's storage.
     35   struct Local {
     36     /// Offset of the local in frame.
     37     unsigned Offset;
     38     /// Descriptor of the local.
     39     Descriptor *Desc;
     40   };
     41 
     42   using LocalVectorTy = llvm::SmallVector<Local, 8>;
     43 
     44   Scope(LocalVectorTy &&Descriptors) : Descriptors(std::move(Descriptors)) {}
     45 
     46   llvm::iterator_range<LocalVectorTy::iterator> locals() {
     47     return llvm::make_range(Descriptors.begin(), Descriptors.end());
     48   }
     49 
     50 private:
     51   /// Object descriptors in this block.
     52   LocalVectorTy Descriptors;
     53 };
     54 
     55 /// Bytecode function.
     56 ///
     57 /// Contains links to the bytecode of the function, as well as metadata
     58 /// describing all arguments and stack-local variables.
     59 class Function {
     60 public:
     61   using ParamDescriptor = std::pair<PrimType, Descriptor *>;
     62 
     63   /// Returns the size of the function's local stack.
     64   unsigned getFrameSize() const { return FrameSize; }
     65   /// Returns the size of the argument stackx
     66   unsigned getArgSize() const { return ArgSize; }
     67 
     68   /// Returns a pointer to the start of the code.
     69   CodePtr getCodeBegin() const;
     70   /// Returns a pointer to the end of the code.
     71   CodePtr getCodeEnd() const;
     72 
     73   /// Returns the original FunctionDecl.
     74   const FunctionDecl *getDecl() const { return F; }
     75 
     76   /// Returns the lcoation.
     77   SourceLocation getLoc() const { return Loc; }
     78 
     79   /// Returns a parameter descriptor.
     80   ParamDescriptor getParamDescriptor(unsigned Offset) const;
     81 
     82   /// Checks if the first argument is a RVO pointer.
     83   bool hasRVO() const { return ParamTypes.size() != Params.size(); }
     84 
     85   /// Range over the scope blocks.
     86   llvm::iterator_range<llvm::SmallVector<Scope, 2>::iterator> scopes() {
     87     return llvm::make_range(Scopes.begin(), Scopes.end());
     88   }
     89 
     90   /// Range over argument types.
     91   using arg_reverse_iterator = SmallVectorImpl<PrimType>::reverse_iterator;
     92   llvm::iterator_range<arg_reverse_iterator> args_reverse() {
     93     return llvm::make_range(ParamTypes.rbegin(), ParamTypes.rend());
     94   }
     95 
     96   /// Returns a specific scope.
     97   Scope &getScope(unsigned Idx) { return Scopes[Idx]; }
     98 
     99   /// Returns the source information at a given PC.
    100   SourceInfo getSource(CodePtr PC) const;
    101 
    102   /// Checks if the function is valid to call in constexpr.
    103   bool isConstexpr() const { return IsValid; }
    104 
    105   /// Checks if the function is virtual.
    106   bool isVirtual() const;
    107 
    108   /// Checks if the function is a constructor.
    109   bool isConstructor() const { return isa<CXXConstructorDecl>(F); }
    110 
    111 private:
    112   /// Construct a function representing an actual function.
    113   Function(Program &P, const FunctionDecl *F, unsigned ArgSize,
    114            llvm::SmallVector<PrimType, 8> &&ParamTypes,
    115            llvm::DenseMap<unsigned, ParamDescriptor> &&Params);
    116 
    117   /// Sets the code of a function.
    118   void setCode(unsigned NewFrameSize, std::vector<char> &&NewCode, SourceMap &&NewSrcMap,
    119                llvm::SmallVector<Scope, 2> &&NewScopes) {
    120     FrameSize = NewFrameSize;
    121     Code = std::move(NewCode);
    122     SrcMap = std::move(NewSrcMap);
    123     Scopes = std::move(NewScopes);
    124     IsValid = true;
    125   }
    126 
    127 private:
    128   friend class Program;
    129   friend class ByteCodeEmitter;
    130 
    131   /// Program reference.
    132   Program &P;
    133   /// Location of the executed code.
    134   SourceLocation Loc;
    135   /// Declaration this function was compiled from.
    136   const FunctionDecl *F;
    137   /// Local area size: storage + metadata.
    138   unsigned FrameSize;
    139   /// Size of the argument stack.
    140   unsigned ArgSize;
    141   /// Program code.
    142   std::vector<char> Code;
    143   /// Opcode-to-expression mapping.
    144   SourceMap SrcMap;
    145   /// List of block descriptors.
    146   llvm::SmallVector<Scope, 2> Scopes;
    147   /// List of argument types.
    148   llvm::SmallVector<PrimType, 8> ParamTypes;
    149   /// Map from byte offset to parameter descriptor.
    150   llvm::DenseMap<unsigned, ParamDescriptor> Params;
    151   /// Flag to indicate if the function is valid.
    152   bool IsValid = false;
    153 
    154 public:
    155   /// Dumps the disassembled bytecode to \c llvm::errs().
    156   void dump() const;
    157   void dump(llvm::raw_ostream &OS) const;
    158 };
    159 
    160 } // namespace interp
    161 } // namespace clang
    162 
    163 #endif
    164