From 1347c61c8ebaa02a947e303dcab89ed675228673 Mon Sep 17 00:00:00 2001 From: Cheng Zhao Date: Tue, 4 Aug 2015 17:13:05 +0800 Subject: [PATCH 1/4] Set AppUserModelID for all renderer processes --- atom/browser/atom_browser_client.cc | 14 ++++++++++++++ atom/browser/native_window.cc | 13 ------------- 2 files changed, 14 insertions(+), 13 deletions(-) diff --git a/atom/browser/atom_browser_client.cc b/atom/browser/atom_browser_client.cc index f98f2b2a8873..65fd7cd031dd 100644 --- a/atom/browser/atom_browser_client.cc +++ b/atom/browser/atom_browser_client.cc @@ -4,6 +4,10 @@ #include "atom/browser/atom_browser_client.h" +#if defined(OS_WIN) +#include +#endif + #include "atom/browser/atom_access_token_store.h" #include "atom/browser/atom_browser_context.h" #include "atom/browser/atom_browser_main_parts.h" @@ -190,10 +194,20 @@ void AtomBrowserClient::AppendExtraCommandLineSwitches( if (process_type != "renderer") return; + // The registered standard schemes. if (!g_custom_schemes.empty()) command_line->AppendSwitchASCII(switches::kRegisterStandardSchemes, g_custom_schemes); +#if defined(OS_WIN) + // Append --app-user-model-id. + PWSTR current_app_id; + if (SUCCEEDED(GetCurrentProcessExplicitAppUserModelID(¤t_app_id))) { + command_line->AppendSwitchNative(switches::kAppUserModelId, current_app_id); + CoTaskMemFree(current_app_id); + } +#endif + NativeWindow* window; WebViewManager::WebViewInfo info; ProcessOwner owner = GetProcessOwner(process_id, &window, &info); diff --git a/atom/browser/native_window.cc b/atom/browser/native_window.cc index fb9bab766dd8..d3c40f928272 100644 --- a/atom/browser/native_window.cc +++ b/atom/browser/native_window.cc @@ -8,10 +8,6 @@ #include #include -#if defined(OS_WIN) -#include -#endif - #include "atom/browser/atom_browser_context.h" #include "atom/browser/atom_browser_main_parts.h" #include "atom/browser/window_list.h" @@ -384,15 +380,6 @@ void NativeWindow::AppendExtraCommandLineSwitches( command_line->AppendSwitchASCII(switches::kZoomFactor, base::DoubleToString(zoom_factor_)); -#if defined(OS_WIN) - // Append --app-user-model-id. - PWSTR current_app_id; - if (SUCCEEDED(GetCurrentProcessExplicitAppUserModelID(¤t_app_id))) { - command_line->AppendSwitchNative(switches::kAppUserModelId, current_app_id); - CoTaskMemFree(current_app_id); - } -#endif - if (web_preferences_.IsEmpty()) return; From 14803e4cf88467a3fe5cad29bc8308e3fe574404 Mon Sep 17 00:00:00 2001 From: Cheng Zhao Date: Tue, 4 Aug 2015 19:18:12 +0800 Subject: [PATCH 2/4] Close handle when waiting is end --- atom/common/crash_reporter/crash_reporter_win.cc | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/atom/common/crash_reporter/crash_reporter_win.cc b/atom/common/crash_reporter/crash_reporter_win.cc index a348cf012612..5c4f9fb4f24f 100644 --- a/atom/common/crash_reporter/crash_reporter_win.cc +++ b/atom/common/crash_reporter/crash_reporter_win.cc @@ -51,8 +51,10 @@ void CrashReporterWin::InitBreakpad(const std::string& product_name, // 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) + if (waiting_event != NULL) { WaitForSingleObject(waiting_event, 1000); + CloseHandle(waiting_event); + } // ExceptionHandler() attaches our handler and ~ExceptionHandler() detaches // it, so we must explicitly reset *before* we instantiate our new handler From db58048077f604f46814a7e5dff3d87a1fd7e3f3 Mon Sep 17 00:00:00 2001 From: Cheng Zhao Date: Tue, 4 Aug 2015 19:30:35 +0800 Subject: [PATCH 3/4] Use different name for wait events for different apps --- atom/common/crash_reporter/crash_reporter_win.cc | 12 +++++++----- atom/common/crash_reporter/win/crash_service.cc | 14 ++++++++------ atom/common/crash_reporter/win/crash_service.h | 3 ++- .../crash_reporter/win/crash_service_main.cc | 3 ++- 4 files changed, 19 insertions(+), 13 deletions(-) diff --git a/atom/common/crash_reporter/crash_reporter_win.cc b/atom/common/crash_reporter/crash_reporter_win.cc index 5c4f9fb4f24f..be096da80e2c 100644 --- a/atom/common/crash_reporter/crash_reporter_win.cc +++ b/atom/common/crash_reporter/crash_reporter_win.cc @@ -21,6 +21,7 @@ const MINIDUMP_TYPE kSmallDumpType = static_cast( MiniDumpWithProcessThreadData | // Get PEB and TEB. MiniDumpWithUnloadedModules); // Get unloaded modules when available. +const wchar_t kWaitEventFormat[] = L"$1CrashServiceWaitEvent"; const wchar_t kPipeNameFormat[] = L"\\\\.\\pipe\\$1 Crash Service"; } // namespace @@ -47,13 +48,14 @@ void CrashReporterWin::InitBreakpad(const std::string& product_name, base::string16 pipe_name = ReplaceStringPlaceholders( kPipeNameFormat, base::UTF8ToUTF16(product_name), NULL); + base::string16 wait_name = ReplaceStringPlaceholders( + kWaitEventFormat, base::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 != NULL) { - WaitForSingleObject(waiting_event, 1000); - CloseHandle(waiting_event); + HANDLE wait_event = ::CreateEventW(NULL, TRUE, FALSE, wait_name.c_str()); + if (wait_event != NULL) { + WaitForSingleObject(wait_event, 1000); + CloseHandle(wait_event); } // ExceptionHandler() attaches our handler and ~ExceptionHandler() detaches diff --git a/atom/common/crash_reporter/win/crash_service.cc b/atom/common/crash_reporter/win/crash_service.cc index 10e0fdfcc555..611c39219bfd 100644 --- a/atom/common/crash_reporter/win/crash_service.cc +++ b/atom/common/crash_reporter/win/crash_service.cc @@ -14,6 +14,7 @@ #include "base/files/file_util.h" #include "base/logging.h" #include "base/strings/string_number_conversions.h" +#include "base/strings/string_util.h" #include "base/time/time.h" #include "base/win/windows_version.h" #include "vendor/breakpad/src/client/windows/crash_generation/client_info.h" @@ -24,6 +25,7 @@ namespace breakpad { namespace { +const wchar_t kWaitEventFormat[] = L"$1CrashServiceWaitEvent"; const wchar_t kTestPipeName[] = L"\\\\.\\pipe\\ChromeCrashServices"; const wchar_t kGoogleReportURL[] = L"https://clients2.google.com/cr/report"; @@ -193,7 +195,8 @@ CrashService::~CrashService() { delete sender_; } -bool CrashService::Initialize(const base::FilePath& operating_dir, +bool CrashService::Initialize(const base::string16& application_name, + const base::FilePath& operating_dir, const base::FilePath& dumps_path) { using google_breakpad::CrashReportSender; using google_breakpad::CrashGenerationServer; @@ -298,11 +301,10 @@ bool CrashService::Initialize(const base::FilePath& operating_dir, // 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_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); + base::string16 wait_name = ReplaceStringPlaceholders( + kWaitEventFormat, application_name, NULL); + HANDLE wait_event = ::CreateEventW(NULL, TRUE, FALSE, wait_name.c_str()); + ::SetEvent(wait_event); return true; } diff --git a/atom/common/crash_reporter/win/crash_service.h b/atom/common/crash_reporter/win/crash_service.h index 730e4da3c6b2..7195ec2a958c 100644 --- a/atom/common/crash_reporter/win/crash_service.h +++ b/atom/common/crash_reporter/win/crash_service.h @@ -37,7 +37,8 @@ class CrashService { // other members in that case. |operating_dir| is where the CrashService // should store breakpad's checkpoint file. |dumps_path| is the directory // where the crash dumps should be stored. - bool Initialize(const base::FilePath& operating_dir, + bool Initialize(const base::string16& application_name, + const base::FilePath& operating_dir, const base::FilePath& dumps_path); // Command line switches: diff --git a/atom/common/crash_reporter/win/crash_service_main.cc b/atom/common/crash_reporter/win/crash_service_main.cc index 0bd72deba9e9..7a5eeb10133a 100644 --- a/atom/common/crash_reporter/win/crash_service_main.cc +++ b/atom/common/crash_reporter/win/crash_service_main.cc @@ -77,7 +77,8 @@ int Main(const wchar_t* cmd) { cmd_line.AppendSwitchNative("pipe-name", pipe_name); breakpad::CrashService crash_service; - if (!crash_service.Initialize(operating_dir, operating_dir)) + if (!crash_service.Initialize(application_name, operating_dir, + operating_dir)) return 2; VLOG(1) << "Ready to process crash requests"; From c872b1a770c49df662fded29005ab760ed2dfe0c Mon Sep 17 00:00:00 2001 From: Cheng Zhao Date: Tue, 4 Aug 2015 19:35:46 +0800 Subject: [PATCH 4/4] Use different name for window class name --- atom/common/crash_reporter/win/crash_service.cc | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-) diff --git a/atom/common/crash_reporter/win/crash_service.cc b/atom/common/crash_reporter/win/crash_service.cc index 611c39219bfd..d315b0b9419e 100644 --- a/atom/common/crash_reporter/win/crash_service.cc +++ b/atom/common/crash_reporter/win/crash_service.cc @@ -26,6 +26,8 @@ namespace breakpad { namespace { const wchar_t kWaitEventFormat[] = L"$1CrashServiceWaitEvent"; +const wchar_t kClassNameFormat[] = L"$1CrashServiceWindow"; + const wchar_t kTestPipeName[] = L"\\\\.\\pipe\\ChromeCrashServices"; const wchar_t kGoogleReportURL[] = L"https://clients2.google.com/cr/report"; @@ -113,13 +115,18 @@ LRESULT __stdcall CrashSvcWndProc(HWND hwnd, UINT message, // This is the main and only application window. HWND g_top_window = NULL; -bool CreateTopWindow(HINSTANCE instance, bool visible) { +bool CreateTopWindow(HINSTANCE instance, + const base::string16& application_name, + bool visible) { + base::string16 class_name = ReplaceStringPlaceholders( + kClassNameFormat, application_name, NULL); + WNDCLASSEXW wcx = {0}; wcx.cbSize = sizeof(wcx); wcx.style = CS_HREDRAW | CS_VREDRAW; wcx.lpfnWndProc = CrashSvcWndProc; wcx.hInstance = instance; - wcx.lpszClassName = L"crash_svc_class"; + wcx.lpszClassName = class_name.c_str(); ATOM atom = ::RegisterClassExW(&wcx); DWORD style = visible ? WS_POPUPWINDOW | WS_VISIBLE : WS_OVERLAPPED; @@ -263,6 +270,7 @@ bool CrashService::Initialize(const base::string16& application_name, } if (!CreateTopWindow(::GetModuleHandleW(NULL), + application_name, !cmd_line.HasSwitch(kNoWindow))) { LOG(ERROR) << "could not create window"; if (security_attributes.lpSecurityDescriptor)