<html><head><meta http-equiv="Content-Type" content="text/html charset=us-ascii"></head><body style="word-wrap: break-word; -webkit-nbsp-mode: space; -webkit-line-break: after-white-space;" class=""><br class=""><div><blockquote type="cite" class=""><div class="">On Jul 24, 2017, at 2:36 PM, David Blaikie <<a href="mailto:dblaikie@gmail.com" class="">dblaikie@gmail.com</a>> wrote:</div><br class="Apple-interchange-newline"><div class=""><div dir="ltr" class="">Why is this a special case for modules? (because the types appear in the weird special case/nested inside the DW_TAG_module?) I take it this is already done for other types?</div></div></blockquote><div><br class=""></div><div>DW_TAG_modules are special because they are anchored by a DW_TAG_imported_declaration, but we don't want their children to survive. The stripping of other unused types happens automatically by virtue of the "normal" dsymutil algorithm, where we DFS through the type hierarchy to mark all used types as kept. For ODR languages the change in shouldKeepDIE() would be enough. For non-ODR languages the DefinedInClangModule flag used to allow dsymutil to cut the DFS short and avoid marking the entire tree of DW_TAG_module as kept.</div><div><br class=""></div>-- adrian<br class=""><blockquote type="cite" class=""><div class=""><br class=""><div class="gmail_quote"><div dir="ltr" class="">On Thu, Jul 20, 2017 at 7:08 PM Adrian Prantl via llvm-commits <<a href="mailto:llvm-commits@lists.llvm.org" class="">llvm-commits@lists.llvm.org</a>> wrote:<br class=""></div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">Author: adrian<br class="">
Date: Thu Jul 20 19:07:33 2017<br class="">
New Revision: 308710<br class="">
<br class="">
URL: <a href="http://llvm.org/viewvc/llvm-project?rev=308710&view=rev" rel="noreferrer" target="_blank" class="">http://llvm.org/viewvc/llvm-project?rev=308710&view=rev</a><br class="">
Log:<br class="">
dsymutil: strip unused types from imported DW_TAG_modules<br class="">
<br class="">
This patch teaches dsymutil to strip types from the imported<br class="">
DW_TAG_module inside of an object file (not inside the PCM) if they<br class="">
can be resolved to the full definition inside the PCM. This reduces<br class="">
the size of the .dSYM from WebCore from <a href="http://webkit.org/" rel="noreferrer" target="_blank" class="">webkit.org</a> by almost 2/3.<br class="">
<br class="">
<<a href="rdar://problem/33047213" class="">rdar://problem/33047213</a>><br class="">
<br class="">
Added:<br class="">
    llvm/trunk/test/tools/dsymutil/Inputs/modules/2.o<br class="">
Modified:<br class="">
    llvm/trunk/test/tools/dsymutil/Inputs/modules/1.o<br class="">
    llvm/trunk/test/tools/dsymutil/X86/modules.m<br class="">
    llvm/trunk/tools/dsymutil/DwarfLinker.cpp<br class="">
<br class="">
Modified: llvm/trunk/test/tools/dsymutil/Inputs/modules/1.o<br class="">
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/test/tools/dsymutil/Inputs/modules/1.o?rev=308710&r1=308709&r2=308710&view=diff" rel="noreferrer" target="_blank" class="">http://llvm.org/viewvc/llvm-project/llvm/trunk/test/tools/dsymutil/Inputs/modules/1.o?rev=308710&r1=308709&r2=308710&view=diff</a><br class="">
==============================================================================<br class="">
Binary files llvm/trunk/test/tools/dsymutil/Inputs/modules/1.o (original) and llvm/trunk/test/tools/dsymutil/Inputs/modules/1.o Thu Jul 20 19:07:33 2017 differ<br class="">
<br class="">
Added: llvm/trunk/test/tools/dsymutil/Inputs/modules/2.o<br class="">
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/test/tools/dsymutil/Inputs/modules/2.o?rev=308710&view=auto" rel="noreferrer" target="_blank" class="">http://llvm.org/viewvc/llvm-project/llvm/trunk/test/tools/dsymutil/Inputs/modules/2.o?rev=308710&view=auto</a><br class="">
==============================================================================<br class="">
Binary files llvm/trunk/test/tools/dsymutil/Inputs/modules/2.o (added) and llvm/trunk/test/tools/dsymutil/Inputs/modules/2.o Thu Jul 20 19:07:33 2017 differ<br class="">
<br class="">
Modified: llvm/trunk/test/tools/dsymutil/X86/modules.m<br class="">
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/test/tools/dsymutil/X86/modules.m?rev=308710&r1=308709&r2=308710&view=diff" rel="noreferrer" target="_blank" class="">http://llvm.org/viewvc/llvm-project/llvm/trunk/test/tools/dsymutil/X86/modules.m?rev=308710&r1=308709&r2=308710&view=diff</a><br class="">
==============================================================================<br class="">
--- llvm/trunk/test/tools/dsymutil/X86/modules.m (original)<br class="">
+++ llvm/trunk/test/tools/dsymutil/X86/modules.m Thu Jul 20 19:07:33 2017<br class="">
@@ -11,9 +11,11 @@<br class="">
 EOF<br class="">
    clang -D BAR_H -E -o Bar.h modules.m<br class="">
    clang -D FOO_H -E -o Foo.h modules.m<br class="">
-   clang -cc1 -emit-obj -fmodules -fmodule-map-file=modules.modulemap \<br class="">
-     -fmodule-format=obj -g -dwarf-ext-refs -fmodules-cache-path=. \<br class="">
-     -fdisable-module-hash modules.m -o 1.o<br class="">
+   clang -D ODR_VIOLATION_C -E -o odr_violation.c modules.m<br class="">
+   clang -c -fmodules -fmodule-map-file=modules.modulemap \<br class="">
+     -g -gmodules -fmodules-cache-path=. \<br class="">
+     -Xclang -fdisable-module-hash modules.m -o 1.o<br class="">
+   clang -c -g odr_violation.c -o 2.o<br class="">
 */<br class="">
<br class="">
 // RUN: llvm-dsymutil -f -oso-prepend-path=%p/../Inputs/modules \<br class="">
@@ -57,7 +59,7 @@ struct PruneMeNot;<br class="">
 // CHECK: 0x0[[FOO:.*]]:  DW_TAG_module<br class="">
 // CHECK-NEXT:              DW_AT_name{{.*}}"Foo"<br class="">
 // CHECK-NOT:               DW_TAG<br class="">
-// CHECK:                   DW_TAG_typedef<br class="">
+// CHECK: 0x0[[BARTD:.*]]: DW_TAG_typedef<br class="">
 // CHECK-NOT:                 DW_TAG<br class="">
 // CHECK:                     DW_AT_type [DW_FORM_ref_addr] (0x{{0*}}[[BAR]])<br class="">
 // CHECK:                   DW_TAG_structure_type<br class="">
@@ -75,19 +77,25 @@ struct S {};<br class="">
 }<br class="">
 @end<br class="">
<br class="">
+#else<br class="">
+// ---------------------------------------------------------------------<br class="">
+#ifdef ODR_VIOLATION_C<br class="">
+// ---------------------------------------------------------------------<br class="">
+<br class="">
+struct Bar {<br class="">
+  int i;<br class="">
+};<br class="">
+typedef struct Bar Bar;<br class="">
+Bar odr_violation = { 42 };<br class="">
+<br class="">
 // ---------------------------------------------------------------------<br class="">
 #else<br class="">
 // ---------------------------------------------------------------------<br class="">
<br class="">
 // CHECK:  DW_TAG_compile_unit<br class="">
 // CHECK:    DW_AT_low_pc<br class="">
-// CHECK-NOT:DW_TAG<br class="">
-// CHECK:     DW_TAG_module<br class="">
-// CHECK-NEXT:  DW_AT_name{{.*}}"Foo"<br class="">
-// CHECK-NOT:   DW_TAG<br class="">
-// CHECK:       DW_TAG_typedef<br class="">
-// CHECK-NOT:     DW_TAG<br class="">
-// CHECK:       NULL<br class="">
+// CHECK-NOT:  DW_TAG_module<br class="">
+// CHECK-NOT:  DW_TAG_typedef<br class="">
 //<br class="">
 // CHECK:   DW_TAG_imported_declaration<br class="">
 // CHECK-NOT: DW_TAG<br class="">
@@ -97,6 +105,10 @@ struct S {};<br class="">
 // CHECK:     DW_AT_name {{.*}}"main"<br class="">
 //<br class="">
 // CHECK:     DW_TAG_variable<br class="">
+// CHECK-NOT:   DW_TAG<br class="">
+// CHECK:       DW_AT_name{{.*}}"bar"<br class="">
+// CHECK-NOT:   DW_TAG<br class="">
+// CHECK:       DW_AT_type [DW_FORM_ref_addr] (0x{{0*}}[[BARTD]]<br class="">
 // CHECK:     DW_TAG_variable<br class="">
 // CHECK-NOT:   DW_TAG<br class="">
 // CHECK:       DW_AT_name{{.*}}"foo"<br class="">
@@ -105,13 +117,26 @@ struct S {};<br class="">
 //<br class="">
 // CHECK: 0x{{0*}}[[PTR]]: DW_TAG_pointer_type<br class="">
 // CHECK-NEXT   DW_AT_type [DW_FORM_ref_addr] {0x{{0*}}[[INTERFACE]])<br class="">
+extern int odr_violation;<br class="">
<br class="">
 @import Foo;<br class="">
 int main(int argc, char **argv) {<br class="">
   Bar bar;<br class="">
   Foo *foo = 0;<br class="">
-  bar.value = 42;<br class="">
+  bar.value = odr_violation;<br class="">
   return bar.value;<br class="">
 }<br class="">
 #endif<br class="">
 #endif<br class="">
+#endif<br class="">
+<br class="">
+// CHECK: DW_TAG_compile_unit<br class="">
+// CHECK:   DW_AT_name {{.*}}"odr_violation.c"<br class="">
+// CHECK: DW_TAG_variable<br class="">
+// CHECK:   DW_AT_name {{.*}}"odr_violation"<br class="">
+// CHECK:   DW_AT_type [DW_FORM_ref4] ({{.*}}{0x{{0*}}[[BAR2:.*]]})<br class="">
+// CHECK: 0x{{0*}}[[BAR2]]: DW_TAG_typedef<br class="">
+// CHECK:   DW_AT_type [DW_FORM_ref4] ({{.*}}{0x{{0*}}[[BAR3:.*]]})<br class="">
+// CHECK:   DW_AT_name {{.*}}"Bar"<br class="">
+// CHECK: 0x{{0*}}[[BAR3]]: DW_TAG_structure_type<br class="">
+// CHECK-NEXT:   DW_AT_name {{.*}}"Bar"<br class="">
<br class="">
Modified: llvm/trunk/tools/dsymutil/DwarfLinker.cpp<br class="">
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/tools/dsymutil/DwarfLinker.cpp?rev=308710&r1=308709&r2=308710&view=diff" rel="noreferrer" target="_blank" class="">http://llvm.org/viewvc/llvm-project/llvm/trunk/tools/dsymutil/DwarfLinker.cpp?rev=308710&r1=308709&r2=308710&view=diff</a><br class="">
==============================================================================<br class="">
--- llvm/trunk/tools/dsymutil/DwarfLinker.cpp (original)<br class="">
+++ llvm/trunk/tools/dsymutil/DwarfLinker.cpp Thu Jul 20 19:07:33 2017<br class="">
@@ -98,6 +98,7 @@ class DeclContext {<br class="">
   uint32_t Line;<br class="">
   uint32_t ByteSize;<br class="">
   uint16_t Tag;<br class="">
+  unsigned DefinedInClangModule : 1;<br class="">
   StringRef Name;<br class="">
   StringRef File;<br class="">
   const DeclContext &Parent;<br class="">
@@ -112,15 +113,17 @@ public:<br class="">
<br class="">
   DeclContext()<br class="">
       : QualifiedNameHash(0), Line(0), ByteSize(0),<br class="">
-        Tag(dwarf::DW_TAG_compile_unit), Name(), File(), Parent(*this),<br class="">
-        LastSeenDIE(), LastSeenCompileUnitID(0), CanonicalDIEOffset(0) {}<br class="">
+        Tag(dwarf::DW_TAG_compile_unit), DefinedInClangModule(0), Name(),<br class="">
+        File(), Parent(*this), LastSeenDIE(), LastSeenCompileUnitID(0),<br class="">
+        CanonicalDIEOffset(0) {}<br class="">
<br class="">
   DeclContext(unsigned Hash, uint32_t Line, uint32_t ByteSize, uint16_t Tag,<br class="">
               StringRef Name, StringRef File, const DeclContext &Parent,<br class="">
               DWARFDie LastSeenDIE = DWARFDie(), unsigned CUId = 0)<br class="">
       : QualifiedNameHash(Hash), Line(Line), ByteSize(ByteSize), Tag(Tag),<br class="">
-        Name(Name), File(File), Parent(Parent), LastSeenDIE(LastSeenDIE),<br class="">
-        LastSeenCompileUnitID(CUId), CanonicalDIEOffset(0) {}<br class="">
+        DefinedInClangModule(0), Name(Name), File(File), Parent(Parent),<br class="">
+        LastSeenDIE(LastSeenDIE), LastSeenCompileUnitID(CUId),<br class="">
+        CanonicalDIEOffset(0) {}<br class="">
<br class="">
   uint32_t getQualifiedNameHash() const { return QualifiedNameHash; }<br class="">
<br class="">
@@ -129,6 +132,9 @@ public:<br class="">
   uint32_t getCanonicalDIEOffset() const { return CanonicalDIEOffset; }<br class="">
   void setCanonicalDIEOffset(uint32_t Offset) { CanonicalDIEOffset = Offset; }<br class="">
<br class="">
+  bool isDefinedInClangModule() const { return DefinedInClangModule; }<br class="">
+  void setDefinedInClangModule(bool Val) { DefinedInClangModule = Val; }<br class="">
+<br class="">
   uint16_t getTag() const { return Tag; }<br class="">
   StringRef getName() const { return Name; }<br class="">
 };<br class="">
@@ -1801,6 +1807,8 @@ static bool analyzeContextInfo(const DWA<br class="">
       CurrentDeclContext = PtrInvalidPair.getPointer();<br class="">
       Info.Ctxt =<br class="">
           PtrInvalidPair.getInt() ? nullptr : PtrInvalidPair.getPointer();<br class="">
+      if (Info.Ctxt)<br class="">
+        Info.Ctxt->setDefinedInClangModule(InClangModule);<br class="">
     } else<br class="">
       Info.Ctxt = CurrentDeclContext = nullptr;<br class="">
   }<br class="">
@@ -2172,7 +2180,6 @@ unsigned DwarfLinker::shouldKeepDIE(Relo<br class="">
     return shouldKeepVariableDIE(RelocMgr, DIE, Unit, MyInfo, Flags);<br class="">
   case dwarf::DW_TAG_subprogram:<br class="">
     return shouldKeepSubprogramDIE(RelocMgr, DIE, Unit, MyInfo, Flags);<br class="">
-  case dwarf::DW_TAG_module:<br class="">
   case dwarf::DW_TAG_imported_module:<br class="">
   case dwarf::DW_TAG_imported_declaration:<br class="">
   case dwarf::DW_TAG_imported_unit:<br class="">
@@ -2232,6 +2239,8 @@ void DwarfLinker::keepDIEAndDependencies<br class="">
             resolveDIEReference(*this, Units, Val, Unit, Die, ReferencedCU)) {<br class="">
       uint32_t RefIdx = ReferencedCU->getOrigUnit().getDIEIndex(RefDIE);<br class="">
       CompileUnit::DIEInfo &Info = ReferencedCU->getInfo(RefIdx);<br class="">
+      bool IsModuleRef = Info.Ctxt && Info.Ctxt->getCanonicalDIEOffset() &&<br class="">
+                         Info.Ctxt->isDefinedInClangModule();<br class="">
       // If the referenced DIE has a DeclContext that has already been<br class="">
       // emitted, then do not keep the one in this CU. We'll link to<br class="">
       // the canonical DIE in cloneDieReferenceAttribute.<br class="">
@@ -2240,7 +2249,8 @@ void DwarfLinker::keepDIEAndDependencies<br class="">
       // ReferencedCU->hasODR() && CU.hasODR().<br class="">
       // FIXME: compatibility with dsymutil-classic. There is no<br class="">
       // reason not to unique ref_addr references.<br class="">
-      if (AttrSpec.Form != dwarf::DW_FORM_ref_addr && UseODR && Info.Ctxt &&<br class="">
+      if (AttrSpec.Form != dwarf::DW_FORM_ref_addr && (UseODR || IsModuleRef) &&<br class="">
+          Info.Ctxt &&<br class="">
           Info.Ctxt != ReferencedCU->getInfo(Info.ParentIdx).Ctxt &&<br class="">
           Info.Ctxt->getCanonicalDIEOffset() && isODRAttribute(AttrSpec.Attr))<br class="">
         continue;<br class="">
<br class="">
<br class="">
_______________________________________________<br class="">
llvm-commits mailing list<br class="">
<a href="mailto:llvm-commits@lists.llvm.org" target="_blank" class="">llvm-commits@lists.llvm.org</a><br class="">
<a href="http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-commits" rel="noreferrer" target="_blank" class="">http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-commits</a><br class="">
</blockquote></div>
</div></blockquote></div><br class=""></body></html>