[compiler-rt] r182372 - [nolibc] Move symbolizer to RTSanitizerCommonLibc, and make it optional using a weak symbol.
Peter Collingbourne
peter at pcc.me.uk
Tue May 21 05:08:38 PDT 2013
Author: pcc
Date: Tue May 21 07:08:37 2013
New Revision: 182372
URL: http://llvm.org/viewvc/llvm-project?rev=182372&view=rev
Log:
[nolibc] Move symbolizer to RTSanitizerCommonLibc, and make it optional using a weak symbol.
Added:
compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer_libcdep.cc
- copied, changed from r182369, compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer.cc
compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer_linux_libcdep.cc
- copied, changed from r182369, compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer_linux.cc
Removed:
compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer.cc
compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer_linux.cc
Modified:
compiler-rt/trunk/lib/sanitizer_common/CMakeLists.txt
compiler-rt/trunk/lib/sanitizer_common/sanitizer_stacktrace.cc
compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer.h
Modified: compiler-rt/trunk/lib/sanitizer_common/CMakeLists.txt
URL: http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/sanitizer_common/CMakeLists.txt?rev=182372&r1=182371&r2=182372&view=diff
==============================================================================
--- compiler-rt/trunk/lib/sanitizer_common/CMakeLists.txt (original)
+++ compiler-rt/trunk/lib/sanitizer_common/CMakeLists.txt Tue May 21 07:08:37 2013
@@ -13,9 +13,7 @@ set(SANITIZER_SOURCES
sanitizer_printf.cc
sanitizer_stackdepot.cc
sanitizer_stacktrace.cc
- sanitizer_symbolizer.cc
sanitizer_symbolizer_itanium.cc
- sanitizer_symbolizer_linux.cc
sanitizer_symbolizer_mac.cc
sanitizer_symbolizer_win.cc
sanitizer_thread_registry.cc
@@ -27,6 +25,8 @@ set(SANITIZER_LIBCDEP_SOURCES
sanitizer_linux_libcdep.cc
sanitizer_posix_libcdep.cc
sanitizer_stoptheworld_linux_libcdep.cc
+ sanitizer_symbolizer_libcdep.cc
+ sanitizer_symbolizer_linux_libcdep.cc
)
# Explicitly list all sanitizer_common headers. Not all of these are
Modified: compiler-rt/trunk/lib/sanitizer_common/sanitizer_stacktrace.cc
URL: http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/sanitizer_common/sanitizer_stacktrace.cc?rev=182372&r1=182371&r2=182372&view=diff
==============================================================================
--- compiler-rt/trunk/lib/sanitizer_common/sanitizer_stacktrace.cc (original)
+++ compiler-rt/trunk/lib/sanitizer_common/sanitizer_stacktrace.cc Tue May 21 07:08:37 2013
@@ -85,7 +85,7 @@ void StackTrace::PrintStack(const uptr *
frame_num++;
}
}
- if (symbolize && addr_frames_num == 0) {
+ if (symbolize && addr_frames_num == 0 && SymbolizeCode) {
// Use our own (online) symbolizer, if necessary.
addr_frames_num = SymbolizeCode(pc, addr_frames.data(),
addr_frames.size());
Removed: compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer.cc
URL: http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer.cc?rev=182371&view=auto
==============================================================================
--- compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer.cc (original)
+++ compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer.cc (removed)
@@ -1,453 +0,0 @@
-//===-- sanitizer_symbolizer.cc -------------------------------------------===//
-//
-// The LLVM Compiler Infrastructure
-//
-// This file is distributed under the University of Illinois Open Source
-// License. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-//
-// This file is shared between AddressSanitizer and ThreadSanitizer
-// run-time libraries. See sanitizer_symbolizer.h for details.
-//===----------------------------------------------------------------------===//
-
-#include "sanitizer_common.h"
-#include "sanitizer_placement_new.h"
-#include "sanitizer_procmaps.h"
-#include "sanitizer_symbolizer.h"
-
-namespace __sanitizer {
-
-void AddressInfo::Clear() {
- InternalFree(module);
- InternalFree(function);
- InternalFree(file);
- internal_memset(this, 0, sizeof(AddressInfo));
-}
-
-LoadedModule::LoadedModule(const char *module_name, uptr base_address) {
- full_name_ = internal_strdup(module_name);
- base_address_ = base_address;
- n_ranges_ = 0;
-}
-
-void LoadedModule::addAddressRange(uptr beg, uptr end) {
- CHECK_LT(n_ranges_, kMaxNumberOfAddressRanges);
- ranges_[n_ranges_].beg = beg;
- ranges_[n_ranges_].end = end;
- n_ranges_++;
-}
-
-bool LoadedModule::containsAddress(uptr address) const {
- for (uptr i = 0; i < n_ranges_; i++) {
- if (ranges_[i].beg <= address && address < ranges_[i].end)
- return true;
- }
- return false;
-}
-
-// Extracts the prefix of "str" that consists of any characters not
-// present in "delims" string, and copies this prefix to "result", allocating
-// space for it.
-// Returns a pointer to "str" after skipping extracted prefix and first
-// delimiter char.
-static const char *ExtractToken(const char *str, const char *delims,
- char **result) {
- uptr prefix_len = internal_strcspn(str, delims);
- *result = (char*)InternalAlloc(prefix_len + 1);
- internal_memcpy(*result, str, prefix_len);
- (*result)[prefix_len] = '\0';
- const char *prefix_end = str + prefix_len;
- if (*prefix_end != '\0') prefix_end++;
- return prefix_end;
-}
-
-// Same as ExtractToken, but converts extracted token to integer.
-static const char *ExtractInt(const char *str, const char *delims,
- int *result) {
- char *buff;
- const char *ret = ExtractToken(str, delims, &buff);
- if (buff != 0) {
- *result = (int)internal_atoll(buff);
- }
- InternalFree(buff);
- return ret;
-}
-
-static const char *ExtractUptr(const char *str, const char *delims,
- uptr *result) {
- char *buff;
- const char *ret = ExtractToken(str, delims, &buff);
- if (buff != 0) {
- *result = (uptr)internal_atoll(buff);
- }
- InternalFree(buff);
- return ret;
-}
-
-// ExternalSymbolizer encapsulates communication between the tool and
-// external symbolizer program, running in a different subprocess,
-// For now we assume the following protocol:
-// For each request of the form
-// <module_name> <module_offset>
-// passed to STDIN, external symbolizer prints to STDOUT response:
-// <function_name>
-// <file_name>:<line_number>:<column_number>
-// <function_name>
-// <file_name>:<line_number>:<column_number>
-// ...
-// <empty line>
-class ExternalSymbolizer {
- public:
- ExternalSymbolizer(const char *path, int input_fd, int output_fd)
- : path_(path),
- input_fd_(input_fd),
- output_fd_(output_fd),
- times_restarted_(0) {
- CHECK(path_);
- CHECK_NE(input_fd_, kInvalidFd);
- CHECK_NE(output_fd_, kInvalidFd);
- }
-
- char *SendCommand(bool is_data, const char *module_name, uptr module_offset) {
- CHECK(module_name);
- internal_snprintf(buffer_, kBufferSize, "%s\"%s\" 0x%zx\n",
- is_data ? "DATA " : "", module_name, module_offset);
- if (!writeToSymbolizer(buffer_, internal_strlen(buffer_)))
- return 0;
- if (!readFromSymbolizer(buffer_, kBufferSize))
- return 0;
- return buffer_;
- }
-
- bool Restart() {
- if (times_restarted_ >= kMaxTimesRestarted) return false;
- times_restarted_++;
- internal_close(input_fd_);
- internal_close(output_fd_);
- return StartSymbolizerSubprocess(path_, &input_fd_, &output_fd_);
- }
-
- void Flush() {
- }
-
- private:
- bool readFromSymbolizer(char *buffer, uptr max_length) {
- if (max_length == 0)
- return true;
- uptr read_len = 0;
- while (true) {
- uptr just_read = internal_read(input_fd_, buffer + read_len,
- max_length - read_len);
- // We can't read 0 bytes, as we don't expect external symbolizer to close
- // its stdout.
- if (just_read == 0 || just_read == (uptr)-1) {
- Report("WARNING: Can't read from symbolizer at fd %d\n", input_fd_);
- return false;
- }
- read_len += just_read;
- // Empty line marks the end of symbolizer output.
- if (read_len >= 2 && buffer[read_len - 1] == '\n' &&
- buffer[read_len - 2] == '\n') {
- break;
- }
- }
- return true;
- }
-
- bool writeToSymbolizer(const char *buffer, uptr length) {
- if (length == 0)
- return true;
- uptr write_len = internal_write(output_fd_, buffer, length);
- if (write_len == 0 || write_len == (uptr)-1) {
- Report("WARNING: Can't write to symbolizer at fd %d\n", output_fd_);
- return false;
- }
- return true;
- }
-
- const char *path_;
- int input_fd_;
- int output_fd_;
-
- static const uptr kBufferSize = 16 * 1024;
- char buffer_[kBufferSize];
-
- static const uptr kMaxTimesRestarted = 5;
- uptr times_restarted_;
-};
-
-static LowLevelAllocator symbolizer_allocator; // Linker initialized.
-
-#if SANITIZER_SUPPORTS_WEAK_HOOKS
-extern "C" {
-SANITIZER_WEAK_ATTRIBUTE SANITIZER_INTERFACE_ATTRIBUTE
-bool __sanitizer_symbolize_code(const char *ModuleName, u64 ModuleOffset,
- char *Buffer, int MaxLength);
-SANITIZER_WEAK_ATTRIBUTE SANITIZER_INTERFACE_ATTRIBUTE
-bool __sanitizer_symbolize_data(const char *ModuleName, u64 ModuleOffset,
- char *Buffer, int MaxLength);
-SANITIZER_WEAK_ATTRIBUTE SANITIZER_INTERFACE_ATTRIBUTE
-void __sanitizer_symbolize_flush();
-} // extern "C"
-
-class InternalSymbolizer {
- public:
- typedef bool (*SanitizerSymbolizeFn)(const char*, u64, char*, int);
-
- static InternalSymbolizer *get() {
- if (__sanitizer_symbolize_code != 0 &&
- __sanitizer_symbolize_data != 0) {
- void *mem = symbolizer_allocator.Allocate(sizeof(InternalSymbolizer));
- return new(mem) InternalSymbolizer();
- }
- return 0;
- }
-
- char *SendCommand(bool is_data, const char *module_name, uptr module_offset) {
- SanitizerSymbolizeFn symbolize_fn = is_data ? __sanitizer_symbolize_data
- : __sanitizer_symbolize_code;
- if (symbolize_fn(module_name, module_offset, buffer_, kBufferSize))
- return buffer_;
- return 0;
- }
-
- void Flush() {
- if (__sanitizer_symbolize_flush)
- __sanitizer_symbolize_flush();
- }
-
- private:
- InternalSymbolizer() { }
-
- static const int kBufferSize = 16 * 1024;
- char buffer_[kBufferSize];
-};
-#else // SANITIZER_SUPPORTS_WEAK_HOOKS
-
-class InternalSymbolizer {
- public:
- static InternalSymbolizer *get() { return 0; }
- char *SendCommand(bool is_data, const char *module_name, uptr module_offset) {
- return 0;
- }
- void Flush() {
- }
-};
-
-#endif // SANITIZER_SUPPORTS_WEAK_HOOKS
-
-class Symbolizer {
- // This class has no constructor, as global constructors are forbidden in
- // sanitizer_common. It should be linker initialized instead.
- public:
- uptr SymbolizeCode(uptr addr, AddressInfo *frames, uptr max_frames) {
- if (max_frames == 0)
- return 0;
- LoadedModule *module = FindModuleForAddress(addr);
- if (module == 0)
- return 0;
- const char *module_name = module->full_name();
- uptr module_offset = addr - module->base_address();
- const char *str = SendCommand(false, module_name, module_offset);
- if (str == 0) {
- // External symbolizer was not initialized or failed. Fill only data
- // about module name and offset.
- AddressInfo *info = &frames[0];
- info->Clear();
- info->FillAddressAndModuleInfo(addr, module_name, module_offset);
- return 1;
- }
- uptr frame_id = 0;
- for (frame_id = 0; frame_id < max_frames; frame_id++) {
- AddressInfo *info = &frames[frame_id];
- char *function_name = 0;
- str = ExtractToken(str, "\n", &function_name);
- CHECK(function_name);
- if (function_name[0] == '\0') {
- // There are no more frames.
- break;
- }
- info->Clear();
- info->FillAddressAndModuleInfo(addr, module_name, module_offset);
- info->function = function_name;
- // Parse <file>:<line>:<column> buffer.
- char *file_line_info = 0;
- str = ExtractToken(str, "\n", &file_line_info);
- CHECK(file_line_info);
- const char *line_info = ExtractToken(file_line_info, ":", &info->file);
- line_info = ExtractInt(line_info, ":", &info->line);
- line_info = ExtractInt(line_info, "", &info->column);
- InternalFree(file_line_info);
-
- // Functions and filenames can be "??", in which case we write 0
- // to address info to mark that names are unknown.
- if (0 == internal_strcmp(info->function, "??")) {
- InternalFree(info->function);
- info->function = 0;
- }
- if (0 == internal_strcmp(info->file, "??")) {
- InternalFree(info->file);
- info->file = 0;
- }
- }
- if (frame_id == 0) {
- // Make sure we return at least one frame.
- AddressInfo *info = &frames[0];
- info->Clear();
- info->FillAddressAndModuleInfo(addr, module_name, module_offset);
- frame_id = 1;
- }
- return frame_id;
- }
-
- bool SymbolizeData(uptr addr, DataInfo *info) {
- LoadedModule *module = FindModuleForAddress(addr);
- if (module == 0)
- return false;
- const char *module_name = module->full_name();
- uptr module_offset = addr - module->base_address();
- internal_memset(info, 0, sizeof(*info));
- info->address = addr;
- info->module = internal_strdup(module_name);
- info->module_offset = module_offset;
- const char *str = SendCommand(true, module_name, module_offset);
- if (str == 0)
- return true;
- str = ExtractToken(str, "\n", &info->name);
- str = ExtractUptr(str, " ", &info->start);
- str = ExtractUptr(str, "\n", &info->size);
- info->start += module->base_address();
- return true;
- }
-
- bool InitializeExternalSymbolizer(const char *path_to_symbolizer) {
- int input_fd, output_fd;
- if (!StartSymbolizerSubprocess(path_to_symbolizer, &input_fd, &output_fd))
- return false;
- void *mem = symbolizer_allocator.Allocate(sizeof(ExternalSymbolizer));
- external_symbolizer_ = new(mem) ExternalSymbolizer(path_to_symbolizer,
- input_fd, output_fd);
- return true;
- }
-
- bool IsSymbolizerAvailable() {
- if (internal_symbolizer_ == 0)
- internal_symbolizer_ = InternalSymbolizer::get();
- return internal_symbolizer_ || external_symbolizer_;
- }
-
- void Flush() {
- if (internal_symbolizer_)
- internal_symbolizer_->Flush();
- if (external_symbolizer_)
- external_symbolizer_->Flush();
- }
-
- private:
- char *SendCommand(bool is_data, const char *module_name, uptr module_offset) {
- // First, try to use internal symbolizer.
- if (!IsSymbolizerAvailable()) {
- return 0;
- }
- if (internal_symbolizer_) {
- return internal_symbolizer_->SendCommand(is_data, module_name,
- module_offset);
- }
- // Otherwise, fall back to external symbolizer.
- if (external_symbolizer_ == 0) {
- ReportExternalSymbolizerError(
- "WARNING: Trying to symbolize code, but external "
- "symbolizer is not initialized!\n");
- return 0;
- }
- for (;;) {
- char *reply = external_symbolizer_->SendCommand(is_data, module_name,
- module_offset);
- if (reply)
- return reply;
- // Try to restart symbolizer subprocess. If we don't succeed, forget
- // about it and don't try to use it later.
- if (!external_symbolizer_->Restart()) {
- ReportExternalSymbolizerError(
- "WARNING: Failed to use and restart external symbolizer!\n");
- external_symbolizer_ = 0;
- return 0;
- }
- }
- }
-
- LoadedModule *FindModuleForAddress(uptr address) {
- bool modules_were_reloaded = false;
- if (modules_ == 0 || !modules_fresh_) {
- modules_ = (LoadedModule*)(symbolizer_allocator.Allocate(
- kMaxNumberOfModuleContexts * sizeof(LoadedModule)));
- CHECK(modules_);
- n_modules_ = GetListOfModules(modules_, kMaxNumberOfModuleContexts,
- /* filter */ 0);
- // FIXME: Return this check when GetListOfModules is implemented on Mac.
- // CHECK_GT(n_modules_, 0);
- CHECK_LT(n_modules_, kMaxNumberOfModuleContexts);
- modules_fresh_ = true;
- modules_were_reloaded = true;
- }
- for (uptr i = 0; i < n_modules_; i++) {
- if (modules_[i].containsAddress(address)) {
- return &modules_[i];
- }
- }
- // Reload the modules and look up again, if we haven't tried it yet.
- if (!modules_were_reloaded) {
- // FIXME: set modules_fresh_ from dlopen()/dlclose() interceptors.
- // It's too aggressive to reload the list of modules each time we fail
- // to find a module for a given address.
- modules_fresh_ = false;
- return FindModuleForAddress(address);
- }
- return 0;
- }
-
- void ReportExternalSymbolizerError(const char *msg) {
- // Don't use atomics here for now, as SymbolizeCode can't be called
- // from multiple threads anyway.
- static bool reported;
- if (!reported) {
- Report(msg);
- reported = true;
- }
- }
-
- // 16K loaded modules should be enough for everyone.
- static const uptr kMaxNumberOfModuleContexts = 1 << 14;
- LoadedModule *modules_; // Array of module descriptions is leaked.
- uptr n_modules_;
- // If stale, need to reload the modules before looking up addresses.
- bool modules_fresh_;
-
- ExternalSymbolizer *external_symbolizer_; // Leaked.
- InternalSymbolizer *internal_symbolizer_; // Leaked.
-};
-
-static Symbolizer symbolizer; // Linker initialized.
-
-uptr SymbolizeCode(uptr address, AddressInfo *frames, uptr max_frames) {
- return symbolizer.SymbolizeCode(address, frames, max_frames);
-}
-
-bool SymbolizeData(uptr address, DataInfo *info) {
- return symbolizer.SymbolizeData(address, info);
-}
-
-bool InitializeExternalSymbolizer(const char *path_to_symbolizer) {
- return symbolizer.InitializeExternalSymbolizer(path_to_symbolizer);
-}
-
-bool IsSymbolizerAvailable() {
- return symbolizer.IsSymbolizerAvailable();
-}
-
-void FlushSymbolizer() {
- symbolizer.Flush();
-}
-
-} // namespace __sanitizer
Modified: compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer.h
URL: http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer.h?rev=182372&r1=182371&r2=182372&view=diff
==============================================================================
--- compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer.h (original)
+++ compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer.h Tue May 21 07:08:37 2013
@@ -66,7 +66,8 @@ struct DataInfo {
// for a given address (in all inlined functions). Returns the number
// of descriptions actually filled.
// This function should NOT be called from two threads simultaneously.
-uptr SymbolizeCode(uptr address, AddressInfo *frames, uptr max_frames);
+uptr SymbolizeCode(uptr address, AddressInfo *frames, uptr max_frames)
+ SANITIZER_WEAK_ATTRIBUTE;
bool SymbolizeData(uptr address, DataInfo *info);
bool IsSymbolizerAvailable();
Copied: compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer_libcdep.cc (from r182369, compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer.cc)
URL: http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer_libcdep.cc?p2=compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer_libcdep.cc&p1=compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer.cc&r1=182369&r2=182372&rev=182372&view=diff
==============================================================================
--- compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer.cc (original)
+++ compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer_libcdep.cc Tue May 21 07:08:37 2013
@@ -1,4 +1,4 @@
-//===-- sanitizer_symbolizer.cc -------------------------------------------===//
+//===-- sanitizer_symbolizer_libcdep.cc -----------------------------------===//
//
// The LLVM Compiler Infrastructure
//
Removed: compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer_linux.cc
URL: http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer_linux.cc?rev=182371&view=auto
==============================================================================
--- compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer_linux.cc (original)
+++ compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer_linux.cc (removed)
@@ -1,199 +0,0 @@
-//===-- sanitizer_symbolizer_linux.cc -------------------------------------===//
-//
-// The LLVM Compiler Infrastructure
-//
-// This file is distributed under the University of Illinois Open Source
-// License. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-//
-// This file is shared between AddressSanitizer and ThreadSanitizer
-// run-time libraries.
-// Linux-specific implementation of symbolizer parts.
-//===----------------------------------------------------------------------===//
-
-#include "sanitizer_platform.h"
-#if SANITIZER_LINUX
-#include "sanitizer_common.h"
-#include "sanitizer_internal_defs.h"
-#include "sanitizer_libc.h"
-#include "sanitizer_placement_new.h"
-#include "sanitizer_symbolizer.h"
-
-// Android NDK r8e elf.h depends on stdint.h without including the latter.
-#include <stdint.h>
-
-#include <elf.h>
-#include <errno.h>
-#include <poll.h>
-#include <sys/socket.h>
-#include <sys/types.h>
-#include <sys/wait.h>
-#include <unistd.h>
-
-#if !SANITIZER_ANDROID
-#include <link.h>
-#endif
-
-namespace __sanitizer {
-
-static const int kSymbolizerStartupTimeMillis = 10;
-
-bool StartSymbolizerSubprocess(const char *path_to_symbolizer,
- int *input_fd, int *output_fd) {
- if (!FileExists(path_to_symbolizer)) {
- Report("WARNING: invalid path to external symbolizer!\n");
- return false;
- }
-
- int *infd = NULL;
- int *outfd = NULL;
- // The client program may close its stdin and/or stdout and/or stderr
- // thus allowing socketpair to reuse file descriptors 0, 1 or 2.
- // In this case the communication between the forked processes may be
- // broken if either the parent or the child tries to close or duplicate
- // these descriptors. The loop below produces two pairs of file
- // descriptors, each greater than 2 (stderr).
- int sock_pair[5][2];
- for (int i = 0; i < 5; i++) {
- if (pipe(sock_pair[i]) == -1) {
- for (int j = 0; j < i; j++) {
- internal_close(sock_pair[j][0]);
- internal_close(sock_pair[j][1]);
- }
- Report("WARNING: Can't create a socket pair to start "
- "external symbolizer (errno: %d)\n", errno);
- return false;
- } else if (sock_pair[i][0] > 2 && sock_pair[i][1] > 2) {
- if (infd == NULL) {
- infd = sock_pair[i];
- } else {
- outfd = sock_pair[i];
- for (int j = 0; j < i; j++) {
- if (sock_pair[j] == infd) continue;
- internal_close(sock_pair[j][0]);
- internal_close(sock_pair[j][1]);
- }
- break;
- }
- }
- }
- CHECK(infd);
- CHECK(outfd);
-
- int pid = fork();
- if (pid == -1) {
- // Fork() failed.
- internal_close(infd[0]);
- internal_close(infd[1]);
- internal_close(outfd[0]);
- internal_close(outfd[1]);
- Report("WARNING: failed to fork external symbolizer "
- " (errno: %d)\n", errno);
- return false;
- } else if (pid == 0) {
- // Child subprocess.
- internal_close(STDOUT_FILENO);
- internal_close(STDIN_FILENO);
- internal_dup2(outfd[0], STDIN_FILENO);
- internal_dup2(infd[1], STDOUT_FILENO);
- internal_close(outfd[0]);
- internal_close(outfd[1]);
- internal_close(infd[0]);
- internal_close(infd[1]);
- for (int fd = getdtablesize(); fd > 2; fd--)
- internal_close(fd);
- execl(path_to_symbolizer, path_to_symbolizer, (char*)0);
- internal__exit(1);
- }
-
- // Continue execution in parent process.
- internal_close(outfd[0]);
- internal_close(infd[1]);
- *input_fd = infd[0];
- *output_fd = outfd[1];
-
- // Check that symbolizer subprocess started successfully.
- int pid_status;
- SleepForMillis(kSymbolizerStartupTimeMillis);
- int exited_pid = waitpid(pid, &pid_status, WNOHANG);
- if (exited_pid != 0) {
- // Either waitpid failed, or child has already exited.
- Report("WARNING: external symbolizer didn't start up correctly!\n");
- return false;
- }
-
- return true;
-}
-
-#if SANITIZER_ANDROID
-uptr GetListOfModules(LoadedModule *modules, uptr max_modules,
- string_predicate_t filter) {
- return 0;
-}
-#else // SANITIZER_ANDROID
-typedef ElfW(Phdr) Elf_Phdr;
-
-struct DlIteratePhdrData {
- LoadedModule *modules;
- uptr current_n;
- bool first;
- uptr max_n;
- string_predicate_t filter;
-};
-
-static const uptr kMaxPathLength = 512;
-
-static int dl_iterate_phdr_cb(dl_phdr_info *info, size_t size, void *arg) {
- DlIteratePhdrData *data = (DlIteratePhdrData*)arg;
- if (data->current_n == data->max_n)
- return 0;
- InternalScopedBuffer<char> module_name(kMaxPathLength);
- module_name.data()[0] = '\0';
- if (data->first) {
- data->first = false;
- // First module is the binary itself.
- uptr module_name_len = internal_readlink(
- "/proc/self/exe", module_name.data(), module_name.size());
- if (internal_iserror(module_name_len)) {
- // We can't read /proc/self/exe for some reason, assume the name of the
- // binary is unknown.
- module_name_len = internal_snprintf(module_name.data(),
- module_name.size(), "/proc/self/exe");
- }
- CHECK_LT(module_name_len, module_name.size());
- module_name[module_name_len] = '\0';
- } else if (info->dlpi_name) {
- internal_strncpy(module_name.data(), info->dlpi_name, module_name.size());
- }
- if (module_name.data()[0] == '\0')
- return 0;
- if (data->filter && !data->filter(module_name.data()))
- return 0;
- void *mem = &data->modules[data->current_n];
- LoadedModule *cur_module = new(mem) LoadedModule(module_name.data(),
- info->dlpi_addr);
- data->current_n++;
- for (int i = 0; i < info->dlpi_phnum; i++) {
- const Elf_Phdr *phdr = &info->dlpi_phdr[i];
- if (phdr->p_type == PT_LOAD) {
- uptr cur_beg = info->dlpi_addr + phdr->p_vaddr;
- uptr cur_end = cur_beg + phdr->p_memsz;
- cur_module->addAddressRange(cur_beg, cur_end);
- }
- }
- return 0;
-}
-
-uptr GetListOfModules(LoadedModule *modules, uptr max_modules,
- string_predicate_t filter) {
- CHECK(modules);
- DlIteratePhdrData data = {modules, 0, true, max_modules, filter};
- dl_iterate_phdr(dl_iterate_phdr_cb, &data);
- return data.current_n;
-}
-#endif // SANITIZER_ANDROID
-
-} // namespace __sanitizer
-
-#endif // SANITIZER_LINUX
Copied: compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer_linux_libcdep.cc (from r182369, compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer_linux.cc)
URL: http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer_linux_libcdep.cc?p2=compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer_linux_libcdep.cc&p1=compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer_linux.cc&r1=182369&r2=182372&rev=182372&view=diff
==============================================================================
--- compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer_linux.cc (original)
+++ compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer_linux_libcdep.cc Tue May 21 07:08:37 2013
@@ -1,4 +1,4 @@
-//===-- sanitizer_symbolizer_linux.cc -------------------------------------===//
+//===-- sanitizer_symbolizer_linux_libcdep.cc -----------------------------===//
//
// The LLVM Compiler Infrastructure
//
More information about the llvm-commits
mailing list