Ignore X Window System errors
This commit is contained in:
parent
5a97cfaa64
commit
6044ab05f3
2 changed files with 88 additions and 12 deletions
|
@ -11,6 +11,7 @@
|
|||
#include "base/command_line.h"
|
||||
#include "base/strings/string_number_conversions.h"
|
||||
#include "components/devtools_http_handler/devtools_http_handler.h"
|
||||
#include "content/public/browser/browser_thread.h"
|
||||
#include "content/public/common/content_switches.h"
|
||||
#include "net/proxy/proxy_resolver_v8.h"
|
||||
|
||||
|
@ -19,21 +20,21 @@
|
|||
#include "ui/views/widget/desktop_aura/desktop_screen.h"
|
||||
#endif
|
||||
|
||||
#if defined(USE_AURA) && defined(USE_X11)
|
||||
#include "chrome/browser/ui/libgtk2ui/gtk2_ui.h"
|
||||
#include "ui/views/linux_ui/linux_ui.h"
|
||||
#include "ui/wm/core/wm_state.h"
|
||||
#endif
|
||||
|
||||
#if defined(TOOLKIT_VIEWS)
|
||||
#include "browser/views/views_delegate.h"
|
||||
#endif
|
||||
|
||||
#if defined(OS_LINUX)
|
||||
#if defined(USE_X11)
|
||||
#include "base/environment.h"
|
||||
#include "base/path_service.h"
|
||||
#include "base/nix/xdg_util.h"
|
||||
#include "base/thread_task_runner_handle.h"
|
||||
#include "browser/brightray_paths.h"
|
||||
#include "chrome/browser/ui/libgtk2ui/gtk2_ui.h"
|
||||
#include "ui/base/x/x11_util.h"
|
||||
#include "ui/base/x/x11_util_internal.h"
|
||||
#include "ui/views/linux_ui/linux_ui.h"
|
||||
#include "ui/wm/core/wm_state.h"
|
||||
#endif
|
||||
|
||||
#if defined(OS_WIN)
|
||||
|
@ -43,6 +44,8 @@
|
|||
#include "ui/gfx/platform_font_win.h"
|
||||
#endif
|
||||
|
||||
using content::BrowserThread;
|
||||
|
||||
namespace brightray {
|
||||
|
||||
namespace {
|
||||
|
@ -58,7 +61,14 @@ int GetMinimumFontSize() {
|
|||
}
|
||||
#endif
|
||||
|
||||
#if defined(OS_LINUX)
|
||||
#if defined(USE_X11)
|
||||
// Indicates that we're currently responding to an IO error (by shutting down).
|
||||
bool g_in_x11_io_error_handler = false;
|
||||
|
||||
// Number of seconds to wait for UI thread to get an IO error if we get it on
|
||||
// the background thread.
|
||||
const int kWaitForUIThreadSeconds = 10;
|
||||
|
||||
void OverrideLinuxAppDataPath() {
|
||||
base::FilePath path;
|
||||
if (PathService::Get(DIR_APP_DATA, &path))
|
||||
|
@ -69,6 +79,53 @@ void OverrideLinuxAppDataPath() {
|
|||
base::nix::kDotConfigDir);
|
||||
PathService::Override(DIR_APP_DATA, path);
|
||||
}
|
||||
|
||||
int BrowserX11ErrorHandler(Display* d, XErrorEvent* error) {
|
||||
if (!g_in_x11_io_error_handler) {
|
||||
base::ThreadTaskRunnerHandle::Get()->PostTask(
|
||||
FROM_HERE, base::Bind(&ui::LogErrorEventDescription, d, *error));
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
// This function is used to help us diagnose crash dumps that happen
|
||||
// during the shutdown process.
|
||||
NOINLINE void WaitingForUIThreadToHandleIOError() {
|
||||
// Ensure function isn't optimized away.
|
||||
asm("");
|
||||
sleep(kWaitForUIThreadSeconds);
|
||||
}
|
||||
|
||||
int BrowserX11IOErrorHandler(Display* d) {
|
||||
if (!BrowserThread::CurrentlyOn(BrowserThread::UI)) {
|
||||
// Wait for the UI thread (which has a different connection to the X server)
|
||||
// to get the error. We can't call shutdown from this thread without
|
||||
// tripping an error. Doing it through a function so that we'll be able
|
||||
// to see it in any crash dumps.
|
||||
WaitingForUIThreadToHandleIOError();
|
||||
return 0;
|
||||
}
|
||||
|
||||
// If there's an IO error it likely means the X server has gone away.
|
||||
// If this CHECK fails, then that means SessionEnding() below triggered some
|
||||
// code that tried to talk to the X server, resulting in yet another error.
|
||||
CHECK(!g_in_x11_io_error_handler);
|
||||
|
||||
g_in_x11_io_error_handler = true;
|
||||
LOG(ERROR) << "X IO error received (X server probably went away)";
|
||||
base::ThreadTaskRunnerHandle::Get()->PostTask(
|
||||
FROM_HERE, base::MessageLoop::QuitWhenIdleClosure());
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int X11EmptyErrorHandler(Display* d, XErrorEvent* error) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
int X11EmptyIOErrorHandler(Display* d) {
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
} // namespace
|
||||
|
@ -84,12 +141,14 @@ void BrowserMainParts::PreEarlyInitialization() {
|
|||
IncreaseFileDescriptorLimit();
|
||||
#endif
|
||||
|
||||
#if defined(USE_AURA) && defined(USE_X11)
|
||||
#if defined(USE_X11)
|
||||
views::LinuxUI::SetInstance(BuildGtk2UI());
|
||||
#endif
|
||||
|
||||
#if defined(OS_LINUX)
|
||||
OverrideLinuxAppDataPath();
|
||||
|
||||
// Installs the X11 error handlers for the browser process used during
|
||||
// startup. They simply print error messages and exit because
|
||||
// we can't shutdown properly while creating and initializing services.
|
||||
ui::SetX11ErrorHandlers(nullptr, nullptr);
|
||||
#endif
|
||||
}
|
||||
|
||||
|
@ -131,8 +190,24 @@ void BrowserMainParts::PreMainMessageLoopRun() {
|
|||
devtools_http_handler_.reset(DevToolsManagerDelegate::CreateHttpHandler());
|
||||
}
|
||||
|
||||
void BrowserMainParts::PostMainMessageLoopStart() {
|
||||
#if defined(USE_X11)
|
||||
// Installs the X11 error handlers for the browser process after the
|
||||
// main message loop has started. This will allow us to exit cleanly
|
||||
// if X exits before us.
|
||||
ui::SetX11ErrorHandlers(BrowserX11ErrorHandler, BrowserX11IOErrorHandler);
|
||||
#endif
|
||||
}
|
||||
|
||||
void BrowserMainParts::PostMainMessageLoopRun() {
|
||||
browser_context_ = nullptr;
|
||||
|
||||
#if defined(USE_X11)
|
||||
// Unset the X11 error handlers. The X11 error handlers log the errors using a
|
||||
// |PostTask()| on the message-loop. But since the message-loop is in the
|
||||
// process of terminating, this can cause errors.
|
||||
ui::SetX11ErrorHandlers(X11EmptyErrorHandler, X11EmptyIOErrorHandler);
|
||||
#endif
|
||||
}
|
||||
|
||||
int BrowserMainParts::PreCreateThreads() {
|
||||
|
|
|
@ -43,6 +43,7 @@ class BrowserMainParts : public content::BrowserMainParts {
|
|||
void ToolkitInitialized() override;
|
||||
void PreMainMessageLoopStart() override;
|
||||
void PreMainMessageLoopRun() override;
|
||||
void PostMainMessageLoopStart() override;
|
||||
void PostMainMessageLoopRun() override;
|
||||
int PreCreateThreads() override;
|
||||
|
||||
|
|
Loading…
Reference in a new issue