Bug 1562847 - Disable double buffering with compositor when device reset happens r=nical,bas
When double buffering is enable with compositor, DXGI_SWAP_EFFECT_FLIP_SEQUENTIAL is used without DirectComposition. There are some devices that swap chain with DXGI_SWAP_EFFECT_FLIP_SEQUENTIAL does not work well. In this case, device reset happens very often. To avoid the situation, the double buffering needs to be disabled when device reset happens. Differential Revision: https://phabricator.services.mozilla.com/D36579
This commit is contained in:
@@ -51,7 +51,8 @@ class gfxVarReceiver;
|
||||
_(AllowD3D11KeyedMutex, bool, false) \
|
||||
_(SystemTextQuality, int32_t, 5 /* CLEARTYPE_QUALITY */) \
|
||||
_(LayersWindowRecordingPath, nsCString, nsCString()) \
|
||||
_(RemoteCanvasEnabled, bool, false)
|
||||
_(RemoteCanvasEnabled, bool, false) \
|
||||
_(UseDoubleBufferingWithCompositor, bool, false)
|
||||
|
||||
/* Add new entries above this line. */
|
||||
|
||||
|
||||
@@ -264,8 +264,7 @@ mozilla::ipc::IPCResult GPUParent::RecvInit(
|
||||
}
|
||||
#ifdef XP_WIN
|
||||
else {
|
||||
if (StaticPrefs::gfx_direct3d11_use_double_buffering() &&
|
||||
IsWin10OrLater()) {
|
||||
if (gfxVars::UseDoubleBufferingWithCompositor()) {
|
||||
// This is needed to avoid freezing the window on a device crash on double
|
||||
// buffering, see bug 1549674.
|
||||
widget::WinCompositorWindowThread::Start();
|
||||
|
||||
@@ -485,6 +485,11 @@ void GPUProcessManager::OnRemoteProcessDeviceReset(GPUProcessHost* aHost) {
|
||||
// indicating that we should give up and use software
|
||||
mDeviceResetCount++;
|
||||
|
||||
// Disable double buffering when device reset happens.
|
||||
if (!gfxVars::UseWebRender() && gfxVars::UseDoubleBufferingWithCompositor()) {
|
||||
gfxVars::SetUseDoubleBufferingWithCompositor(false);
|
||||
}
|
||||
|
||||
auto newTime = TimeStamp::Now();
|
||||
auto delta = (int32_t)(newTime - mDeviceResetLastTime).ToMilliseconds();
|
||||
mDeviceResetLastTime = newTime;
|
||||
|
||||
@@ -201,8 +201,8 @@ bool CompositorD3D11::Initialize(nsCString* const out_failureReason) {
|
||||
(IDXGIFactory2**)getter_AddRefs(dxgiFactory2));
|
||||
|
||||
#if (_WIN32_WINDOWS_MAXVER >= 0x0A00)
|
||||
if (StaticPrefs::gfx_direct3d11_use_double_buffering() && SUCCEEDED(hr) &&
|
||||
dxgiFactory2 && IsWindows10OrGreater()) {
|
||||
if (gfxVars::UseDoubleBufferingWithCompositor() && SUCCEEDED(hr) &&
|
||||
dxgiFactory2) {
|
||||
// DXGI_SCALING_NONE is not available on Windows 7 with Platform Update.
|
||||
// This looks awful for things like the awesome bar and browser window
|
||||
// resizing so we don't use a flip buffer chain here. When using
|
||||
|
||||
@@ -234,9 +234,9 @@ bool MLGSwapChainD3D11::Initialize(CompositorWidget* aWidget) {
|
||||
}
|
||||
|
||||
RefPtr<IDXGIFactory2> dxgiFactory2;
|
||||
if (StaticPrefs::gfx_direct3d11_use_double_buffering() &&
|
||||
if (gfxVars::UseDoubleBufferingWithCompositor() &&
|
||||
SUCCEEDED(dxgiFactory->QueryInterface(dxgiFactory2.StartAssignment())) &&
|
||||
dxgiFactory2 && IsWin10OrLater() && XRE_IsGPUProcess()) {
|
||||
dxgiFactory2 && XRE_IsGPUProcess()) {
|
||||
// DXGI_SCALING_NONE is not available on Windows 7 with the Platform Update:
|
||||
// This looks awful for things like the awesome bar and browser window
|
||||
// resizing, so we don't use a flip buffer chain here. (Note when using
|
||||
|
||||
@@ -1553,8 +1553,7 @@ PLayerTransactionParent* CompositorBridgeParent::AllocPLayerTransactionParent(
|
||||
#ifdef XP_WIN
|
||||
// This is needed to avoid freezing the window on a device crash on double
|
||||
// buffering, see bug 1549674.
|
||||
if (StaticPrefs::gfx_direct3d11_use_double_buffering() && IsWin10OrLater() &&
|
||||
XRE_IsGPUProcess()) {
|
||||
if (gfxVars::UseDoubleBufferingWithCompositor() && XRE_IsGPUProcess()) {
|
||||
mWidget->AsWindows()->EnsureCompositorWindow();
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -1357,8 +1357,7 @@ void gfxPlatform::WillShutdown() {
|
||||
#endif
|
||||
}
|
||||
|
||||
gfxPlatform::~gfxPlatform() {
|
||||
}
|
||||
gfxPlatform::~gfxPlatform() {}
|
||||
|
||||
/* static */
|
||||
already_AddRefed<DrawTarget> gfxPlatform::CreateDrawTargetForSurface(
|
||||
@@ -2418,6 +2417,10 @@ void gfxPlatform::InitAcceleration() {
|
||||
gfxCriticalNote << "Cannot evaluate keyed mutex feature status";
|
||||
gfxVars::SetAllowD3D11KeyedMutex(true);
|
||||
}
|
||||
if (StaticPrefs::gfx_direct3d11_use_double_buffering() &&
|
||||
IsWin10OrLater()) {
|
||||
gfxVars::SetUseDoubleBufferingWithCompositor(true);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
@@ -2613,13 +2616,12 @@ static bool CalculateWrQualifiedPrefValue() {
|
||||
}
|
||||
|
||||
static void HardwareTooOldForWR(FeatureState& aFeature) {
|
||||
aFeature.Disable(
|
||||
FeatureStatus::BlockedDeviceTooOld, "Device too old",
|
||||
NS_LITERAL_CSTRING("FEATURE_FAILURE_DEVICE_TOO_OLD"));
|
||||
aFeature.Disable(FeatureStatus::BlockedDeviceTooOld, "Device too old",
|
||||
NS_LITERAL_CSTRING("FEATURE_FAILURE_DEVICE_TOO_OLD"));
|
||||
}
|
||||
|
||||
static void UpdateWRQualificationForNvidia(FeatureState& aFeature,
|
||||
int32_t aDeviceId) {
|
||||
int32_t aDeviceId) {
|
||||
// 0x6c0 is the lowest Fermi device id. Unfortunately some Tesla
|
||||
// devices that don't support D3D 10.1 have higher deviceIDs. They
|
||||
// will be included, but blocked by ANGLE.
|
||||
@@ -2634,18 +2636,17 @@ static void UpdateWRQualificationForNvidia(FeatureState& aFeature,
|
||||
}
|
||||
|
||||
static void UpdateWRQualificationForAMD(FeatureState& aFeature,
|
||||
int32_t aDeviceId) {
|
||||
int32_t aDeviceId) {
|
||||
// AMD deviceIDs are not very well ordered. This
|
||||
// condition is based off the information in gpu-db
|
||||
bool supported =
|
||||
(aDeviceId >= 0x6600 && aDeviceId < 0x66b0) ||
|
||||
(aDeviceId >= 0x6700 && aDeviceId < 0x6720) ||
|
||||
(aDeviceId >= 0x6780 && aDeviceId < 0x6840) ||
|
||||
(aDeviceId >= 0x6860 && aDeviceId < 0x6880) ||
|
||||
(aDeviceId >= 0x6900 && aDeviceId < 0x6a00) ||
|
||||
(aDeviceId == 0x7300) ||
|
||||
(aDeviceId >= 0x9830 && aDeviceId < 0x9870) ||
|
||||
(aDeviceId >= 0x9900 && aDeviceId < 0x9a00);
|
||||
bool supported = (aDeviceId >= 0x6600 && aDeviceId < 0x66b0) ||
|
||||
(aDeviceId >= 0x6700 && aDeviceId < 0x6720) ||
|
||||
(aDeviceId >= 0x6780 && aDeviceId < 0x6840) ||
|
||||
(aDeviceId >= 0x6860 && aDeviceId < 0x6880) ||
|
||||
(aDeviceId >= 0x6900 && aDeviceId < 0x6a00) ||
|
||||
(aDeviceId == 0x7300) ||
|
||||
(aDeviceId >= 0x9830 && aDeviceId < 0x9870) ||
|
||||
(aDeviceId >= 0x9900 && aDeviceId < 0x9a00);
|
||||
|
||||
if (!supported) {
|
||||
HardwareTooOldForWR(aFeature);
|
||||
@@ -2656,15 +2657,15 @@ static void UpdateWRQualificationForAMD(FeatureState& aFeature,
|
||||
// so treat the device as qualified unless it is not Windows
|
||||
// and not nightly.
|
||||
#if !defined(XP_WIN) && !defined(NIGHTLY_BUILD)
|
||||
aFeature.Disable(
|
||||
FeatureStatus::BlockedReleaseChannelAMD,
|
||||
"Release channel and AMD",
|
||||
NS_LITERAL_CSTRING("FEATURE_FAILURE_RELEASE_CHANNEL_AMD"));
|
||||
aFeature.Disable(FeatureStatus::BlockedReleaseChannelAMD,
|
||||
"Release channel and AMD",
|
||||
NS_LITERAL_CSTRING("FEATURE_FAILURE_RELEASE_CHANNEL_AMD"));
|
||||
#endif // !XPWIN && !NIGHTLY_BUILD
|
||||
}
|
||||
|
||||
static void UpdateWRQualificationForIntel(FeatureState& aFeature,
|
||||
int32_t aDeviceId, int32_t aScreenPixels) {
|
||||
int32_t aDeviceId,
|
||||
int32_t aScreenPixels) {
|
||||
const uint16_t supportedDevices[] = {
|
||||
// skylake gt2+
|
||||
0x1912,
|
||||
@@ -2776,9 +2777,8 @@ static void UpdateWRQualificationForIntel(FeatureState& aFeature,
|
||||
return;
|
||||
}
|
||||
if (aScreenPixels <= 0) {
|
||||
aFeature.Disable(
|
||||
FeatureStatus::BlockedScreenUnknown, "Screen size unknown",
|
||||
NS_LITERAL_CSTRING("FEATURE_FAILURE_SCREEN_SIZE_UNKNOWN"));
|
||||
aFeature.Disable(FeatureStatus::BlockedScreenUnknown, "Screen size unknown",
|
||||
NS_LITERAL_CSTRING("FEATURE_FAILURE_SCREEN_SIZE_UNKNOWN"));
|
||||
return;
|
||||
}
|
||||
#endif
|
||||
@@ -2789,10 +2789,9 @@ static void UpdateWRQualificationForIntel(FeatureState& aFeature,
|
||||
// on Linux nightly.
|
||||
#else
|
||||
// Disqualify everywhere else
|
||||
aFeature.Disable(
|
||||
FeatureStatus::BlockedReleaseChannelIntel,
|
||||
"Release channel and Intel",
|
||||
NS_LITERAL_CSTRING("FEATURE_FAILURE_RELEASE_CHANNEL_INTEL"));
|
||||
aFeature.Disable(FeatureStatus::BlockedReleaseChannelIntel,
|
||||
"Release channel and Intel",
|
||||
NS_LITERAL_CSTRING("FEATURE_FAILURE_RELEASE_CHANNEL_INTEL"));
|
||||
#endif
|
||||
}
|
||||
|
||||
@@ -2843,7 +2842,7 @@ static FeatureState& WebRenderHardwareQualificationStatus(
|
||||
|
||||
const int32_t screenPixels = aScreenSize.width * aScreenSize.height;
|
||||
|
||||
if (adapterVendorID == u"0x10de") { // Nvidia
|
||||
if (adapterVendorID == u"0x10de") { // Nvidia
|
||||
UpdateWRQualificationForNvidia(featureWebRenderQualified, deviceID);
|
||||
} else if (adapterVendorID == u"0x1002") { // AMD
|
||||
UpdateWRQualificationForAMD(featureWebRenderQualified, deviceID);
|
||||
|
||||
Reference in New Issue
Block a user