[cfe-commits] r51553 - in /cfe/trunk: include/clang/AST/Type.h lib/CodeGen/CGDebugInfo.cpp lib/CodeGen/CGDebugInfo.h lib/CodeGen/CGStmt.cpp lib/CodeGen/CodeGenFunction.cpp

Sanjiv Gupta sanjiv.gupta at microchip.com
Sat May 24 22:15:42 PDT 2008


Author: sgupta
Date: Sun May 25 00:15:42 2008
New Revision: 51553

URL: http://llvm.org/viewvc/llvm-project?rev=51553&view=rev
Log:
Generate subprogram debug info with -g.
Also take care of freeing memory at the right places.

Modified:
    cfe/trunk/include/clang/AST/Type.h
    cfe/trunk/lib/CodeGen/CGDebugInfo.cpp
    cfe/trunk/lib/CodeGen/CGDebugInfo.h
    cfe/trunk/lib/CodeGen/CGStmt.cpp
    cfe/trunk/lib/CodeGen/CodeGenFunction.cpp

Modified: cfe/trunk/include/clang/AST/Type.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/Type.h?rev=51553&r1=51552&r2=51553&view=diff

==============================================================================
--- cfe/trunk/include/clang/AST/Type.h (original)
+++ cfe/trunk/include/clang/AST/Type.h Sun May 25 00:15:42 2008
@@ -133,6 +133,10 @@
   void addVolatile() { ThePtr |= Volatile; }
   void addRestrict() { ThePtr |= Restrict; }
 
+  void removeConst()    { ThePtr &= ~Const; }
+  void removeVolatile() { ThePtr &= ~Volatile; }
+  void removeRestrict() { ThePtr &= ~Restrict; }
+
   QualType getQualifiedType(unsigned TQs) const {
     return QualType(getTypePtr(), TQs);
   }

Modified: cfe/trunk/lib/CodeGen/CGDebugInfo.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CGDebugInfo.cpp?rev=51553&r1=51552&r2=51553&view=diff

==============================================================================
--- cfe/trunk/lib/CodeGen/CGDebugInfo.cpp (original)
+++ cfe/trunk/lib/CodeGen/CGDebugInfo.cpp Sun May 25 00:15:42 2008
@@ -13,20 +13,20 @@
 
 #include "CGDebugInfo.h"
 #include "CodeGenModule.h"
+#include "clang/AST/ASTContext.h"
+#include "clang/Basic/SourceManager.h"
+#include "clang/Basic/FileManager.h"
 #include "llvm/Constants.h"
 #include "llvm/DerivedTypes.h"
 #include "llvm/Instructions.h"
 #include "llvm/Intrinsics.h"
 #include "llvm/Module.h"
-#include "llvm/Support/Dwarf.h"
-#include "llvm/Support/IRBuilder.h"
-#include "llvm/Target/TargetMachine.h"
 #include "llvm/ADT/StringExtras.h"
 #include "llvm/ADT/SmallVector.h"
 #include "llvm/CodeGen/MachineModuleInfo.h"
-#include "clang/Basic/SourceManager.h"
-#include "clang/Basic/FileManager.h"
-#include "clang/AST/ASTContext.h"
+#include "llvm/Support/Dwarf.h"
+#include "llvm/Support/IRBuilder.h"
+#include "llvm/Target/TargetMachine.h"
 using namespace clang;
 using namespace clang::CodeGen;
 
@@ -35,13 +35,16 @@
 , CurLoc()
 , PrevLoc()
 , CompileUnitCache()
+, TypeCache()
 , StopPointFn(NULL)
-, CompileUnitAnchor(NULL)
-, SubProgramAnchor(NULL)
+, FuncStartFn(NULL)
+, DeclareFn(NULL)
 , RegionStartFn(NULL)
 , RegionEndFn(NULL)
-, FuncStartFn(NULL)
-, CurFuncDesc(NULL)
+, CompileUnitAnchor(NULL)
+, SubprogramAnchor(NULL)
+, RegionStack()
+, Subprogram(NULL)
 {
   SR = new llvm::DISerializer();
   SR->setModule (&M->getModule());
@@ -50,19 +53,28 @@
 CGDebugInfo::~CGDebugInfo()
 {
   delete SR;
-  // Clean up allocated debug info; we can't do this until after the
-  // serializer is destroyed because it caches pointers to
-  // the debug info
+
+  // Free CompileUnitCache.
+  for (std::map<unsigned, llvm::CompileUnitDesc *>::iterator I 
+       = CompileUnitCache.begin(); I != CompileUnitCache.end(); ++I) {
+    delete I->second;
+  }
+  CompileUnitCache.clear();
+
+  // Free TypeCache.
+  for (std::map<void *, llvm::TypeDesc *>::iterator I 
+       = TypeCache.begin(); I != TypeCache.end(); ++I) {
+    delete I->second;
+  }
+  TypeCache.clear();
+
+  for (std::vector<llvm::DebugInfoDesc *>::iterator I 
+       = RegionStack.begin(); I != RegionStack.end(); ++I) {
+    delete *I;
+  }
+  
   delete CompileUnitAnchor;
-  delete SubProgramAnchor;
-  // Clean up compile unit descriptions
-  std::map<unsigned, llvm::CompileUnitDesc *>::iterator MI;
-  for (MI = CompileUnitCache.begin(); MI != CompileUnitCache.end(); ++MI)
-    delete MI->second;
-  // Clean up misc allocations
-  std::vector<llvm::DebugInfoDesc*>::iterator VI;
-  for (VI = DebugAllocationList.begin(); VI != DebugAllocationList.end(); ++VI)
-    delete *VI;
+  delete SubprogramAnchor;
 }
 
 
@@ -73,6 +85,12 @@
                                         SR->getEmptyStructPtrType());
 }
 
+/// getValueFor - Return a llvm representation for a given debug information
+/// descriptor.
+llvm::Value *CGDebugInfo::getValueFor(llvm::DebugInfoDesc *DD) {
+  return SR->Serialize(DD);
+}
+
 /// getOrCreateCompileUnit - Get the compile unit from the cache or create a new
 /// one if necessary.
 llvm::CompileUnitDesc 
@@ -123,10 +141,313 @@
 }
 
 
+llvm::TypeDesc *
+CGDebugInfo::getOrCreateCVRType(QualType type, llvm::CompileUnitDesc *Unit)
+{
+  // We will create a Derived type.
+  llvm::DerivedTypeDesc *DTy = NULL;
+  llvm::TypeDesc *FromTy = NULL;
+
+  if (type.isConstQualified()) {
+    DTy = new llvm::DerivedTypeDesc(llvm::dwarf::DW_TAG_const_type);
+    type.removeConst(); 
+    FromTy = getOrCreateType(type, Unit);
+  } else if (type.isVolatileQualified()) {
+    DTy = new llvm::DerivedTypeDesc(llvm::dwarf::DW_TAG_volatile_type);
+    type.removeVolatile(); 
+    FromTy = getOrCreateType(type, Unit);
+  } else if (type.isRestrictQualified()) {
+    DTy = new llvm::DerivedTypeDesc(llvm::dwarf::DW_TAG_restrict_type);
+    type.removeRestrict(); 
+    FromTy = getOrCreateType(type, Unit);
+  }
+
+  // No need to fill in the Name, Line, Size, Alignment, Offset in case of        // CVR derived types.
+  DTy->setContext(Unit);
+  DTy->setFromType(FromTy);
+
+  return DTy;
+}
+
+   
+/// getOrCreateType - Get the Basic type from the cache or create a new
+/// one if necessary.
+llvm::TypeDesc *
+CGDebugInfo::getOrCreateBuiltinType(QualType type, llvm::CompileUnitDesc *Unit)
+{
+  assert (type->getTypeClass() == Type::Builtin);
+
+  const BuiltinType *BT = type->getAsBuiltinType(); 
+
+  unsigned Encoding = 0;
+  switch (BT->getKind())
+  {
+    case BuiltinType::Void:
+      return NULL;
+    case BuiltinType::UChar:
+    case BuiltinType::Char_U:
+      Encoding = llvm::dwarf::DW_ATE_unsigned_char;
+      break;
+    case BuiltinType::Char_S:
+    case BuiltinType::SChar:
+      Encoding = llvm::dwarf::DW_ATE_signed_char;
+      break;
+    case BuiltinType::UShort:
+    case BuiltinType::UInt:
+    case BuiltinType::ULong:
+    case BuiltinType::ULongLong:
+      Encoding = llvm::dwarf::DW_ATE_unsigned;
+      break;
+    case BuiltinType::Short:
+    case BuiltinType::Int:
+    case BuiltinType::Long:
+    case BuiltinType::LongLong:
+      Encoding = llvm::dwarf::DW_ATE_signed;
+      break;
+    case BuiltinType::Bool:
+      Encoding = llvm::dwarf::DW_ATE_boolean;
+      break;
+    case BuiltinType::Float:
+    case BuiltinType::Double:
+      Encoding = llvm::dwarf::DW_ATE_float;
+      break;
+    default:
+      Encoding = llvm::dwarf::DW_ATE_signed;
+      break;
+  } 
+
+  // Ty will have contain the resulting type.
+  llvm::BasicTypeDesc *BTy = new llvm::BasicTypeDesc();
+
+  // Get the name and location early to assist debugging.
+  const char *TyName = BT->getName();
+
+  // Bit size, align and offset of the type.
+  uint64_t Size = M->getContext().getTypeSize(type);
+  uint64_t Align = M->getContext().getTypeAlign(type);
+  uint64_t Offset = 0;
+                                                  
+  // If the type is defined, fill in the details.
+  if (BTy) {
+    BTy->setContext(Unit);
+    BTy->setName(TyName);
+    BTy->setSize(Size);
+    BTy->setAlign(Align);
+    BTy->setOffset(Offset);
+    BTy->setEncoding(Encoding);
+  }
+                                                                                
+  return BTy;
+}
+
+llvm::TypeDesc *
+CGDebugInfo::getOrCreatePointerType(QualType type, llvm::CompileUnitDesc *Unit)
+{
+  // type*
+  llvm::DerivedTypeDesc *DTy =
+    new llvm::DerivedTypeDesc(llvm::dwarf::DW_TAG_pointer_type);
+
+  // Handle the derived type.
+  const PointerType *PTRT = type->getAsPointerType();
+  llvm::TypeDesc *FromTy = getOrCreateType(PTRT->getPointeeType(), Unit);
+ 
+  // Get the name and location early to assist debugging.
+  SourceManager &SM = M->getContext().getSourceManager();
+  uint64_t Line = SM.getLogicalLineNumber(CurLoc);
+                                                                               
+  // Bit size, align and offset of the type.
+  uint64_t Size = M->getContext().getTypeSize(type);
+  uint64_t Align = M->getContext().getTypeAlign(type);
+  uint64_t Offset = 0;
+                                                                               
+  // If the type is defined, fill in the details.
+  if (DTy) {
+    DTy->setContext(Unit);
+    DTy->setLine(Line);
+    DTy->setSize(Size);
+    DTy->setAlign(Align);
+    DTy->setOffset(Offset);
+    DTy->setFromType(FromTy);
+  }
+
+  return DTy;
+}
+
+llvm::TypeDesc *
+CGDebugInfo::getOrCreateTypedefType(QualType type, llvm::CompileUnitDesc *Unit)
+{
+  // typedefs are derived from some other type.
+  llvm::DerivedTypeDesc *DTy =
+    new llvm::DerivedTypeDesc(llvm::dwarf::DW_TAG_typedef);
+
+  // Handle derived type.
+  const TypedefType *TDT = type->getAsTypedefType();
+  llvm::TypeDesc *FromTy = getOrCreateType(TDT->LookThroughTypedefs(),
+                                               Unit);
+
+  // Get the name and location early to assist debugging.
+  const char *TyName = TDT->getDecl()->getName();
+  SourceManager &SM = M->getContext().getSourceManager();
+  uint64_t Line = SM.getLogicalLineNumber(TDT->getDecl()->getLocation());
+                                                                                
+  // If the type is defined, fill in the details.
+  if (DTy) {
+    DTy->setContext(Unit);
+    DTy->setFile(getOrCreateCompileUnit(TDT->getDecl()->getLocation()));
+    DTy->setLine(Line);
+    DTy->setName(TyName);
+    DTy->setFromType(FromTy);
+  }
+
+  return DTy;
+}
+
+llvm::TypeDesc *
+CGDebugInfo::getOrCreateFunctionType(QualType type, llvm::CompileUnitDesc *Unit)
+{
+  llvm::CompositeTypeDesc *SubrTy =
+    new llvm::CompositeTypeDesc(llvm::dwarf::DW_TAG_subroutine_type);
+
+  // Prepare to add the arguments for the subroutine.
+  std::vector<llvm::DebugInfoDesc *> &Elements = SubrTy->getElements();
+
+  // Get result type.
+  const FunctionType *FT = type->getAsFunctionType();
+  llvm::TypeDesc *ArgTy = getOrCreateType(FT->getResultType(), Unit);
+  if (ArgTy) Elements.push_back(ArgTy);
+
+  // Set up remainder of arguments.
+  if (type->getTypeClass() == Type::FunctionProto) {
+    const FunctionTypeProto *FTPro = dyn_cast<FunctionTypeProto>(type);
+    for (unsigned int i =0; i < FTPro->getNumArgs(); i++) {
+      QualType ParamType = FTPro->getArgType(i);
+      ArgTy = getOrCreateType(ParamType, Unit);
+      if (ArgTy) Elements.push_back(ArgTy);
+    }
+  }
+
+  // FIXME: set other fields file, line here.	
+  SubrTy->setContext(Unit);
+
+  return SubrTy;
+}
+
+
+  
+/// getOrCreateType - Get the type from the cache or create a new
+/// one if necessary.
+llvm::TypeDesc *
+CGDebugInfo::getOrCreateType(QualType type, llvm::CompileUnitDesc *Unit)
+{
+  if (type.isNull())
+    return NULL;
+
+  // Check to see if the compile unit already has created this type.
+  llvm::TypeDesc *&Slot = TypeCache[type.getAsOpaquePtr()];
+  if (Slot) return Slot;
+
+  // We need to check for the CVR qualifiers as the first thing.
+  if (type.getCVRQualifiers()) {
+    Slot = getOrCreateCVRType (type, Unit);
+    return Slot;
+  }
+
+  // Work out details of type.
+  switch(type->getTypeClass()) {
+    case Type::Complex:
+    case Type::Reference:
+    case Type::ConstantArray:
+    case Type::VariableArray:
+    case Type::IncompleteArray:
+    case Type::Vector:
+    case Type::ExtVector:
+    case Type::Tagged:
+    case Type::ASQual:
+    case Type::ObjCInterface:
+    case Type::ObjCQualifiedInterface:
+    case Type::ObjCQualifiedId:
+    case Type::TypeOfExp:
+    case Type::TypeOfTyp:
+    default:
+    {
+      assert (0 && "Unsupported type");
+      return NULL;
+    }
+
+    case Type::TypeName:
+      Slot = getOrCreateTypedefType(type, Unit);
+      break;
+
+    case Type::FunctionProto:
+    case Type::FunctionNoProto:
+      Slot = getOrCreateFunctionType(type, Unit);
+      break;
+
+    case Type::Builtin:
+      Slot = getOrCreateBuiltinType(type, Unit);
+      break;
+
+    case Type::Pointer:
+      Slot = getOrCreatePointerType(type, Unit);
+      break;
+  }
+
+  return Slot;
+}
+
+/// EmitFunctionStart - Constructs the debug code for entering a function -
+/// "llvm.dbg.func.start.".
+void CGDebugInfo::EmitFunctionStart(const FunctionDecl *FnDecl,
+                                    llvm::Function *Fn,
+                                    llvm::IRBuilder &Builder)
+{
+  // Create subprogram descriptor.
+  Subprogram = new llvm::SubprogramDesc();
+
+  // Make sure we have an anchor.
+  if (!SubprogramAnchor) {
+    SubprogramAnchor = new llvm::AnchorDesc(Subprogram);
+  }
+
+  // Get name information.
+  Subprogram->setName(FnDecl->getName());
+  Subprogram->setFullName(FnDecl->getName());
+
+  // Gather location information.
+  llvm::CompileUnitDesc *Unit = getOrCreateCompileUnit(CurLoc);
+  SourceManager &SM = M->getContext().getSourceManager();
+  uint64_t Loc = SM.getLogicalLineNumber(CurLoc);
+
+  // Get Function Type.
+  QualType type = FnDecl->getResultType();
+  llvm::TypeDesc *SPTy = getOrCreateType(type, Unit);
+
+  Subprogram->setAnchor(SubprogramAnchor);
+  Subprogram->setContext(Unit);
+  Subprogram->setFile(Unit);
+  Subprogram->setLine(Loc);
+  Subprogram->setType(SPTy);
+  Subprogram->setIsStatic(Fn->hasInternalLinkage());
+  Subprogram->setIsDefinition(true);
+
+  // Lazily construct llvm.dbg.func.start.
+  if (!FuncStartFn)
+    FuncStartFn = llvm::Intrinsic::getDeclaration(&M->getModule(),
+                    llvm::Intrinsic::dbg_func_start);
+
+  // Call llvm.dbg.func.start which also implicitly calls llvm.dbg.stoppoint.
+  Builder.CreateCall(FuncStartFn, getCastValueFor(Subprogram), "");
+
+  // Push function on region stack.
+  RegionStack.push_back(Subprogram);
+}
+
+
 void 
-CGDebugInfo::EmitStopPoint(llvm::Function *Fn, llvm::IRBuilder &Builder) {
+CGDebugInfo::EmitStopPoint(llvm::Function *Fn, llvm::IRBuilder &Builder) 
+{
   if (CurLoc.isInvalid() || CurLoc.isMacroID()) return;
-
+  
   // Don't bother if things are the same as last time.
   SourceManager &SM = M->getContext().getSourceManager();
   if (CurLoc == PrevLoc 
@@ -157,35 +478,25 @@
 
 /// EmitRegionStart- Constructs the debug code for entering a declarative
 /// region - "llvm.dbg.region.start.".
-void CGDebugInfo::EmitFunctionStart(llvm::Function *Fn, llvm::IRBuilder &Builder) 
+void CGDebugInfo::EmitRegionStart(llvm::Function *Fn, llvm::IRBuilder &Builder) 
 {
-  // Get the appropriate compile unit.
-  llvm::CompileUnitDesc *Unit = getOrCreateCompileUnit(CurLoc);
+  llvm::BlockDesc *Block = new llvm::BlockDesc();
+  if (RegionStack.size() > 0)
+    Block->setContext(RegionStack.back());
+  RegionStack.push_back(Block);
+
+  // Lazily construct llvm.dbg.region.start function.
+  if (!RegionStartFn)
+    RegionStartFn = llvm::Intrinsic::getDeclaration(&M->getModule(), 
+                                llvm::Intrinsic::dbg_region_start);
 
-  llvm::SubprogramDesc* Block = new llvm::SubprogramDesc;
-  DebugAllocationList.push_back(Block);
-  Block->setFile(Unit);
-  Block->setContext(Unit);
-  if (!SubProgramAnchor) {
-    SubProgramAnchor = new llvm::AnchorDesc(Block);
-    SR->Serialize(SubProgramAnchor);
-  }
-  Block->setAnchor(SubProgramAnchor);
-  Block->setName(Fn->getName());
-  Block->setFullName(Fn->getName());
-  Block->setIsDefinition(true);
-  SourceManager &SM = M->getContext().getSourceManager();
-  Block->setLine(SM.getLogicalLineNumber(CurLoc));
-  CurFuncDesc = getCastValueFor(Block);
-  if (!FuncStartFn)
-    FuncStartFn = llvm::Intrinsic::getDeclaration(&M->getModule(),
-                                llvm::Intrinsic::dbg_func_start);
-  Builder.CreateCall(FuncStartFn, CurFuncDesc);
+  // Call llvm.dbg.func.start.
+  Builder.CreateCall(RegionStartFn, getCastValueFor(Block), "");
 }
 
 /// EmitRegionEnd - Constructs the debug code for exiting a declarative
 /// region - "llvm.dbg.region.end."
-void CGDebugInfo::EmitFunctionEnd(llvm::Function *Fn, llvm::IRBuilder &Builder) 
+void CGDebugInfo::EmitRegionEnd(llvm::Function *Fn, llvm::IRBuilder &Builder) 
 {
   // Lazily construct llvm.dbg.region.end function.
   if (!RegionEndFn)
@@ -196,6 +507,8 @@
   EmitStopPoint(Fn, Builder);
   
   // Call llvm.dbg.func.end.
-  Builder.CreateCall(RegionEndFn, CurFuncDesc, "");
+  llvm::DebugInfoDesc *DID = RegionStack.back();
+  Builder.CreateCall(RegionEndFn, getCastValueFor(DID), "");
+  RegionStack.pop_back();
 }
 

Modified: cfe/trunk/lib/CodeGen/CGDebugInfo.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CGDebugInfo.h?rev=51553&r1=51552&r2=51553&view=diff

==============================================================================
--- cfe/trunk/lib/CodeGen/CGDebugInfo.h (original)
+++ cfe/trunk/lib/CodeGen/CGDebugInfo.h Sun May 25 00:15:42 2008
@@ -14,6 +14,7 @@
 #ifndef CLANG_CODEGEN_CGDEBUGINFO_H
 #define CLANG_CODEGEN_CGDEBUGINFO_H
 
+#include "clang/AST/Type.h"
 #include "clang/Basic/SourceLocation.h"
 #include <map>
 #include <vector>
@@ -28,14 +29,18 @@
   class AnchorDesc;
   class DebugInfoDesc;
   class Value;
+  class TypeDesc;
+  class SubprogramDesc;
 }
 
 namespace clang {
+  class FunctionDecl;
 namespace CodeGen {
   class CodeGenModule;
 
-/// DebugInfo - This class gathers all debug information during compilation and
-/// is responsible for emitting to llvm globals or pass directly to the backend.
+/// CGDebugInfo - This class gathers all debug information during compilation 
+/// and is responsible for emitting to llvm globals or pass directly to 
+/// the backend.
 class CGDebugInfo {
 private:
   CodeGenModule *M;
@@ -45,41 +50,70 @@
 
   /// CompileUnitCache - Cache of previously constructed CompileUnits.
   std::map<unsigned, llvm::CompileUnitDesc *> CompileUnitCache;
-  std::vector<llvm::DebugInfoDesc*> DebugAllocationList;
+
+  /// TypeCache - Cache of previously constructed Types.
+  std::map<void *, llvm::TypeDesc *> TypeCache;
   
   llvm::Function *StopPointFn;
-  llvm::AnchorDesc *CompileUnitAnchor;
-  llvm::AnchorDesc *SubProgramAnchor;
+  llvm::Function *FuncStartFn;
+  llvm::Function *DeclareFn;
   llvm::Function *RegionStartFn;
   llvm::Function *RegionEndFn;
-  llvm::Function *FuncStartFn;
-  llvm::Value *CurFuncDesc;  
-
-  /// getOrCreateCompileUnit - Get the compile unit from the cache or create a
-  /// new one if necessary.
-  llvm::CompileUnitDesc *getOrCreateCompileUnit(SourceLocation loc);
-
-  /// getCastValueFor - Return a llvm representation for a given debug
-  /// information descriptor cast to an empty struct pointer.
-  llvm::Value *getCastValueFor(llvm::DebugInfoDesc *DD);
+  llvm::AnchorDesc *CompileUnitAnchor;
+  llvm::AnchorDesc *SubprogramAnchor;
+  std::vector<llvm::DebugInfoDesc *> RegionStack;  
+  llvm::SubprogramDesc *Subprogram;
+
+  /// Helper functions for getOrCreateType.
+  llvm::TypeDesc *getOrCreateCVRType(QualType type, 
+                                     llvm::CompileUnitDesc *unit);
+  llvm::TypeDesc *getOrCreateBuiltinType(QualType type, 
+                                     llvm::CompileUnitDesc *unit);
+  llvm::TypeDesc *getOrCreateTypedefType(QualType type, 
+                                     llvm::CompileUnitDesc *unit);
+  llvm::TypeDesc *getOrCreatePointerType(QualType type, 
+                                     llvm::CompileUnitDesc *unit);
+  llvm::TypeDesc *getOrCreateFunctionType(QualType type, 
+                                     llvm::CompileUnitDesc *unit);
 
 public:
   CGDebugInfo(CodeGenModule *m);
   ~CGDebugInfo();
 
-  void setLocation(SourceLocation loc) { CurLoc = loc; };
+  void setLocation(SourceLocation loc) { CurLoc = loc; }
 
   /// EmitStopPoint - Emit a call to llvm.dbg.stoppoint to indicate a change of
   /// source line.
   void EmitStopPoint(llvm::Function *Fn, llvm::IRBuilder &Builder);
+
+  /// EmitFunctionStart - Emit a call to llvm.dbg.function.start to indicate
+  /// start of a new function
+  void EmitFunctionStart(const FunctionDecl *FnDecl, llvm::Function *Fn,
+                         llvm::IRBuilder &Builder);
   
-  /// EmitFunctionStart - Emit a call to llvm.dbg.func.start to indicate start
+  /// EmitRegionStart - Emit a call to llvm.dbg.region.start to indicate start
   /// of a new block.  
-  void EmitFunctionStart(llvm::Function *Fn, llvm::IRBuilder &Builder);
+  void EmitRegionStart(llvm::Function *Fn, llvm::IRBuilder &Builder);
   
-  /// EmitFunctionEnd - Emit call to llvm.dbg.region.end to indicate end of a 
+  /// EmitRegionEnd - Emit call to llvm.dbg.region.end to indicate end of a 
   /// block.
-  void EmitFunctionEnd(llvm::Function *Fn, llvm::IRBuilder &Builder);
+  void EmitRegionEnd(llvm::Function *Fn, llvm::IRBuilder &Builder);
+ 
+  /// getOrCreateCompileUnit - Get the compile unit from the cache or create a
+  /// new one if necessary.
+  llvm::CompileUnitDesc *getOrCreateCompileUnit(SourceLocation loc);
+
+  /// getOrCreateType - Get the type from the cache or create a new type if
+  /// necessary.
+  llvm::TypeDesc *getOrCreateType(QualType type, llvm::CompileUnitDesc *unit);
+
+  /// getCastValueFor - Return a llvm representation for a given debug
+  /// information descriptor cast to an empty struct pointer.
+  llvm::Value *getCastValueFor(llvm::DebugInfoDesc *DD);
+
+  /// getValueFor - Return a llvm representation for a given debug information
+  /// descriptor.
+  llvm::Value *getValueFor(llvm::DebugInfoDesc *DD);
 };
 } // namespace CodeGen
 } // namespace clang

Modified: cfe/trunk/lib/CodeGen/CGStmt.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CGStmt.cpp?rev=51553&r1=51552&r2=51553&view=diff

==============================================================================
--- cfe/trunk/lib/CodeGen/CGStmt.cpp (original)
+++ cfe/trunk/lib/CodeGen/CGStmt.cpp Sun May 25 00:15:42 2008
@@ -88,10 +88,25 @@
   // FIXME: handle vla's etc.
   if (S.body_empty() || !isa<Expr>(S.body_back())) GetLast = false;
 
+  CGDebugInfo *DI = CGM.getDebugInfo();
+  if (DI) {
+    if (S.getLBracLoc().isValid()) {
+      DI->setLocation(S.getLBracLoc());
+    }
+    DI->EmitRegionStart(CurFn, Builder);
+  }
+
   for (CompoundStmt::const_body_iterator I = S.body_begin(),
        E = S.body_end()-GetLast; I != E; ++I)
     EmitStmt(*I);
 
+  if (DI) {
+    if (S.getRBracLoc().isValid()) {
+      DI->setLocation(S.getRBracLoc());
+    }
+    DI->EmitRegionEnd(CurFn, Builder);
+  }
+
   if (!GetLast)
     return RValue::get(0);
   
@@ -368,15 +383,6 @@
     EmitAggExpr(RV, SRetPtr, false);
   }
 
-  CGDebugInfo *DI = CGM.getDebugInfo();
-  if (DI) {
-    CompoundStmt* body = cast<CompoundStmt>(CurFuncDecl->getBody());
-    if (body->getRBracLoc().isValid()) {
-      DI->setLocation(body->getRBracLoc());
-    }
-    DI->EmitFunctionEnd(CurFn, Builder);
-  }
-
   if (RetValue) {
     Builder.CreateRet(RetValue);
   } else {

Modified: cfe/trunk/lib/CodeGen/CodeGenFunction.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CodeGenFunction.cpp?rev=51553&r1=51552&r2=51553&view=diff

==============================================================================
--- cfe/trunk/lib/CodeGen/CodeGenFunction.cpp (original)
+++ cfe/trunk/lib/CodeGen/CodeGenFunction.cpp Sun May 25 00:15:42 2008
@@ -205,7 +205,7 @@
     if (body->getLBracLoc().isValid()) {
       DI->setLocation(body->getLBracLoc());
     }
-    DI->EmitFunctionStart(CurFn, Builder);
+    DI->EmitFunctionStart(FD, CurFn, Builder);
   }
 
   // Emit allocs for param decls.  Give the LLVM Argument nodes names.
@@ -225,21 +225,20 @@
   // Emit the function body.
   EmitStmt(FD->getBody());
   
+  if (DI) {
+    CompoundStmt* body = cast<CompoundStmt>(CurFuncDecl->getBody());
+    if (body->getRBracLoc().isValid()) {
+      DI->setLocation(body->getRBracLoc());
+    }
+    DI->EmitRegionEnd(CurFn, Builder);
+  }
+
   // Emit a return for code that falls off the end. If insert point
   // is a dummy block with no predecessors then remove the block itself.
   llvm::BasicBlock *BB = Builder.GetInsertBlock();
   if (isDummyBlock(BB))
     BB->eraseFromParent();
   else {
-    CGDebugInfo *DI = CGM.getDebugInfo();
-    if (DI) {
-      CompoundStmt* body = cast<CompoundStmt>(CurFuncDecl->getBody());
-      if (body->getRBracLoc().isValid()) {
-        DI->setLocation(body->getRBracLoc());
-      }
-      DI->EmitFunctionEnd(CurFn, Builder);
-    }
-
     // FIXME: if this is C++ main, this should return 0.
     if (CurFn->getReturnType() == llvm::Type::VoidTy)
       Builder.CreateRetVoid();





More information about the cfe-commits mailing list