From 717b664802beeba532ae31155e94565ac705c09e Mon Sep 17 00:00:00 2001 From: Cheng Zhao Date: Sun, 24 Nov 2013 22:22:08 +0800 Subject: [PATCH] win: Make out-of-process crash dump work. --- common/api/lib/crash-reporter.coffee | 15 ++++++--- common/crash_reporter/crash_reporter_win.cc | 43 ++++++++++++++++++++++--- common/crash_reporter/win/crash_service.cc | 4 +-- common/crash_reporter/win/crash_service_main.cc | 5 ++- 4 files changed, 52 insertions(+), 15 deletions(-) diff --git a/common/api/lib/crash-reporter.coffee b/common/api/lib/crash-reporter.coffee index ae97461..3dd8821 100644 --- a/common/api/lib/crash-reporter.coffee +++ b/common/api/lib/crash-reporter.coffee @@ -5,21 +5,26 @@ class CrashReporter start: (options={}) -> {productName, companyName, submitUrl, autoSubmit, ignoreSystemCrashHandler, extra} = options - productName ?= 'atom-shell' + productName ?= 'Atom-Shell' companyName ?= 'GitHub, Inc' submitUrl ?= 'http://54.249.141.25:1127/post' autoSubmit ?= true ignoreSystemCrashHandler ?= false extra ?= {} - if process.platform isnt 'darwin' + start = -> binding.start productName, companyName, submitUrl, autoSubmit, ignoreSystemCrashHandler, extra + + if process.platform is 'darwin' + start() + else args = [ - "--reporter-url=#{submitUrl}", + "--reporter-url=#{submitUrl}" "--application-name=#{productName}" + "--v=1" ] env = ATOM_SHELL_INTERNAL_CRASH_SERVICE: 1 - spawn process.execPath, args, {env} - binding.start productName, companyName, submitUrl, autoSubmit, ignoreSystemCrashHandler, extra + spawn process.execPath, args, {env, detached: true} + start() module.exports = new CrashReporter diff --git a/common/crash_reporter/crash_reporter_win.cc b/common/crash_reporter/crash_reporter_win.cc index 65d5b8d..4a7f601 100644 --- a/common/crash_reporter/crash_reporter_win.cc +++ b/common/crash_reporter/crash_reporter_win.cc @@ -4,11 +4,25 @@ #include "common/crash_reporter/crash_reporter_win.h" +#include "base/file_util.h" #include "base/logging.h" #include "base/memory/singleton.h" +#include "base/string_util.h" +#include "base/utf_string_conversions.h" namespace crash_reporter { +namespace { + +// Minidump with stacks, PEB, TEB, and unloaded module list. +const MINIDUMP_TYPE kSmallDumpType = static_cast( + MiniDumpWithProcessThreadData | // Get PEB and TEB. + MiniDumpWithUnloadedModules); // Get unloaded modules when available. + +const wchar_t kPipeNameFormat[] = L"\\\\.\\pipe\\$1 Crash Service"; + +} // namespace + CrashReporterWin::CrashReporterWin() { } @@ -23,14 +37,35 @@ void CrashReporterWin::InitBreakpad(const std::string& product_name, bool skip_system_crash_handler) { skip_system_crash_handler_ = skip_system_crash_handler; - wchar_t temp_dir[MAX_PATH] = { 0 }; - ::GetTempPathW(MAX_PATH, temp_dir); + base::FilePath temp_dir; + if (!file_util::GetTempDir(&temp_dir)) { + LOG(ERROR) << "Cannot get temp directory"; + return; + } - breakpad_.reset(new google_breakpad::ExceptionHandler(temp_dir, + string16 pipe_name = ReplaceStringPlaceholders(kPipeNameFormat, + UTF8ToUTF16(product_name), + NULL); + + // Wait until the crash service is started. + HANDLE waiting_event = + ::CreateEventW(NULL, TRUE, FALSE, L"g_atom_shell_crash_service"); + if (waiting_event != INVALID_HANDLE_VALUE) + WaitForSingleObject(waiting_event, 1000); + + google_breakpad::CustomClientInfo custom_info = { NULL, 0 }; + breakpad_.reset(new google_breakpad::ExceptionHandler( + temp_dir.value(), FilterCallback, MinidumpCallback, this, - google_breakpad::ExceptionHandler::HANDLER_ALL)); + google_breakpad::ExceptionHandler::HANDLER_ALL, + kSmallDumpType, + pipe_name.c_str(), + &custom_info)); + + if (!breakpad_->IsOutOfProcess()) + LOG(ERROR) << "Cannot initialize out-of-process crash handler"; } void CrashReporterWin::SetUploadParameters() { diff --git a/common/crash_reporter/win/crash_service.cc b/common/crash_reporter/win/crash_service.cc index 202c479..3cbbf33 100644 --- a/common/crash_reporter/win/crash_service.cc +++ b/common/crash_reporter/win/crash_service.cc @@ -270,12 +270,10 @@ bool CrashService::Initialize(const base::FilePath& operating_dir, if (security_attributes.lpSecurityDescriptor) LocalFree(security_attributes.lpSecurityDescriptor); - // This is throwaway code. We don't need to sync with the browser process - // once Google Update is updated to a version supporting OOP crash handling. // Create or open an event to signal the browser process that the crash // service is initialized. HANDLE running_event = - ::CreateEventW(NULL, TRUE, TRUE, L"g_chrome_crash_svc"); + ::CreateEventW(NULL, TRUE, TRUE, L"g_atom_shell_crash_service"); // If the browser already had the event open, the CreateEvent call did not // signal it. We need to do it manually. ::SetEvent(running_event); diff --git a/common/crash_reporter/win/crash_service_main.cc b/common/crash_reporter/win/crash_service_main.cc index 46f9690..649f358 100644 --- a/common/crash_reporter/win/crash_service_main.cc +++ b/common/crash_reporter/win/crash_service_main.cc @@ -7,8 +7,6 @@ #include "base/at_exit.h" #include "base/command_line.h" #include "base/file_util.h" -#include "base/files/file_path.h" -#include "base/path_service.h" #include "base/logging.h" #include "base/string_util.h" #include "common/crash_reporter/win/crash_service.h" @@ -18,7 +16,8 @@ namespace crash_service { namespace { const char kApplicationName[] = "application-name"; -const wchar_t kPipeNameFormat[] = L"\\\\.\\pipe\\$1CrashService"; + +const wchar_t kPipeNameFormat[] = L"\\\\.\\pipe\\$1 Crash Service"; const wchar_t kStandardLogFile[] = L"operation_log.txt"; bool GetCrashServiceDirectory(const std::wstring& application_name, -- 2.7.4