xref: /llvm-project/lldb/test/API/functionalities/module_cache/bsd/TestModuleCacheBSD.py (revision 2238dcc39358353cac21df75c3c3286ab20b8f53)
1da816ca0SGreg Clayton"""Test the LLDB module cache funcionality."""
2da816ca0SGreg Clayton
3da816ca0SGreg Claytonimport glob
4da816ca0SGreg Claytonimport lldb
5da816ca0SGreg Claytonfrom lldbsuite.test.decorators import *
6da816ca0SGreg Claytonfrom lldbsuite.test.lldbtest import *
7da816ca0SGreg Claytonfrom lldbsuite.test import lldbutil
8da816ca0SGreg Claytonimport os
9da816ca0SGreg Claytonimport time
10da816ca0SGreg Clayton
11da816ca0SGreg Clayton
12da816ca0SGreg Claytonclass ModuleCacheTestcaseBSD(TestBase):
13da816ca0SGreg Clayton    def setUp(self):
14da816ca0SGreg Clayton        # Call super's setUp().
15da816ca0SGreg Clayton        TestBase.setUp(self)
16da816ca0SGreg Clayton        # Find the line number in a(int) to break at.
17*2238dcc3SJonas Devlieghere        self.line_a = line_number("a.c", "// Set file and line breakpoint inside a().")
18*2238dcc3SJonas Devlieghere        self.line_b = line_number("b.c", "// Set file and line breakpoint inside b().")
19*2238dcc3SJonas Devlieghere        self.line_c = line_number("c.c", "// Set file and line breakpoint inside c().")
20*2238dcc3SJonas Devlieghere        self.cache_dir = os.path.join(self.getBuildDir(), "lldb-module-cache")
21da816ca0SGreg Clayton        # Set the lldb module cache directory to a directory inside the build
22da816ca0SGreg Clayton        # artifacts directory so no other tests are interfered with.
23*2238dcc3SJonas Devlieghere        self.runCmd(
24*2238dcc3SJonas Devlieghere            'settings set symbols.lldb-index-cache-path "%s"' % (self.cache_dir)
25*2238dcc3SJonas Devlieghere        )
26*2238dcc3SJonas Devlieghere        self.runCmd("settings set symbols.enable-lldb-index-cache true")
27da816ca0SGreg Clayton        self.build()
28da816ca0SGreg Clayton
29da816ca0SGreg Clayton    def get_module_cache_files(self, basename):
30*2238dcc3SJonas Devlieghere        module_cache_glob = os.path.join(
31*2238dcc3SJonas Devlieghere            self.cache_dir, "llvmcache-*%s*symtab*" % (basename)
32*2238dcc3SJonas Devlieghere        )
33da816ca0SGreg Clayton        return glob.glob(module_cache_glob)
34da816ca0SGreg Clayton
35da816ca0SGreg Clayton    # Requires no dSYM, so we let the Makefile make the right stuff for us
36da816ca0SGreg Clayton    @no_debug_info_test
37da816ca0SGreg Clayton    @skipUnlessDarwin
38da816ca0SGreg Clayton    def test(self):
39da816ca0SGreg Clayton        """
40b6087ba7SGreg Clayton        This test has been modified to make sure .o files that don't have
41b6087ba7SGreg Clayton        UUIDs are not cached after discovering build systems that play with
42b6087ba7SGreg Clayton        modification times of .o files that the modification times are not
43b6087ba7SGreg Clayton        unique enough to ensure the .o file within the .a file are the right
44b6087ba7SGreg Clayton        files as this was causing older cache files to be accepted for new
45b6087ba7SGreg Clayton        updated .o files.
46b6087ba7SGreg Clayton
47b6087ba7SGreg Clayton        ELF .o files do calculate a UUID from the contents of the file,
48b6087ba7SGreg Clayton        which is expensive, but no one loads .o files into a debug sessions
49b6087ba7SGreg Clayton        when using ELF files. Mach-o .o files do not have UUID values and do
50b6087ba7SGreg Clayton        no calculate one as they _are_ used during debug sessions when no
51b6087ba7SGreg Clayton        dSYM file is generated. If we can find a way to uniquely and cheaply
52b6087ba7SGreg Clayton        create UUID values for mach-o .o files in the future, this test will
53b6087ba7SGreg Clayton        be updated to test this functionality. This test will now make sure
54b6087ba7SGreg Clayton        there are no cache entries for any .o files in BSD archives.
55b6087ba7SGreg Clayton
56b6087ba7SGreg Clayton        The old test case description is below in case we enable caching for
57b6087ba7SGreg Clayton        .o files again:
58b6087ba7SGreg Clayton
59da816ca0SGreg Clayton        Test module cache functionality for bsd archive object files.
60da816ca0SGreg Clayton
61da816ca0SGreg Clayton        This will test that if we enable the module cache, we have a
62da816ca0SGreg Clayton        corresponding cache entry for the .o files in libfoo.a.
63da816ca0SGreg Clayton
64da816ca0SGreg Clayton        The static library has two entries for "a.o":
65da816ca0SGreg Clayton        - one from a.c
66da816ca0SGreg Clayton        - one from c.c which had c.o renamed to a.o and then put into the
67da816ca0SGreg Clayton          libfoo.a as an extra .o file with different contents from the
68da816ca0SGreg Clayton          original a.o
69da816ca0SGreg Clayton
70da816ca0SGreg Clayton        We do this to test that we can correctly cache duplicate .o files
71da816ca0SGreg Clayton        that appear in .a files.
72da816ca0SGreg Clayton
73da816ca0SGreg Clayton        This test only works on darwin because of the way DWARF is stored
74da816ca0SGreg Clayton        where the debug map will refer to .o files inside of .a files.
75da816ca0SGreg Clayton        """
76da816ca0SGreg Clayton        exe = self.getBuildArtifact("a.out")
77da816ca0SGreg Clayton
787240436cSGabriel Ravier        # Create a module with no dependencies.
79da816ca0SGreg Clayton        target = self.createTestTarget(load_dependent_modules=False)
80da816ca0SGreg Clayton
81*2238dcc3SJonas Devlieghere        self.runCmd("breakpoint set -f a.c -l %d" % (self.line_a))
82*2238dcc3SJonas Devlieghere        self.runCmd("breakpoint set -f b.c -l %d" % (self.line_b))
83*2238dcc3SJonas Devlieghere        self.runCmd("breakpoint set -f c.c -l %d" % (self.line_c))
84da816ca0SGreg Clayton
85da816ca0SGreg Clayton        # Get the executable module and get the number of symbols to make
86da816ca0SGreg Clayton        # sure the symbol table gets parsed and cached. The module cache is
87da816ca0SGreg Clayton        # enabled in the setUp() function.
88da816ca0SGreg Clayton        main_module = target.GetModuleAtIndex(0)
89da816ca0SGreg Clayton        self.assertTrue(main_module.IsValid())
90da816ca0SGreg Clayton        # Make sure the symbol table gets loaded and cached
91da816ca0SGreg Clayton        main_module.GetNumSymbols()
92da816ca0SGreg Clayton        a_o_cache_files = self.get_module_cache_files("libfoo.a(a.o)")
93da816ca0SGreg Clayton        b_o_cache_files = self.get_module_cache_files("libfoo.a(b.o)")
94b6087ba7SGreg Clayton
95da816ca0SGreg Clayton        # We expect the directory for a.o to have two cache directories:
96da816ca0SGreg Clayton        # - 1 for the a.o with a earlier mod time
97da816ca0SGreg Clayton        # - 1 for the a.o that was renamed from c.o that should be 2 seconds older
98b6087ba7SGreg Clayton        # self.assertEqual(len(a_o_cache_files), 2,
99b6087ba7SGreg Clayton        #         "make sure there are two files in the module cache directory (%s) for libfoo.a(a.o)" % (self.cache_dir))
100b6087ba7SGreg Clayton        # self.assertEqual(len(b_o_cache_files), 1,
101b6087ba7SGreg Clayton        #         "make sure there are two files in the module cache directory (%s) for libfoo.a(b.o)" % (self.cache_dir))
102b6087ba7SGreg Clayton
103b6087ba7SGreg Clayton        # We are no longer caching .o files in the lldb index cache. If we ever
104b6087ba7SGreg Clayton        # re-enable this functionality, we can uncomment out the above lines of
105b6087ba7SGreg Clayton        # code.
106*2238dcc3SJonas Devlieghere        self.assertEqual(
107*2238dcc3SJonas Devlieghere            len(a_o_cache_files),
108*2238dcc3SJonas Devlieghere            0,
109*2238dcc3SJonas Devlieghere            "make sure there are no files in the module cache directory (%s) for libfoo.a(a.o)"
110*2238dcc3SJonas Devlieghere            % (self.cache_dir),
111*2238dcc3SJonas Devlieghere        )
112*2238dcc3SJonas Devlieghere        self.assertEqual(
113*2238dcc3SJonas Devlieghere            len(b_o_cache_files),
114*2238dcc3SJonas Devlieghere            0,
115*2238dcc3SJonas Devlieghere            "make sure there are no files in the module cache directory (%s) for libfoo.a(b.o)"
116*2238dcc3SJonas Devlieghere            % (self.cache_dir),
117*2238dcc3SJonas Devlieghere        )
118