diff --git a/test/tools/llvm-readobj/Inputs/comdat-function-linetables.obj.coff-2013-i386 b/test/tools/llvm-readobj/Inputs/comdat-function-linetables.obj.coff-2013-i386 new file mode 100755 index 00000000000..4adaf2edc6f Binary files /dev/null and b/test/tools/llvm-readobj/Inputs/comdat-function-linetables.obj.coff-2013-i386 differ diff --git a/test/tools/llvm-readobj/codeview-linetables.test b/test/tools/llvm-readobj/codeview-linetables.test index 28e34b7d4fb..4b169336cd9 100644 --- a/test/tools/llvm-readobj/codeview-linetables.test +++ b/test/tools/llvm-readobj/codeview-linetables.test @@ -1,3 +1,4 @@ +;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ; The following two object files were generated using the following command: ; D:\> cl /Z7 /c source.c ; with the following contents of D:\source.c: @@ -22,25 +23,6 @@ RUN: | FileCheck %s -check-prefix MFUN32 RUN: llvm-readobj -s -codeview-linetables %p/Inputs/multifunction-linetables.obj.coff-2013-x86_64 \ RUN: | FileCheck %s -check-prefix MFUN64 -; The following two object files were generated using the following command: -; D:\> cl /Z7 /c input.c -; with the following contents of D:\input.c: -; void g(void); -; -; void f(void) { -; #line 1 "one.c" -; g(); -; #line 2 "two.c" -; g(); -; #line 7 "one.c" -; g(); -; } -; using CL v18.00.21005.1 32-/64-bit versions respectively. -RUN: llvm-readobj -s -codeview-linetables %p/Inputs/multifile-linetables.obj.coff-2013-i368 \ -RUN: | FileCheck %s -check-prefix MFILE32 -RUN: llvm-readobj -s -codeview-linetables %p/Inputs/multifile-linetables.obj.coff-2013-x86_64 \ -RUN: | FileCheck %s -check-prefix MFILE64 - MFUN32: CodeViewLineTables [ MFUN32-NEXT: Magic: 0x4 MFUN32-NEXT: Subsection [ @@ -211,6 +193,26 @@ MFUN64-NEXT: ] MFUN64-NEXT: ] MFUN64-NEXT: ] +;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; +; The following two object files were generated using the following command: +; D:\> cl /Z7 /c input.c +; with the following contents of D:\input.c: +; void g(void); +; +; void f(void) { +; #line 1 "one.c" +; g(); +; #line 2 "two.c" +; g(); +; #line 7 "one.c" +; g(); +; } +; using CL v18.00.21005.1 32-/64-bit versions respectively. +RUN: llvm-readobj -s -codeview-linetables %p/Inputs/multifile-linetables.obj.coff-2013-i368 \ +RUN: | FileCheck %s -check-prefix MFILE32 +RUN: llvm-readobj -s -codeview-linetables %p/Inputs/multifile-linetables.obj.coff-2013-x86_64 \ +RUN: | FileCheck %s -check-prefix MFILE64 + MFILE32: CodeViewLineTables [ MFILE32-NEXT: Magic: 0x4 MFILE32-NEXT: Subsection [ @@ -314,3 +316,41 @@ MFILE64-NEXT: +0x13: 8 MFILE64-NEXT: ] MFILE64-NEXT: ] MFILE64-NEXT: ] + +;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; +; The following object file was generated using the following command: +; C:\src> cl /Z7 /Gy /c test.cc +; with the following contents of C:\src\test.cc: +; int f() +; { +; return 0; +; } +; +; int g() +; { +; return 0; +; } +; using 32-version of CL v18.00.21005.1. +RUN: llvm-readobj -s -codeview-linetables %p/Inputs/comdat-function-linetables.obj.coff-2013-i386 \ +RUN: | FileCheck %s -check-prefix MCOMDAT + +MCOMDAT: FunctionLineTable [ +MCOMDAT-NEXT: FunctionName: ?f@@YAHXZ +MCOMDAT-NEXT: CodeSize: 0x7 +MCOMDAT-NEXT: FilenameSegment [ +MCOMDAT-NEXT: Filename: c:\src\test.cc +MCOMDAT-NEXT: +0x0: 2 +MCOMDAT-NEXT: +0x3: 3 +MCOMDAT-NEXT: +0x5: 4 +MCOMDAT-NEXT: ] +MCOMDAT-NEXT: ] +MCOMDAT: FunctionLineTable [ +MCOMDAT-NEXT: FunctionName: ?g@@YAHXZ +MCOMDAT-NEXT: CodeSize: 0x7 +MCOMDAT-NEXT: FilenameSegment [ +MCOMDAT-NEXT: Filename: c:\src\test.cc +MCOMDAT-NEXT: +0x0: 7 +MCOMDAT-NEXT: +0x3: 8 +MCOMDAT-NEXT: +0x5: 9 +MCOMDAT-NEXT: ] +MCOMDAT-NEXT: ] diff --git a/tools/llvm-readobj/COFFDumper.cpp b/tools/llvm-readobj/COFFDumper.cpp index 53fba14a36e..8e7fcc06c1b 100644 --- a/tools/llvm-readobj/COFFDumper.cpp +++ b/tools/llvm-readobj/COFFDumper.cpp @@ -82,6 +82,8 @@ private: const llvm::object::COFFObjectFile *Obj; RelocMapTy RelocMap; + StringRef CVFileIndexToStringOffsetTable; + StringRef CVStringTable; }; } // namespace @@ -440,8 +442,6 @@ void COFFDumper::printCodeViewLineTables(const SectionRef &Section) { SmallVector FunctionNames; StringMap FunctionLineTables; - StringRef FileIndexToStringOffsetTable; - StringRef StringTable; ListScope D(W, "CodeViewLineTables"); { @@ -502,25 +502,25 @@ void COFFDumper::printCodeViewLineTables(const SectionRef &Section) { break; } case COFF::DEBUG_STRING_TABLE_SUBSECTION: - if (PayloadSize == 0 || StringTable.data() != nullptr || + if (PayloadSize == 0 || CVStringTable.data() != nullptr || Contents.back() != '\0') { // Empty or duplicate or non-null-terminated subsection. error(object_error::parse_failed); return; } - StringTable = Contents; + CVStringTable = Contents; break; case COFF::DEBUG_INDEX_SUBSECTION: // Holds the translation table from file indices // to offsets in the string table. if (PayloadSize == 0 || - FileIndexToStringOffsetTable.data() != nullptr) { + CVFileIndexToStringOffsetTable.data() != nullptr) { // Empty or duplicate subsection. error(object_error::parse_failed); return; } - FileIndexToStringOffsetTable = Contents; + CVFileIndexToStringOffsetTable = Contents; break; } Offset += PayloadSize; @@ -555,7 +555,7 @@ void COFFDumper::printCodeViewLineTables(const SectionRef &Section) { uint32_t FilenameOffset; { - DataExtractor SDE(FileIndexToStringOffsetTable, true, 4); + DataExtractor SDE(CVFileIndexToStringOffsetTable, true, 4); uint32_t OffsetInSDE = OffsetInIndex; if (!SDE.isValidOffset(OffsetInSDE)) { error(object_error::parse_failed); @@ -564,15 +564,15 @@ void COFFDumper::printCodeViewLineTables(const SectionRef &Section) { FilenameOffset = SDE.getU32(&OffsetInSDE); } - if (FilenameOffset == 0 || FilenameOffset + 1 >= StringTable.size() || - StringTable.data()[FilenameOffset - 1] != '\0') { + if (FilenameOffset == 0 || FilenameOffset + 1 >= CVStringTable.size() || + CVStringTable.data()[FilenameOffset - 1] != '\0') { // Each string in an F3 subsection should be preceded by a null // character. error(object_error::parse_failed); return; } - StringRef Filename(StringTable.data() + FilenameOffset); + StringRef Filename(CVStringTable.data() + FilenameOffset); ListScope S(W, "FilenameSegment"); W.printString("Filename", Filename); for (unsigned J = 0; J != SegmentLength && DE.isValidOffset(Offset);