Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(239)

Side by Side Diff: content/gpu/gpu_info_collector_win.cc

Issue 11576052: Revert 173248, broke building on the official chrome/win bot: (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src/
Patch Set: Created 8 years ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « content/gpu/gpu_info_collector_unittest_win.cc ('k') | content/gpu/gpu_main.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2012 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 "content/gpu/gpu_info_collector.h" 5 #include "content/gpu/gpu_info_collector.h"
6 6
7 #include <windows.h> 7 #include <windows.h>
8 #include <d3d9.h> 8 #include <d3d9.h>
9 #include <setupapi.h> 9 #include <setupapi.h>
10 10
(...skipping 139 matching lines...) Expand 10 before | Expand all | Expand 10 after
150 stats.graphics * 10, 10, 200, 50); 150 stats.graphics * 10, 10, 200, 50);
151 UMA_HISTOGRAM_CUSTOM_COUNTS("GPU.WinSAT.GamingScore2", 151 UMA_HISTOGRAM_CUSTOM_COUNTS("GPU.WinSAT.GamingScore2",
152 stats.gaming * 10, 10, 200, 50); 152 stats.gaming * 10, 10, 200, 50);
153 UMA_HISTOGRAM_BOOLEAN( 153 UMA_HISTOGRAM_BOOLEAN(
154 "GPU.WinSAT.HasResults", 154 "GPU.WinSAT.HasResults",
155 stats.overall != 0.0 && stats.graphics != 0.0 && stats.gaming != 0.0); 155 stats.overall != 0.0 && stats.graphics != 0.0 && stats.gaming != 0.0);
156 156
157 return stats; 157 return stats;
158 } 158 }
159 159
160 // Advanced Micro Devices has interesting configurations on laptops were 160 } // namespace anonymous
161 // there are two videocards that can alternatively a given process output. 161
162 enum AMDVideoCardType { 162 namespace gpu_info_collector {
163 UNKNOWN,
164 STANDALONE,
165 INTEGRATED,
166 SWITCHABLE
167 };
168 163
169 #if !defined(GOOGLE_CHROME_BUILD) 164 #if !defined(GOOGLE_CHROME_BUILD)
170 AMDVideoCardType GetAMDVideocardType() { 165 AMDVideoCardType GetAMDVideocardType() {
171 return UNKNOWN; 166 return UNKNOWN;
172 } 167 }
173 #else 168 #else
174 // This function has a real implementation for official builds that can 169 // This function has a real implementation for official builds that can
175 // be found in src/third_party/amd. 170 // be found in src/third_party/amd.
176 AMDVideoCardType GetAMDVideocardType(); 171 AMDVideoCardType GetAMDVideocardType();
177 #endif 172 #endif
178 173
179 bool CollectDriverInfoD3D(const std::wstring& device_id, 174 bool CollectGraphicsInfo(content::GPUInfo* gpu_info) {
180 content::GPUInfo* gpu_info) {
181 TRACE_EVENT0("gpu", "CollectDriverInfoD3D");
182
183 // create device info for the display device
184 HDEVINFO device_info = SetupDiGetClassDevsW(
185 NULL, device_id.c_str(), NULL,
186 DIGCF_PRESENT | DIGCF_PROFILE | DIGCF_ALLCLASSES);
187 if (device_info == INVALID_HANDLE_VALUE) {
188 LOG(ERROR) << "Creating device info failed";
189 return false;
190 }
191
192 DWORD index = 0;
193 bool found = false;
194 SP_DEVINFO_DATA device_info_data;
195 device_info_data.cbSize = sizeof(device_info_data);
196 while (SetupDiEnumDeviceInfo(device_info, index++, &device_info_data)) {
197 WCHAR value[255];
198 if (SetupDiGetDeviceRegistryPropertyW(device_info,
199 &device_info_data,
200 SPDRP_DRIVER,
201 NULL,
202 reinterpret_cast<PBYTE>(value),
203 sizeof(value),
204 NULL)) {
205 HKEY key;
206 std::wstring driver_key = L"System\\CurrentControlSet\\Control\\Class\\";
207 driver_key += value;
208 LONG result = RegOpenKeyExW(
209 HKEY_LOCAL_MACHINE, driver_key.c_str(), 0, KEY_QUERY_VALUE, &key);
210 if (result == ERROR_SUCCESS) {
211 DWORD dwcb_data = sizeof(value);
212 std::string driver_version;
213 result = RegQueryValueExW(
214 key, L"DriverVersion", NULL, NULL,
215 reinterpret_cast<LPBYTE>(value), &dwcb_data);
216 if (result == ERROR_SUCCESS)
217 driver_version = WideToASCII(std::wstring(value));
218
219 std::string driver_date;
220 dwcb_data = sizeof(value);
221 result = RegQueryValueExW(
222 key, L"DriverDate", NULL, NULL,
223 reinterpret_cast<LPBYTE>(value), &dwcb_data);
224 if (result == ERROR_SUCCESS)
225 driver_date = WideToASCII(std::wstring(value));
226
227 std::string driver_vendor;
228 dwcb_data = sizeof(value);
229 result = RegQueryValueExW(
230 key, L"ProviderName", NULL, NULL,
231 reinterpret_cast<LPBYTE>(value), &dwcb_data);
232 if (result == ERROR_SUCCESS) {
233 driver_vendor = WideToASCII(std::wstring(value));
234 if (driver_vendor == "Advanced Micro Devices, Inc." ||
235 driver_vendor == "ATI Technologies Inc.") {
236 // We are conservative and assume that in the absence of a clear
237 // signal the videocard is assumed to be switchable. Additionally,
238 // some switchable systems with Intel GPUs aren't correctly
239 // detected, so always count them.
240 AMDVideoCardType amd_card_type = GetAMDVideocardType();
241 gpu_info->amd_switchable = (gpu_info->gpu.vendor_id == 0x8086) ||
242 (amd_card_type != STANDALONE);
243 }
244 }
245
246 gpu_info->driver_vendor = driver_vendor;
247 gpu_info->driver_version = driver_version;
248 gpu_info->driver_date = driver_date;
249 found = true;
250 RegCloseKey(key);
251 break;
252 }
253 }
254 }
255 SetupDiDestroyDeviceInfoList(device_info);
256 return found;
257 }
258
259 } // namespace anonymous
260
261 namespace gpu_info_collector {
262
263 bool CollectContextGraphicsInfo(content::GPUInfo* gpu_info) {
264 TRACE_EVENT0("gpu", "CollectGraphicsInfo"); 175 TRACE_EVENT0("gpu", "CollectGraphicsInfo");
265 176
266 DCHECK(gpu_info); 177 DCHECK(gpu_info);
178 *gpu_info = content::GPUInfo();
179
180 gpu_info->performance_stats = RetrieveGpuPerformanceStats();
267 181
268 if (CommandLine::ForCurrentProcess()->HasSwitch(switches::kUseGL)) { 182 if (CommandLine::ForCurrentProcess()->HasSwitch(switches::kUseGL)) {
269 std::string requested_implementation_name = 183 std::string requested_implementation_name =
270 CommandLine::ForCurrentProcess()->GetSwitchValueASCII(switches::kUseGL); 184 CommandLine::ForCurrentProcess()->GetSwitchValueASCII(switches::kUseGL);
271 if (requested_implementation_name == "swiftshader") { 185 if (requested_implementation_name == "swiftshader") {
272 gpu_info->software_rendering = true; 186 gpu_info->software_rendering = true;
273 return false; 187 return false;
274 } 188 }
275 } 189 }
276 190
(...skipping 17 matching lines...) Expand all
294 LOG(ERROR) << "display->getDevice() failed"; 208 LOG(ERROR) << "display->getDevice() failed";
295 return false; 209 return false;
296 } 210 }
297 211
298 base::win::ScopedComPtr<IDirect3D9> d3d; 212 base::win::ScopedComPtr<IDirect3D9> d3d;
299 if (FAILED(device->GetDirect3D(d3d.Receive()))) { 213 if (FAILED(device->GetDirect3D(d3d.Receive()))) {
300 LOG(ERROR) << "device->GetDirect3D(&d3d) failed"; 214 LOG(ERROR) << "device->GetDirect3D(&d3d) failed";
301 return false; 215 return false;
302 } 216 }
303 217
304 // Get can_lose_context 218 if (!CollectGraphicsInfoD3D(d3d, gpu_info))
305 base::win::ScopedComPtr<IDirect3D9Ex> d3dex; 219 return false;
306 if (SUCCEEDED(d3dex.QueryFrom(d3d))) 220
307 gpu_info->can_lose_context = false; 221 // DirectX diagnostics are collected asynchronously because it takes a
308 else 222 // couple of seconds. Do not mark gpu_info as complete until that is done.
309 gpu_info->can_lose_context = true; 223 return true;
224 }
225
226 bool CollectPreliminaryGraphicsInfo(content::GPUInfo* gpu_info) {
227 TRACE_EVENT0("gpu", "CollectPreliminaryGraphicsInfo");
228
229 DCHECK(gpu_info);
230
231 bool rt = true;
232 if (!CollectVideoCardInfo(gpu_info))
233 rt = false;
234
235 gpu_info->performance_stats = RetrieveGpuPerformanceStatsWithHistograms();
236
237 return rt;
238 }
239
240 bool CollectGraphicsInfoD3D(IDirect3D9* d3d, content::GPUInfo* gpu_info) {
241 TRACE_EVENT0("gpu", "CollectGraphicsInfoD3D");
242
243 DCHECK(d3d);
244 DCHECK(gpu_info);
245
246 bool succeed = CollectVideoCardInfo(gpu_info);
310 247
311 // Get version information 248 // Get version information
312 D3DCAPS9 d3d_caps; 249 D3DCAPS9 d3d_caps;
313 if (d3d->GetDeviceCaps(D3DADAPTER_DEFAULT, 250 if (d3d->GetDeviceCaps(D3DADAPTER_DEFAULT,
314 D3DDEVTYPE_HAL, 251 D3DDEVTYPE_HAL,
315 &d3d_caps) == D3D_OK) { 252 &d3d_caps) == D3D_OK) {
316 gpu_info->pixel_shader_version = 253 gpu_info->pixel_shader_version =
317 VersionNumberToString(d3d_caps.PixelShaderVersion); 254 VersionNumberToString(d3d_caps.PixelShaderVersion);
318 gpu_info->vertex_shader_version = 255 gpu_info->vertex_shader_version =
319 VersionNumberToString(d3d_caps.VertexShaderVersion); 256 VersionNumberToString(d3d_caps.VertexShaderVersion);
320 } else { 257 } else {
321 LOG(ERROR) << "d3d->GetDeviceCaps() failed"; 258 LOG(ERROR) << "d3d->GetDeviceCaps() failed";
322 return false; 259 succeed = false;
323 } 260 }
324 261
325 // DirectX diagnostics are collected asynchronously because it takes a 262 // Get can_lose_context
326 // couple of seconds. Do not mark gpu_info as complete until that is done. 263 base::win::ScopedComPtr<IDirect3D9Ex> d3dex;
264 if (SUCCEEDED(d3dex.QueryFrom(d3d)))
265 gpu_info->can_lose_context = false;
266 else
267 gpu_info->can_lose_context = true;
268
327 return true; 269 return true;
328 } 270 }
329 271
330 bool CollectBasicGraphicsInfo(content::GPUInfo* gpu_info) { 272 bool CollectVideoCardInfo(content::GPUInfo* gpu_info) {
331 TRACE_EVENT0("gpu", "CollectPreliminaryGraphicsInfo"); 273 TRACE_EVENT0("gpu", "CollectVideoCardInfo");
332 274
333 DCHECK(gpu_info); 275 DCHECK(gpu_info);
334 276
335 gpu_info->performance_stats = RetrieveGpuPerformanceStatsWithHistograms();
336
337 // nvd3d9wrap.dll is loaded into all processes when Optimus is enabled. 277 // nvd3d9wrap.dll is loaded into all processes when Optimus is enabled.
338 HMODULE nvd3d9wrap = GetModuleHandleW(L"nvd3d9wrap.dll"); 278 HMODULE nvd3d9wrap = GetModuleHandleW(L"nvd3d9wrap.dll");
339 gpu_info->optimus = nvd3d9wrap != NULL; 279 gpu_info->optimus = nvd3d9wrap != NULL;
340 280
341 // Taken from http://developer.nvidia.com/object/device_ids.html 281 // Taken from http://developer.nvidia.com/object/device_ids.html
342 DISPLAY_DEVICE dd; 282 DISPLAY_DEVICE dd;
343 dd.cb = sizeof(DISPLAY_DEVICE); 283 dd.cb = sizeof(DISPLAY_DEVICE);
344 int i = 0; 284 int i = 0;
345 std::wstring id; 285 std::wstring id;
346 for (int i = 0; EnumDisplayDevices(NULL, i, &dd, 0); ++i) { 286 for (int i = 0; EnumDisplayDevices(NULL, i, &dd, 0); ++i) {
(...skipping 10 matching lines...) Expand all
357 base::HexStringToInt(WideToASCII(vendor_id_string), &vendor_id); 297 base::HexStringToInt(WideToASCII(vendor_id_string), &vendor_id);
358 base::HexStringToInt(WideToASCII(device_id_string), &device_id); 298 base::HexStringToInt(WideToASCII(device_id_string), &device_id);
359 gpu_info->gpu.vendor_id = vendor_id; 299 gpu_info->gpu.vendor_id = vendor_id;
360 gpu_info->gpu.device_id = device_id; 300 gpu_info->gpu.device_id = device_id;
361 // TODO(zmo): we only need to call CollectDriverInfoD3D() if we use ANGLE. 301 // TODO(zmo): we only need to call CollectDriverInfoD3D() if we use ANGLE.
362 return CollectDriverInfoD3D(id, gpu_info); 302 return CollectDriverInfoD3D(id, gpu_info);
363 } 303 }
364 return false; 304 return false;
365 } 305 }
366 306
307 bool CollectDriverInfoD3D(const std::wstring& device_id,
308 content::GPUInfo* gpu_info) {
309 TRACE_EVENT0("gpu", "CollectDriverInfoD3D");
310
311 // create device info for the display device
312 HDEVINFO device_info = SetupDiGetClassDevsW(
313 NULL, device_id.c_str(), NULL,
314 DIGCF_PRESENT | DIGCF_PROFILE | DIGCF_ALLCLASSES);
315 if (device_info == INVALID_HANDLE_VALUE) {
316 LOG(ERROR) << "Creating device info failed";
317 return false;
318 }
319
320 DWORD index = 0;
321 bool found = false;
322 SP_DEVINFO_DATA device_info_data;
323 device_info_data.cbSize = sizeof(device_info_data);
324 while (SetupDiEnumDeviceInfo(device_info, index++, &device_info_data)) {
325 WCHAR value[255];
326 if (SetupDiGetDeviceRegistryPropertyW(device_info,
327 &device_info_data,
328 SPDRP_DRIVER,
329 NULL,
330 reinterpret_cast<PBYTE>(value),
331 sizeof(value),
332 NULL)) {
333 HKEY key;
334 std::wstring driver_key = L"System\\CurrentControlSet\\Control\\Class\\";
335 driver_key += value;
336 LONG result = RegOpenKeyExW(
337 HKEY_LOCAL_MACHINE, driver_key.c_str(), 0, KEY_QUERY_VALUE, &key);
338 if (result == ERROR_SUCCESS) {
339 DWORD dwcb_data = sizeof(value);
340 std::string driver_version;
341 result = RegQueryValueExW(
342 key, L"DriverVersion", NULL, NULL,
343 reinterpret_cast<LPBYTE>(value), &dwcb_data);
344 if (result == ERROR_SUCCESS)
345 driver_version = WideToASCII(std::wstring(value));
346
347 std::string driver_date;
348 dwcb_data = sizeof(value);
349 result = RegQueryValueExW(
350 key, L"DriverDate", NULL, NULL,
351 reinterpret_cast<LPBYTE>(value), &dwcb_data);
352 if (result == ERROR_SUCCESS)
353 driver_date = WideToASCII(std::wstring(value));
354
355 std::string driver_vendor;
356 dwcb_data = sizeof(value);
357 result = RegQueryValueExW(
358 key, L"ProviderName", NULL, NULL,
359 reinterpret_cast<LPBYTE>(value), &dwcb_data);
360 if (result == ERROR_SUCCESS) {
361 driver_vendor = WideToASCII(std::wstring(value));
362 if (driver_vendor == "Advanced Micro Devices, Inc." ||
363 driver_vendor == "ATI Technologies Inc.") {
364 // We are conservative and assume that in the absence of a clear
365 // signal the videocard is assumed to be switchable. Additionally,
366 // some switchable systems with Intel GPUs aren't correctly
367 // detected, so always count them.
368 AMDVideoCardType amd_card_type = GetAMDVideocardType();
369 gpu_info->amd_switchable = (gpu_info->gpu.vendor_id == 0x8086) ||
370 (amd_card_type != STANDALONE);
371 }
372 }
373
374 gpu_info->driver_vendor = driver_vendor;
375 gpu_info->driver_version = driver_version;
376 gpu_info->driver_date = driver_date;
377 found = true;
378 RegCloseKey(key);
379 break;
380 }
381 }
382 }
383 SetupDiDestroyDeviceInfoList(device_info);
384 return found;
385 }
386
367 bool CollectDriverInfoGL(content::GPUInfo* gpu_info) { 387 bool CollectDriverInfoGL(content::GPUInfo* gpu_info) {
368 TRACE_EVENT0("gpu", "CollectDriverInfoGL"); 388 TRACE_EVENT0("gpu", "CollectDriverInfoGL");
369 389
370 DCHECK(gpu_info); 390 DCHECK(gpu_info);
371 391
372 std::string gl_version_string = gpu_info->gl_version_string; 392 std::string gl_version_string = gpu_info->gl_version_string;
373 393
374 // TODO(zmo): We assume the driver version is in the end of GL_VERSION 394 // TODO(zmo): We assume the driver version is in the end of GL_VERSION
375 // string. Need to verify if it is true for majority drivers. 395 // string. Need to verify if it is true for majority drivers.
376 396
377 size_t pos = gl_version_string.find_last_not_of("0123456789."); 397 size_t pos = gl_version_string.find_last_not_of("0123456789.");
378 if (pos != std::string::npos && pos < gl_version_string.length() - 1) { 398 if (pos != std::string::npos && pos < gl_version_string.length() - 1) {
379 gpu_info->driver_version = gl_version_string.substr(pos + 1); 399 gpu_info->driver_version = gl_version_string.substr(pos + 1);
380 return true; 400 return true;
381 } 401 }
382 return false; 402 return false;
383 } 403 }
384 404
385 void MergeGPUInfo(content::GPUInfo* basic_gpu_info,
386 const content::GPUInfo& context_gpu_info) {
387 DCHECK(basic_gpu_info);
388
389 if (context_gpu_info.software_rendering) {
390 basic_gpu_info->software_rendering = true;
391 return;
392 }
393
394 if (!context_gpu_info.gl_vendor.empty()) {
395 MergeGPUInfoGL(basic_gpu_info, context_gpu_info);
396 return;
397 }
398
399 basic_gpu_info->pixel_shader_version =
400 context_gpu_info.pixel_shader_version;
401 basic_gpu_info->vertex_shader_version =
402 context_gpu_info.vertex_shader_version;
403
404 basic_gpu_info->dx_diagnostics = context_gpu_info.dx_diagnostics;
405
406 basic_gpu_info->can_lose_context = context_gpu_info.can_lose_context;
407 basic_gpu_info->sandboxed = context_gpu_info.sandboxed;
408 basic_gpu_info->gpu_accessible = context_gpu_info.gpu_accessible;
409 basic_gpu_info->finalized = context_gpu_info.finalized;
410 basic_gpu_info->initialization_time = context_gpu_info.initialization_time;
411 }
412
413 } // namespace gpu_info_collector 405 } // namespace gpu_info_collector
OLDNEW
« no previous file with comments | « content/gpu/gpu_info_collector_unittest_win.cc ('k') | content/gpu/gpu_main.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698