OLD | NEW |
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 "chrome/browser/ui/webui/gpu_internals_ui.h" | 5 #include "chrome/browser/ui/webui/gpu_internals_ui.h" |
6 | 6 |
7 #include <string> | 7 #include <string> |
8 | 8 |
9 #include "base/bind.h" | 9 #include "base/bind.h" |
10 #include "base/bind_helpers.h" | 10 #include "base/bind_helpers.h" |
11 #include "base/command_line.h" | 11 #include "base/command_line.h" |
12 #include "base/i18n/time_formatting.h" | 12 #include "base/i18n/time_formatting.h" |
13 #include "base/string_number_conversions.h" | 13 #include "base/string_number_conversions.h" |
14 #include "base/stringprintf.h" | 14 #include "base/stringprintf.h" |
15 #include "base/sys_info.h" | 15 #include "base/sys_info.h" |
16 #include "base/values.h" | 16 #include "base/values.h" |
17 #include "chrome/browser/crash_upload_list.h" | 17 #include "chrome/browser/crash_upload_list.h" |
18 #include "chrome/browser/gpu_blacklist.h" | |
19 #include "chrome/browser/gpu_util.h" | |
20 #include "chrome/browser/profiles/profile.h" | 18 #include "chrome/browser/profiles/profile.h" |
21 #include "chrome/browser/ui/webui/chrome_url_data_manager.h" | 19 #include "chrome/browser/ui/webui/chrome_url_data_manager.h" |
22 #include "chrome/browser/ui/webui/chrome_web_ui_data_source.h" | 20 #include "chrome/browser/ui/webui/chrome_web_ui_data_source.h" |
23 #include "chrome/browser/ui/webui/crashes_ui.h" | 21 #include "chrome/browser/ui/webui/crashes_ui.h" |
24 #include "chrome/common/chrome_version_info.h" | 22 #include "chrome/common/chrome_version_info.h" |
25 #include "chrome/common/url_constants.h" | 23 #include "chrome/common/url_constants.h" |
26 #include "content/public/browser/browser_thread.h" | 24 #include "content/public/browser/browser_thread.h" |
27 #include "content/public/browser/gpu_data_manager.h" | 25 #include "content/public/browser/gpu_data_manager.h" |
28 #include "content/public/browser/gpu_data_manager_observer.h" | 26 #include "content/public/browser/gpu_data_manager_observer.h" |
29 #include "content/public/browser/web_contents.h" | 27 #include "content/public/browser/web_contents.h" |
30 #include "content/public/browser/web_ui.h" | 28 #include "content/public/browser/web_ui.h" |
31 #include "content/public/browser/web_ui_message_handler.h" | 29 #include "content/public/browser/web_ui_message_handler.h" |
| 30 #include "content/public/common/compositor_util.h" |
| 31 #include "content/public/common/content_switches.h" |
| 32 #include "content/public/common/gpu_info.h" |
32 #include "grit/browser_resources.h" | 33 #include "grit/browser_resources.h" |
33 #include "grit/generated_resources.h" | 34 #include "grit/generated_resources.h" |
34 #include "third_party/angle/src/common/version.h" | 35 #include "third_party/angle/src/common/version.h" |
35 #include "ui/base/l10n/l10n_util.h" | 36 #include "ui/base/l10n/l10n_util.h" |
36 | 37 |
37 using content::BrowserThread; | 38 using content::BrowserThread; |
38 using content::GpuDataManager; | 39 using content::GpuDataManager; |
| 40 using content::GpuFeatureType; |
39 using content::WebContents; | 41 using content::WebContents; |
40 using content::WebUIMessageHandler; | 42 using content::WebUIMessageHandler; |
41 | 43 |
42 namespace { | 44 namespace { |
43 | 45 |
| 46 struct GpuFeatureInfo { |
| 47 std::string name; |
| 48 uint32 blocked; |
| 49 bool disabled; |
| 50 std::string disabled_description; |
| 51 bool fallback_to_software; |
| 52 }; |
| 53 |
44 ChromeWebUIDataSource* CreateGpuHTMLSource() { | 54 ChromeWebUIDataSource* CreateGpuHTMLSource() { |
45 ChromeWebUIDataSource* source = | 55 ChromeWebUIDataSource* source = |
46 new ChromeWebUIDataSource(chrome::kChromeUIGpuInternalsHost); | 56 new ChromeWebUIDataSource(chrome::kChromeUIGpuInternalsHost); |
47 | 57 |
48 source->set_json_path("strings.js"); | 58 source->set_json_path("strings.js"); |
49 source->add_resource_path("gpu_internals.js", IDR_GPU_INTERNALS_JS); | 59 source->add_resource_path("gpu_internals.js", IDR_GPU_INTERNALS_JS); |
50 source->set_default_resource(IDR_GPU_INTERNALS_HTML); | 60 source->set_default_resource(IDR_GPU_INTERNALS_HTML); |
51 return source; | 61 return source; |
52 } | 62 } |
53 | 63 |
| 64 DictionaryValue* NewDescriptionValuePair(const std::string& desc, |
| 65 const std::string& value) { |
| 66 DictionaryValue* dict = new DictionaryValue(); |
| 67 dict->SetString("description", desc); |
| 68 dict->SetString("value", value); |
| 69 return dict; |
| 70 } |
| 71 |
| 72 DictionaryValue* NewDescriptionValuePair(const std::string& desc, |
| 73 Value* value) { |
| 74 DictionaryValue* dict = new DictionaryValue(); |
| 75 dict->SetString("description", desc); |
| 76 dict->Set("value", value); |
| 77 return dict; |
| 78 } |
| 79 |
| 80 Value* NewStatusValue(const char* name, const char* status) { |
| 81 DictionaryValue* value = new DictionaryValue(); |
| 82 value->SetString("name", name); |
| 83 value->SetString("status", status); |
| 84 return value; |
| 85 } |
| 86 |
| 87 // Output DxDiagNode tree as nested array of {description,value} pairs |
| 88 ListValue* DxDiagNodeToList(const content::DxDiagNode& node) { |
| 89 ListValue* list = new ListValue(); |
| 90 for (std::map<std::string, std::string>::const_iterator it = |
| 91 node.values.begin(); |
| 92 it != node.values.end(); |
| 93 ++it) { |
| 94 list->Append(NewDescriptionValuePair(it->first, it->second)); |
| 95 } |
| 96 |
| 97 for (std::map<std::string, content::DxDiagNode>::const_iterator it = |
| 98 node.children.begin(); |
| 99 it != node.children.end(); |
| 100 ++it) { |
| 101 ListValue* sublist = DxDiagNodeToList(it->second); |
| 102 list->Append(NewDescriptionValuePair(it->first, sublist)); |
| 103 } |
| 104 return list; |
| 105 } |
| 106 |
| 107 std::string GPUDeviceToString(const content::GPUInfo::GPUDevice& gpu) { |
| 108 std::string vendor = base::StringPrintf("0x%04x", gpu.vendor_id); |
| 109 if (!gpu.vendor_string.empty()) |
| 110 vendor += " [" + gpu.vendor_string + "]"; |
| 111 std::string device = base::StringPrintf("0x%04x", gpu.device_id); |
| 112 if (!gpu.device_string.empty()) |
| 113 device += " [" + gpu.device_string + "]"; |
| 114 return base::StringPrintf( |
| 115 "VENDOR = %s, DEVICE= %s", vendor.c_str(), device.c_str()); |
| 116 } |
| 117 |
| 118 DictionaryValue* GpuInfoAsDictionaryValue() { |
| 119 content::GPUInfo gpu_info = GpuDataManager::GetInstance()->GetGPUInfo(); |
| 120 ListValue* basic_info = new ListValue(); |
| 121 basic_info->Append(NewDescriptionValuePair( |
| 122 "Initialization time", |
| 123 base::Int64ToString(gpu_info.initialization_time.InMilliseconds()))); |
| 124 basic_info->Append(NewDescriptionValuePair( |
| 125 "GPU0", GPUDeviceToString(gpu_info.gpu))); |
| 126 for (size_t i = 0; i < gpu_info.secondary_gpus.size(); ++i) { |
| 127 basic_info->Append(NewDescriptionValuePair( |
| 128 base::StringPrintf("GPU%d", static_cast<int>(i + 1)), |
| 129 GPUDeviceToString(gpu_info.secondary_gpus[i]))); |
| 130 } |
| 131 basic_info->Append(NewDescriptionValuePair( |
| 132 "Optimus", Value::CreateBooleanValue(gpu_info.optimus))); |
| 133 basic_info->Append(NewDescriptionValuePair( |
| 134 "AMD switchable", Value::CreateBooleanValue(gpu_info.amd_switchable))); |
| 135 basic_info->Append(NewDescriptionValuePair("Driver vendor", |
| 136 gpu_info.driver_vendor)); |
| 137 basic_info->Append(NewDescriptionValuePair("Driver version", |
| 138 gpu_info.driver_version)); |
| 139 basic_info->Append(NewDescriptionValuePair("Driver date", |
| 140 gpu_info.driver_date)); |
| 141 basic_info->Append(NewDescriptionValuePair("Pixel shader version", |
| 142 gpu_info.pixel_shader_version)); |
| 143 basic_info->Append(NewDescriptionValuePair("Vertex shader version", |
| 144 gpu_info.vertex_shader_version)); |
| 145 basic_info->Append(NewDescriptionValuePair("GL version", |
| 146 gpu_info.gl_version)); |
| 147 basic_info->Append(NewDescriptionValuePair("GL_VENDOR", |
| 148 gpu_info.gl_vendor)); |
| 149 basic_info->Append(NewDescriptionValuePair("GL_RENDERER", |
| 150 gpu_info.gl_renderer)); |
| 151 basic_info->Append(NewDescriptionValuePair("GL_VERSION", |
| 152 gpu_info.gl_version_string)); |
| 153 basic_info->Append(NewDescriptionValuePair("GL_EXTENSIONS", |
| 154 gpu_info.gl_extensions)); |
| 155 |
| 156 DictionaryValue* info = new DictionaryValue(); |
| 157 info->Set("basic_info", basic_info); |
| 158 |
| 159 #if defined(OS_WIN) |
| 160 ListValue* perf_info = new ListValue(); |
| 161 perf_info->Append(NewDescriptionValuePair( |
| 162 "Graphics", |
| 163 base::StringPrintf("%.1f", gpu_info.performance_stats.graphics))); |
| 164 perf_info->Append(NewDescriptionValuePair( |
| 165 "Gaming", |
| 166 base::StringPrintf("%.1f", gpu_info.performance_stats.gaming))); |
| 167 perf_info->Append(NewDescriptionValuePair( |
| 168 "Overall", |
| 169 base::StringPrintf("%.1f", gpu_info.performance_stats.overall))); |
| 170 info->Set("performance_info", perf_info); |
| 171 |
| 172 Value* dx_info; |
| 173 if (gpu_info.dx_diagnostics.children.size()) |
| 174 dx_info = DxDiagNodeToList(gpu_info.dx_diagnostics); |
| 175 else |
| 176 dx_info = Value::CreateNullValue(); |
| 177 info->Set("diagnostics", dx_info); |
| 178 #endif |
| 179 |
| 180 return info; |
| 181 } |
| 182 |
| 183 // Determine if accelerated-2d-canvas is supported, which depends on whether |
| 184 // lose_context could happen and whether skia is the backend. |
| 185 bool SupportsAccelerated2dCanvas() { |
| 186 if (GpuDataManager::GetInstance()->GetGPUInfo().can_lose_context) |
| 187 return false; |
| 188 #if defined(USE_SKIA) |
| 189 return true; |
| 190 #else |
| 191 return false; |
| 192 #endif |
| 193 } |
| 194 |
| 195 Value* GetFeatureStatus() { |
| 196 const CommandLine& command_line = *CommandLine::ForCurrentProcess(); |
| 197 bool gpu_access_blocked = !GpuDataManager::GetInstance()->GpuAccessAllowed(); |
| 198 |
| 199 uint32 flags = GpuDataManager::GetInstance()->GetBlacklistedFeatures(); |
| 200 DictionaryValue* status = new DictionaryValue(); |
| 201 |
| 202 const GpuFeatureInfo kGpuFeatureInfo[] = { |
| 203 { |
| 204 "2d_canvas", |
| 205 flags & content::GPU_FEATURE_TYPE_ACCELERATED_2D_CANVAS, |
| 206 command_line.HasSwitch(switches::kDisableAccelerated2dCanvas) || |
| 207 !SupportsAccelerated2dCanvas(), |
| 208 "Accelerated 2D canvas is unavailable: either disabled at the command" |
| 209 " line or not supported by the current system.", |
| 210 true |
| 211 }, |
| 212 { |
| 213 "compositing", |
| 214 flags & content::GPU_FEATURE_TYPE_ACCELERATED_COMPOSITING, |
| 215 command_line.HasSwitch(switches::kDisableAcceleratedCompositing), |
| 216 "Accelerated compositing has been disabled, either via about:flags or" |
| 217 " command line. This adversely affects performance of all hardware" |
| 218 " accelerated features.", |
| 219 true |
| 220 }, |
| 221 { |
| 222 "3d_css", |
| 223 flags & content::GPU_FEATURE_TYPE_ACCELERATED_COMPOSITING, |
| 224 command_line.HasSwitch(switches::kDisableAcceleratedLayers), |
| 225 "Accelerated layers have been disabled at the command line.", |
| 226 false |
| 227 }, |
| 228 { |
| 229 "css_animation", |
| 230 flags & content::GPU_FEATURE_TYPE_ACCELERATED_COMPOSITING, |
| 231 command_line.HasSwitch(switches::kDisableThreadedAnimation) || |
| 232 command_line.HasSwitch(switches::kDisableAcceleratedCompositing), |
| 233 "Accelerated CSS animation has been disabled at the command line.", |
| 234 true |
| 235 }, |
| 236 { |
| 237 "webgl", |
| 238 flags & content::GPU_FEATURE_TYPE_WEBGL, |
| 239 #if defined(OS_ANDROID) |
| 240 !command_line.HasSwitch(switches::kEnableExperimentalWebGL), |
| 241 #else |
| 242 command_line.HasSwitch(switches::kDisableExperimentalWebGL), |
| 243 #endif |
| 244 "WebGL has been disabled, either via about:flags or command line.", |
| 245 false |
| 246 }, |
| 247 { |
| 248 "multisampling", |
| 249 flags & content::GPU_FEATURE_TYPE_MULTISAMPLING, |
| 250 command_line.HasSwitch(switches::kDisableGLMultisampling), |
| 251 "Multisampling has been disabled, either via about:flags or command" |
| 252 " line.", |
| 253 false |
| 254 }, |
| 255 { |
| 256 "flash_3d", |
| 257 flags & content::GPU_FEATURE_TYPE_FLASH3D, |
| 258 command_line.HasSwitch(switches::kDisableFlash3d), |
| 259 "Using 3d in flash has been disabled, either via about:flags or" |
| 260 " command line.", |
| 261 false |
| 262 }, |
| 263 { |
| 264 "flash_stage3d", |
| 265 flags & content::GPU_FEATURE_TYPE_FLASH_STAGE3D, |
| 266 command_line.HasSwitch(switches::kDisableFlashStage3d), |
| 267 "Using Stage3d in Flash has been disabled, either via about:flags or" |
| 268 " command line.", |
| 269 false |
| 270 }, |
| 271 { |
| 272 "texture_sharing", |
| 273 flags & content::GPU_FEATURE_TYPE_TEXTURE_SHARING, |
| 274 command_line.HasSwitch(switches::kDisableImageTransportSurface), |
| 275 "Sharing textures between processes has been disabled, either via" |
| 276 " about:flags or command line.", |
| 277 false |
| 278 }, |
| 279 { |
| 280 "video_decode", |
| 281 flags & content::GPU_FEATURE_TYPE_ACCELERATED_VIDEO_DECODE, |
| 282 command_line.HasSwitch(switches::kDisableAcceleratedVideoDecode), |
| 283 "Accelerated video decode has been disabled, either via about:flags" |
| 284 " or command line.", |
| 285 true |
| 286 } |
| 287 }; |
| 288 const size_t kNumFeatures = sizeof(kGpuFeatureInfo) / sizeof(GpuFeatureInfo); |
| 289 |
| 290 // Build the feature_status field. |
| 291 { |
| 292 ListValue* feature_status_list = new ListValue(); |
| 293 |
| 294 for (size_t i = 0; i < kNumFeatures; ++i) { |
| 295 std::string status; |
| 296 if (kGpuFeatureInfo[i].disabled) { |
| 297 status = "disabled"; |
| 298 if (kGpuFeatureInfo[i].name == "css_animation") { |
| 299 status += "_software_animated"; |
| 300 } else { |
| 301 if (kGpuFeatureInfo[i].fallback_to_software) |
| 302 status += "_software"; |
| 303 else |
| 304 status += "_off"; |
| 305 } |
| 306 } else if (GpuDataManager::GetInstance()->ShouldUseSoftwareRendering()) { |
| 307 status = "unavailable_software"; |
| 308 } else if (kGpuFeatureInfo[i].blocked || |
| 309 gpu_access_blocked) { |
| 310 status = "unavailable"; |
| 311 if (kGpuFeatureInfo[i].fallback_to_software) |
| 312 status += "_software"; |
| 313 else |
| 314 status += "_off"; |
| 315 } else { |
| 316 status = "enabled"; |
| 317 if (kGpuFeatureInfo[i].name == "webgl" && |
| 318 (command_line.HasSwitch(switches::kDisableAcceleratedCompositing) || |
| 319 (flags & content::GPU_FEATURE_TYPE_ACCELERATED_COMPOSITING))) |
| 320 status += "_readback"; |
| 321 bool has_thread = content::IsThreadedCompositingEnabled(); |
| 322 if (kGpuFeatureInfo[i].name == "compositing") { |
| 323 bool force_compositing = |
| 324 content::IsForceCompositingModeEnabled(); |
| 325 if (force_compositing) |
| 326 status += "_force"; |
| 327 if (has_thread) |
| 328 status += "_threaded"; |
| 329 } |
| 330 if (kGpuFeatureInfo[i].name == "css_animation") { |
| 331 if (has_thread) |
| 332 status = "accelerated_threaded"; |
| 333 else |
| 334 status = "accelerated"; |
| 335 } |
| 336 } |
| 337 feature_status_list->Append( |
| 338 NewStatusValue(kGpuFeatureInfo[i].name.c_str(), status.c_str())); |
| 339 } |
| 340 |
| 341 status->Set("featureStatus", feature_status_list); |
| 342 } |
| 343 |
| 344 // Build the problems list. |
| 345 { |
| 346 ListValue* problem_list = |
| 347 GpuDataManager::GetInstance()->GetBlacklistReasons(); |
| 348 |
| 349 if (gpu_access_blocked) { |
| 350 DictionaryValue* problem = new DictionaryValue(); |
| 351 problem->SetString("description", |
| 352 "GPU process was unable to boot. Access to GPU disallowed."); |
| 353 problem->Set("crBugs", new ListValue()); |
| 354 problem->Set("webkitBugs", new ListValue()); |
| 355 problem_list->Append(problem); |
| 356 } |
| 357 |
| 358 for (size_t i = 0; i < kNumFeatures; ++i) { |
| 359 if (kGpuFeatureInfo[i].disabled) { |
| 360 DictionaryValue* problem = new DictionaryValue(); |
| 361 problem->SetString( |
| 362 "description", kGpuFeatureInfo[i].disabled_description); |
| 363 problem->Set("crBugs", new ListValue()); |
| 364 problem->Set("webkitBugs", new ListValue()); |
| 365 problem_list->Append(problem); |
| 366 } |
| 367 } |
| 368 |
| 369 status->Set("problems", problem_list); |
| 370 } |
| 371 |
| 372 return status; |
| 373 } |
| 374 |
54 // This class receives javascript messages from the renderer. | 375 // This class receives javascript messages from the renderer. |
55 // Note that the WebUI infrastructure runs on the UI thread, therefore all of | 376 // Note that the WebUI infrastructure runs on the UI thread, therefore all of |
56 // this class's methods are expected to run on the UI thread. | 377 // this class's methods are expected to run on the UI thread. |
57 class GpuMessageHandler | 378 class GpuMessageHandler |
58 : public WebUIMessageHandler, | 379 : public WebUIMessageHandler, |
59 public base::SupportsWeakPtr<GpuMessageHandler>, | 380 public base::SupportsWeakPtr<GpuMessageHandler>, |
60 public content::GpuDataManagerObserver, | 381 public content::GpuDataManagerObserver, |
61 public CrashUploadList::Delegate { | 382 public CrashUploadList::Delegate { |
62 public: | 383 public: |
63 GpuMessageHandler(); | 384 GpuMessageHandler(); |
(...skipping 161 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
225 dict->SetString("operating_system", | 546 dict->SetString("operating_system", |
226 base::SysInfo::OperatingSystemName() + " " + | 547 base::SysInfo::OperatingSystemName() + " " + |
227 base::SysInfo::OperatingSystemVersion()); | 548 base::SysInfo::OperatingSystemVersion()); |
228 dict->SetString("angle_revision", base::UintToString(BUILD_REVISION)); | 549 dict->SetString("angle_revision", base::UintToString(BUILD_REVISION)); |
229 #if defined(USE_SKIA) | 550 #if defined(USE_SKIA) |
230 dict->SetString("graphics_backend", "Skia"); | 551 dict->SetString("graphics_backend", "Skia"); |
231 #else | 552 #else |
232 dict->SetString("graphics_backend", "Core Graphics"); | 553 dict->SetString("graphics_backend", "Core Graphics"); |
233 #endif | 554 #endif |
234 dict->SetString("blacklist_version", | 555 dict->SetString("blacklist_version", |
235 GpuBlacklist::GetInstance()->GetVersion()); | 556 GpuDataManager::GetInstance()->GetBlacklistVersion()); |
236 | 557 |
237 return dict; | 558 return dict; |
238 } | 559 } |
239 | 560 |
240 Value* GpuMessageHandler::OnRequestLogMessages(const ListValue*) { | 561 Value* GpuMessageHandler::OnRequestLogMessages(const ListValue*) { |
241 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 562 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
242 | 563 |
243 return GpuDataManager::GetInstance()->GetLogMessages(); | 564 return GpuDataManager::GetInstance()->GetLogMessages(); |
244 } | 565 } |
245 | 566 |
(...skipping 20 matching lines...) Expand all Loading... |
266 crash->SetString("time", | 587 crash->SetString("time", |
267 base::TimeFormatFriendlyDateAndTime(i->crash_time)); | 588 base::TimeFormatFriendlyDateAndTime(i->crash_time)); |
268 list_value->Append(crash); | 589 list_value->Append(crash); |
269 } | 590 } |
270 return list_value; | 591 return list_value; |
271 } | 592 } |
272 | 593 |
273 void GpuMessageHandler::OnGpuInfoUpdate() { | 594 void GpuMessageHandler::OnGpuInfoUpdate() { |
274 // Get GPU Info. | 595 // Get GPU Info. |
275 scoped_ptr<base::DictionaryValue> gpu_info_val( | 596 scoped_ptr<base::DictionaryValue> gpu_info_val( |
276 gpu_util::GpuInfoAsDictionaryValue()); | 597 GpuInfoAsDictionaryValue()); |
277 | 598 |
278 // Add in blacklisting features | 599 // Add in blacklisting features |
279 Value* feature_status = gpu_util::GetFeatureStatus(); | 600 Value* feature_status = GetFeatureStatus(); |
280 if (feature_status) | 601 if (feature_status) |
281 gpu_info_val->Set("featureStatus", feature_status); | 602 gpu_info_val->Set("featureStatus", feature_status); |
282 | 603 |
283 // Send GPU Info to javascript. | 604 // Send GPU Info to javascript. |
284 web_ui()->CallJavascriptFunction("browserBridge.onGpuInfoUpdate", | 605 web_ui()->CallJavascriptFunction("browserBridge.onGpuInfoUpdate", |
285 *(gpu_info_val.get())); | 606 *(gpu_info_val.get())); |
286 } | 607 } |
287 | 608 |
288 void GpuMessageHandler::OnCrashListAvailable() { | 609 void GpuMessageHandler::OnCrashListAvailable() { |
289 crash_list_available_ = true; | 610 crash_list_available_ = true; |
290 } | 611 } |
291 | 612 |
292 } // namespace | 613 } // namespace |
293 | 614 |
294 | 615 |
295 //////////////////////////////////////////////////////////////////////////////// | 616 //////////////////////////////////////////////////////////////////////////////// |
296 // | 617 // |
297 // GpuInternalsUI | 618 // GpuInternalsUI |
298 // | 619 // |
299 //////////////////////////////////////////////////////////////////////////////// | 620 //////////////////////////////////////////////////////////////////////////////// |
300 | 621 |
301 GpuInternalsUI::GpuInternalsUI(content::WebUI* web_ui) | 622 GpuInternalsUI::GpuInternalsUI(content::WebUI* web_ui) |
302 : WebUIController(web_ui) { | 623 : WebUIController(web_ui) { |
303 web_ui->AddMessageHandler(new GpuMessageHandler()); | 624 web_ui->AddMessageHandler(new GpuMessageHandler()); |
304 | 625 |
305 // Set up the chrome://gpu-internals/ source. | 626 // Set up the chrome://gpu-internals/ source. |
306 Profile* profile = Profile::FromWebUI(web_ui); | 627 Profile* profile = Profile::FromWebUI(web_ui); |
307 ChromeURLDataManager::AddDataSource(profile, CreateGpuHTMLSource()); | 628 ChromeURLDataManager::AddDataSource(profile, CreateGpuHTMLSource()); |
308 } | 629 } |
OLD | NEW |