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