From b4fdb7e0c8df9eef84256696181a04e92bac4a62 Mon Sep 17 00:00:00 2001 From: Arlo Siemsen Date: Thu, 12 Mar 2020 16:25:01 -0700 Subject: [PATCH] Add support for SHA256 source file checksums in debug info LLVM currently supports CSK_MD5 and CSK_SHA1 source file checksums in debug info. This change adds support for CSK_SHA256 checksums. The SHA256 checksums are supported by the CodeView debug format. Reviewed By: aprantl Differential Revision: https://reviews.llvm.org/D75785 --- docs/LangRef.rst | 2 +- include/llvm/IR/DebugInfoMetadata.h | 3 ++- lib/CodeGen/AsmPrinter/CodeViewDebug.cpp | 11 +++++++++-- lib/IR/DebugInfoMetadata.cpp | 6 ++++-- lib/IR/Verifier.cpp | 3 +++ test/Assembler/dbg-checksum.ll | 20 ++++++++++++++++++++ 6 files changed, 39 insertions(+), 6 deletions(-) create mode 100644 test/Assembler/dbg-checksum.ll diff --git a/docs/LangRef.rst b/docs/LangRef.rst index 4db8aa1bc93..3d1f9d38831 100644 --- a/docs/LangRef.rst +++ b/docs/LangRef.rst @@ -4568,7 +4568,7 @@ DIFile Files are sometimes used in ``scope:`` fields, and are the only valid target for ``file:`` fields. -Valid values for ``checksumkind:`` field are: {CSK_None, CSK_MD5, CSK_SHA1} +Valid values for ``checksumkind:`` field are: {CSK_None, CSK_MD5, CSK_SHA1, CSK_SHA256} .. _DIBasicType: diff --git a/include/llvm/IR/DebugInfoMetadata.h b/include/llvm/IR/DebugInfoMetadata.h index 221ff519e2f..6056337fdff 100644 --- a/include/llvm/IR/DebugInfoMetadata.h +++ b/include/llvm/IR/DebugInfoMetadata.h @@ -465,7 +465,8 @@ public: // encoding is reserved. CSK_MD5 = 1, CSK_SHA1 = 2, - CSK_Last = CSK_SHA1 // Should be last enumeration. + CSK_SHA256 = 3, + CSK_Last = CSK_SHA256 // Should be last enumeration. }; /// A single checksum, represented by a \a Kind and a \a Value (a string). diff --git a/lib/CodeGen/AsmPrinter/CodeViewDebug.cpp b/lib/CodeGen/AsmPrinter/CodeViewDebug.cpp index 6dc6fde9a29..814273c6a39 100644 --- a/lib/CodeGen/AsmPrinter/CodeViewDebug.cpp +++ b/lib/CodeGen/AsmPrinter/CodeViewDebug.cpp @@ -250,8 +250,15 @@ unsigned CodeViewDebug::maybeRecordFile(const DIFile *F) { ChecksumAsBytes = ArrayRef( reinterpret_cast(CKMem), Checksum.size()); switch (F->getChecksum()->Kind) { - case DIFile::CSK_MD5: CSKind = FileChecksumKind::MD5; break; - case DIFile::CSK_SHA1: CSKind = FileChecksumKind::SHA1; break; + case DIFile::CSK_MD5: + CSKind = FileChecksumKind::MD5; + break; + case DIFile::CSK_SHA1: + CSKind = FileChecksumKind::SHA1; + break; + case DIFile::CSK_SHA256: + CSKind = FileChecksumKind::SHA256; + break; } } bool Success = OS.EmitCVFileDirective(NextId, FullPath, ChecksumAsBytes, diff --git a/lib/IR/DebugInfoMetadata.cpp b/lib/IR/DebugInfoMetadata.cpp index 0c0ea50dde7..289d4159683 100644 --- a/lib/IR/DebugInfoMetadata.cpp +++ b/lib/IR/DebugInfoMetadata.cpp @@ -479,8 +479,9 @@ DISubroutineType *DISubroutineType::getImpl(LLVMContext &Context, DIFlags Flags, // FIXME: Implement this string-enum correspondence with a .def file and macros, // so that the association is explicit rather than implied. static const char *ChecksumKindName[DIFile::CSK_Last] = { - "CSK_MD5", - "CSK_SHA1" + "CSK_MD5", + "CSK_SHA1", + "CSK_SHA256", }; StringRef DIFile::getChecksumKindAsString(ChecksumKind CSKind) { @@ -495,6 +496,7 @@ Optional DIFile::getChecksumKind(StringRef CSKindStr) { return StringSwitch>(CSKindStr) .Case("CSK_MD5", DIFile::CSK_MD5) .Case("CSK_SHA1", DIFile::CSK_SHA1) + .Case("CSK_SHA256", DIFile::CSK_SHA256) .Default(None); } diff --git a/lib/IR/Verifier.cpp b/lib/IR/Verifier.cpp index 676f98dae0b..1053304995c 100644 --- a/lib/IR/Verifier.cpp +++ b/lib/IR/Verifier.cpp @@ -1034,6 +1034,9 @@ void Verifier::visitDIFile(const DIFile &N) { case DIFile::CSK_SHA1: Size = 40; break; + case DIFile::CSK_SHA256: + Size = 64; + break; } AssertDI(Checksum->Value.size() == Size, "invalid checksum length", &N); AssertDI(Checksum->Value.find_if_not(llvm::isHexDigit) == StringRef::npos, diff --git a/test/Assembler/dbg-checksum.ll b/test/Assembler/dbg-checksum.ll new file mode 100644 index 00000000000..47af2adbf8c --- /dev/null +++ b/test/Assembler/dbg-checksum.ll @@ -0,0 +1,20 @@ +; Test that DIFile(checksumkind, checksum) can round-trip through bitcode. +; +; RUN: llvm-as < %s | llvm-dis | llvm-as | llvm-dis | FileCheck %s + +!llvm.dbg.cu = !{!1, !2, !3, !4} +!llvm.module.flags = !{!9} + +!1 = distinct !DICompileUnit(language: DW_LANG_C99, file: !5, isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug) +!2 = distinct !DICompileUnit(language: DW_LANG_C99, file: !6, isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug) +!3 = distinct !DICompileUnit(language: DW_LANG_C99, file: !7, isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug) +!4 = distinct !DICompileUnit(language: DW_LANG_C99, file: !8, isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug) +; CHECK: !DIFile(filename: "a.h", directory: "/test") +!5 = !DIFile(filename: "a.h", directory: "/test") +; CHECK: !DIFile(filename: "b.h", directory: "/test", checksumkind: CSK_MD5, checksum: "595f44fec1e92a71d3e9e77456ba80d1") +!6 = !DIFile(filename: "b.h", directory: "/test", checksumkind: CSK_MD5, checksum: "595f44fec1e92a71d3e9e77456ba80d1") +; CHECK: !DIFile(filename: "c.h", directory: "/test", checksumkind: CSK_SHA1, checksum: "d5db29cd03a2ed055086cef9c31c252b4587d6d0") +!7 = !DIFile(filename: "c.h", directory: "/test", checksumkind: CSK_SHA1, checksum: "d5db29cd03a2ed055086cef9c31c252b4587d6d0") +; CHECK: !DIFile(filename: "d.h", directory: "/test", checksumkind: CSK_SHA256, checksum: "e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855") +!8 = !DIFile(filename: "d.h", directory: "/test", checksumkind: CSK_SHA256, checksum: "e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855") +!9 = !{i32 2, !"Debug Info Version", i32 3}