zcov: / lib/CodeGen/CodeGenTypes.cpp


Files: 1 Branches Taken: 77.4% 89 / 115
Generated: 2010-02-10 01:31 Branches Executed: 93.0% 107 / 115
Line Coverage: 95.4% 187 / 196


Programs: 1 Runs 2897


       1                 : //===--- CodeGenTypes.cpp - Type translation for LLVM CodeGen -------------===//
       2                 : //
       3                 : //                     The LLVM Compiler Infrastructure
       4                 : //
       5                 : // This file is distributed under the University of Illinois Open Source
       6                 : // License. See LICENSE.TXT for details.
       7                 : //
       8                 : //===----------------------------------------------------------------------===//
       9                 : //
      10                 : // This is the code that handles AST -> LLVM type lowering.
      11                 : //
      12                 : //===----------------------------------------------------------------------===//
      13                 : 
      14                 : #include "CodeGenTypes.h"
      15                 : #include "clang/AST/ASTContext.h"
      16                 : #include "clang/AST/DeclObjC.h"
      17                 : #include "clang/AST/DeclCXX.h"
      18                 : #include "clang/AST/Expr.h"
      19                 : #include "clang/AST/RecordLayout.h"
      20                 : #include "llvm/DerivedTypes.h"
      21                 : #include "llvm/Module.h"
      22                 : #include "llvm/Target/TargetData.h"
      23                 : 
      24                 : #include "CGCall.h"
      25                 : #include "CGRecordLayoutBuilder.h"
      26                 : 
      27                 : using namespace clang;
      28                 : using namespace CodeGen;
      29                 : 
      30                 : CodeGenTypes::CodeGenTypes(ASTContext &Ctx, llvm::Module& M,
      31              625:                            const llvm::TargetData &TD, const ABIInfo &Info)
      32                 :   : Context(Ctx), Target(Ctx.Target), TheModule(M), TheTargetData(TD),
      33              625:     TheABIInfo(Info) {
      34              625: }
      35                 : 
      36              599: CodeGenTypes::~CodeGenTypes() {
                     1327: branch 3 taken
                      599: branch 4 taken
                        0: branch 8 not taken
                        0: branch 9 not taken
      37             1926:   for (llvm::DenseMap<const Type *, CGRecordLayout *>::iterator
      38              599:          I = CGRecordLayouts.begin(), E = CGRecordLayouts.end();
      39                 :       I != E; ++I)
      40             1327:     delete I->second;
      41                 : 
                     2818: branch 1 taken
                      599: branch 2 taken
                        0: branch 4 not taken
                        0: branch 5 not taken
      42             4016:   for (llvm::FoldingSet<CGFunctionInfo>::iterator
      43              599:        I = FunctionInfos.begin(), E = FunctionInfos.end(); I != E; )
                     2818: branch 2 taken
                        0: branch 3 not taken
                        0: branch 8 not taken
                        0: branch 9 not taken
      44             2818:     delete &*I++;
      45              599: }
      46                 : 
      47                 : /// ConvertType - Convert the specified type to its LLVM form.
      48            28340: const llvm::Type *CodeGenTypes::ConvertType(QualType T) {
      49            28340:   llvm::PATypeHolder Result = ConvertTypeRecursive(T);
      50                 : 
      51                 :   // Any pointers that were converted defered evaluation of their pointee type,
      52                 :   // creating an opaque type instead.  This is in order to avoid problems with
      53                 :   // circular types.  Loop through all these defered pointees, if any, and
      54                 :   // resolve them now.
                     1692: branch 1 taken
                    28340: branch 2 taken
      55            58372:   while (!PointersToResolve.empty()) {
      56             1692:     std::pair<QualType, llvm::OpaqueType*> P = PointersToResolve.pop_back_val();
      57                 :     
      58                 :     // We can handle bare pointers here because we know that the only pointers
      59                 :     // to the Opaque type are P.second and from other types.  Refining the
      60                 :     // opqaue type away will invalidate P.second, but we don't mind :).
      61             1692:     const llvm::Type *NT = ConvertTypeForMemRecursive(P.first);
      62             1692:     P.second->refineAbstractTypeTo(NT);
      63                 :   }
      64                 : 
      65            28340:   return Result;
      66                 : }
      67                 : 
      68            32788: const llvm::Type *CodeGenTypes::ConvertTypeRecursive(QualType T) {
      69            32788:   T = Context.getCanonicalType(T);
      70                 : 
      71                 :   // See if type is already cached.
      72                 :   llvm::DenseMap<Type *, llvm::PATypeHolder>::iterator
      73            32788:     I = TypeCache.find(T.getTypePtr());
      74                 :   // If type is found in map and this is not a definition for a opaque
      75                 :   // place holder type then use it. Otherwise, convert type T.
                    25099: branch 3 taken
                     7689: branch 4 taken
      76            32788:   if (I != TypeCache.end())
      77            25099:     return I->second.get();
      78                 : 
      79             7689:   const llvm::Type *ResultType = ConvertNewType(T);
      80                 :   TypeCache.insert(std::make_pair(T.getTypePtr(),
      81             7689:                                   llvm::PATypeHolder(ResultType)));
      82             7689:   return ResultType;
      83                 : }
      84                 : 
      85             3885: const llvm::Type *CodeGenTypes::ConvertTypeForMemRecursive(QualType T) {
      86             3885:   const llvm::Type *ResultType = ConvertTypeRecursive(T);
                       70: branch 1 taken
                     3815: branch 2 taken
      87             3885:   if (ResultType->isInteger(1))
      88                 :     return llvm::IntegerType::get(getLLVMContext(),
      89               70:                                   (unsigned)Context.getTypeSize(T));
      90                 :   // FIXME: Should assert that the llvm type and AST type has the same size.
      91             3815:   return ResultType;
      92                 : }
      93                 : 
      94                 : /// ConvertTypeForMem - Convert type T into a llvm::Type.  This differs from
      95                 : /// ConvertType in that it is used to convert to the memory representation for
      96                 : /// a type.  For example, the scalar representation for _Bool is i1, but the
      97                 : /// memory representation is usually i8 or i32, depending on the target.
      98             6742: const llvm::Type *CodeGenTypes::ConvertTypeForMem(QualType T) {
      99             6742:   const llvm::Type *R = ConvertType(T);
     100                 : 
     101                 :   // If this is a non-bool type, don't map it.
                     6703: branch 1 taken
                       39: branch 2 taken
     102             6742:   if (!R->isInteger(1))
     103             6703:     return R;
     104                 : 
     105                 :   // Otherwise, return an integer of the target-specified size.
     106                 :   return llvm::IntegerType::get(getLLVMContext(),
     107               39:                                 (unsigned)Context.getTypeSize(T));
     108                 : 
     109                 : }
     110                 : 
     111                 : // Code to verify a given function type is complete, i.e. the return type
     112                 : // and all of the argument types are complete.
     113             1340: static const TagType *VerifyFuncTypeComplete(const Type* T) {
     114             1340:   const FunctionType *FT = cast<FunctionType>(T);
                      129: branch 3 taken
                     1211: branch 4 taken
     115             1340:   if (const TagType* TT = FT->getResultType()->getAs<TagType>())
                        3: branch 2 taken
                      126: branch 3 taken
     116              129:     if (!TT->getDecl()->isDefinition())
     117                3:       return TT;
                     1101: branch 1 taken
                      236: branch 2 taken
     118             1337:   if (const FunctionProtoType *FPT = dyn_cast<FunctionProtoType>(T))
                      941: branch 1 taken
                     1097: branch 2 taken
     119             2038:     for (unsigned i = 0; i < FPT->getNumArgs(); i++)
                      120: branch 3 taken
                      821: branch 4 taken
     120              941:       if (const TagType* TT = FPT->getArgType(i)->getAs<TagType>())
                        4: branch 2 taken
                      116: branch 3 taken
     121              120:         if (!TT->getDecl()->isDefinition())
     122                4:           return TT;
     123             1333:   return 0;
     124                 : }
     125                 : 
     126                 : /// UpdateCompletedType - When we find the full definition for a TagDecl,
     127                 : /// replace the 'opaque' type we previously made for it if applicable.
     128             1509: void CodeGenTypes::UpdateCompletedType(const TagDecl *TD) {
     129             1509:   const Type *Key = Context.getTagDeclType(TD).getTypePtr();
     130                 :   llvm::DenseMap<const Type*, llvm::PATypeHolder>::iterator TDTI =
     131             1509:     TagDeclTypes.find(Key);
                        4: branch 3 taken
                     1505: branch 4 taken
     132             1509:   if (TDTI == TagDeclTypes.end()) return;
     133                 : 
     134                 :   // Remember the opaque LLVM type for this tagdecl.
     135                4:   llvm::PATypeHolder OpaqueHolder = TDTI->second;
     136                 :   assert(isa<llvm::OpaqueType>(OpaqueHolder.get()) &&
                        4: branch 2 taken
                        0: branch 3 not taken
     137                4:          "Updating compilation of an already non-opaque type?");
     138                 : 
     139                 :   // Remove it from TagDeclTypes so that it will be regenerated.
     140                4:   TagDeclTypes.erase(TDTI);
     141                 : 
     142                 :   // Generate the new type.
     143                4:   const llvm::Type *NT = ConvertTagDeclType(TD);
     144                 : 
     145                 :   // Refine the old opaque type to its new definition.
     146                4:   cast<llvm::OpaqueType>(OpaqueHolder.get())->refineAbstractTypeTo(NT);
     147                 : 
     148                 :   // Since we just completed a tag type, check to see if any function types
     149                 :   // were completed along with the tag type.
     150                 :   // FIXME: This is very inefficient; if we track which function types depend
     151                 :   // on which tag types, though, it should be reasonably efficient.
     152                4:   llvm::DenseMap<const Type*, llvm::PATypeHolder>::iterator i;
                        6: branch 5 taken
                        4: branch 6 taken
     153               10:   for (i = FunctionTypes.begin(); i != FunctionTypes.end(); ++i) {
                        3: branch 2 taken
                        3: branch 3 taken
     154                6:     if (const TagType* TT = VerifyFuncTypeComplete(i->first)) {
     155                 :       // This function type still depends on an incomplete tag type; make sure
     156                 :       // that tag type has an associated opaque type.
     157                3:       ConvertTagDeclType(TT->getDecl());
     158                 :     } else {
     159                 :       // This function no longer depends on an incomplete tag type; create the
     160                 :       // function type, and refine the opaque type to the new function type.
     161                3:       llvm::PATypeHolder OpaqueHolder = i->second;
     162                3:       const llvm::Type *NFT = ConvertNewType(QualType(i->first, 0));
     163                3:       cast<llvm::OpaqueType>(OpaqueHolder.get())->refineAbstractTypeTo(NFT);
     164                3:       FunctionTypes.erase(i);
     165                 :     }
     166                4:   }
     167                 : }
     168                 : 
     169                 : static const llvm::Type* getTypeForFormat(llvm::LLVMContext &VMContext,
     170              159:                                           const llvm::fltSemantics &format) {
                       78: branch 0 taken
                       81: branch 1 taken
     171              159:   if (&format == &llvm::APFloat::IEEEsingle)
     172               78:     return llvm::Type::getFloatTy(VMContext);
                       67: branch 0 taken
                       14: branch 1 taken
     173               81:   if (&format == &llvm::APFloat::IEEEdouble)
     174               67:     return llvm::Type::getDoubleTy(VMContext);
                        0: branch 0 not taken
                       14: branch 1 taken
     175               14:   if (&format == &llvm::APFloat::IEEEquad)
     176                0:     return llvm::Type::getFP128Ty(VMContext);
                        0: branch 0 not taken
                       14: branch 1 taken
     177               14:   if (&format == &llvm::APFloat::PPCDoubleDouble)
     178                0:     return llvm::Type::getPPC_FP128Ty(VMContext);
                       14: branch 0 taken
                        0: branch 1 not taken
     179               14:   if (&format == &llvm::APFloat::x87DoubleExtended)
     180               14:     return llvm::Type::getX86_FP80Ty(VMContext);
     181                0:   assert(0 && "Unknown float format!");
     182                 :   return 0;
     183                 : }
     184                 : 
     185             7692: const llvm::Type *CodeGenTypes::ConvertNewType(QualType T) {
     186             7692:   const clang::Type &Ty = *Context.getCanonicalType(T).getTypePtr();
     187                 : 
                        0: branch 1 not taken
                     2179: branch 2 taken
                       42: branch 3 taken
                      164: branch 4 taken
                     1497: branch 5 taken
                       18: branch 6 taken
                        9: branch 7 taken
                      268: branch 8 taken
                       45: branch 9 taken
                     1334: branch 10 taken
                      282: branch 11 taken
                      429: branch 12 taken
                     1360: branch 13 taken
                       31: branch 14 taken
                       34: branch 15 taken
                        0: branch 16 not taken
                        0: branch 17 not taken
     188             7692:   switch (Ty.getTypeClass()) {
     189                 : #define TYPE(Class, Base)
     190                 : #define ABSTRACT_TYPE(Class, Base)
     191                 : #define NON_CANONICAL_TYPE(Class, Base) case Type::Class:
     192                 : #define DEPENDENT_TYPE(Class, Base) case Type::Class:
     193                 : #include "clang/AST/TypeNodes.def"
     194                0:     assert(false && "Non-canonical or dependent types aren't possible.");
     195                 :     break;
     196                 : 
     197                 :   case Type::Builtin: {
                      566: branch 2 taken
                       37: branch 3 taken
                     1412: branch 4 taken
                      159: branch 5 taken
                        2: branch 6 taken
                        3: branch 7 taken
                        0: branch 8 not taken
                        0: branch 9 not taken
     198             2179:     switch (cast<BuiltinType>(Ty).getKind()) {
     199                 :     case BuiltinType::Void:
     200                 :     case BuiltinType::ObjCId:
     201                 :     case BuiltinType::ObjCClass:
     202                 :     case BuiltinType::ObjCSel:
     203                 :       // LLVM void type can only be used as the result of a function call.  Just
     204                 :       // map to the same as char.
     205              566:       return llvm::IntegerType::get(getLLVMContext(), 8);
     206                 : 
     207                 :     case BuiltinType::Bool:
     208                 :       // Note that we always return bool as i1 for use as a scalar type.
     209               37:       return llvm::Type::getInt1Ty(getLLVMContext());
     210                 : 
     211                 :     case BuiltinType::Char_S:
     212                 :     case BuiltinType::Char_U:
     213                 :     case BuiltinType::SChar:
     214                 :     case BuiltinType::UChar:
     215                 :     case BuiltinType::Short:
     216                 :     case BuiltinType::UShort:
     217                 :     case BuiltinType::Int:
     218                 :     case BuiltinType::UInt:
     219                 :     case BuiltinType::Long:
     220                 :     case BuiltinType::ULong:
     221                 :     case BuiltinType::LongLong:
     222                 :     case BuiltinType::ULongLong:
     223                 :     case BuiltinType::WChar:
     224                 :     case BuiltinType::Char16:
     225                 :     case BuiltinType::Char32:
     226                 :       return llvm::IntegerType::get(getLLVMContext(),
     227             1412:         static_cast<unsigned>(Context.getTypeSize(T)));
     228                 : 
     229                 :     case BuiltinType::Float:
     230                 :     case BuiltinType::Double:
     231                 :     case BuiltinType::LongDouble:
     232                 :       return getTypeForFormat(getLLVMContext(),
     233              159:                               Context.getFloatTypeSemantics(T));
     234                 : 
     235                 :     case BuiltinType::NullPtr: {
     236                 :       // Model std::nullptr_t as i8*
     237                2:       const llvm::Type *Ty = llvm::IntegerType::get(getLLVMContext(), 8);
     238                2:       return llvm::PointerType::getUnqual(Ty);
     239                 :     }
     240                 :         
     241                 :     case BuiltinType::UInt128:
     242                 :     case BuiltinType::Int128:
     243                3:       return llvm::IntegerType::get(getLLVMContext(), 128);
     244                 :     
     245                 :     case BuiltinType::Overload:
     246                 :     case BuiltinType::Dependent:
     247                 :     case BuiltinType::UndeducedAuto:
     248                0:       assert(0 && "Unexpected builtin type!");
     249                 :       break;
     250                 :     }
     251                0:     assert(0 && "Unknown builtin type!");
     252                 :     break;
     253                 :   }
     254                 :   case Type::Complex: {
     255                 :     const llvm::Type *EltTy =
     256               42:       ConvertTypeRecursive(cast<ComplexType>(Ty).getElementType());
     257               42:     return llvm::StructType::get(TheModule.getContext(), EltTy, EltTy, NULL);
     258                 :   }
     259                 :   case Type::LValueReference:
     260                 :   case Type::RValueReference: {
     261              164:     const ReferenceType &RTy = cast<ReferenceType>(Ty);
     262              164:     QualType ETy = RTy.getPointeeType();
     263              164:     llvm::OpaqueType *PointeeType = llvm::OpaqueType::get(getLLVMContext());
     264              164:     PointersToResolve.push_back(std::make_pair(ETy, PointeeType));
     265              164:     return llvm::PointerType::get(PointeeType, ETy.getAddressSpace());
     266                 :   }
     267                 :   case Type::Pointer: {
     268             1497:     const PointerType &PTy = cast<PointerType>(Ty);
     269             1497:     QualType ETy = PTy.getPointeeType();
     270             1497:     llvm::OpaqueType *PointeeType = llvm::OpaqueType::get(getLLVMContext());
     271             1497:     PointersToResolve.push_back(std::make_pair(ETy, PointeeType));
     272             1497:     return llvm::PointerType::get(PointeeType, ETy.getAddressSpace());
     273                 :   }
     274                 : 
     275                 :   case Type::VariableArray: {
     276               18:     const VariableArrayType &A = cast<VariableArrayType>(Ty);
     277                 :     assert(A.getIndexTypeCVRQualifiers() == 0 &&
                       18: branch 1 taken
                        0: branch 2 not taken
     278               18:            "FIXME: We only handle trivial array types so far!");
     279                 :     // VLAs resolve to the innermost element type; this matches
     280                 :     // the return of alloca, and there isn't any obviously better choice.
     281               18:     return ConvertTypeForMemRecursive(A.getElementType());
     282                 :   }
     283                 :   case Type::IncompleteArray: {
     284                9:     const IncompleteArrayType &A = cast<IncompleteArrayType>(Ty);
     285                 :     assert(A.getIndexTypeCVRQualifiers() == 0 &&
                        9: branch 1 taken
                        0: branch 2 not taken
     286                9:            "FIXME: We only handle trivial array types so far!");
     287                 :     // int X[] -> [0 x int]
     288                9:     return llvm::ArrayType::get(ConvertTypeForMemRecursive(A.getElementType()), 0);
     289                 :   }
     290                 :   case Type::ConstantArray: {
     291              268:     const ConstantArrayType &A = cast<ConstantArrayType>(Ty);
     292              268:     const llvm::Type *EltTy = ConvertTypeForMemRecursive(A.getElementType());
     293              268:     return llvm::ArrayType::get(EltTy, A.getSize().getZExtValue());
     294                 :   }
     295                 :   case Type::ExtVector:
     296                 :   case Type::Vector: {
     297               45:     const VectorType &VT = cast<VectorType>(Ty);
     298                 :     return llvm::VectorType::get(ConvertTypeRecursive(VT.getElementType()),
     299               45:                                  VT.getNumElements());
     300                 :   }
     301                 :   case Type::FunctionNoProto:
     302                 :   case Type::FunctionProto: {
     303                 :     // First, check whether we can build the full function type.
                        4: branch 1 taken
                     1330: branch 2 taken
     304             1334:     if (const TagType* TT = VerifyFuncTypeComplete(&Ty)) {
     305                 :       // This function's type depends on an incomplete tag type; make sure
     306                 :       // we have an opaque type corresponding to the tag type.
     307                4:       ConvertTagDeclType(TT->getDecl());
     308                 :       // Create an opaque type for this function type, save it, and return it.
     309                4:       llvm::Type *ResultType = llvm::OpaqueType::get(getLLVMContext());
     310                4:       FunctionTypes.insert(std::make_pair(&Ty, ResultType));
     311                4:       return ResultType;
     312                 :     }
     313                 :     // The function type can be built; call the appropriate routines to
     314                 :     // build it.
                     1095: branch 1 taken
                      235: branch 2 taken
     315             1330:     if (const FunctionProtoType *FPT = dyn_cast<FunctionProtoType>(&Ty))
     316             1095:       return GetFunctionType(getFunctionInfo(FPT), FPT->isVariadic());
     317                 : 
     318              235:     const FunctionNoProtoType *FNPT = cast<FunctionNoProtoType>(&Ty);
     319              235:     return GetFunctionType(getFunctionInfo(FNPT), true);
     320                 :   }
     321                 : 
     322                 :   case Type::ObjCInterface: {
     323                 :     // Objective-C interfaces are always opaque (outside of the
     324                 :     // runtime, which can do whatever it likes); we never refine
     325                 :     // these.
     326              282:     const llvm::Type *&T = InterfaceTypes[cast<ObjCInterfaceType>(&Ty)];
                      282: branch 0 taken
                        0: branch 1 not taken
     327              282:     if (!T)
     328              282:         T = llvm::OpaqueType::get(getLLVMContext());
     329              282:     return T;
     330                 :   }
     331                 : 
     332                 :   case Type::ObjCObjectPointer: {
     333                 :     // Protocol qualifications do not influence the LLVM type, we just return a
     334                 :     // pointer to the underlying interface type. We don't need to worry about
     335                 :     // recursive conversion.
     336                 :     const llvm::Type *T =
     337              429:       ConvertTypeRecursive(cast<ObjCObjectPointerType>(Ty).getPointeeType());
     338              429:     return llvm::PointerType::getUnqual(T);
     339                 :   }
     340                 : 
     341                 :   case Type::Record:
     342                 :   case Type::Enum: {
     343             1360:     const TagDecl *TD = cast<TagType>(Ty).getDecl();
     344             1360:     const llvm::Type *Res = ConvertTagDeclType(TD);
     345                 : 
     346             1360:     std::string TypeName(TD->getKindName());
     347             1360:     TypeName += '.';
     348                 : 
     349                 :     // Name the codegen type after the typedef name
     350                 :     // if there is no tag type name available
                     1214: branch 1 taken
                      146: branch 2 taken
     351             1360:     if (TD->getIdentifier())
     352                 :       // FIXME: We should not have to check for a null decl context here.
     353                 :       // Right now we do it because the implicit Obj-C decls don't have one.
     354                 :       TypeName += TD->getDeclContext() ? TD->getQualifiedNameAsString() :
                     1064: branch 1 taken
                      150: branch 2 taken
     355             1214:         TD->getNameAsString();
                        0: branch 1 not taken
                      146: branch 2 taken
     356              146:     else if (const TypedefType *TdT = dyn_cast<TypedefType>(T))
     357                 :       // FIXME: We should not have to check for a null decl context here.
     358                 :       // Right now we do it because the implicit Obj-C decls don't have one.
     359                 :       TypeName += TdT->getDecl()->getDeclContext() ? 
     360                 :         TdT->getDecl()->getQualifiedNameAsString() :
                        0: branch 2 not taken
                        0: branch 3 not taken
     361                0:         TdT->getDecl()->getNameAsString();
     362                 :     else
     363              146:       TypeName += "anon";
     364                 : 
     365             1360:     TheModule.addTypeName(TypeName, Res);
     366             1360:     return Res;
     367                 :   }
     368                 : 
     369                 :   case Type::BlockPointer: {
     370               31:     const QualType FTy = cast<BlockPointerType>(Ty).getPointeeType();
     371               31:     llvm::OpaqueType *PointeeType = llvm::OpaqueType::get(getLLVMContext());
     372               31:     PointersToResolve.push_back(std::make_pair(FTy, PointeeType));
     373               31:     return llvm::PointerType::get(PointeeType, FTy.getAddressSpace());
     374                 :   }
     375                 : 
     376                 :   case Type::MemberPointer: {
     377                 :     // FIXME: This is ABI dependent. We use the Itanium C++ ABI.
     378                 :     // http://www.codesourcery.com/public/cxx-abi/abi.html#member-pointers
     379                 :     // If we ever want to support other ABIs this needs to be abstracted.
     380                 : 
     381               34:     QualType ETy = cast<MemberPointerType>(Ty).getPointeeType();
     382                 :     const llvm::Type *PtrDiffTy =
     383               34:         ConvertTypeRecursive(Context.getPointerDiffType());
                       24: branch 2 taken
                       10: branch 3 taken
     384               34:     if (ETy->isFunctionType())
     385                 :       return llvm::StructType::get(TheModule.getContext(), PtrDiffTy, PtrDiffTy,
     386               24:                                    NULL);
     387               10:     return PtrDiffTy;
     388                 :   }
     389                 : 
     390                 :   case Type::TemplateSpecialization:
     391                0:     assert(false && "Dependent types can't get here");
     392                 :   }
     393                 : 
     394                 :   // FIXME: implement.
     395                0:   return llvm::OpaqueType::get(getLLVMContext());
     396                 : }
     397                 : 
     398                 : /// ConvertTagDeclType - Lay out a tagged decl type like struct or union or
     399                 : /// enum.
     400             1774: const llvm::Type *CodeGenTypes::ConvertTagDeclType(const TagDecl *TD) {
     401                 : 
     402                 :   // TagDecl's are not necessarily unique, instead use the (clang)
     403                 :   // type connected to the decl.
     404                 :   const Type *Key =
     405             1774:     Context.getTagDeclType(TD).getTypePtr();
     406                 :   llvm::DenseMap<const Type*, llvm::PATypeHolder>::iterator TDTI =
     407             1774:     TagDeclTypes.find(Key);
     408                 : 
     409                 :   // If we've already compiled this tag type, use the previous definition.
                      398: branch 3 taken
                     1376: branch 4 taken
     410             1774:   if (TDTI != TagDeclTypes.end())
     411              398:     return TDTI->second;
     412                 : 
     413                 :   // If this is still a forward declaration, just define an opaque
     414                 :   // type to use for this tagged decl.
                       22: branch 1 taken
                     1354: branch 2 taken
     415             1376:   if (!TD->isDefinition()) {
     416               22:     llvm::Type *ResultType = llvm::OpaqueType::get(getLLVMContext());
     417               22:     TagDeclTypes.insert(std::make_pair(Key, ResultType));
     418               22:     return ResultType;
     419                 :   }
     420                 : 
     421                 :   // Okay, this is a definition of a type.  Compile the implementation now.
     422                 : 
                       13: branch 1 taken
                     1341: branch 2 taken
     423             1354:   if (TD->isEnum())  // Don't bother storing enums in TagDeclTypes.
     424               13:     return ConvertTypeRecursive(cast<EnumDecl>(TD)->getIntegerType());
     425                 : 
     426                 :   // This decl could well be recursive.  In this case, insert an opaque
     427                 :   // definition of this type, which the recursive uses will get.  We will then
     428                 :   // refine this opaque version later.
     429                 : 
     430                 :   // Create new OpaqueType now for later use in case this is a recursive
     431                 :   // type.  This will later be refined to the actual type.
     432             1341:   llvm::PATypeHolder ResultHolder = llvm::OpaqueType::get(getLLVMContext());
     433             1341:   TagDeclTypes.insert(std::make_pair(Key, ResultHolder));
     434                 : 
     435             1341:   const RecordDecl *RD = cast<const RecordDecl>(TD);
     436                 : 
     437                 :   // Force conversion of non-virtual base classes recursively.
                      767: branch 1 taken
                      574: branch 2 taken
     438             1341:   if (const CXXRecordDecl *RD = dyn_cast<CXXRecordDecl>(TD)) {    
                      337: branch 1 taken
                      767: branch 2 taken
     439             1871:     for (CXXRecordDecl::base_class_const_iterator i = RD->bases_begin(),
     440              767:          e = RD->bases_end(); i != e; ++i) {
                      193: branch 1 taken
                      144: branch 2 taken
     441              337:       if (!i->isVirtual()) {
     442                 :         const CXXRecordDecl *Base =
     443              193:           cast<CXXRecordDecl>(i->getType()->getAs<RecordType>()->getDecl());
     444              193:         ConvertTagDeclType(Base);
     445                 :       }
     446                 :     }
     447                 :   }
     448                 : 
     449                 :   // Layout fields.
     450             1341:   CGRecordLayout *Layout = CGRecordLayoutBuilder::ComputeLayout(*this, RD);
     451                 : 
     452             1341:   CGRecordLayouts[Key] = Layout;
     453             1341:   const llvm::Type *ResultType = Layout->getLLVMType();
     454                 : 
     455                 :   // Refine our Opaque type to ResultType.  This can invalidate ResultType, so
     456                 :   // make sure to read the result out of the holder.
     457                 :   cast<llvm::OpaqueType>(ResultHolder.get())
     458             1341:     ->refineAbstractTypeTo(ResultType);
     459                 : 
     460             1341:   return ResultHolder.get();
     461                 : }
     462                 : 
     463                 : /// getLLVMFieldNo - Return llvm::StructType element number
     464                 : /// that corresponds to the field FD.
     465             1194: unsigned CodeGenTypes::getLLVMFieldNo(const FieldDecl *FD) {
                     1194: branch 1 taken
                        0: branch 2 not taken
     466             1194:   assert(!FD->isBitField() && "Don't use getLLVMFieldNo on bit fields!");
     467                 : 
     468             1194:   llvm::DenseMap<const FieldDecl*, unsigned>::iterator I = FieldInfo.find(FD);
                     1194: branch 3 taken
                        0: branch 4 not taken
     469             1194:   assert (I != FieldInfo.end()  && "Unable to find field info");
     470             1194:   return I->second;
     471                 : }
     472                 : 
     473                 : /// addFieldInfo - Assign field number to field FD.
     474             1755: void CodeGenTypes::addFieldInfo(const FieldDecl *FD, unsigned No) {
     475             1755:   FieldInfo[FD] = No;
     476             1755: }
     477                 : 
     478                 : /// getBitFieldInfo - Return the BitFieldInfo  that corresponds to the field FD.
     479               96: CodeGenTypes::BitFieldInfo CodeGenTypes::getBitFieldInfo(const FieldDecl *FD) {
     480                 :   llvm::DenseMap<const FieldDecl *, BitFieldInfo>::iterator
     481               96:     I = BitFields.find(FD);
                       96: branch 3 taken
                        0: branch 4 not taken
     482               96:   assert (I != BitFields.end()  && "Unable to find bitfield info");
     483               96:   return I->second;
     484                 : }
     485                 : 
     486                 : /// addBitFieldInfo - Assign a start bit and a size to field FD.
     487                 : void CodeGenTypes::addBitFieldInfo(const FieldDecl *FD, unsigned FieldNo,
     488               93:                                    unsigned Start, unsigned Size) {
     489               93:   BitFields.insert(std::make_pair(FD, BitFieldInfo(FieldNo, Start, Size)));
     490               93: }
     491                 : 
     492                 : /// getCGRecordLayout - Return record layout info for the given llvm::Type.
     493                 : const CGRecordLayout &
     494              210: CodeGenTypes::getCGRecordLayout(const TagDecl *TD) const {
     495              210:   const Type *Key = Context.getTagDeclType(TD).getTypePtr();
     496                 :   llvm::DenseMap<const Type*, CGRecordLayout *>::const_iterator I
     497              210:     = CGRecordLayouts.find(Key);
     498                 :   assert (I != CGRecordLayouts.end()
                      210: branch 2 taken
                        0: branch 3 not taken
     499              210:           && "Unable to find record layout information for type");
     500              210:   return *I->second;
     501                 : }

Generated: 2010-02-10 01:31 by zcov