//===-- go-llvm.h - LLVM implementation of gofrontend 'Backend' class -----===//
//
// Copyright 2018 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
//
//===----------------------------------------------------------------------===//
//
// Defines Llvm_backend and related classes
//
//===----------------------------------------------------------------------===//

#ifndef LLVMGOFRONTEND_GO_LLVM_H
#define LLVMGOFRONTEND_GO_LLVM_H

// Currently these need to be included before backend.h
#include "go-llvm-linemap.h"
#include "go-location.h"

// Definitions of Btype, Bexpression, and related B* classes.
#include "go-llvm-btype.h"
#include "go-llvm-bexpression.h"
#include "go-llvm-bstatement.h"
#include "go-llvm-bfunction.h"
#include "go-llvm-bvariable.h"

// Other helper classes
#include "go-llvm-containertypes.h"
#include "go-llvm-tree-integrity.h"
#include "go-llvm-typemanager.h"

#include "namegen.h"

#include "backend.h"

#include <unordered_map>
#include <unordered_set>

namespace llvm {
class Argument;
class ArrayType;
class BasicBlock;
class CallInst;
class Constant;
class ConstantFolder;
class DataLayout;
class DICompileUnit;
class DIFile;
class DIScope;
class DIBuilder;
class Function;
class Instruction;
class LLVMContext;
class Module;
class StructType;
class TargetLibraryInfo;
class Type;
class Value;
class raw_ostream;
}

class BuiltinEntry;
class BuiltinTable;
class BlockLIRBuilder;
struct GenCallState;

#include "llvm/IR/GlobalValue.h"
#include "llvm/ADT/Triple.h"

//
// LLVM-specific implementation of the Backend class; the code in
// gofrontend instantiates an object of this class and then invokes
// the various methods to convert its IR into LLVM IR. Nearly all of
// the interesting methods below are virtual.
//

class Llvm_backend : public Backend, public TypeManager, public NameGen {
public:
  Llvm_backend(llvm::LLVMContext &context,
               llvm::Module *module,
               Llvm_linemap *linemap,
               unsigned addrspace,
               llvm::Triple triple,
               /* Temporarily set the parameter as optional to workaround the unit tests. */
               llvm::CallingConv::ID cconv=llvm::CallingConv::X86_64_SysV);
  ~Llvm_backend();

  // Types.

  Btype *error_type();

  Btype *void_type();

  Btype *bool_type();

  Btype *integer_type(bool, int);

  Btype *float_type(int);

  Btype *complex_type(int);

  Btype *pointer_type(Btype *);

  Btype *function_type(const Btyped_identifier &,
                       const std::vector<Btyped_identifier> &,
                       const std::vector<Btyped_identifier> &, Btype *,
                       const Location);

  Btype *struct_type(const std::vector<Btyped_identifier> &);

  Btype *array_type(Btype *, Bexpression *);

  Btype *placeholder_pointer_type(const std::string &, Location, bool);

  bool set_placeholder_pointer_type(Btype *, Btype *);

  bool set_placeholder_function_type(Btype *, Btype *);

  Btype *placeholder_struct_type(const std::string &, Location);

  bool set_placeholder_struct_type(Btype *placeholder,
                                   const std::vector<Btyped_identifier> &);

  Btype *placeholder_array_type(const std::string &, Location);

  bool set_placeholder_array_type(Btype *, Btype *, Bexpression *);

  Btype *named_type(const std::string &, Btype *, Location);

  Btype *circular_pointer_type(Btype *, bool);

  bool is_circular_pointer_type(Btype *);

  int64_t type_size(Btype *);

  int64_t type_alignment(Btype *);

  int64_t type_field_alignment(Btype *);

  int64_t type_field_offset(Btype *, size_t index);

  // Expressions.

  Bexpression *zero_expression(Btype *);

  Bexpression *error_expression();

  Bexpression *nil_pointer_expression();

  Bexpression *var_expression(Bvariable *var, Location);

  Bexpression *indirect_expression(Btype *, Bexpression *expr, bool known_valid,
                                   Location);

  Bexpression *named_constant_expression(Btype *btype, const std::string &name,
                                         Bexpression *val, Location);

  Bexpression *integer_constant_expression(Btype *btype, mpz_t val);

  Bexpression *float_constant_expression(Btype *btype, mpfr_t val);

  Bexpression *complex_constant_expression(Btype *btype, mpc_t val);

  Bexpression *string_constant_expression(const std::string &val);

  Bexpression *boolean_constant_expression(bool val);

  Bexpression *real_part_expression(Bexpression *bcomplex, Location);

  Bexpression *imag_part_expression(Bexpression *bcomplex, Location);

  Bexpression *complex_expression(Bexpression *breal, Bexpression *bimag,
                                  Location);

  Bexpression *convert_expression(Btype *type, Bexpression *expr, Location);

  Bexpression *function_code_expression(Bfunction *, Location);

  Bexpression *address_expression(Bexpression *, Location);

  Bexpression *struct_field_expression(Bexpression *, size_t, Location);

  Bexpression *compound_expression(Bstatement *, Bexpression *, Location);

  Bexpression *conditional_expression(Bfunction *,
                                      Btype *, Bexpression *, Bexpression *,
                                      Bexpression *, Location);

  Bexpression *unary_expression(Operator, Bexpression *, Location);

  Bexpression *binary_expression(Operator, Bexpression *, Bexpression *,
                                 Location);

  Bexpression *
  constructor_expression(Btype *, const std::vector<Bexpression *> &, Location);

  Bexpression *array_constructor_expression(Btype *,
                                            const std::vector<unsigned long> &,
                                            const std::vector<Bexpression *> &,
                                            Location);

  Bexpression *pointer_offset_expression(Bexpression *base, Bexpression *offset,
                                         Location);

  Bexpression *array_index_expression(Bexpression *array, Bexpression *index,
                                      Location);

  Bexpression *call_expression(Bfunction *caller,
                               Bexpression *fn,
                               const std::vector<Bexpression *> &args,
                               Bexpression *static_chain,
                               Location);
  // Statements.

  Bstatement *error_statement();

  Bstatement *expression_statement(Bfunction *, Bexpression *);

  Bstatement *init_statement(Bfunction*, Bvariable *var, Bexpression *init);

  Bstatement *assignment_statement(Bfunction*,
                                   Bexpression *lhs, Bexpression *rhs,
                                   Location);

  Bstatement *return_statement(Bfunction *, const std::vector<Bexpression *> &,
                               Location);

  Bstatement *if_statement(Bfunction *func,
                           Bexpression *condition, Bblock *then_block,
                           Bblock *else_block, Location);

  Bstatement *
  switch_statement(Bfunction *function, Bexpression *value,
                   const std::vector<std::vector<Bexpression *>> &cases,
                   const std::vector<Bstatement *> &statements, Location);

  Bstatement *compound_statement(Bstatement *, Bstatement *);

  Bstatement *statement_list(const std::vector<Bstatement *> &);

  Bstatement *exception_handler_statement(Bstatement *bstat,
                                          Bstatement *except_stmt,
                                          Bstatement *finally_stmt, Location);

  // Blocks.

  Bblock *block(Bfunction *, Bblock *, const std::vector<Bvariable *> &,
                Location, Location);

  void block_add_statements(Bblock *, const std::vector<Bstatement *> &);

  Bstatement *block_statement(Bblock *);

  // Variables.

  Bvariable *error_variable();

  Bvariable *global_variable(const std::string &var_name,
                             const std::string &asm_name, Btype *btype,
                             unsigned int flags, Location location);

  void global_variable_set_init(Bvariable *, Bexpression *);

  Bvariable *local_variable(Bfunction *, const std::string &, Btype *,
                            Bvariable *, unsigned int flags, Location);

  Bvariable *parameter_variable(Bfunction *, const std::string &, Btype *,
                                unsigned int flags, Location);

  Bvariable *static_chain_variable(Bfunction *, const std::string &, Btype *,
                                   unsigned int flags, Location);

  Bvariable *temporary_variable(Bfunction *, Bblock *, Btype *, Bexpression *,
                                unsigned int flags, Location, Bstatement **);

  Bvariable *implicit_variable(const std::string &, const std::string &,
                               Btype *, unsigned int flags, int64_t);

  void implicit_variable_set_init(Bvariable *, const std::string &, Btype *,
                                  unsigned int flags, Bexpression *);

  Bvariable *implicit_variable_reference(const std::string &,
                                         const std::string &, Btype *);

  Bvariable *immutable_struct(const std::string &, const std::string &,
                              unsigned int flags, Btype *, Location);

  void immutable_struct_set_init(Bvariable *, const std::string &,
                                 unsigned int flags, Btype *, Location,
                                 Bexpression *);

  Bvariable *immutable_struct_reference(const std::string &,
                                        const std::string &, Btype *, Location);

  // Labels.

  Blabel *label(Bfunction *, const std::string &name, Location);

  Bstatement *label_definition_statement(Blabel *);

  Bstatement *goto_statement(Blabel *, Location);

  Bexpression *label_address(Blabel *, Location);

  // Functions.

  Bfunction *error_function();

  Bfunction *function(Btype *fntype, const std::string &name,
                      const std::string &asm_name, unsigned flags,
                      Location);

  Bstatement *function_defer_statement(Bfunction *function,
                                       Bexpression *undefer, Bexpression *defer,
                                       Location);

  bool function_set_parameters(Bfunction *function,
                               const std::vector<Bvariable *> &);

  bool function_set_body(Bfunction *function, Bstatement *code_stmt);

  Bfunction *lookup_builtin(const std::string &);

  void write_global_definitions(const std::vector<Btype *> &,
                                const std::vector<Bexpression *> &,
                                const std::vector<Bfunction *> &,
                                const std::vector<Bvariable *> &);

  void write_export_data(const char *bytes, unsigned int size);

  Llvm_linemap *linemap() const { return linemap_; }

  // Module, datalayout and triple
  llvm::Module &module() { return *module_; }
  const llvm::DataLayout &datalayout() { return *datalayout_; }
  const llvm::Triple &triple() const { return triple_; }

  // Type manager functionality
  TypeManager *typeManager() const;

  // DI build helper. Will be NULL if debug meta-data generation disabled.
  DIBuildHelper *dibuildhelper() { return dibuildhelper_.get(); }

  // Support for -fdebug-prefix=
  void addDebugPrefix(std::pair<llvm::StringRef, llvm::StringRef> prefix);

  // Bnode builder
  BnodeBuilder &nodeBuilder() { return nbuilder_; }

  // Finalize export data for the module. Exposed for unit testing.
  void finalizeExportData();

  // Run the module verifier.
  void verifyModule();

  // Dump LLVM IR for module
  void dumpModule();

  // Dump expression or stmt with line information. For debugging purposes.
  void dumpExpr(Bexpression *);
  void dumpStmt(Bstatement *);
  void dumpVar(Bvariable *);

  // Exposed for unit testing

  // Helpers to check tree integrity. Checks to make sure that we
  // don't have instructions that are parented by more than one
  // Bexpression or Bstatement, or Bexpressions parented by more than
  // one expr/stmt. Returns <TRUE,""> if tree is ok, otherwise returns
  // <FALSE,descriptive_message>.
  std::pair<bool, std::string>
  checkTreeIntegrity(Bnode *n, TreeIntegCtl control);

  // Similar to the above, but prints message to std::cerr and aborts if fail
  void enforceTreeIntegrity(Bnode *n);

  // Disable tree integrity checking. This is mainly
  // so that we can unit test the integrity checker.
  void disableIntegrityChecks();

  // Disable debug meta-data generation. Should be used only during
  // unit testing, where we're manufacturing IR that might not verify
  // if meta-data is created.
  void disableDebugMetaDataGeneration() { createDebugMetaData_ = false; }

  // Return true if this is a module-scope value such as a constant
  bool moduleScopeValue(llvm::Value *val, Btype *btype) const;

  // For debugging
  void setTraceLevel(unsigned level);
  unsigned traceLevel() const { return traceLevel_; }

  // Disable inlining if set to true.
  void setNoInline(bool b) { noInline_ = b; }

  // Disable frame pointer elimination if set to true.
  void setNoFpElim(bool b) { noFpElim_ = b; }

  // Enable/disable the use of split stacks.
  void setUseSplitStack(bool b) { useSplitStack_ = b; }

  // Target CPU and features
  void setTargetCpuAttr(const std::string &cpu);
  void setTargetFeaturesAttr(const std::string &attrs);

  // Set GC strategy
  void setGCStrategy(std::string s) { gcStrategy_ = s; }

  // Whether we are compiling the runtime package
  void setCompilingRuntime() { compilingRuntime_ = true; }

  // Personality function
  llvm::Function *personalityFunction();

  // Dummy personality function
  llvm::Function *dummyPersonalityFunction();

  // Inform bridge that we may be using AutoFDO.
  void setEnableAutoFDO() { autoFDO_ = true; }

 private:
  Bexpression *errorExpression() const { return errorExpression_; }
  Bstatement *errorStatement() const { return errorStatement_; }

  // create a Bfunction for an intrinsic function with specified name
  Bfunction *createIntrinsicFcn(const std::string &name,
                                llvm::Function *fcn);

  // create a Bfunction for a predefined builtin function. Used for
  // libcall builtins and inlined builtins.
  Bfunction *createBuiltinFcn(BuiltinEntry *be);

  // Certain Bexpressions we want to cache (constants for example,
  // or lvalue references to global variables). This helper looks up
  // the specified expr in a table keyed by <llvm::Value,Btype>. If
  // the lookup succeeds, the cached value is returned, otherwise the
  // specified Bexpression is installed in the table and returned.
  Bexpression *makeGlobalExpression(Bexpression *expr,
                                   llvm::Value *val,
                                   Btype *btype,
                                   Location location);

  enum ModVarConstant { MV_Constant, MV_NonConstant };
  enum ModVarSec { MV_UniqueSection, MV_DefaultSection };
  enum ModVarComdat { MV_InComdat, MV_NotInComdat };
  enum ModVarExtInit { MV_ExternallyInitialized, MV_NotExternallyInitialized };
  enum ModVarGenDebug { MV_GenDebug, MV_SkipDebug };

  // Make a module-scope variable (static, global, or external).
  Bvariable *makeModuleVar(Btype *btype,
                           const std::string &name,
                           const std::string &asm_name,
                           Location location,
                           ModVarConstant constant,
                           ModVarSec inUniqueSection,
                           ModVarComdat inComdat,
                           ModVarExtInit isExtInit,
                           ModVarGenDebug genDebug,
                           llvm::GlobalValue::LinkageTypes linkage,
                           llvm::Constant *initializer,
                           unsigned alignmentInBytes = 0);

  // Helper for creating a constant-valued array/struct expression.
  Bexpression *makeConstCompositeExpr(Btype *btype,
                                      llvm::Type *llct,
                                      unsigned numElements,
                                      const std::vector<unsigned long> *indexes,
                                      const std::vector<Bexpression *> &vals,
                                      Location location);

  // Helper for creating a non-constant-valued array or struct expression.
  Bexpression *makeDelayedCompositeExpr(Btype *btype,
                                        llvm::Type *llct,
                                        unsigned numElements,
                                        const std::vector<unsigned long> *idxs,
                                        const std::vector<Bexpression *> &vals,
                                        Location location);

  // Helper for creating a complex binary expression.
  Bexpression *makeComplexBinaryExpr(Operator op,
                                     Bexpression *left,
                                     Bexpression *right,
                                     Location location);

  // Helper for creating a complex conversion expression.
  Bexpression *makeComplexConvertExpr(Btype *type, Bexpression *expr,
                                      Location location);

  // Field GEP helper
  llvm::Value *makeFieldGEP(unsigned fieldIndex,
                            llvm::Value *sptr);

  // Array indexing GEP helper
  llvm::Value *makeArrayIndexGEP(llvm::ArrayType *at,
                                 llvm::Value *idx,
                                 llvm::Value *sptr);

  // Pointer indexing GEP helper
  llvm::Value *makePointerOffsetGEP(llvm::PointerType *pt,
                                    llvm::Value *idx,
                                    llvm::Value *sptr);

  // Assignment helper
  Bstatement *makeAssignment(Bfunction *function, llvm::Value *lvalue,
                             Bexpression *lhs, Bexpression *rhs, Location);

  // Helper to make init statement
  Bstatement *makeInitStatement(Bfunction *bfunction, Bvariable *var,
                              Bexpression *init);

  // Helper to make a temporary variable holding the value of an
  // expression
  std::pair<Bvariable*, Bstatement*> makeTempVar(Bexpression *expr,
                                                 Location location);

  // Helper to set up entry block for function
  llvm::BasicBlock *genEntryBlock(Bfunction *bfunction);

  // Helper to fix up epilog block for function (add return if needed)
  void fixupEpilogBlock(Bfunction *bfunction, llvm::BasicBlock *epilog);

  // Load-generation helper.
  // If resultTyp is null, this load is for resolving a pending
  // var expression, and the result type will be the same type
  // as space.
  Bexpression *genLoad(Bexpression *space,
                       Btype *resultTyp,
                       Location loc,
                       const std::string &tag);

  // Store generation helper. Creates store or memcpy call.
  Bexpression *genStore(Bfunction *func,
                        Bexpression *srcExpr,
                        Bexpression *dstExpr,
                        Location location);

  // Lower-level version of the above
  llvm::Value *genStore(BlockLIRBuilder *builder,
                        Btype *srcType,
                        bool srcConstant,
                        llvm::Type *dstType,
                        llvm::Value *srcValue,
                        llvm::Value *dstLoc);

  // Returns TRUE if loads/stores to/from the specified type should be
  // carried out via memcpy as opposed to concrete load/store
  // instructions.
  bool useCopyForLoadStore(Btype *typ) {
    assert(typ);
    assert(!typ->isPlaceholder());
    if (! typ->type()->isAggregateType())
      return false;
    //if (typeSize(typ) <= compositeSizeThreshold_)
    //  return false;
    return true;
  }

  // Similar to above but operates on LLVM type.
  bool useCopyForLoadStore(llvm::Type *typ) {
    assert(typ);
    if (! typ->isAggregateType())
      return false;
    //if (llvmTypeAllocSize(typ) <= compositeSizeThreshold_)
    //  return false;
    return true;
  }

  // Return context disposition based on expression type.
  // Composite values need to be referred to by address,
  // whereas non-composite values can be used directly.
  Varexpr_context varContextDisp(Bexpression *varexp);

  // Materialize a composite constant into a variable
  Bvariable *genVarForConstant(llvm::Constant *conval, Btype *type);

  // Convert a constant to another type. Returns nullptr if the conversion is
  // not allowed. Intended primarily for aggregate constants, where the two
  // types are structurally identical but may differ due to the presence
  // or absence of placeholders.
  llvm::Constant *genConvertedConstant(llvm::Constant *fromVal,
                                       llvm::Type *llToType);

  // Examine vector of values to test whether they are constants.
  // Checks for and handles pending composite inits.
  static bool
  valuesAreConstant(const std::vector<Bexpression *> &vals);

  // Array init helper
  Bexpression *genArrayInit(llvm::ArrayType *llat,
                            Bexpression *expr,
                            llvm::Value *storage);

  // Struct init helper
  Bexpression *genStructInit(llvm::StructType *llst,
                             Bexpression *expr,
                             llvm::Value *storage);

  // Composite init management
  Bexpression *resolveCompositeInit(Bexpression *expr,
                                    llvm::Value *storage);
  // Var expr management
  Bexpression *resolveVarContext(Bexpression *expr,
                                 Varexpr_context ctx=VE_rvalue);

  // General-purpose resolver, handles var expr context and
  // composite init context.
  Bexpression *resolve(Bexpression *expr, Varexpr_context ctx=VE_rvalue);

  // Check a vector of Bexpression's to see if any are the
  // error expression, returning TRUE if so.
  bool exprVectorHasError(const std::vector<Bexpression *> &vals);

  // Check a vector of Bstatement's to see if any are the
  // error statement, returning TRUE if so.
  bool stmtVectorHasError(const std::vector<Bstatement *> &stmts);

  // Converts value "src" for assignment to container of type
  // "dstType" in assignment-like contexts. This helper exists to help
  // with cases where the frontend is creating an assignment of form
  // "X = Y" where X and Y's types are considered matching by the
  // front end, but are non-matching in an LLVM context. For example,
  //
  //   type Ifi func(int) int
  //   ...
  //   var fp Ifi = myfunctionfoobar
  //
  // Here the right hand side will come out as pointer-to-descriptor,
  // whereas variable "fp" will have type "pointer to functon", which are
  // not the same. Another example is assignments involving nil, e.g.
  //
  //   var ip *float32
  //   ...
  //   ip = nil
  //
  // The type of the right hand side of the assignment will be a
  // generic "*i64" as opposed to "*float32", since the backend
  // "nil_pointer_expression" does not allow for creation of nil
  // pointers of specific types.
  //
  // Return value will be a new convert Bexpression if a convert is
  // needed, NULL otherwise.
  llvm::Value *convertForAssignment(Bexpression *src,
                                    llvm::Type *dstToType);
  // lower-level version of the routine above
  llvm::Value *convertForAssignment(Btype *srcType,
                                    llvm::Value *srcVal,
                                    llvm::Type *dstToType,
                                    BlockLIRBuilder *builder);


  // Apply type conversion for a binary operation. This helper exists
  // to resolve situations where expressions are created by the front
  // end have incomplete or "polymorphic" type. A good example is pointer
  // comparison with nil, e.g.
  //
  //    var ip *A = foobar()
  //    if ip == nil { ...
  //
  // The type of the right hand side of the '==' above will be a generic
  // "*i64" as opposed to "*A", since the backend "nil_pointer_expression"
  // does not allow for creation of nil pointers of specific types.
  //
  // Input expressions 'left' and 'right' correspond to the original
  // uncoerced expressions; if conversions are needed, any additional
  // instructions will be added to the args and the resulting LLVM
  // values will be returned.
  std::pair<llvm::Value *, llvm::Value *>
  convertForBinary(Operator op, Bexpression *left, Bexpression *right);

  // Generate a conversion induced by the use of a circular pointer type.
  Bexpression *genCircularConversion(Btype *toType, Bexpression *expr,
                                     Location loc);

  // Helpers for call sequence generation.
  void genCallProlog(GenCallState &state);
  void genCallAttributes(GenCallState &state, llvm::CallInst *call);
  void genCallMarshallArgs(const std::vector<Bexpression *> &fn_args,
                           GenCallState &state);
  void genCallEpilog(GenCallState &state, llvm::Instruction *callInst,
                     Bexpression *callExpr);

  // Store the value in question to a temporary, returning the alloca
  // for the temp.
  llvm::Instruction *storeToTemporary(Bfunction *func, llvm::Value *val);

  // Generate a "late" type conversion (e.g. during materialization,
  // hence no delayed value creation).
  Bexpression *lateConvert(Btype *type, Bexpression *expr, Location);

  // Manufacture a complex constant corresponding to -0.0-0.0i
  Bexpression *minusZeroExpr(BComplexType *typ);

  // Manufacture a floating point constant corresponding to -0.0
  Bexpression *minusZeroExpr(BFloatType *typ);

  // Create integer constant 1 (for use with type creation)
  Bexpression *makeIntegerOneExpr();

 public:

  // Performs a bottom-up walk to materialize LLVM values for each
  // node in the expression tree. Made public for unit testing.
  Bexpression *materialize(Bexpression *expr,
                           Varexpr_context lvalueContext=VE_rvalue);

  // Helper routines to materialize llvm::Value's for expression nodes,
  // invoked by routine above. Public primarily because we need to call
  // them from MaterializeVisitor (could be privatized if the materializer
  // was added as a friend).
  Bexpression *materializeIndirect(Bexpression *indExpr, bool isLHS);
  Bexpression *materializeAddress(Bexpression *addrExpr);
  Bexpression *materializeConversion(Bexpression *convExpr);
  Bexpression *materializeStructField(Bexpression *fieldExpr);
  Bexpression *materializeConditional(Bexpression *condExpr);
  Bexpression *materializeUnary(Bexpression *unaryExpr);
  Bexpression *materializeBinary(Bexpression *binExpr);
  Bexpression *materializeConstructor(Bexpression *conExpr);
  Bexpression *materializeComposite(Bexpression *comExpr);
  Bexpression *materializeCompound(Bexpression *comExpr);
  Bexpression *materializePointerOffset(Bexpression *ptroffExpr);
  Bexpression *materializeArrayIndex(Bexpression *arindExpr);
  Bexpression *materializeCall(Bexpression *callExpr);

 private:
  typedef std::pair<llvm::Value *, Btype *> valbtype;
  typedef pairvalmap<llvm::Value *, Btype *, Bexpression *>
  btyped_value_expr_maptyp;

  // Context information needed for the LLVM backend.
  llvm::LLVMContext &context_;

  // The LLVM module we're emitting IR into. If client did not supply
  // a module during construction, then ownModule_ is filled in.
  llvm::Module *module_;
  std::unique_ptr<llvm::Module> ownModule_;

  // Data layout info from the module.
  const llvm::DataLayout *datalayout_;

  // The target triple.
  llvm::Triple triple_;

  // Builder for constructing Bexpressions and Bstatements.
  BnodeBuilder nbuilder_;

  // Debug info builder.
  std::unique_ptr<DIBuildHelper> dibuildhelper_;

  // Linemap to use. If client did not supply a linemap during
  // construction, then ownLinemap_ is filled in.
  Llvm_linemap *linemap_;
  std::unique_ptr<Llvm_linemap> ownLinemap_;

  // Address space designator for pointer types.
  unsigned addressSpace_;

  // Debug trace level
  unsigned traceLevel_;

  // Whether to disable inlining.
  bool noInline_;

  // Whether to disable frame pointer elimination.
  bool noFpElim_;

  // Whether to use split stacks.
  bool useSplitStack_;

  // Whether we are compiling the runtime.
  bool compilingRuntime_;

  // Whether to check for unexpected node sharing (e.g. same Bexpression
  // or statement pointed to by multiple parents).
  bool checkIntegrity_;

  // Whether to create debug meta data. On by default, can be
  // disabled for unit testing.
  bool createDebugMetaData_;

  // Whether we've started / finalized export data for the module.
  bool exportDataStarted_;
  bool exportDataFinalized_;

  // This counter gets incremented when the FE requests an error
  // object (error variable, error type, etc). We check to see whether
  // it is non-zero before walking function bodies to emit debug
  // meta-data (the idea being that there is no point going through
  // that process if there were errors).
  unsigned errorCount_;

  // Composite value load/store size threshold. Tells the bridge
  // that for any composite value whose size in bytes is greater than X,
  // emit memcpy operations for loads and stores as opposed to
  // emitting direct load/store instructions.
  unsigned compositeSizeThreshold_;

  // Target library info oracle
  llvm::TargetLibraryInfo *TLI_;

  // maps name to entry storing info on builtin function
  std::unique_ptr<BuiltinTable> builtinTable_;

  // Error function
  std::unique_ptr<Bfunction> errorFunction_;

  // Error expression
  Bexpression *errorExpression_;

  // Error statement
  Bstatement *errorStatement_;

  // Error variable
  std::unique_ptr<Bvariable> errorVariable_;

  // Map from LLVM-value/Btype pair to Bexpression. This is
  // used to cache + reuse things like global constants.
  btyped_value_expr_maptyp valueExprmap_;

  // Map from LLVM values to Bvariable. This is used for
  // module-scope variables, not vars local to a function.
  std::unordered_map<llvm::Value *, Bvariable *> valueVarMap_;

  // This is used to cache compiler-constructed vars to capture
  // constant values (created in genVarForConstant).
  std::unordered_map<llvm::Value *, Bvariable *> genVarConstMap_;

  // This table is a cache for converted constants; key is a pair
  // [FromVal,ToType] and value is a constant value equivalent
  // to FromVal but converted to ToType.
  pairvalmap<llvm::Constant *, llvm::Type *, llvm::Constant *> genConvConstMap_;

  // Table for commoning strings by value. String constants have
  // concrete types like "[5 x i8]", whereas we would like to return
  // things that have type "i8*". To manage this, we eagerly create
  // module-scope vars with strings, but this tends to defeat the
  // caching mechanisms, so here we have a map from constant string
  // value to Bexpression holding that string const.
  std::unordered_map<llvm::Value *, Bexpression*> stringConstantMap_;

  // For caching of immutable struct references. Similar situation here
  // as above, in that we can't look for such things in valueVarMap_
  // without creating what it is we're looking for.
  std::unordered_map<std::string, Bvariable *> immutableStructRefs_;

  typedef std::pair<BFunctionType *, std::string> fcnNameAndType;
  typedef pairvalmap<BFunctionType *, std::string, Bfunction*> fcnDeclMapTyp;

  // This maps from <name, type> pairs to Bfunction object; it is used
  // to cache declarations of external functions (for example,
  // well-known functions in the runtime). Only declarations will be
  // placed in this map-- if a function is being defined, it will only
  // be added to the functions_ list below.
  fcnDeclMapTyp fcnDeclMap_;

  // Currently we don't do any commoning of Bfunction objects created
  // by the frontend, so here we keep track of all returned Bfunctions
  // so that we can free them on exit.
  std::vector<Bfunction *> functions_;

  // Personality function
  llvm::Function *personalityFunction_;
  llvm::Function *dummyPersonalityFunction_;

  // Target cpu and attributes to be attached to any generated fcns.
  std::string targetCpuAttr_;
  std::string targetFeaturesAttr_;

  // GC strategy
  std::string gcStrategy_;

  // Prepare for use of AutoFDO.
  bool autoFDO_;
};

#endif
