Skip to content
ASTContext.cpp 83.3 KiB
Newer Older
//===--- ASTContext.cpp - Context to hold long-lived AST nodes ------------===//
//
//                     The LLVM Compiler Infrastructure
//
// This file is distributed under the University of Illinois Open Source
// License. See LICENSE.TXT for details.
//
//===----------------------------------------------------------------------===//
//
//  This file implements the ASTContext interface.
//
//===----------------------------------------------------------------------===//

#include "clang/AST/ASTContext.h"
#include "clang/AST/DeclCXX.h"
Steve Naroff's avatar
 
Steve Naroff committed
#include "clang/AST/DeclObjC.h"
Daniel Dunbar's avatar
Daniel Dunbar committed
#include "clang/AST/Expr.h"
#include "clang/AST/RecordLayout.h"
#include "clang/Basic/TargetInfo.h"
#include "llvm/ADT/StringExtras.h"
#include "llvm/Bitcode/Serialize.h"
#include "llvm/Bitcode/Deserialize.h"
Steve Naroff's avatar
Steve Naroff committed
enum FloatingRank {
  FloatRank, DoubleRank, LongDoubleRank
};

ASTContext::ASTContext(const LangOptions& LOpts, SourceManager &SM,
                       TargetInfo &t,
Daniel Dunbar's avatar
Daniel Dunbar committed
                       IdentifierTable &idents, SelectorTable &sels,
                       unsigned size_reserve) : 
  CFConstantStringTypeDecl(0), ObjCFastEnumerationStateTypeDecl(0),
  SourceMgr(SM), LangOpts(LOpts), Target(t), 
Daniel Dunbar's avatar
Daniel Dunbar committed
  Idents(idents), Selectors(sels) 
{  
  if (size_reserve > 0) Types.reserve(size_reserve);    
  InitBuiltinTypes();
  BuiltinInfo.InitializeBuiltins(idents, Target);
  TUDecl = TranslationUnitDecl::Create(*this);
}

ASTContext::~ASTContext() {
  // Deallocate all the types.
  while (!Types.empty()) {
Eli Friedman's avatar
Eli Friedman committed

  TUDecl->Destroy(*this);
void ASTContext::PrintStats() const {
  fprintf(stderr, "*** AST Context Stats:\n");
  fprintf(stderr, "  %d types total.\n", (int)Types.size());
  unsigned NumBuiltin = 0, NumPointer = 0, NumArray = 0, NumFunctionP = 0;
  unsigned NumVector = 0, NumComplex = 0, NumBlockPointer = 0;
Bill Wendling's avatar
Bill Wendling committed
  unsigned NumFunctionNP = 0, NumTypeName = 0, NumTagged = 0, NumReference = 0;
  
  unsigned NumTagStruct = 0, NumTagUnion = 0, NumTagEnum = 0, NumTagClass = 0;
  unsigned NumObjCInterfaces = 0, NumObjCQualifiedInterfaces = 0;
  unsigned NumObjCQualifiedIds = 0;
  unsigned NumTypeOfTypes = 0, NumTypeOfExprs = 0;
  
  for (unsigned i = 0, e = Types.size(); i != e; ++i) {
    Type *T = Types[i];
    if (isa<BuiltinType>(T))
      ++NumBuiltin;
    else if (isa<PointerType>(T))
      ++NumPointer;
    else if (isa<BlockPointerType>(T))
      ++NumBlockPointer;
Bill Wendling's avatar
Bill Wendling committed
    else if (isa<ReferenceType>(T))
      ++NumReference;
    else if (isa<ComplexType>(T))
      ++NumComplex;
    else if (isa<ArrayType>(T))
      ++NumArray;
    else if (isa<VectorType>(T))
      ++NumVector;
    else if (isa<FunctionTypeNoProto>(T))
      ++NumFunctionNP;
    else if (isa<FunctionTypeProto>(T))
      ++NumFunctionP;
    else if (isa<TypedefType>(T))
Steve Naroff's avatar
Steve Naroff committed
    else if (TagType *TT = dyn_cast<TagType>(T)) {
Argyrios Kyrtzidis's avatar
Argyrios Kyrtzidis committed
      switch (TT->getDecl()->getTagKind()) {
      default: assert(0 && "Unknown tagged type!");
Argyrios Kyrtzidis's avatar
Argyrios Kyrtzidis committed
      case TagDecl::TK_struct: ++NumTagStruct; break;
      case TagDecl::TK_union:  ++NumTagUnion; break;
      case TagDecl::TK_class:  ++NumTagClass; break; 
      case TagDecl::TK_enum:   ++NumTagEnum; break;
    } else if (isa<ObjCInterfaceType>(T))
      ++NumObjCInterfaces;
    else if (isa<ObjCQualifiedInterfaceType>(T))
      ++NumObjCQualifiedInterfaces;
    else if (isa<ObjCQualifiedIdType>(T))
      ++NumObjCQualifiedIds;
    else if (isa<TypeOfType>(T))
      ++NumTypeOfTypes;
    else if (isa<TypeOfExpr>(T))
      ++NumTypeOfExprs;
Steve Naroff's avatar
 
Steve Naroff committed
    else {
Chris Lattner's avatar
Chris Lattner committed
      QualType(T, 0).dump();
      assert(0 && "Unknown type!");
    }
  }

  fprintf(stderr, "    %d builtin types\n", NumBuiltin);
  fprintf(stderr, "    %d pointer types\n", NumPointer);
  fprintf(stderr, "    %d block pointer types\n", NumBlockPointer);
Bill Wendling's avatar
Bill Wendling committed
  fprintf(stderr, "    %d reference types\n", NumReference);
  fprintf(stderr, "    %d complex types\n", NumComplex);
  fprintf(stderr, "    %d array types\n", NumArray);
  fprintf(stderr, "    %d vector types\n", NumVector);
  fprintf(stderr, "    %d function types with proto\n", NumFunctionP);
  fprintf(stderr, "    %d function types with no proto\n", NumFunctionNP);
  fprintf(stderr, "    %d typename (typedef) types\n", NumTypeName);
  fprintf(stderr, "    %d tagged types\n", NumTagged);
  fprintf(stderr, "      %d struct types\n", NumTagStruct);
  fprintf(stderr, "      %d union types\n", NumTagUnion);
  fprintf(stderr, "      %d class types\n", NumTagClass);
  fprintf(stderr, "      %d enum types\n", NumTagEnum);
  fprintf(stderr, "    %d interface types\n", NumObjCInterfaces);
Chris Lattner's avatar
Chris Lattner committed
  fprintf(stderr, "    %d protocol qualified interface types\n",
  fprintf(stderr, "    %d protocol qualified id types\n",
  fprintf(stderr, "    %d typeof types\n", NumTypeOfTypes);
  fprintf(stderr, "    %d typeof exprs\n", NumTypeOfExprs);
  
  fprintf(stderr, "Total bytes = %d\n", int(NumBuiltin*sizeof(BuiltinType)+
Steve Naroff's avatar
Steve Naroff committed
    NumPointer*sizeof(PointerType)+NumArray*sizeof(ArrayType)+
    NumComplex*sizeof(ComplexType)+NumVector*sizeof(VectorType)+
    NumFunctionP*sizeof(FunctionTypeProto)+
    NumFunctionNP*sizeof(FunctionTypeNoProto)+
    NumTypeName*sizeof(TypedefType)+NumTagged*sizeof(TagType)+
    NumTypeOfTypes*sizeof(TypeOfType)+NumTypeOfExprs*sizeof(TypeOfExpr)));
Steve Naroff's avatar
Steve Naroff committed
void ASTContext::InitBuiltinType(QualType &R, BuiltinType::Kind K) {
  Types.push_back((R = QualType(new BuiltinType(K),0)).getTypePtr());
void ASTContext::InitBuiltinTypes() {
  assert(VoidTy.isNull() && "Context reinitialized?");
  
  // C99 6.2.5p19.
  InitBuiltinType(VoidTy,              BuiltinType::Void);
  InitBuiltinType(BoolTy,              BuiltinType::Bool);
    InitBuiltinType(CharTy,            BuiltinType::Char_S);
  else
    InitBuiltinType(CharTy,            BuiltinType::Char_U);
  InitBuiltinType(SignedCharTy,        BuiltinType::SChar);
  InitBuiltinType(ShortTy,             BuiltinType::Short);
  InitBuiltinType(IntTy,               BuiltinType::Int);
  InitBuiltinType(LongTy,              BuiltinType::Long);
  InitBuiltinType(LongLongTy,          BuiltinType::LongLong);
  InitBuiltinType(UnsignedCharTy,      BuiltinType::UChar);
  InitBuiltinType(UnsignedShortTy,     BuiltinType::UShort);
  InitBuiltinType(UnsignedIntTy,       BuiltinType::UInt);
  InitBuiltinType(UnsignedLongTy,      BuiltinType::ULong);
  InitBuiltinType(UnsignedLongLongTy,  BuiltinType::ULongLong);
  InitBuiltinType(FloatTy,             BuiltinType::Float);
  InitBuiltinType(DoubleTy,            BuiltinType::Double);
  InitBuiltinType(LongDoubleTy,        BuiltinType::LongDouble);

  // C++ 3.9.1p5
  InitBuiltinType(WCharTy,             BuiltinType::WChar);

  // Placeholder type for functions.
  InitBuiltinType(OverloadTy,         BuiltinType::Overload);

  FloatComplexTy      = getComplexType(FloatTy);
  DoubleComplexTy     = getComplexType(DoubleTy);
  LongDoubleComplexTy = getComplexType(LongDoubleTy);
Steve Naroff's avatar
 
Steve Naroff committed
  BuiltinVaListType = QualType();
Steve Naroff's avatar
 
Steve Naroff committed
  IdStructType = 0;
  ClassStructType = 0;
  
  ObjCConstantStringType = QualType();
Loading
Loading full blame...