IDXGIAdapter1* DeviceManagerDx::GetDXGIAdapter() { if (mAdapter) { return mAdapter; } nsModuleHandle dxgiModule(LoadLibrarySystem32(L"dxgi.dll")); decltype(CreateDXGIFactory1)* createDXGIFactory1 = (decltype(CreateDXGIFactory1)*) GetProcAddress(dxgiModule, "CreateDXGIFactory1"); if (!createDXGIFactory1) { return nullptr; } // Try to use a DXGI 1.1 adapter in order to share resources // across processes. RefPtr<IDXGIFactory1> factory1; HRESULT hr = createDXGIFactory1(__uuidof(IDXGIFactory1), getter_AddRefs(factory1)); if (FAILED(hr) || !factory1) { // This seems to happen with some people running the iZ3D driver. // They won't get acceleration. return nullptr; } if (!mDeviceStatus) { // If we haven't created a device yet, and have no existing device status, // then this must be the compositor device. Pick the first adapter we can. MOZ_ASSERT(ProcessOwnsCompositor()); if (FAILED(factory1->EnumAdapters1(0, getter_AddRefs(mAdapter)))) { return nullptr; } } else { // In the UI and GPU process, we clear mDeviceStatus on device reset, so we // should never reach here. Furthermore, the UI process does not create // devices when using a GPU process. // // So, this should only ever get called on the content process. MOZ_ASSERT(XRE_IsContentProcess()); // In the child process, we search for the adapter that matches the parent // process. The first adapter can be mismatched on dual-GPU systems. for (UINT index = 0; ; index++) { RefPtr<IDXGIAdapter1> adapter; if (FAILED(factory1->EnumAdapters1(index, getter_AddRefs(adapter)))) { break; } const DxgiAdapterDesc& preferred = mDeviceStatus->adapter(); DXGI_ADAPTER_DESC desc; if (SUCCEEDED(adapter->GetDesc(&desc)) && desc.AdapterLuid.HighPart == preferred.AdapterLuid.HighPart && desc.AdapterLuid.LowPart == preferred.AdapterLuid.LowPart && desc.VendorId == preferred.VendorId && desc.DeviceId == preferred.DeviceId) { mAdapter = adapter.forget(); break; } } } if (!mAdapter) { return nullptr; } // We leak this module everywhere, we might as well do so here as well. dxgiModule.disown(); return mAdapter; }
bool IsDX10Available() { DWORD isDX10Available; if (GetDWORDRegKey(metroDX10Available, isDX10Available)) { return isDX10Available; } HMODULE dxgiModule = LoadLibraryA("dxgi.dll"); if (!dxgiModule) { SetDWORDRegKey(metroDX10Available, 0); return false; } CreateDXGIFactory1Func createDXGIFactory1 = (CreateDXGIFactory1Func) GetProcAddress(dxgiModule, "CreateDXGIFactory1"); if (!createDXGIFactory1) { SetDWORDRegKey(metroDX10Available, 0); return false; } HMODULE d3d10module = LoadLibraryA("d3d10_1.dll"); if (!d3d10module) { SetDWORDRegKey(metroDX10Available, 0); return false; } D3D10CreateDevice1Func createD3DDevice = (D3D10CreateDevice1Func) GetProcAddress(d3d10module, "D3D10CreateDevice1"); if (!createD3DDevice) { SetDWORDRegKey(metroDX10Available, 0); return false; } CComPtr<IDXGIFactory1> factory1; if (FAILED(createDXGIFactory1(__uuidof(IDXGIFactory1), (void**)&factory1))) { SetDWORDRegKey(metroDX10Available, 0); return false; } CComPtr<IDXGIAdapter1> adapter1; if (FAILED(factory1->EnumAdapters1(0, &adapter1))) { SetDWORDRegKey(metroDX10Available, 0); return false; } CComPtr<ID3D10Device1> device; // Try for DX10.1 if (FAILED(createD3DDevice(adapter1, D3D10_DRIVER_TYPE_HARDWARE, nullptr, D3D10_CREATE_DEVICE_BGRA_SUPPORT | D3D10_CREATE_DEVICE_PREVENT_INTERNAL_THREADING_OPTIMIZATIONS, D3D10_FEATURE_LEVEL_10_1, D3D10_1_SDK_VERSION, &device))) { // Try for DX10 if (FAILED(createD3DDevice(adapter1, D3D10_DRIVER_TYPE_HARDWARE, nullptr, D3D10_CREATE_DEVICE_BGRA_SUPPORT | D3D10_CREATE_DEVICE_PREVENT_INTERNAL_THREADING_OPTIMIZATIONS, D3D10_FEATURE_LEVEL_10_0, D3D10_1_SDK_VERSION, &device))) { // Try for DX9.3 (we fall back to cairo and cairo has support for D3D 9.3) if (FAILED(createD3DDevice(adapter1, D3D10_DRIVER_TYPE_HARDWARE, nullptr, D3D10_CREATE_DEVICE_BGRA_SUPPORT | D3D10_CREATE_DEVICE_PREVENT_INTERNAL_THREADING_OPTIMIZATIONS, D3D10_FEATURE_LEVEL_9_3, D3D10_1_SDK_VERSION, &device))) { SetDWORDRegKey(metroDX10Available, 0); return false; } } } SetDWORDRegKey(metroDX10Available, 1); return true; }