[LLVMSymbolize] Move ModuleInfo into a separate class (SymbolizableModule).
[oota-llvm.git] / lib / DebugInfo / Symbolize / Symbolize.cpp
1 //===-- LLVMSymbolize.cpp -------------------------------------------------===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 //
10 // Implementation for LLVM symbolization library.
11 //
12 //===----------------------------------------------------------------------===//
13
14 #include "llvm/DebugInfo/Symbolize/Symbolize.h"
15
16 #include "SymbolizableObjectFile.h"
17
18 #include "llvm/ADT/STLExtras.h"
19 #include "llvm/Config/config.h"
20 #include "llvm/DebugInfo/DWARF/DWARFContext.h"
21 #include "llvm/DebugInfo/PDB/PDB.h"
22 #include "llvm/DebugInfo/PDB/PDBContext.h"
23 #include "llvm/Object/ELFObjectFile.h"
24 #include "llvm/Object/MachO.h"
25 #include "llvm/Support/COFF.h"
26 #include "llvm/Support/Casting.h"
27 #include "llvm/Support/Compression.h"
28 #include "llvm/Support/DataExtractor.h"
29 #include "llvm/Support/Errc.h"
30 #include "llvm/Support/FileSystem.h"
31 #include "llvm/Support/MemoryBuffer.h"
32 #include "llvm/Support/Path.h"
33 #include <sstream>
34 #include <stdlib.h>
35
36 #if defined(_MSC_VER)
37 #include <Windows.h>
38 #include <DbgHelp.h>
39 #pragma comment(lib, "dbghelp.lib")
40
41 // Windows.h conflicts with our COFF header definitions.
42 #ifdef IMAGE_FILE_MACHINE_I386
43 #undef IMAGE_FILE_MACHINE_I386
44 #endif
45 #endif
46
47 namespace llvm {
48 namespace symbolize {
49
50 // FIXME: Move this to llvm-symbolizer tool.
51 static bool error(std::error_code ec) {
52   if (!ec)
53     return false;
54   errs() << "LLVMSymbolizer: error reading file: " << ec.message() << ".\n";
55   return true;
56 }
57
58
59 const char LLVMSymbolizer::kBadString[] = "??";
60
61 std::string LLVMSymbolizer::symbolizeCode(const std::string &ModuleName,
62                                           uint64_t ModuleOffset) {
63   SymbolizableModule *Info = getOrCreateModuleInfo(ModuleName);
64   if (!Info)
65     return printDILineInfo(DILineInfo(), Info);
66
67   // If the user is giving us relative addresses, add the preferred base of the
68   // object to the offset before we do the query. It's what DIContext expects.
69   if (Opts.RelativeAddresses)
70     ModuleOffset += Info->getModulePreferredBase();
71
72   if (Opts.PrintInlining) {
73     DIInliningInfo InlinedContext = Info->symbolizeInlinedCode(
74         ModuleOffset, Opts.PrintFunctions, Opts.UseSymbolTable);
75     uint32_t FramesNum = InlinedContext.getNumberOfFrames();
76     assert(FramesNum > 0);
77     std::string Result;
78     for (uint32_t i = 0; i < FramesNum; i++) {
79       DILineInfo LineInfo = InlinedContext.getFrame(i);
80       Result += printDILineInfo(LineInfo, Info);
81     }
82     return Result;
83   }
84   DILineInfo LineInfo = Info->symbolizeCode(ModuleOffset, Opts.PrintFunctions,
85                                             Opts.UseSymbolTable);
86   return printDILineInfo(LineInfo, Info);
87 }
88
89 std::string LLVMSymbolizer::symbolizeData(const std::string &ModuleName,
90                                           uint64_t ModuleOffset) {
91   std::string Name = kBadString;
92   uint64_t Start = 0;
93   uint64_t Size = 0;
94   if (Opts.UseSymbolTable) {
95     if (SymbolizableModule *Info = getOrCreateModuleInfo(ModuleName)) {
96       // If the user is giving us relative addresses, add the preferred base of
97       // the object to the offset before we do the query. It's what DIContext
98       // expects.
99       if (Opts.RelativeAddresses)
100         ModuleOffset += Info->getModulePreferredBase();
101       if (Info->symbolizeData(ModuleOffset, Name, Start, Size) && Opts.Demangle)
102         Name = DemangleName(Name, Info);
103     }
104   }
105   std::stringstream ss;
106   ss << Name << "\n" << Start << " " << Size << "\n";
107   return ss.str();
108 }
109
110 void LLVMSymbolizer::flush() {
111   Modules.clear();
112   ObjectPairForPathArch.clear();
113   ObjectFileForArch.clear();
114 }
115
116 // For Path="/path/to/foo" and Basename="foo" assume that debug info is in
117 // /path/to/foo.dSYM/Contents/Resources/DWARF/foo.
118 // For Path="/path/to/bar.dSYM" and Basename="foo" assume that debug info is in
119 // /path/to/bar.dSYM/Contents/Resources/DWARF/foo.
120 static
121 std::string getDarwinDWARFResourceForPath(
122     const std::string &Path, const std::string &Basename) {
123   SmallString<16> ResourceName = StringRef(Path);
124   if (sys::path::extension(Path) != ".dSYM") {
125     ResourceName += ".dSYM";
126   }
127   sys::path::append(ResourceName, "Contents", "Resources", "DWARF");
128   sys::path::append(ResourceName, Basename);
129   return ResourceName.str();
130 }
131
132 static bool checkFileCRC(StringRef Path, uint32_t CRCHash) {
133   ErrorOr<std::unique_ptr<MemoryBuffer>> MB =
134       MemoryBuffer::getFileOrSTDIN(Path);
135   if (!MB)
136     return false;
137   return !zlib::isAvailable() || CRCHash == zlib::crc32(MB.get()->getBuffer());
138 }
139
140 static bool findDebugBinary(const std::string &OrigPath,
141                             const std::string &DebuglinkName, uint32_t CRCHash,
142                             std::string &Result) {
143   std::string OrigRealPath = OrigPath;
144 #if defined(HAVE_REALPATH)
145   if (char *RP = realpath(OrigPath.c_str(), nullptr)) {
146     OrigRealPath = RP;
147     free(RP);
148   }
149 #endif
150   SmallString<16> OrigDir(OrigRealPath);
151   llvm::sys::path::remove_filename(OrigDir);
152   SmallString<16> DebugPath = OrigDir;
153   // Try /path/to/original_binary/debuglink_name
154   llvm::sys::path::append(DebugPath, DebuglinkName);
155   if (checkFileCRC(DebugPath, CRCHash)) {
156     Result = DebugPath.str();
157     return true;
158   }
159   // Try /path/to/original_binary/.debug/debuglink_name
160   DebugPath = OrigRealPath;
161   llvm::sys::path::append(DebugPath, ".debug", DebuglinkName);
162   if (checkFileCRC(DebugPath, CRCHash)) {
163     Result = DebugPath.str();
164     return true;
165   }
166   // Try /usr/lib/debug/path/to/original_binary/debuglink_name
167   DebugPath = "/usr/lib/debug";
168   llvm::sys::path::append(DebugPath, llvm::sys::path::relative_path(OrigDir),
169                           DebuglinkName);
170   if (checkFileCRC(DebugPath, CRCHash)) {
171     Result = DebugPath.str();
172     return true;
173   }
174   return false;
175 }
176
177 static bool getGNUDebuglinkContents(const ObjectFile *Obj, std::string &DebugName,
178                                     uint32_t &CRCHash) {
179   if (!Obj)
180     return false;
181   for (const SectionRef &Section : Obj->sections()) {
182     StringRef Name;
183     Section.getName(Name);
184     Name = Name.substr(Name.find_first_not_of("._"));
185     if (Name == "gnu_debuglink") {
186       StringRef Data;
187       Section.getContents(Data);
188       DataExtractor DE(Data, Obj->isLittleEndian(), 0);
189       uint32_t Offset = 0;
190       if (const char *DebugNameStr = DE.getCStr(&Offset)) {
191         // 4-byte align the offset.
192         Offset = (Offset + 3) & ~0x3;
193         if (DE.isValidOffsetForDataOfSize(Offset, 4)) {
194           DebugName = DebugNameStr;
195           CRCHash = DE.getU32(&Offset);
196           return true;
197         }
198       }
199       break;
200     }
201   }
202   return false;
203 }
204
205 static
206 bool darwinDsymMatchesBinary(const MachOObjectFile *DbgObj,
207                              const MachOObjectFile *Obj) {
208   ArrayRef<uint8_t> dbg_uuid = DbgObj->getUuid();
209   ArrayRef<uint8_t> bin_uuid = Obj->getUuid();
210   if (dbg_uuid.empty() || bin_uuid.empty())
211     return false;
212   return !memcmp(dbg_uuid.data(), bin_uuid.data(), dbg_uuid.size());
213 }
214
215 ObjectFile *LLVMSymbolizer::lookUpDsymFile(const std::string &ExePath,
216     const MachOObjectFile *MachExeObj, const std::string &ArchName) {
217   // On Darwin we may find DWARF in separate object file in
218   // resource directory.
219   std::vector<std::string> DsymPaths;
220   StringRef Filename = sys::path::filename(ExePath);
221   DsymPaths.push_back(getDarwinDWARFResourceForPath(ExePath, Filename));
222   for (const auto &Path : Opts.DsymHints) {
223     DsymPaths.push_back(getDarwinDWARFResourceForPath(Path, Filename));
224   }
225   for (const auto &path : DsymPaths) {
226     ErrorOr<OwningBinary<Binary>> BinaryOrErr = createBinary(path);
227     std::error_code EC = BinaryOrErr.getError();
228     if (EC != errc::no_such_file_or_directory && !error(EC)) {
229       OwningBinary<Binary> B = std::move(BinaryOrErr.get());
230       ObjectFile *DbgObj =
231           getObjectFileFromBinary(B.getBinary(), ArchName);
232       const MachOObjectFile *MachDbgObj =
233           dyn_cast<const MachOObjectFile>(DbgObj);
234       if (!MachDbgObj) continue;
235       if (darwinDsymMatchesBinary(MachDbgObj, MachExeObj)) {
236         addOwningBinary(std::move(B));
237         return DbgObj; 
238       }
239     }
240   }
241   return nullptr;
242 }
243
244 LLVMSymbolizer::ObjectPair
245 LLVMSymbolizer::getOrCreateObjects(const std::string &Path,
246                                    const std::string &ArchName) {
247   const auto &I = ObjectPairForPathArch.find(std::make_pair(Path, ArchName));
248   if (I != ObjectPairForPathArch.end())
249     return I->second;
250   ObjectFile *Obj = nullptr;
251   ObjectFile *DbgObj = nullptr;
252   ErrorOr<OwningBinary<Binary>> BinaryOrErr = createBinary(Path);
253   if (!error(BinaryOrErr.getError())) {
254     OwningBinary<Binary> &B = BinaryOrErr.get();
255     Obj = getObjectFileFromBinary(B.getBinary(), ArchName);
256     if (!Obj) {
257       ObjectPair Res = std::make_pair(nullptr, nullptr);
258       ObjectPairForPathArch[std::make_pair(Path, ArchName)] = Res;
259       return Res;
260     }
261     addOwningBinary(std::move(B));
262     if (auto MachObj = dyn_cast<const MachOObjectFile>(Obj))
263       DbgObj = lookUpDsymFile(Path, MachObj, ArchName);
264     // Try to locate the debug binary using .gnu_debuglink section.
265     if (!DbgObj) {
266       std::string DebuglinkName;
267       uint32_t CRCHash;
268       std::string DebugBinaryPath;
269       if (getGNUDebuglinkContents(Obj, DebuglinkName, CRCHash) &&
270           findDebugBinary(Path, DebuglinkName, CRCHash, DebugBinaryPath)) {
271         BinaryOrErr = createBinary(DebugBinaryPath);
272         if (!error(BinaryOrErr.getError())) {
273           OwningBinary<Binary> B = std::move(BinaryOrErr.get());
274           DbgObj = getObjectFileFromBinary(B.getBinary(), ArchName);
275           addOwningBinary(std::move(B));
276         }
277       }
278     }
279   }
280   if (!DbgObj)
281     DbgObj = Obj;
282   ObjectPair Res = std::make_pair(Obj, DbgObj);
283   ObjectPairForPathArch[std::make_pair(Path, ArchName)] = Res;
284   return Res;
285 }
286
287 ObjectFile *
288 LLVMSymbolizer::getObjectFileFromBinary(Binary *Bin,
289                                         const std::string &ArchName) {
290   if (!Bin)
291     return nullptr;
292   ObjectFile *Res = nullptr;
293   if (MachOUniversalBinary *UB = dyn_cast<MachOUniversalBinary>(Bin)) {
294     const auto &I = ObjectFileForArch.find(
295         std::make_pair(UB, ArchName));
296     if (I != ObjectFileForArch.end())
297       return I->second;
298     ErrorOr<std::unique_ptr<ObjectFile>> ParsedObj =
299         UB->getObjectForArch(ArchName);
300     if (ParsedObj) {
301       Res = ParsedObj.get().get();
302       ParsedBinariesAndObjects.push_back(std::move(ParsedObj.get()));
303     }
304     ObjectFileForArch[std::make_pair(UB, ArchName)] = Res;
305   } else if (Bin->isObject()) {
306     Res = cast<ObjectFile>(Bin);
307   }
308   return Res;
309 }
310
311 SymbolizableModule *
312 LLVMSymbolizer::getOrCreateModuleInfo(const std::string &ModuleName) {
313   const auto &I = Modules.find(ModuleName);
314   if (I != Modules.end())
315     return I->second.get();
316   std::string BinaryName = ModuleName;
317   std::string ArchName = Opts.DefaultArch;
318   size_t ColonPos = ModuleName.find_last_of(':');
319   // Verify that substring after colon form a valid arch name.
320   if (ColonPos != std::string::npos) {
321     std::string ArchStr = ModuleName.substr(ColonPos + 1);
322     if (Triple(ArchStr).getArch() != Triple::UnknownArch) {
323       BinaryName = ModuleName.substr(0, ColonPos);
324       ArchName = ArchStr;
325     }
326   }
327   ObjectPair Objects = getOrCreateObjects(BinaryName, ArchName);
328
329   if (!Objects.first) {
330     // Failed to find valid object file.
331     Modules.insert(std::make_pair(ModuleName, nullptr));
332     return nullptr;
333   }
334   std::unique_ptr<DIContext> Context;
335   if (auto CoffObject = dyn_cast<COFFObjectFile>(Objects.first)) {
336     // If this is a COFF object, assume it contains PDB debug information.  If
337     // we don't find any we will fall back to the DWARF case.
338     std::unique_ptr<IPDBSession> Session;
339     PDB_ErrorCode Error = loadDataForEXE(PDB_ReaderType::DIA,
340                                          Objects.first->getFileName(), Session);
341     if (Error == PDB_ErrorCode::Success) {
342       Context.reset(new PDBContext(*CoffObject, std::move(Session)));
343     }
344   }
345   if (!Context)
346     Context.reset(new DWARFContextInMemory(*Objects.second));
347   assert(Context);
348   auto ErrOrInfo =
349       SymbolizableObjectFile::create(Objects.first, std::move(Context));
350   if (error(ErrOrInfo.getError())) {
351     Modules.insert(std::make_pair(ModuleName, nullptr));
352     return nullptr;
353   }
354   SymbolizableModule *Res = ErrOrInfo.get().get();
355   Modules.insert(std::make_pair(ModuleName, std::move(ErrOrInfo.get())));
356   return Res;
357 }
358
359 std::string
360 LLVMSymbolizer::printDILineInfo(DILineInfo LineInfo,
361                                 const SymbolizableModule *ModInfo) const {
362   // By default, DILineInfo contains "<invalid>" for function/filename it
363   // cannot fetch. We replace it to "??" to make our output closer to addr2line.
364   static const std::string kDILineInfoBadString = "<invalid>";
365   std::stringstream Result;
366   if (Opts.PrintFunctions != FunctionNameKind::None) {
367     std::string FunctionName = LineInfo.FunctionName;
368     if (FunctionName == kDILineInfoBadString)
369       FunctionName = kBadString;
370     else if (Opts.Demangle)
371       FunctionName = DemangleName(FunctionName, ModInfo);
372     Result << FunctionName << "\n";
373   }
374   std::string Filename = LineInfo.FileName;
375   if (Filename == kDILineInfoBadString)
376     Filename = kBadString;
377   Result << Filename << ":" << LineInfo.Line << ":" << LineInfo.Column << "\n";
378   return Result.str();
379 }
380
381 // Undo these various manglings for Win32 extern "C" functions:
382 // cdecl       - _foo
383 // stdcall     - _foo@12
384 // fastcall    - @foo@12
385 // vectorcall  - foo@@12
386 // These are all different linkage names for 'foo'.
387 static StringRef demanglePE32ExternCFunc(StringRef SymbolName) {
388   // Remove any '_' or '@' prefix.
389   char Front = SymbolName.empty() ? '\0' : SymbolName[0];
390   if (Front == '_' || Front == '@')
391     SymbolName = SymbolName.drop_front();
392
393   // Remove any '@[0-9]+' suffix.
394   if (Front != '?') {
395     size_t AtPos = SymbolName.rfind('@');
396     if (AtPos != StringRef::npos &&
397         std::all_of(SymbolName.begin() + AtPos + 1, SymbolName.end(),
398                     [](char C) { return C >= '0' && C <= '9'; })) {
399       SymbolName = SymbolName.substr(0, AtPos);
400     }
401   }
402
403   // Remove any ending '@' for vectorcall.
404   if (SymbolName.endswith("@"))
405     SymbolName = SymbolName.drop_back();
406
407   return SymbolName;
408 }
409
410 #if !defined(_MSC_VER)
411 // Assume that __cxa_demangle is provided by libcxxabi (except for Windows).
412 extern "C" char *__cxa_demangle(const char *mangled_name, char *output_buffer,
413                                 size_t *length, int *status);
414 #endif
415
416 std::string LLVMSymbolizer::DemangleName(const std::string &Name,
417                                          const SymbolizableModule *ModInfo) {
418 #if !defined(_MSC_VER)
419   // We can spoil names of symbols with C linkage, so use an heuristic
420   // approach to check if the name should be demangled.
421   if (Name.substr(0, 2) == "_Z") {
422     int status = 0;
423     char *DemangledName = __cxa_demangle(Name.c_str(), nullptr, nullptr, &status);
424     if (status != 0)
425       return Name;
426     std::string Result = DemangledName;
427     free(DemangledName);
428     return Result;
429   }
430 #else
431   if (!Name.empty() && Name.front() == '?') {
432     // Only do MSVC C++ demangling on symbols starting with '?'.
433     char DemangledName[1024] = {0};
434     DWORD result = ::UnDecorateSymbolName(
435         Name.c_str(), DemangledName, 1023,
436         UNDNAME_NO_ACCESS_SPECIFIERS |       // Strip public, private, protected
437             UNDNAME_NO_ALLOCATION_LANGUAGE | // Strip __thiscall, __stdcall, etc
438             UNDNAME_NO_THROW_SIGNATURES |    // Strip throw() specifications
439             UNDNAME_NO_MEMBER_TYPE | // Strip virtual, static, etc specifiers
440             UNDNAME_NO_MS_KEYWORDS | // Strip all MS extension keywords
441             UNDNAME_NO_FUNCTION_RETURNS); // Strip function return types
442     return (result == 0) ? Name : std::string(DemangledName);
443   }
444 #endif
445   if (ModInfo->isWin32Module())
446     return std::string(demanglePE32ExternCFunc(Name));
447   return Name;
448 }
449
450 } // namespace symbolize
451 } // namespace llvm