/// addCompileUnit - Add compile unit into CUs. bool DebugInfoFinder::addCompileUnit(DICompileUnit CU) { if (!CU.Verify()) return false; if (!NodesSeen.insert(CU)) return false; CUs.push_back(CU); return true; }
void DebugInfoFinder::processModule(const Module &M) { InitializeTypeMap(M); if (NamedMDNode *CU_Nodes = M.getNamedMetadata("llvm.dbg.cu")) { for (unsigned i = 0, e = CU_Nodes->getNumOperands(); i != e; ++i) { DICompileUnit CU = cast<MDCompileUnit>(CU_Nodes->getOperand(i)); addCompileUnit(CU); for (DIGlobalVariable DIG : CU->getGlobalVariables()) { if (addGlobalVariable(DIG)) { processScope(DIG.getContext()); processType(DIG.getType().resolve(TypeIdentifierMap)); } } for (auto *SP : CU->getSubprograms()) processSubprogram(SP); for (auto *ET : CU->getEnumTypes()) processType(ET); for (auto *RT : CU->getRetainedTypes()) processType(RT); for (DIImportedEntity Import : CU->getImportedEntities()) { DIDescriptor Entity = Import.getEntity().resolve(TypeIdentifierMap); if (auto *T = dyn_cast<MDType>(Entity)) processType(T); else if (auto *SP = dyn_cast<MDSubprogram>(Entity)) processSubprogram(SP); else if (auto *NS = dyn_cast<MDNamespace>(Entity)) processScope(NS->getScope()); } } } }
/// CreateVariable - Create a new descriptor for the specified variable. DIVariable DIFactory::CreateVariable(unsigned Tag, DIDescriptor Context, const char * Name, DICompileUnit CompileUnit, unsigned LineNo, DIType Type) { Value *Elts[] = { GetTagConstant(Tag), Context.getNode(), MDString::get(VMContext, Name), CompileUnit.getNode(), ConstantInt::get(Type::getInt32Ty(VMContext), LineNo), Type.getNode(), }; return DIVariable(MDNode::get(VMContext, &Elts[0], 6)); }
/// Verify - Verify that a global variable descriptor is well formed. bool DIGlobalVariable::Verify() const { if (isNull()) return false; if (!getDisplayName()) return false; if (getContext().isNull()) return false; DICompileUnit CU = getCompileUnit(); if (!CU.isNull() && !CU.Verify()) return false; DIType Ty = getType(); if (!Ty.Verify()) return false; if (!getGlobal()) return false; return true; }
bool getLocationInfo(const Value *V, std::string &DisplayName, std::string &Type, unsigned &LineNo, std::string &File, std::string &Dir) { DICompileUnit Unit; DIType TypeD; if (GlobalVariable *GV = dyn_cast<GlobalVariable>(const_cast<Value*>(V))) { Value *DIGV = findDbgGlobalDeclare(GV); if (!DIGV) return false; DIGlobalVariable Var(cast<MDNode>(DIGV)); if (const char *D = Var.getDisplayName()) DisplayName = D; LineNo = Var.getLineNumber(); Unit = Var.getCompileUnit(); TypeD = Var.getType(); } else { const DbgDeclareInst *DDI = findDbgDeclare(V); if (!DDI) return false; DIVariable Var(cast<MDNode>(DDI->getVariable())); if (const char *D = Var.getName()) DisplayName = D; LineNo = Var.getLineNumber(); Unit = Var.getCompileUnit(); TypeD = Var.getType(); } if (const char *T = TypeD.getName()) Type = T; if (const char *F = Unit.getFilename()) File = F; if (const char *D = Unit.getDirectory()) Dir = D; return true; }
DITypeIdentifierMap llvm::generateDITypeIdentifierMap(const NamedMDNode *CU_Nodes) { DITypeIdentifierMap Map; for (unsigned CUi = 0, CUe = CU_Nodes->getNumOperands(); CUi != CUe; ++CUi) { DICompileUnit CU = cast<MDCompileUnit>(CU_Nodes->getOperand(CUi)); DIArray Retain = CU.getRetainedTypes(); for (unsigned Ti = 0, Te = Retain.size(); Ti != Te; ++Ti) { if (!isa<MDCompositeType>(Retain[Ti])) continue; DICompositeType Ty = cast<MDCompositeType>(Retain[Ti]); if (MDString *TypeId = Ty.getIdentifier()) { // Definition has priority over declaration. // Try to insert (TypeId, Ty) to Map. std::pair<DITypeIdentifierMap::iterator, bool> P = Map.insert(std::make_pair(TypeId, Ty)); // If TypeId already exists in Map and this is a definition, replace // whatever we had (declaration or definition) with the definition. if (!P.second && !Ty.isForwardDecl()) P.first->second = Ty; } } } return Map; }
/// CreateComplexVariable - Create a new descriptor for the specified variable /// which has a complex address expression for its address. DIVariable DIFactory::CreateComplexVariable(unsigned Tag, DIDescriptor Context, const std::string &Name, DICompileUnit CompileUnit, unsigned LineNo, DIType Type, SmallVector<Value *, 9> &addr) { SmallVector<Value *, 9> Elts; Elts.push_back(GetTagConstant(Tag)); Elts.push_back(Context.getNode()); Elts.push_back(MDString::get(VMContext, Name)); Elts.push_back(CompileUnit.getNode()); Elts.push_back(ConstantInt::get(Type::getInt32Ty(VMContext), LineNo)); Elts.push_back(Type.getNode()); Elts.insert(Elts.end(), addr.begin(), addr.end()); return DIVariable(MDNode::get(VMContext, &Elts[0], 6+addr.size())); }
std::string GCOVProfiler::mangleName(DICompileUnit CU, const char *NewStem) { if (NamedMDNode *GCov = M->getNamedMetadata("llvm.gcov")) { for (int i = 0, e = GCov->getNumOperands(); i != e; ++i) { MDNode *N = GCov->getOperand(i); if (N->getNumOperands() != 2) continue; MDString *GCovFile = dyn_cast<MDString>(N->getOperand(0)); MDNode *CompileUnit = dyn_cast<MDNode>(N->getOperand(1)); if (!GCovFile || !CompileUnit) continue; if (CompileUnit == CU) { SmallString<128> Filename = GCovFile->getString(); sys::path::replace_extension(Filename, NewStem); return Filename.str(); } } } SmallString<128> Filename = CU.getFilename(); sys::path::replace_extension(Filename, NewStem); return sys::path::filename(Filename.str()); }
/// CreateBasicType - Create a basic type like int, float, etc. DIBasicType DIFactory::CreateBasicTypeEx(DIDescriptor Context, const char * Name, DICompileUnit CompileUnit, unsigned LineNumber, Constant *SizeInBits, Constant *AlignInBits, Constant *OffsetInBits, unsigned Flags, unsigned Encoding) { Value *Elts[] = { GetTagConstant(dwarf::DW_TAG_base_type), Context.getNode(), MDString::get(VMContext, Name), CompileUnit.getNode(), ConstantInt::get(Type::getInt32Ty(VMContext), LineNumber), SizeInBits, AlignInBits, OffsetInBits, ConstantInt::get(Type::getInt32Ty(VMContext), Flags), ConstantInt::get(Type::getInt32Ty(VMContext), Encoding) }; return DIBasicType(MDNode::get(VMContext, &Elts[0], 10)); }
/// CreateSubprogram - Create a new descriptor for the specified subprogram. /// See comments in DISubprogram for descriptions of these fields. This /// method does not unique the generated descriptors. DISubprogram DIFactory::CreateSubprogram(DIDescriptor Context, const char * Name, const char * DisplayName, const char * LinkageName, DICompileUnit CompileUnit, unsigned LineNo, DIType Type, bool isLocalToUnit, bool isDefinition) { Value *Elts[] = { GetTagConstant(dwarf::DW_TAG_subprogram), llvm::Constant::getNullValue(Type::getInt32Ty(VMContext)), Context.getNode(), MDString::get(VMContext, Name), MDString::get(VMContext, DisplayName), MDString::get(VMContext, LinkageName), CompileUnit.getNode(), ConstantInt::get(Type::getInt32Ty(VMContext), LineNo), Type.getNode(), ConstantInt::get(Type::getInt1Ty(VMContext), isLocalToUnit), ConstantInt::get(Type::getInt1Ty(VMContext), isDefinition) }; return DISubprogram(MDNode::get(VMContext, &Elts[0], 11)); }
/// CreateDerivedType - Create a derived type like const qualified type, /// pointer, typedef, etc. DIDerivedType DIFactory::CreateDerivedTypeEx(unsigned Tag, DIDescriptor Context, const char * Name, DICompileUnit CompileUnit, unsigned LineNumber, Constant *SizeInBits, Constant *AlignInBits, Constant *OffsetInBits, unsigned Flags, DIType DerivedFrom) { Value *Elts[] = { GetTagConstant(Tag), Context.getNode(), MDString::get(VMContext, Name), CompileUnit.getNode(), ConstantInt::get(Type::getInt32Ty(VMContext), LineNumber), SizeInBits, AlignInBits, OffsetInBits, ConstantInt::get(Type::getInt32Ty(VMContext), Flags), DerivedFrom.getNode(), }; return DIDerivedType(MDNode::get(VMContext, &Elts[0], 10)); }
void DIEItem::ShowCompileUnit(DetailsView* detailsView, DICompileUnit cu) { detailsView->Add(_("CompileUnit"), toWxStr(cu.getDirectory()) + _("/") + toWxStr(cu.getFilename())); }