From 8883ec7da2e9d010c1355d90fc2f0c543826f355 Mon Sep 17 00:00:00 2001 From: Nico Weber Date: Wed, 7 Aug 2019 19:29:04 +0000 Subject: [PATCH] Add support for deterministically linked binaries on macOS to lldb. When ld64 links a binary deterministically using the flag ZERO_AR_DATE, it sets a timestamp of 0 for N_OSO members in the symtab section, rather than the usual last modified date of the object file. Prior to this patch, lldb would compare the timestamp from the N_OSO member against the last modified date of the object file, and skip loading the object file if there was a mismatch. This patch updates the logic to ignore the timestamp check if the N_OSO member has timestamp 0. The original logic was added in https://reviews.llvm.org/rL181631 as a safety check to avoid problems when debugging if the object file was out of date. This was prior to the introduction of deterministic build in ld64. lld still doesn't support deterministic build. Other code in llvm already relies on and uses the assumption that a timestamp of 0 means deterministic build. For example, commit 9ccfddc39d4d27f9b16fcc72ab30d483151d6d08 adds similar timestamp checking logic to dsymutil, but special cases timestamp 0. Likewise, commit 0d1bb79a0413f221432a7b1d0d2d10c84c4bbb99 adds a long comment describing deterministic archive, which mostly uses timestamp 0 for determinism. Patch from Erik Chen ! Differential Revision: https://reviews.llvm.org/D65826 llvm-svn: 368199 --- lldb/lit/SymbolFile/DWARF/deterministic-build.cpp | 11 +++++++++++ .../Plugins/SymbolFile/DWARF/SymbolFileDWARFDebugMap.cpp | 6 +++++- 2 files changed, 16 insertions(+), 1 deletion(-) create mode 100644 lldb/lit/SymbolFile/DWARF/deterministic-build.cpp diff --git a/lldb/lit/SymbolFile/DWARF/deterministic-build.cpp b/lldb/lit/SymbolFile/DWARF/deterministic-build.cpp new file mode 100644 index 0000000..576c4ab --- /dev/null +++ b/lldb/lit/SymbolFile/DWARF/deterministic-build.cpp @@ -0,0 +1,11 @@ +// Test that binaries linked deterministically (N_OSO has timestamp 0) can still +// have their object files loaded by lldb. Note that the env var ZERO_AR_DATE +// requires the ld64 linker, which clang invokes by default. +// REQUIRES: system-darwin +// RUN: %clang %s -g -c -o %t.o +// RUN: ZERO_AR_DATE=1 %clang %t.o -g -o %t +// RUN: %lldb %t -o "breakpoint set -f %s -l 11" -o run -o exit | FileCheck %s +// CHECK: stop reason = breakpoint + + +int main() { return 0; } diff --git a/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARFDebugMap.cpp b/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARFDebugMap.cpp index af04d05e..536002d 100644 --- a/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARFDebugMap.cpp +++ b/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARFDebugMap.cpp @@ -420,7 +420,11 @@ Module *SymbolFileDWARFDebugMap::GetModuleByCompUnitInfo( // than the one from the CU. auto oso_mod_time = std::chrono::time_point_cast( FileSystem::Instance().GetModificationTime(oso_file)); - if (oso_mod_time != comp_unit_info->oso_mod_time) { + // A timestamp of 0 means that the linker was in deterministic mode. In + // that case, we should skip the check against the filesystem last + // modification timestamp, since it will never match. + if (comp_unit_info->oso_mod_time != llvm::sys::TimePoint<>() && + oso_mod_time != comp_unit_info->oso_mod_time) { obj_file->GetModule()->ReportError( "debug map object file '%s' has changed (actual time is " "%s, debug map time is %s" -- 2.7.4