Added basic support for typedefs.


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@26339 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/include/llvm/CodeGen/MachineDebugInfo.h b/include/llvm/CodeGen/MachineDebugInfo.h
index c51b3ea..f2119c2 100644
--- a/include/llvm/CodeGen/MachineDebugInfo.h
+++ b/include/llvm/CodeGen/MachineDebugInfo.h
@@ -62,7 +62,8 @@
   DI_TAG_compile_unit,
   DI_TAG_global_variable,
   DI_TAG_subprogram,
-  DI_TAG_basictype
+  DI_TAG_basictype,
+  DI_TAG_typedef
 };
 
 //===----------------------------------------------------------------------===//
@@ -342,6 +343,42 @@
 #endif
 };
 
+
+//===----------------------------------------------------------------------===//
+/// TypedefDesc - This class packages debug information associated with a
+/// derived typedef.
+class TypedefDesc : public TypeDesc {
+private:
+  TypeDesc *FromType;                   // Type derived from.
+  CompileUnitDesc *File;                // Declared compile unit.
+  int Line;                             // Declared line#.
+
+public:
+  TypedefDesc();
+  
+  // Accessors
+  TypeDesc *getFromType()                    const { return FromType; }
+  CompileUnitDesc *getFile()                 const { return File; }
+  int getLine()                              const { return Line; }
+  void setFromType(TypeDesc *F)                    { FromType = F; }
+  void setFile(CompileUnitDesc *U)                 { File = U; }
+  void setLine(int L)                              { Line = L; }
+
+  // Implement isa/cast/dyncast.
+  static bool classof(const TypedefDesc *)  { return true; }
+  static bool classof(const DebugInfoDesc *D) {
+    return D->getTag() == DI_TAG_typedef;
+  }
+  
+  /// ApplyToFields - Target the visitor to the fields of the  TypedefDesc.
+  ///
+  virtual void ApplyToFields(DIVisitor *Visitor);
+
+#ifndef NDEBUG
+  virtual void dump();
+#endif
+};
+
 //===----------------------------------------------------------------------===//
 /// GlobalDesc - This class is the base descriptor for global functions and
 /// variables.
@@ -712,7 +749,7 @@
                              getGlobalVariablesUsing(M, Desc.getAnchorString());
     std::vector<T *> AnchoredDescs;
     for (unsigned i = 0, N = Globals.size(); i < N; ++i) {
-      AnchoredDescs.push_back(static_cast<T *>(DR.Deserialize(Globals[i])));
+      AnchoredDescs.push_back(cast<T>(DR.Deserialize(Globals[i])));
     }
 
     return AnchoredDescs;
diff --git a/lib/CodeGen/DwarfWriter.cpp b/lib/CodeGen/DwarfWriter.cpp
index 2ead4ce..9512f54 100644
--- a/lib/CodeGen/DwarfWriter.cpp
+++ b/lib/CodeGen/DwarfWriter.cpp
@@ -1244,23 +1244,34 @@
   // FIXME - handle larger sizes.
   unsigned Size = TyDesc->getSize() >> 3;
   
-  // Determine how to handle.
-  if (BasicTypeDesc *BasicTyDesc = dyn_cast<BasicTypeDesc>(TyDesc)) {
-    unsigned Encoding = BasicTyDesc->getEncoding();
+  DIE *Ty = NULL;
   
-    DIE *Ty = new DIE(DW_TAG_base_type);
-    if (!Name.empty())  Ty->AddString(DW_AT_name, DW_FORM_string, Name);
-
-    Ty->AddUInt  (DW_AT_byte_size, 0,              Size);
-    Ty->AddUInt  (DW_AT_encoding,  DW_FORM_data1,  Encoding);
+  // Determine how to handle.
+  if (BasicTypeDesc *BasicTy = dyn_cast<BasicTypeDesc>(TyDesc)) {
+    Slot = Ty = new DIE(DW_TAG_base_type);
+    unsigned Encoding = BasicTy->getEncoding();
+    Ty->AddUInt  (DW_AT_encoding,  DW_FORM_data1, Encoding);
+  } else if (TypedefDesc *TypedefTy = dyn_cast<TypedefDesc>(TyDesc)) {
+    Slot = Ty = new DIE(DW_TAG_typedef);
+    TypeDesc *FromTy = TypedefTy->getFromType();
+    DIE *FromTyDie = NewType(Unit, FromTy);
+    CompileUnitDesc *File = TypedefTy->getFile();
+    unsigned FileID = DebugInfo->RecordSource(File);
+    int Line = TypedefTy->getLine();
     
-    Slot = Ty;
-  } else {
-    assert(0 && "Type not supported yet");
+    Ty->AddDIEntry(DW_AT_type,      DW_FORM_ref4, FromTyDie);
+    Ty->AddUInt   (DW_AT_decl_file, 0,            FileID);
+    Ty->AddUInt   (DW_AT_decl_line, 0,            Line);
   }
+  
+  assert(Ty && "Type not supported yet");
  
+  // Add common information.
+  if (Size) Ty->AddUInt(DW_AT_byte_size, 0, Size);
+  if (!Name.empty()) Ty->AddString(DW_AT_name, DW_FORM_string, Name);
+
   // Add to context owner.
-  Unit->AddChild(Slot);
+  Unit->AddChild(Ty);
   
   return Slot;
 }
diff --git a/lib/CodeGen/MachineDebugInfo.cpp b/lib/CodeGen/MachineDebugInfo.cpp
index 44b71fa..1652881 100644
--- a/lib/CodeGen/MachineDebugInfo.cpp
+++ b/lib/CodeGen/MachineDebugInfo.cpp
@@ -430,6 +430,7 @@
   case DI_TAG_global_variable: return new GlobalVariableDesc();
   case DI_TAG_subprogram:      return new SubprogramDesc();
   case DI_TAG_basictype:       return new BasicTypeDesc();
+  case DI_TAG_typedef:         return new TypedefDesc();
   default: break;
   }
   return NULL;
@@ -561,8 +562,6 @@
 
 //===----------------------------------------------------------------------===//
 
-//===----------------------------------------------------------------------===//
-
 TypeDesc::TypeDesc(unsigned T)
 : DebugInfoDesc(T)
 , Context(NULL)
@@ -627,6 +626,37 @@
             << "Encoding(" << Encoding << ")\n";
 }
 #endif
+//===----------------------------------------------------------------------===//
+
+TypedefDesc::TypedefDesc()
+: TypeDesc(DI_TAG_typedef)
+, FromType(NULL)
+, File(NULL)
+, Line(0)
+{}
+
+/// ApplyToFields - Target the visitor to the fields of the  TypedefDesc.
+///
+void TypedefDesc::ApplyToFields(DIVisitor *Visitor) {
+  TypeDesc::ApplyToFields(Visitor);
+  
+  Visitor->Apply((DebugInfoDesc *&)FromType);
+  Visitor->Apply((DebugInfoDesc *&)File);
+  Visitor->Apply(Line);
+}
+
+#ifndef NDEBUG
+void TypedefDesc::dump() {
+  std::cerr << getDescString() << " "
+            << "Tag(" << getTag() << "), "
+            << "Context(" << getContext() << "), "
+            << "Name(\"" << getName() << "\"), "
+            << "Size(" << getSize() << "), "
+            << "FromType(" << FromType << "), "
+            << "File(" << File << "), "
+            << "Line(" << Line << ")\n";
+}
+#endif
 
 //===----------------------------------------------------------------------===//