OLD | NEW |
---|---|
1 // Copyright (c) 2010 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2010 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "chrome/gpu/gpu_info_collector.h" | 5 #include "chrome/gpu/gpu_info_collector.h" |
6 | 6 |
7 #include <windows.h> | 7 #include <windows.h> |
8 #include <d3d9.h> | 8 #include <d3d9.h> |
9 | 9 |
10 #include "app/gfx/gl/gl_context_egl.h" | 10 #include "app/gfx/gl/gl_context_egl.h" |
11 #include "app/gfx/gl/gl_implementation.h" | 11 #include "app/gfx/gl/gl_implementation.h" |
12 #include "base/file_path.h" | 12 #include "base/file_path.h" |
13 #include "base/scoped_native_library.h" | 13 #include "base/scoped_native_library.h" |
14 #include "base/string_number_conversions.h" | |
14 #include "base/string_util.h" | 15 #include "base/string_util.h" |
15 | 16 |
16 // ANGLE seems to require that main.h be included before any other ANGLE header. | 17 // ANGLE seems to require that main.h be included before any other ANGLE header. |
17 #include "libEGL/main.h" | 18 #include "libEGL/main.h" |
18 #include "libEGL/Display.h" | 19 #include "libEGL/Display.h" |
19 | 20 |
20 namespace gpu_info_collector { | 21 namespace gpu_info_collector { |
21 | 22 |
22 bool CollectGraphicsInfo(GPUInfo* gpu_info) { | 23 bool CollectGraphicsInfo(GPUInfo* gpu_info) { |
23 // TODO: collect OpenGL info if not using ANGLE? | 24 DCHECK(gpu_info); |
24 if (gfx::GetGLImplementation() != gfx::kGLImplementationEGLGLES2) | 25 |
25 return true; | 26 if (gfx::GetGLImplementation() != gfx::kGLImplementationEGLGLES2) { |
27 gpu_info->SetProgress(GPUInfo::kComplete); | |
28 return CollectGraphicsInfoGL(gpu_info); | |
29 } | |
26 | 30 |
27 egl::Display* display = static_cast<egl::Display*>( | 31 egl::Display* display = static_cast<egl::Display*>( |
28 gfx::BaseEGLContext::GetDisplay()); | 32 gfx::BaseEGLContext::GetDisplay()); |
29 if (!display) | 33 if (!display) |
30 return false; | 34 return false; |
31 | 35 |
32 IDirect3DDevice9* device = display->getDevice(); | 36 IDirect3DDevice9* device = display->getDevice(); |
Ken Russell (switch to Gerrit)
2011/01/19 22:11:43
We should add a TODO indicating that this code wil
Zhenyao Mo
2011/01/19 23:36:22
In the beginning of this function we already handl
Ken Russell (switch to Gerrit)
2011/01/19 23:46:50
Running on EGL+GLES2 on Windows doesn't necessaril
| |
33 if (!device) | 37 if (!device) |
34 return false; | 38 return false; |
35 | 39 |
36 IDirect3D9* d3d = NULL; | 40 IDirect3D9* d3d = NULL; |
37 if (FAILED(device->GetDirect3D(&d3d))) | 41 if (FAILED(device->GetDirect3D(&d3d))) |
38 return false; | 42 return false; |
39 | 43 |
40 if (!CollectGraphicsInfoD3D(d3d, gpu_info)) | 44 if (!CollectGraphicsInfoD3D(d3d, gpu_info)) |
41 return false; | 45 return false; |
42 | 46 |
43 // DirectX diagnostics are collected asynchronously because it takes a | 47 // DirectX diagnostics are collected asynchronously because it takes a |
44 // couple of seconds. Do not mark as complete until that is done. | 48 // couple of seconds. Do not mark as complete until that is done. |
45 gpu_info->SetProgress(GPUInfo::kPartial); | 49 gpu_info->SetProgress(GPUInfo::kPartial); |
46 | |
47 return true; | 50 return true; |
48 } | 51 } |
49 | 52 |
50 bool CollectGraphicsInfoD3D(IDirect3D9* d3d, GPUInfo* gpu_info) { | 53 bool CollectGraphicsInfoD3D(IDirect3D9* d3d, GPUInfo* gpu_info) { |
51 DCHECK(d3d); | 54 DCHECK(d3d); |
52 DCHECK(gpu_info); | 55 DCHECK(gpu_info); |
53 | 56 |
54 // Get device information | 57 bool succeed = true; |
58 | |
59 // Get device/driver information | |
55 D3DADAPTER_IDENTIFIER9 identifier; | 60 D3DADAPTER_IDENTIFIER9 identifier; |
56 HRESULT hr = d3d->GetAdapterIdentifier(D3DADAPTER_DEFAULT, 0, &identifier); | 61 if (d3d->GetAdapterIdentifier(D3DADAPTER_DEFAULT, 0, &identifier) == D3D_OK) { |
57 if (hr != D3D_OK) { | 62 gpu_info->SetVideoCardInfo(identifier.VendorId, identifier.DeviceId); |
58 d3d->Release(); | 63 |
59 return false; | 64 uint32 driver_major_version_hi = HIWORD(identifier.DriverVersion.HighPart); |
65 uint32 driver_major_version_lo = LOWORD(identifier.DriverVersion.HighPart); | |
66 uint32 driver_minor_version_hi = HIWORD(identifier.DriverVersion.LowPart); | |
67 uint32 driver_minor_version_lo = LOWORD(identifier.DriverVersion.LowPart); | |
68 std::string driver_version = StringPrintf("%d.%d.%d.%d", | |
69 driver_major_version_hi, | |
70 driver_major_version_lo, | |
71 driver_minor_version_hi, | |
72 driver_minor_version_lo); | |
73 gpu_info->SetDriverInfo("", driver_version); | |
74 } else { | |
75 succeed = false; | |
60 } | 76 } |
61 uint32 vendor_id = identifier.VendorId; | |
62 uint32 device_id = identifier.DeviceId; | |
63 | 77 |
64 // Get version information | 78 // Get version information |
65 D3DCAPS9 d3d_caps; | 79 D3DCAPS9 d3d_caps; |
66 HRESULT caps_result = d3d->GetDeviceCaps(D3DADAPTER_DEFAULT, | 80 if (d3d->GetDeviceCaps(D3DADAPTER_DEFAULT, |
67 D3DDEVTYPE_HAL, | 81 D3DDEVTYPE_HAL, |
68 &d3d_caps); | 82 &d3d_caps) == D3D_OK) { |
69 if (caps_result != D3D_OK) { | 83 gpu_info->SetShaderVersion(d3d_caps.PixelShaderVersion, |
70 d3d->Release(); | 84 d3d_caps.VertexShaderVersion); |
71 return false; | 85 } else { |
86 succeed = false; | |
72 } | 87 } |
73 uint32 driver_major_version_hi = HIWORD(identifier.DriverVersion.HighPart); | |
74 uint32 driver_major_version_lo = LOWORD(identifier.DriverVersion.HighPart); | |
75 uint32 driver_minor_version_hi = HIWORD(identifier.DriverVersion.LowPart); | |
76 uint32 driver_minor_version_lo = LOWORD(identifier.DriverVersion.LowPart); | |
77 std::wstring driver_version = StringPrintf(L"%d.%d.%d.%d", | |
78 driver_major_version_hi, | |
79 driver_major_version_lo, | |
80 driver_minor_version_hi, | |
81 driver_minor_version_lo); | |
82 | 88 |
89 // Get can_lose_context | |
83 bool can_lose_context = false; | 90 bool can_lose_context = false; |
84 IDirect3D9Ex* d3dex = NULL; | 91 IDirect3D9Ex* d3dex = NULL; |
85 if (SUCCEEDED(d3d->QueryInterface(__uuidof(IDirect3D9Ex), | 92 if (SUCCEEDED(d3d->QueryInterface(__uuidof(IDirect3D9Ex), |
86 reinterpret_cast<void**>(&d3dex)))) { | 93 reinterpret_cast<void**>(&d3dex)))) { |
87 d3dex->Release(); | 94 d3dex->Release(); |
88 } else { | 95 } else { |
89 can_lose_context = true; | 96 can_lose_context = true; |
90 } | 97 } |
98 gpu_info->SetCanLoseContext(can_lose_context); | |
91 | 99 |
92 d3d->Release(); | 100 d3d->Release(); |
93 | |
94 // Get shader versions | |
95 uint32 pixel_shader_version = d3d_caps.PixelShaderVersion; | |
96 uint32 vertex_shader_version = d3d_caps.VertexShaderVersion; | |
97 | |
98 gpu_info->SetGraphicsInfo(vendor_id, | |
99 device_id, | |
100 driver_version, | |
101 pixel_shader_version, | |
102 vertex_shader_version, | |
103 0, | |
104 can_lose_context); | |
105 return true; | 101 return true; |
106 } | 102 } |
107 | 103 |
108 bool CollectGraphicsInfoGL(GPUInfo* gpu_info) { | 104 bool CollectVideoCardInfo(GPUInfo* gpu_info) { |
105 DCHECK(gpu_info); | |
106 | |
109 // Taken from http://developer.nvidia.com/object/device_ids.html | 107 // Taken from http://developer.nvidia.com/object/device_ids.html |
110 DISPLAY_DEVICE dd; | 108 DISPLAY_DEVICE dd; |
111 dd.cb = sizeof(DISPLAY_DEVICE); | 109 dd.cb = sizeof(DISPLAY_DEVICE); |
112 int i = 0; | 110 int i = 0; |
113 std::wstring id; | 111 std::wstring id; |
114 for (int i = 0; EnumDisplayDevices(NULL, i, &dd, 0); ++i) { | 112 for (int i = 0; EnumDisplayDevices(NULL, i, &dd, 0); ++i) { |
115 if (dd.StateFlags & DISPLAY_DEVICE_PRIMARY_DEVICE) { | 113 if (dd.StateFlags & DISPLAY_DEVICE_PRIMARY_DEVICE) { |
116 id = dd.DeviceID; | 114 id = dd.DeviceID; |
117 break; | 115 break; |
118 } | 116 } |
119 } | 117 } |
120 if (id.empty()) { | 118 |
121 return false; | 119 if (id.length() > 20) { |
120 int vendor_id = 0, device_id = 0; | |
121 std::wstring vendor_id_string = id.substr(8, 4); | |
122 std::wstring device_id_string = id.substr(17, 4); | |
123 base::HexStringToInt(WideToASCII(vendor_id_string), &vendor_id); | |
124 base::HexStringToInt(WideToASCII(device_id_string), &device_id); | |
125 gpu_info->SetVideoCardInfo(vendor_id, device_id); | |
126 return true; | |
122 } | 127 } |
123 uint32 vendor_id; | 128 return false; |
124 uint32 device_id; | 129 } |
125 std::wstring vendorid = id.substr(8, 4); | |
126 std::wstring deviceid = id.substr(17, 4); | |
127 swscanf_s(vendorid.c_str(), L"%x", &vendor_id); | |
128 swscanf_s(deviceid.c_str(), L"%x", &device_id); | |
129 | 130 |
130 std::wstring driver_version = L""; | 131 bool CollectDriverInfo(GPUInfo* gpu_info) { |
131 uint32 pixel_shader_version = 0; | 132 DCHECK(gpu_info); |
132 uint32 vertex_shader_version = 0; | |
133 gpu_info->SetGraphicsInfo(vendor_id, device_id, driver_version, | |
134 pixel_shader_version, | |
135 vertex_shader_version, | |
136 0, // GL version of 0 indicates D3D | |
137 false); | |
138 return true; | |
139 | 133 |
140 // TODO(rlp): Add driver and pixel versions | 134 std::string gl_version_string = gpu_info->gl_version_string(); |
135 | |
136 size_t pos = gl_version_string.find_last_not_of("0123456789."); | |
Ken Russell (switch to Gerrit)
2011/01/19 22:11:43
Could you add a comment indicating the expected fo
Zhenyao Mo
2011/01/19 23:36:22
Done.
| |
137 if (pos != std::string::npos && pos < gl_version_string.length() - 1) { | |
138 gpu_info->SetDriverInfo("", gl_version_string.substr(pos + 1)); | |
139 return true; | |
140 } | |
141 return false; | |
141 } | 142 } |
142 | 143 |
143 } // namespace gpu_info_collector | 144 } // namespace gpu_info_collector |
OLD | NEW |