Skip to content

Commit

Permalink
Search for llvm-symbolizer binary in the same directory as argv[0], b…
Browse files Browse the repository at this point in the history
…efore

looking for it along $PATH. This allows installs of LLVM tools outside of
$PATH to find the symbolizer and produce pretty backtraces if they crash.


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@272232 91177308-0d34-0410-b5e6-96231b3b80d8
  • Loading branch information
zygoloid committed Jun 9, 2016
1 parent 14f9bce commit 0eeb3d4
Show file tree
Hide file tree
Showing 41 changed files with 87 additions and 73 deletions.
10 changes: 8 additions & 2 deletions include/llvm/Support/Signals.h
Original file line number Diff line number Diff line change
Expand Up @@ -38,8 +38,14 @@ namespace sys {

/// When an error signal (such as SIBABRT or SIGSEGV) is delivered to the
/// process, print a stack trace and then exit.
/// @brief Print a stack trace if a fatal signal occurs.
void PrintStackTraceOnErrorSignal(bool DisableCrashReporting = false);
/// \brief Print a stack trace if a fatal signal occurs.
/// \param Argv0 the current binary name, used to find the symbolizer
/// relative to the current binary before searching $PATH; can be
/// StringRef(), in which case we will only search $PATH.
/// \param DisableCrashReporting if \c true, disable the normal crash
/// reporting mechanisms on the underlying operating system.
void PrintStackTraceOnErrorSignal(StringRef Argv0,
bool DisableCrashReporting = false);

/// Disable all system dialog boxes that appear when the process crashes.
void DisableSystemDialogsOnCrash();
Expand Down
34 changes: 23 additions & 11 deletions lib/Support/Signals.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -62,28 +62,40 @@ static FormattedNumber format_ptr(void *PC) {
return format_hex((uint64_t)PC, PtrWidth);
}

static bool printSymbolizedStackTrace(void **StackTrace, int Depth,
static bool printSymbolizedStackTrace(StringRef Argv0,
void **StackTrace, int Depth,
llvm::raw_ostream &OS)
LLVM_ATTRIBUTE_USED;

/// Helper that launches llvm-symbolizer and symbolizes a backtrace.
static bool printSymbolizedStackTrace(void **StackTrace, int Depth,
static bool printSymbolizedStackTrace(StringRef Argv0,
void **StackTrace, int Depth,
llvm::raw_ostream &OS) {
// Don't recursively invoke the llvm-symbolizer binary.
if (Argv0.find("llvm-symbolizer") != std::string::npos)
return false;

// FIXME: Subtract necessary number from StackTrace entries to turn return addresses
// into actual instruction addresses.
// Use llvm-symbolizer tool to symbolize the stack traces.
ErrorOr<std::string> LLVMSymbolizerPathOrErr =
sys::findProgramByName("llvm-symbolizer");
// Use llvm-symbolizer tool to symbolize the stack traces. First look for it
// alongside our binary, then in $PATH.
ErrorOr<std::string> LLVMSymbolizerPathOrErr = std::error_code();
if (!Argv0.empty()) {
StringRef Parent = llvm::sys::path::parent_path(Argv0);
if (!Parent.empty())
LLVMSymbolizerPathOrErr = sys::findProgramByName("llvm-symbolizer", Parent);
}
if (!LLVMSymbolizerPathOrErr)
LLVMSymbolizerPathOrErr = sys::findProgramByName("llvm-symbolizer");
if (!LLVMSymbolizerPathOrErr)
return false;
const std::string &LLVMSymbolizerPath = *LLVMSymbolizerPathOrErr;
// We don't know argv0 or the address of main() at this point, but try
// to guess it anyway (it's possible on some platforms).
std::string MainExecutableName = sys::fs::getMainExecutable(nullptr, nullptr);
if (MainExecutableName.empty() ||
MainExecutableName.find("llvm-symbolizer") != std::string::npos)
return false;

// If we don't know argv0 or the address of main() at this point, try
// to guess it anyway (it's possible on some platforms).
std::string MainExecutableName =
Argv0.empty() ? sys::fs::getMainExecutable(nullptr, nullptr)
: (std::string)Argv0;
BumpPtrAllocator Allocator;
StringSaver StrPool(Allocator);
std::vector<const char *> Modules(Depth, nullptr);
Expand Down
9 changes: 7 additions & 2 deletions lib/Support/Unix/Signals.inc
Original file line number Diff line number Diff line change
Expand Up @@ -68,6 +68,8 @@ static void (*InterruptFunction)() = nullptr;

static ManagedStatic<std::vector<std::string>> FilesToRemove;

static StringRef Argv0;

// IntSigs - Signals that represent requested termination. There's no bug
// or failure, or if there is, it's not our direct responsibility. For whatever
// reason, our continued execution is no longer desirable.
Expand Down Expand Up @@ -408,7 +410,7 @@ void llvm::sys::PrintStackTrace(raw_ostream &OS) {
if (!depth)
return;

if (printSymbolizedStackTrace(StackTrace, depth, OS))
if (printSymbolizedStackTrace(Argv0, StackTrace, depth, OS))
return;
#if HAVE_DLFCN_H && __GNUG__
int width = 0;
Expand Down Expand Up @@ -471,7 +473,10 @@ void llvm::sys::DisableSystemDialogsOnCrash() {}

/// PrintStackTraceOnErrorSignal - When an error signal (such as SIGABRT or
/// SIGSEGV) is delivered to the process, print a stack trace and then exit.
void llvm::sys::PrintStackTraceOnErrorSignal(bool DisableCrashReporting) {
void llvm::sys::PrintStackTraceOnErrorSignal(StringRef Argv0,
bool DisableCrashReporting) {
::Argv0 = Argv0;

AddSignalHandler(PrintStackTraceSignalHandler, nullptr);

#if defined(__APPLE__) && defined(ENABLE_CRASH_OVERRIDES)
Expand Down
9 changes: 7 additions & 2 deletions lib/Support/Windows/Signals.inc
Original file line number Diff line number Diff line change
Expand Up @@ -206,6 +206,8 @@ static PTOP_LEVEL_EXCEPTION_FILTER OldFilter = NULL;
static CRITICAL_SECTION CriticalSection;
static bool CriticalSectionInitialized = false;

static StringRef Argv0;

enum {
#if defined(_M_X64)
NativeMachineType = IMAGE_FILE_MACHINE_AMD64
Expand Down Expand Up @@ -240,7 +242,7 @@ static bool printStackTraceWithLLVMSymbolizer(llvm::raw_ostream &OS,
break;
}

return printSymbolizedStackTrace(&StackTrace[0], Depth, OS);
return printSymbolizedStackTrace(Argv0, &StackTrace[0], Depth, OS);
}

namespace {
Expand Down Expand Up @@ -496,7 +498,10 @@ void sys::DisableSystemDialogsOnCrash() {

/// PrintStackTraceOnErrorSignal - When an error signal (such as SIBABRT or
/// SIGSEGV) is delivered to the process, print a stack trace and then exit.
void sys::PrintStackTraceOnErrorSignal(bool DisableCrashReporting) {
void sys::PrintStackTraceOnErrorSignal(StringRef Argv0,
bool DisableCrashReporting) {
::Argv0 = Argv0;

if (DisableCrashReporting || getenv("LLVM_DISABLE_CRASH_REPORT"))
Process::PreventCoreFiles();

Expand Down
2 changes: 1 addition & 1 deletion tools/bugpoint/bugpoint.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -113,7 +113,7 @@ void initializePollyPasses(llvm::PassRegistry &Registry);

int main(int argc, char **argv) {
#ifndef DEBUG_BUGPOINT
llvm::sys::PrintStackTraceOnErrorSignal();
llvm::sys::PrintStackTraceOnErrorSignal(argv[0]);
llvm::PrettyStackTraceProgram X(argc, argv);
llvm_shutdown_obj Y; // Call llvm_shutdown() on exit.
#endif
Expand Down
2 changes: 1 addition & 1 deletion tools/dsymutil/dsymutil.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -237,7 +237,7 @@ void llvm::dsymutil::exitDsymutil(int ExitStatus) {
}

int main(int argc, char **argv) {
llvm::sys::PrintStackTraceOnErrorSignal();
llvm::sys::PrintStackTraceOnErrorSignal(argv[0]);
llvm::PrettyStackTraceProgram StackPrinter(argc, argv);
llvm::llvm_shutdown_obj Shutdown;
LinkOptions Options;
Expand Down
2 changes: 1 addition & 1 deletion tools/llc/llc.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -202,7 +202,7 @@ static void DiagnosticHandler(const DiagnosticInfo &DI, void *Context) {
// main - Entry point for the llc compiler.
//
int main(int argc, char **argv) {
sys::PrintStackTraceOnErrorSignal();
sys::PrintStackTraceOnErrorSignal(argv[0]);
PrettyStackTraceProgram X(argc, argv);

// Enable debug stream buffering.
Expand Down
2 changes: 1 addition & 1 deletion tools/lli/lli.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -365,7 +365,7 @@ CodeGenOpt::Level getOptLevel() {
// main Driver function
//
int main(int argc, char **argv, char * const *envp) {
sys::PrintStackTraceOnErrorSignal();
sys::PrintStackTraceOnErrorSignal(argv[0]);
PrettyStackTraceProgram X(argc, argv);

atexit(llvm_shutdown); // Call llvm_shutdown() on exit.
Expand Down
2 changes: 1 addition & 1 deletion tools/llvm-ar/llvm-ar.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -773,7 +773,7 @@ static int ranlib_main() {
int main(int argc, char **argv) {
ToolName = argv[0];
// Print a stack trace if we signal out.
sys::PrintStackTraceOnErrorSignal();
sys::PrintStackTraceOnErrorSignal(argv[0]);
PrettyStackTraceProgram X(argc, argv);
llvm_shutdown_obj Y; // Call llvm_shutdown() on exit.

Expand Down
2 changes: 1 addition & 1 deletion tools/llvm-as/llvm-as.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -89,7 +89,7 @@ static void WriteOutputFile(const Module *M) {

int main(int argc, char **argv) {
// Print a stack trace if we signal out.
sys::PrintStackTraceOnErrorSignal();
sys::PrintStackTraceOnErrorSignal(argv[0]);
PrettyStackTraceProgram X(argc, argv);
LLVMContext Context;
llvm_shutdown_obj Y; // Call llvm_shutdown() on exit.
Expand Down
2 changes: 1 addition & 1 deletion tools/llvm-bcanalyzer/llvm-bcanalyzer.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -915,7 +915,7 @@ static int AnalyzeBitcode() {

int main(int argc, char **argv) {
// Print a stack trace if we signal out.
sys::PrintStackTraceOnErrorSignal();
sys::PrintStackTraceOnErrorSignal(argv[0]);
PrettyStackTraceProgram X(argc, argv);
llvm_shutdown_obj Y; // Call llvm_shutdown() on exit.
cl::ParseCommandLineOptions(argc, argv, "llvm-bcanalyzer file analyzer\n");
Expand Down
8 changes: 0 additions & 8 deletions tools/llvm-cov/CodeCoverage.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -26,11 +26,8 @@
#include "llvm/Support/CommandLine.h"
#include "llvm/Support/FileSystem.h"
#include "llvm/Support/Format.h"
#include "llvm/Support/ManagedStatic.h"
#include "llvm/Support/Path.h"
#include "llvm/Support/PrettyStackTrace.h"
#include "llvm/Support/Process.h"
#include "llvm/Support/Signals.h"
#include <functional>
#include <system_error>

Expand Down Expand Up @@ -240,11 +237,6 @@ std::unique_ptr<CoverageMapping> CodeCoverageTool::load() {
}

int CodeCoverageTool::run(Command Cmd, int argc, const char **argv) {
// Print a stack trace if we signal out.
sys::PrintStackTraceOnErrorSignal();
PrettyStackTraceProgram X(argc, argv);
llvm_shutdown_obj Y; // Call llvm_shutdown() on exit.

cl::opt<std::string, true> ObjectFilename(
cl::Positional, cl::Required, cl::location(this->ObjectFilename),
cl::desc("Covered executable or object file."));
Expand Down
7 changes: 0 additions & 7 deletions tools/llvm-cov/TestingSupport.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -11,9 +11,6 @@
#include "llvm/ProfileData/InstrProf.h"
#include "llvm/Support/CommandLine.h"
#include "llvm/Support/LEB128.h"
#include "llvm/Support/ManagedStatic.h"
#include "llvm/Support/PrettyStackTrace.h"
#include "llvm/Support/Signals.h"
#include "llvm/Support/raw_ostream.h"
#include <functional>
#include <system_error>
Expand All @@ -22,10 +19,6 @@ using namespace llvm;
using namespace object;

int convertForTestingMain(int argc, const char *argv[]) {
sys::PrintStackTraceOnErrorSignal();
PrettyStackTraceProgram X(argc, argv);
llvm_shutdown_obj Y; // Call llvm_shutdown() on exit.

cl::opt<std::string> InputSourceFile(cl::Positional, cl::Required,
cl::desc("<Source file>"));

Expand Down
8 changes: 0 additions & 8 deletions tools/llvm-cov/gcov.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -16,10 +16,7 @@
#include "llvm/Support/Errc.h"
#include "llvm/Support/FileSystem.h"
#include "llvm/Support/GCOV.h"
#include "llvm/Support/ManagedStatic.h"
#include "llvm/Support/Path.h"
#include "llvm/Support/PrettyStackTrace.h"
#include "llvm/Support/Signals.h"
#include <system_error>
using namespace llvm;

Expand Down Expand Up @@ -85,11 +82,6 @@ static void reportCoverage(StringRef SourceFile, StringRef ObjectDir,
}

int gcovMain(int argc, const char *argv[]) {
// Print a stack trace if we signal out.
sys::PrintStackTraceOnErrorSignal();
PrettyStackTraceProgram X(argc, argv);
llvm_shutdown_obj Y; // Call llvm_shutdown() on exit.

cl::list<std::string> SourceFiles(cl::Positional, cl::OneOrMore,
cl::desc("SOURCEFILE"));

Expand Down
8 changes: 8 additions & 0 deletions tools/llvm-cov/llvm-cov.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -14,8 +14,11 @@
#include "llvm/ADT/StringRef.h"
#include "llvm/ADT/StringSwitch.h"
#include "llvm/Support/CommandLine.h"
#include "llvm/Support/ManagedStatic.h"
#include "llvm/Support/Path.h"
#include "llvm/Support/PrettyStackTrace.h"
#include "llvm/Support/Process.h"
#include "llvm/Support/Signals.h"
#include "llvm/Support/raw_ostream.h"
#include <string>

Expand Down Expand Up @@ -51,6 +54,11 @@ static int versionMain(int argc, const char *argv[]) {
}

int main(int argc, const char **argv) {
// Print a stack trace if we signal out.
sys::PrintStackTraceOnErrorSignal(argv[0]);
PrettyStackTraceProgram X(argc, argv);
llvm_shutdown_obj Y; // Call llvm_shutdown() on exit.

// If argv[0] is or ends with 'gcov', always be gcov compatible
if (sys::path::stem(argv[0]).endswith_lower("gcov"))
return gcovMain(argc, argv);
Expand Down
2 changes: 1 addition & 1 deletion tools/llvm-cxxdump/llvm-cxxdump.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -525,7 +525,7 @@ static void dumpInput(StringRef File) {
}

int main(int argc, const char *argv[]) {
sys::PrintStackTraceOnErrorSignal();
sys::PrintStackTraceOnErrorSignal(argv[0]);
PrettyStackTraceProgram X(argc, argv);
llvm_shutdown_obj Y;

Expand Down
2 changes: 1 addition & 1 deletion tools/llvm-dis/llvm-dis.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -134,7 +134,7 @@ static void diagnosticHandler(const DiagnosticInfo &DI, void *Context) {

int main(int argc, char **argv) {
// Print a stack trace if we signal out.
sys::PrintStackTraceOnErrorSignal();
sys::PrintStackTraceOnErrorSignal(argv[0]);
PrettyStackTraceProgram X(argc, argv);

LLVMContext Context;
Expand Down
2 changes: 1 addition & 1 deletion tools/llvm-dwarfdump/llvm-dwarfdump.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -146,7 +146,7 @@ static std::vector<std::string> expandBundle(const std::string &InputPath) {

int main(int argc, char **argv) {
// Print a stack trace if we signal out.
sys::PrintStackTraceOnErrorSignal();
sys::PrintStackTraceOnErrorSignal(argv[0]);
PrettyStackTraceProgram X(argc, argv);
llvm_shutdown_obj Y; // Call llvm_shutdown() on exit.

Expand Down
2 changes: 1 addition & 1 deletion tools/llvm-extract/llvm-extract.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -102,7 +102,7 @@ static cl::opt<bool> PreserveAssemblyUseListOrder(

int main(int argc, char **argv) {
// Print a stack trace if we signal out.
sys::PrintStackTraceOnErrorSignal();
sys::PrintStackTraceOnErrorSignal(argv[0]);
PrettyStackTraceProgram X(argc, argv);

LLVMContext Context;
Expand Down
2 changes: 1 addition & 1 deletion tools/llvm-jitlistener/llvm-jitlistener.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -179,7 +179,7 @@ InputFilename(cl::Positional, cl::desc("<input IR file>"),

int main(int argc, char **argv) {
// Print a stack trace if we signal out.
sys::PrintStackTraceOnErrorSignal();
sys::PrintStackTraceOnErrorSignal(argv[0]);
PrettyStackTraceProgram X(argc, argv);
llvm_shutdown_obj Y; // Call llvm_shutdown() on exit.

Expand Down
2 changes: 1 addition & 1 deletion tools/llvm-link/llvm-link.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -335,7 +335,7 @@ static bool linkFiles(const char *argv0, LLVMContext &Context, Linker &L,

int main(int argc, char **argv) {
// Print a stack trace if we signal out.
sys::PrintStackTraceOnErrorSignal();
sys::PrintStackTraceOnErrorSignal(argv[0]);
PrettyStackTraceProgram X(argc, argv);

LLVMContext Context;
Expand Down
2 changes: 1 addition & 1 deletion tools/llvm-lto/llvm-lto.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -691,7 +691,7 @@ class ThinLTOProcessing {

int main(int argc, char **argv) {
// Print a stack trace if we signal out.
sys::PrintStackTraceOnErrorSignal();
sys::PrintStackTraceOnErrorSignal(argv[0]);
PrettyStackTraceProgram X(argc, argv);

llvm_shutdown_obj Y; // Call llvm_shutdown() on exit.
Expand Down
2 changes: 1 addition & 1 deletion tools/llvm-mc/llvm-mc.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -369,7 +369,7 @@ static int AssembleInput(const char *ProgName, const Target *TheTarget,

int main(int argc, char **argv) {
// Print a stack trace if we signal out.
sys::PrintStackTraceOnErrorSignal();
sys::PrintStackTraceOnErrorSignal(argv[0]);
PrettyStackTraceProgram X(argc, argv);
llvm_shutdown_obj Y; // Call llvm_shutdown() on exit.

Expand Down
2 changes: 1 addition & 1 deletion tools/llvm-mcmarkup/llvm-mcmarkup.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -208,7 +208,7 @@ static void parseMCMarkup(StringRef Filename) {

int main(int argc, char **argv) {
// Print a stack trace if we signal out.
sys::PrintStackTraceOnErrorSignal();
sys::PrintStackTraceOnErrorSignal(argv[0]);
PrettyStackTraceProgram X(argc, argv);

llvm_shutdown_obj Y; // Call llvm_shutdown() on exit.
Expand Down
2 changes: 1 addition & 1 deletion tools/llvm-nm/llvm-nm.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1347,7 +1347,7 @@ static void dumpSymbolNamesFromFile(std::string &Filename) {

int main(int argc, char **argv) {
// Print a stack trace if we signal out.
sys::PrintStackTraceOnErrorSignal();
sys::PrintStackTraceOnErrorSignal(argv[0]);
PrettyStackTraceProgram X(argc, argv);

llvm_shutdown_obj Y; // Call llvm_shutdown() on exit.
Expand Down
2 changes: 1 addition & 1 deletion tools/llvm-objdump/llvm-objdump.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1736,7 +1736,7 @@ static void DumpInput(StringRef file) {

int main(int argc, char **argv) {
// Print a stack trace if we signal out.
sys::PrintStackTraceOnErrorSignal();
sys::PrintStackTraceOnErrorSignal(argv[0]);
PrettyStackTraceProgram X(argc, argv);
llvm_shutdown_obj Y; // Call llvm_shutdown() on exit.

Expand Down
2 changes: 1 addition & 1 deletion tools/llvm-pdbdump/llvm-pdbdump.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -433,7 +433,7 @@ static void dumpInput(StringRef Path) {

int main(int argc_, const char *argv_[]) {
// Print a stack trace if we signal out.
sys::PrintStackTraceOnErrorSignal();
sys::PrintStackTraceOnErrorSignal(argv_[0]);
PrettyStackTraceProgram X(argc_, argv_);

ExitOnErr.setBanner("llvm-pdbdump: ");
Expand Down
Loading

0 comments on commit 0eeb3d4

Please sign in to comment.