Source code

Revision control

Copy as Markdown

Other Tools

/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at */
#ifndef gfx_src_DriverCrashGuard_h__
#define gfx_src_DriverCrashGuard_h__
#include "nsCOMPtr.h"
#include "nsIGfxInfo.h"
#include "nsIFile.h"
#include "nsString.h"
#include <functional>
#include <string>
namespace mozilla {
namespace dom {
class ContentParent;
} // namespace dom
namespace gfx {
enum class DriverInitStatus {
// Drivers have not been initialized yet.
// We're attempting to initialize drivers.
// Drivers were successfully initialized last run.
// We crashed during driver initialization, and have restarted.
enum class CrashGuardType : uint32_t {
// Add new entries above this line, update the name array in
// DriverCrashGuard.cpp, make sure to add an entry in ContentParent.cpp,
// and add a fluent identifier in aboutSupport.ftl.
// DriverCrashGuard is used to detect crashes at graphics driver callsites.
// If the graphics environment is unrecognized or has changed since the last
// session, the crash guard will activate and will detect any crashes within
// the scope of the guard object.
// If a callsite has a previously encountered crash, and the environment has
// not changed since the last session, then the guard will set a status flag
// indicating that the driver should not be used.
class DriverCrashGuard {
DriverCrashGuard(CrashGuardType aType, dom::ContentParent* aContentParent);
virtual ~DriverCrashGuard();
bool Crashed();
void NotifyCrashed();
// These are the values reported to Telemetry (GRAPHICS_DRIVER_STARTUP_TEST).
// Values should not change; add new values to the end.
enum class TelemetryState {
Okay = 0,
EnvironmentChanged = 1,
RecoveredFromCrash = 2,
FeatureDisabled = 3
enum class Mode {
// Normal operation.
// Acting as a proxy between the parent and child process.
typedef std::function<void(const char* aName, const char* aPrefName)>
static void ForEachActiveCrashGuard(const CrashGuardCallback& aCallback);
virtual void Initialize();
// UpdateEnvironment needs to return true should we need to attempt the
// operation once again.
// It should return true once only so that in case of a crash, we won't
// needlessly attempt the operation over and over again leading to continual
// crashes. several times
virtual bool UpdateEnvironment() {
// We don't care about any extra preferences here.
return false;
virtual void LogCrashRecovery() = 0;
virtual void LogFeatureDisabled() = 0;
// Helper functions.
bool FeatureEnabled(int aFeature, bool aDefault = true);
bool CheckAndUpdatePref(const char* aPrefName,
const nsAString& aCurrentValue);
bool CheckAndUpdateBoolPref(const char* aPrefName, bool aCurrentValue);
std::string GetFullPrefName(const char* aPref);
// Either process.
void InitializeIfNeeded();
bool CheckOrRefreshEnvironment();
bool UpdateBaseEnvironment();
DriverInitStatus GetStatus() const;
// Parent process only.
nsCOMPtr<nsIFile> GetGuardFile();
bool RecoverFromCrash();
void ActivateGuard();
void FlushPreferences();
void SetStatus(DriverInitStatus aStatus);
CrashGuardType mType;
Mode mMode;
bool mInitialized;
bool mGuardActivated;
bool mCrashDetected;
nsCOMPtr<nsIFile> mGuardFile;
nsCString mStatusPref;
nsCOMPtr<nsIGfxInfo> mGfxInfo;
class D3D11LayersCrashGuard final : public DriverCrashGuard {
explicit D3D11LayersCrashGuard(dom::ContentParent* aContentParent = nullptr);
void Initialize() override;
bool UpdateEnvironment() override;
void LogCrashRecovery() override;
void LogFeatureDisabled() override;
void RecordTelemetry(TelemetryState aState);
class GLContextCrashGuard final : public DriverCrashGuard {
explicit GLContextCrashGuard(dom::ContentParent* aContentParent = nullptr);
void Initialize() override;
bool UpdateEnvironment() override;
void LogCrashRecovery() override;
void LogFeatureDisabled() override;
class WMFVPXVideoCrashGuard final : public DriverCrashGuard {
explicit WMFVPXVideoCrashGuard(dom::ContentParent* aContentParent = nullptr);
void LogCrashRecovery() override;
void LogFeatureDisabled() override;
} // namespace gfx
} // namespace mozilla
#endif // gfx_src_DriverCrashGuard_h__