forked from OSchip/llvm-project
Fix support for distinguishing archive members by timestamp on Darwin.
On Darwin, the binary's symbol table points to debug info in object files -- potentially object files within a static library. Such a library may have multiple entries with the same name, distinguished only by timestamp. The code was already _attempting_ to handle this case (see the code in ObjectContainerBSDArchive::Archive::FindObject which disambiguates via timestamp). But, unfortunately, while the timestamp was taken into account on the _first_ lookup, the result was then cached in a map keyed only off of the path. Added the timestamp to the cache, and added a test case. Differential Revision: https://reviews.llvm.org/D47660 llvm-svn: 333813
This commit is contained in:
parent
1534929623
commit
9c2d52014c
|
@ -0,0 +1,22 @@
|
|||
LEVEL = ../../make
|
||||
|
||||
C_SOURCES := main.c
|
||||
|
||||
# Make an archive that has two object files with the same name, but
|
||||
# different timestamps. Do it all in one rule so that the timestamps
|
||||
# can be controlled without confusing Make.
|
||||
libfoo.a: a.c sub1/a.c
|
||||
$(CC) $(CFLAGS) -c $(<D)/a.c -o a.o
|
||||
mkdir -p sub1
|
||||
$(CC) $(CFLAGS) -c $(<D)/sub1/a.c -o sub1/a.o
|
||||
touch -t '198001010000.00' a.o
|
||||
touch -t '198001010000.01' sub1/a.o
|
||||
$(AR) $(ARFLAGS) $@ a.o sub1/a.o
|
||||
rm a.o sub1/a.o
|
||||
|
||||
include $(LEVEL)/Makefile.rules
|
||||
|
||||
# Needs to come after include
|
||||
OBJECTS += libfoo.a
|
||||
$(EXE) : libfoo.a
|
||||
.DEFAULT_GOAL := $(EXE)
|
|
@ -0,0 +1,62 @@
|
|||
"""Test breaking inside functions defined within a BSD archive file libfoo.a."""
|
||||
|
||||
from __future__ import print_function
|
||||
|
||||
|
||||
import os
|
||||
import time
|
||||
import lldb
|
||||
from lldbsuite.test.decorators import *
|
||||
from lldbsuite.test.lldbtest import *
|
||||
from lldbsuite.test import lldbutil
|
||||
|
||||
|
||||
class BSDArchivesTestCase(TestBase):
|
||||
|
||||
mydir = TestBase.compute_mydir(__file__)
|
||||
|
||||
def setUp(self):
|
||||
# Call super's setUp().
|
||||
TestBase.setUp(self)
|
||||
# Find the line number in a(int) to break at.
|
||||
self.line = line_number(
|
||||
'a.c', '// Set file and line breakpoint inside a().')
|
||||
|
||||
@expectedFailureAll(
|
||||
oslist=["windows"],
|
||||
bugnumber="llvm.org/pr24527. Makefile.rules doesn't know how to build static libs on Windows")
|
||||
def test(self):
|
||||
"""Break inside a() and b() defined within libfoo.a."""
|
||||
self.build()
|
||||
|
||||
exe = self.getBuildArtifact("a.out")
|
||||
self.runCmd("file " + exe, CURRENT_EXECUTABLE_SET)
|
||||
|
||||
# Break on a() and b() symbols
|
||||
lldbutil.run_break_set_by_symbol(
|
||||
self, "a", sym_exact=True)
|
||||
lldbutil.run_break_set_by_symbol(
|
||||
self, "b", sym_exact=True)
|
||||
|
||||
self.runCmd("run", RUN_SUCCEEDED)
|
||||
|
||||
# The stop reason of the thread should be breakpoint.
|
||||
self.expect("thread list", STOPPED_DUE_TO_BREAKPOINT,
|
||||
substrs=['stopped',
|
||||
'stop reason = breakpoint'])
|
||||
|
||||
# Break at a(int) first.
|
||||
self.expect("frame variable", VARIABLES_DISPLAYED_CORRECTLY,
|
||||
substrs=['(int) arg = 1'])
|
||||
self.expect("frame variable __a_global", VARIABLES_DISPLAYED_CORRECTLY,
|
||||
substrs=['(int) __a_global = 1'])
|
||||
|
||||
# Continue the program, we should break at b(int) next.
|
||||
self.runCmd("continue")
|
||||
self.expect("thread list", STOPPED_DUE_TO_BREAKPOINT,
|
||||
substrs=['stopped',
|
||||
'stop reason = breakpoint'])
|
||||
self.expect("frame variable", VARIABLES_DISPLAYED_CORRECTLY,
|
||||
substrs=['(int) arg = 2'])
|
||||
self.expect("frame variable __b_global", VARIABLES_DISPLAYED_CORRECTLY,
|
||||
substrs=['(int) __b_global = 2'])
|
|
@ -0,0 +1,14 @@
|
|||
//===-- a.c -----------------------------------------------------*- C++ -*-===//
|
||||
//
|
||||
// The LLVM Compiler Infrastructure
|
||||
//
|
||||
// This file is distributed under the University of Illinois Open Source
|
||||
// License. See LICENSE.TXT for details.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
int __a_global = 1;
|
||||
|
||||
int a(int arg) {
|
||||
int result = arg + __a_global;
|
||||
return result;
|
||||
}
|
|
@ -0,0 +1,17 @@
|
|||
//===-- main.c --------------------------------------------------*- C++ -*-===//
|
||||
//
|
||||
// The LLVM Compiler Infrastructure
|
||||
//
|
||||
// This file is distributed under the University of Illinois Open Source
|
||||
// License. See LICENSE.TXT for details.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
#include <stdio.h>
|
||||
|
||||
extern int a(int);
|
||||
extern int b(int);
|
||||
int main (int argc, char const *argv[])
|
||||
{
|
||||
printf ("a(1) returns %d\n", a(1));
|
||||
printf ("b(2) returns %d\n", b(2));
|
||||
}
|
|
@ -0,0 +1,14 @@
|
|||
//===-- a.c -----------------------------------------------------*- C++ -*-===//
|
||||
//
|
||||
// The LLVM Compiler Infrastructure
|
||||
//
|
||||
// This file is distributed under the University of Illinois Open Source
|
||||
// License. See LICENSE.TXT for details.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
static int __b_global = 2;
|
||||
|
||||
int b(int arg) {
|
||||
int result = arg + __b_global;
|
||||
return result;
|
||||
}
|
|
@ -411,13 +411,15 @@ Module *SymbolFileDWARFDebugMap::GetModuleByOSOIndex(uint32_t oso_idx) {
|
|||
Module *SymbolFileDWARFDebugMap::GetModuleByCompUnitInfo(
|
||||
CompileUnitInfo *comp_unit_info) {
|
||||
if (!comp_unit_info->oso_sp) {
|
||||
auto pos = m_oso_map.find(comp_unit_info->oso_path);
|
||||
auto pos = m_oso_map.find(
|
||||
{comp_unit_info->oso_path, comp_unit_info->oso_mod_time});
|
||||
if (pos != m_oso_map.end()) {
|
||||
comp_unit_info->oso_sp = pos->second;
|
||||
} else {
|
||||
ObjectFile *obj_file = GetObjectFile();
|
||||
comp_unit_info->oso_sp.reset(new OSOInfo());
|
||||
m_oso_map[comp_unit_info->oso_path] = comp_unit_info->oso_sp;
|
||||
m_oso_map[{comp_unit_info->oso_path, comp_unit_info->oso_mod_time}] =
|
||||
comp_unit_info->oso_sp;
|
||||
const char *oso_path = comp_unit_info->oso_path.GetCString();
|
||||
FileSpec oso_file(oso_path, false);
|
||||
ConstString oso_object;
|
||||
|
|
|
@ -300,7 +300,9 @@ protected:
|
|||
std::vector<CompileUnitInfo> m_compile_unit_infos;
|
||||
std::vector<uint32_t> m_func_indexes; // Sorted by address
|
||||
std::vector<uint32_t> m_glob_indexes;
|
||||
std::map<lldb_private::ConstString, OSOInfoSP> m_oso_map;
|
||||
std::map<std::pair<lldb_private::ConstString, llvm::sys::TimePoint<>>,
|
||||
OSOInfoSP>
|
||||
m_oso_map;
|
||||
UniqueDWARFASTTypeMap m_unique_ast_type_map;
|
||||
lldb_private::LazyBool m_supports_DW_AT_APPLE_objc_complete_type;
|
||||
DebugMap m_debug_map;
|
||||
|
|
Loading…
Reference in New Issue