| OLD | NEW |
| 1 # Copyright 2013 The Chromium Authors. All rights reserved. | 1 # Copyright 2013 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 import random | 5 import random |
| 6 import unittest | 6 import unittest |
| 7 | 7 |
| 8 from metrics.rendering_stats import UI_COMP_NAME, BEGIN_COMP_NAME, END_COMP_NAME | 8 from metrics.rendering_stats import UI_COMP_NAME, BEGIN_COMP_NAME, END_COMP_NAME |
| 9 from metrics.rendering_stats import GetScrollInputLatencyEvents | 9 from metrics.rendering_stats import GetScrollInputLatencyEvents |
| 10 from metrics.rendering_stats import ComputeMouseWheelScrollLatency | 10 from metrics.rendering_stats import ComputeMouseWheelScrollLatency |
| 11 from metrics.rendering_stats import ComputeTouchScrollLatency | 11 from metrics.rendering_stats import ComputeTouchScrollLatency |
| 12 from metrics.rendering_stats import HasRenderingStats |
| 12 from metrics.rendering_stats import RenderingStats | 13 from metrics.rendering_stats import RenderingStats |
| 13 import telemetry.core.timeline.bounds as timeline_bounds | 14 import telemetry.core.timeline.bounds as timeline_bounds |
| 14 from telemetry.core.timeline import model | 15 from telemetry.core.timeline import model |
| 15 import telemetry.core.timeline.async_slice as tracing_async_slice | 16 import telemetry.core.timeline.async_slice as tracing_async_slice |
| 16 | 17 |
| 17 | 18 |
| 18 class MockTimer(object): | 19 class MockTimer(object): |
| 19 """A mock timer class which can generate random durations. | 20 """A mock timer class which can generate random durations. |
| 20 | 21 |
| 21 An instance of this class is used as a global timer to generate random | 22 An instance of this class is used as a global timer to generate random |
| (...skipping 170 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 192 ref_latency_stats.touch_scroll_events.append(async_sub_slice) | 193 ref_latency_stats.touch_scroll_events.append(async_sub_slice) |
| 193 ref_latency_stats.touch_scroll_latency.append( | 194 ref_latency_stats.touch_scroll_latency.append( |
| 194 (data[END_COMP_NAME]['time'] - data[UI_COMP_NAME]['time']) / 1000.0) | 195 (data[END_COMP_NAME]['time'] - data[UI_COMP_NAME]['time']) / 1000.0) |
| 195 | 196 |
| 196 if input_type == 'TouchMove': | 197 if input_type == 'TouchMove': |
| 197 ref_latency_stats.js_touch_scroll_events.append(async_sub_slice) | 198 ref_latency_stats.js_touch_scroll_events.append(async_sub_slice) |
| 198 ref_latency_stats.js_touch_scroll_latency.append( | 199 ref_latency_stats.js_touch_scroll_latency.append( |
| 199 (data[END_COMP_NAME]['time'] - data[UI_COMP_NAME]['time']) / 1000.0) | 200 (data[END_COMP_NAME]['time'] - data[UI_COMP_NAME]['time']) / 1000.0) |
| 200 | 201 |
| 201 class RenderingStatsUnitTest(unittest.TestCase): | 202 class RenderingStatsUnitTest(unittest.TestCase): |
| 203 def testHasRenderingStats(self): |
| 204 timeline = model.TimelineModel() |
| 205 timer = MockTimer() |
| 206 |
| 207 # A process without rendering stats |
| 208 process_without_stats = timeline.GetOrCreateProcess(pid = 1) |
| 209 thread_without_stats = process_without_stats.GetOrCreateThread(tid = 11) |
| 210 process_without_stats.FinalizeImport() |
| 211 self.assertFalse(HasRenderingStats(thread_without_stats)) |
| 212 |
| 213 # A process with rendering stats, but no frames in them |
| 214 process_without_frames = timeline.GetOrCreateProcess(pid = 2) |
| 215 thread_without_frames = process_without_frames.GetOrCreateThread(tid = 21) |
| 216 AddMainThreadRenderingStats(timer, thread_without_frames, True, None) |
| 217 process_without_frames.FinalizeImport() |
| 218 self.assertFalse(HasRenderingStats(thread_without_frames)) |
| 219 |
| 220 # A process with rendering stats and frames in them |
| 221 process_with_frames = timeline.GetOrCreateProcess(pid = 3) |
| 222 thread_with_frames = process_with_frames.GetOrCreateThread(tid = 31) |
| 223 AddImplThreadRenderingStats(timer, thread_with_frames, True, None) |
| 224 process_with_frames.FinalizeImport() |
| 225 self.assertTrue(HasRenderingStats(thread_with_frames)) |
| 226 |
| 202 def testFromTimeline(self): | 227 def testFromTimeline(self): |
| 203 timeline = model.TimelineModel() | 228 timeline = model.TimelineModel() |
| 204 | 229 |
| 205 # Create a browser process and a renderer process, and a main thread and | 230 # Create a browser process and a renderer process, and a main thread and |
| 206 # impl thread for each. | 231 # impl thread for each. |
| 207 browser = timeline.GetOrCreateProcess(pid = 1) | 232 browser = timeline.GetOrCreateProcess(pid = 1) |
| 208 browser_main = browser.GetOrCreateThread(tid = 11) | 233 browser_main = browser.GetOrCreateThread(tid = 11) |
| 209 browser_compositor = browser.GetOrCreateThread(tid = 12) | 234 browser_compositor = browser.GetOrCreateThread(tid = 12) |
| 210 renderer = timeline.GetOrCreateProcess(pid = 2) | 235 renderer = timeline.GetOrCreateProcess(pid = 2) |
| 211 renderer_main = renderer.GetOrCreateThread(tid = 21) | 236 renderer_main = renderer.GetOrCreateThread(tid = 21) |
| 212 renderer_compositor = renderer.GetOrCreateThread(tid = 22) | 237 renderer_compositor = renderer.GetOrCreateThread(tid = 22) |
| 213 | 238 |
| 214 timer = MockTimer() | 239 timer = MockTimer() |
| 215 ref_stats = ReferenceRenderingStats() | 240 ref_stats = ReferenceRenderingStats() |
| 216 | 241 |
| 217 # Create 10 main and impl rendering stats events for Action A. | 242 # Create 10 main and impl rendering stats events for Action A. |
| 218 timer.Advance() | 243 timer.Advance() |
| 219 renderer_main.BeginSlice('webkit.console', 'ActionA', timer.Get(), '') | 244 renderer_main.BeginSlice('webkit.console', 'ActionA', timer.Get(), '') |
| 220 ref_stats.AppendNewRange() | 245 ref_stats.AppendNewRange() |
| 221 for i in xrange(0, 10): | 246 for i in xrange(0, 10): |
| 222 first = (i == 0) | 247 first = (i == 0) |
| 223 AddMainThreadRenderingStats(timer, renderer_main, first, ref_stats) | 248 AddMainThreadRenderingStats(timer, renderer_main, first, None) |
| 224 AddImplThreadRenderingStats(timer, renderer_compositor, first, ref_stats) | 249 AddImplThreadRenderingStats(timer, renderer_compositor, first, None) |
| 225 AddMainThreadRenderingStats(timer, browser_main, first, None) | 250 AddMainThreadRenderingStats(timer, browser_main, first, ref_stats) |
| 226 AddImplThreadRenderingStats(timer, browser_compositor, first, None) | 251 AddImplThreadRenderingStats(timer, browser_compositor, first, ref_stats) |
| 227 renderer_main.EndSlice(timer.Get()) | 252 renderer_main.EndSlice(timer.Get()) |
| 228 | 253 |
| 229 # Create 5 main and impl rendering stats events not within any action. | 254 # Create 5 main and impl rendering stats events not within any action. |
| 230 for i in xrange(0, 5): | 255 for i in xrange(0, 5): |
| 231 first = (i == 0) | 256 first = (i == 0) |
| 232 AddMainThreadRenderingStats(timer, renderer_main, first, None) | 257 AddMainThreadRenderingStats(timer, renderer_main, first, None) |
| 233 AddImplThreadRenderingStats(timer, renderer_compositor, first, None) | 258 AddImplThreadRenderingStats(timer, renderer_compositor, first, None) |
| 234 AddMainThreadRenderingStats(timer, browser_main, first, None) | 259 AddMainThreadRenderingStats(timer, browser_main, first, None) |
| 235 AddImplThreadRenderingStats(timer, browser_compositor, first, None) | 260 AddImplThreadRenderingStats(timer, browser_compositor, first, None) |
| 236 | 261 |
| 237 # Create 10 main and impl rendering stats events for Action B. | 262 # Create 10 main and impl rendering stats events for Action B. |
| 238 timer.Advance() | 263 timer.Advance() |
| 239 renderer_main.BeginSlice('webkit.console', 'ActionB', timer.Get(), '') | 264 renderer_main.BeginSlice('webkit.console', 'ActionB', timer.Get(), '') |
| 240 ref_stats.AppendNewRange() | 265 ref_stats.AppendNewRange() |
| 241 for i in xrange(0, 10): | 266 for i in xrange(0, 10): |
| 242 first = (i == 0) | 267 first = (i == 0) |
| 243 AddMainThreadRenderingStats(timer, renderer_main, first, ref_stats) | 268 AddMainThreadRenderingStats(timer, renderer_main, first, None) |
| 244 AddImplThreadRenderingStats(timer, renderer_compositor, first, ref_stats) | 269 AddImplThreadRenderingStats(timer, renderer_compositor, first, None) |
| 245 AddMainThreadRenderingStats(timer, browser_main, first, None) | 270 AddMainThreadRenderingStats(timer, browser_main, first, ref_stats) |
| 246 AddImplThreadRenderingStats(timer, browser_compositor, first, None) | 271 AddImplThreadRenderingStats(timer, browser_compositor, first, ref_stats) |
| 247 renderer_main.EndSlice(timer.Get()) | 272 renderer_main.EndSlice(timer.Get()) |
| 248 | 273 |
| 249 # Create 10 main and impl rendering stats events for Action A. | 274 # Create 10 main and impl rendering stats events for Action A. |
| 250 timer.Advance() | 275 timer.Advance() |
| 251 renderer_main.BeginSlice('webkit.console', 'ActionA', timer.Get(), '') | 276 renderer_main.BeginSlice('webkit.console', 'ActionA', timer.Get(), '') |
| 252 ref_stats.AppendNewRange() | 277 ref_stats.AppendNewRange() |
| 253 for i in xrange(0, 10): | 278 for i in xrange(0, 10): |
| 254 first = (i == 0) | 279 first = (i == 0) |
| 255 AddMainThreadRenderingStats(timer, renderer_main, first, ref_stats) | 280 AddMainThreadRenderingStats(timer, renderer_main, first, None) |
| 256 AddImplThreadRenderingStats(timer, renderer_compositor, first, ref_stats) | 281 AddImplThreadRenderingStats(timer, renderer_compositor, first, None) |
| 257 AddMainThreadRenderingStats(timer, browser_main, first, None) | 282 AddMainThreadRenderingStats(timer, browser_main, first, ref_stats) |
| 258 AddImplThreadRenderingStats(timer, browser_compositor, first, None) | 283 AddImplThreadRenderingStats(timer, browser_compositor, first, ref_stats) |
| 259 renderer_main.EndSlice(timer.Get()) | 284 renderer_main.EndSlice(timer.Get()) |
| 260 | 285 |
| 261 renderer_main.FinalizeImport() | 286 browser.FinalizeImport() |
| 262 renderer_compositor.FinalizeImport() | 287 renderer.FinalizeImport() |
| 263 | 288 |
| 264 timeline_markers = timeline.FindTimelineMarkers( | 289 timeline_markers = timeline.FindTimelineMarkers( |
| 265 ['ActionA', 'ActionB', 'ActionA']) | 290 ['ActionA', 'ActionB', 'ActionA']) |
| 266 timeline_ranges = [ timeline_bounds.Bounds.CreateFromEvent(marker) | 291 timeline_ranges = [ timeline_bounds.Bounds.CreateFromEvent(marker) |
| 267 for marker in timeline_markers ] | 292 for marker in timeline_markers ] |
| 268 stats = RenderingStats(renderer, browser, timeline_ranges) | 293 stats = RenderingStats(renderer, browser, timeline_ranges) |
| 269 | 294 |
| 295 # Check if we are using the browser compositor's stats |
| 296 self.assertEquals(stats.top_level_process, browser) |
| 297 |
| 270 # Compare rendering stats to reference. | 298 # Compare rendering stats to reference. |
| 271 self.assertEquals(stats.frame_timestamps, ref_stats.frame_timestamps) | 299 self.assertEquals(stats.frame_timestamps, ref_stats.frame_timestamps) |
| 272 self.assertEquals(stats.frame_times, ref_stats.frame_times) | 300 self.assertEquals(stats.frame_times, ref_stats.frame_times) |
| 273 self.assertEquals(stats.rasterize_times, ref_stats.rasterize_times) | 301 self.assertEquals(stats.rasterize_times, ref_stats.rasterize_times) |
| 274 self.assertEquals(stats.rasterized_pixel_counts, | 302 self.assertEquals(stats.rasterized_pixel_counts, |
| 275 ref_stats.rasterized_pixel_counts) | 303 ref_stats.rasterized_pixel_counts) |
| 276 self.assertEquals(stats.paint_times, ref_stats.paint_times) | 304 self.assertEquals(stats.paint_times, ref_stats.paint_times) |
| 277 self.assertEquals(stats.painted_pixel_counts, | 305 self.assertEquals(stats.painted_pixel_counts, |
| 278 ref_stats.painted_pixel_counts) | 306 ref_stats.painted_pixel_counts) |
| 279 self.assertEquals(stats.record_times, ref_stats.record_times) | 307 self.assertEquals(stats.record_times, ref_stats.record_times) |
| (...skipping 50 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 330 renderer_main.BeginSlice('webkit.console', 'ActionA', timer.Get(), '') | 358 renderer_main.BeginSlice('webkit.console', 'ActionA', timer.Get(), '') |
| 331 for _ in xrange(0, 10): | 359 for _ in xrange(0, 10): |
| 332 AddInputLatencyStats(timer, 'MouseWheel', browser_main, | 360 AddInputLatencyStats(timer, 'MouseWheel', browser_main, |
| 333 renderer_main, ref_latency_stats) | 361 renderer_main, ref_latency_stats) |
| 334 AddInputLatencyStats(timer, 'GestureScrollUpdate', browser_main, | 362 AddInputLatencyStats(timer, 'GestureScrollUpdate', browser_main, |
| 335 renderer_main, ref_latency_stats) | 363 renderer_main, ref_latency_stats) |
| 336 AddInputLatencyStats(timer, 'TouchMove', browser_main, | 364 AddInputLatencyStats(timer, 'TouchMove', browser_main, |
| 337 renderer_main, ref_latency_stats) | 365 renderer_main, ref_latency_stats) |
| 338 renderer_main.EndSlice(timer.Get()) | 366 renderer_main.EndSlice(timer.Get()) |
| 339 | 367 |
| 340 browser_main.FinalizeImport() | 368 browser.FinalizeImport() |
| 341 renderer_main.FinalizeImport() | 369 renderer.FinalizeImport() |
| 342 | 370 |
| 343 mouse_wheel_scroll_events = [] | 371 mouse_wheel_scroll_events = [] |
| 344 touch_scroll_events = [] | 372 touch_scroll_events = [] |
| 345 js_touch_scroll_events = [] | 373 js_touch_scroll_events = [] |
| 346 | 374 |
| 347 timeline_markers = timeline.FindTimelineMarkers( | 375 timeline_markers = timeline.FindTimelineMarkers( |
| 348 ['ActionA', 'ActionB', 'ActionA']) | 376 ['ActionA', 'ActionB', 'ActionA']) |
| 349 for timeline_range in [ timeline_bounds.Bounds.CreateFromEvent(marker) | 377 for timeline_range in [ timeline_bounds.Bounds.CreateFromEvent(marker) |
| 350 for marker in timeline_markers ]: | 378 for marker in timeline_markers ]: |
| 351 if timeline_range.is_empty: | 379 if timeline_range.is_empty: |
| (...skipping 13 matching lines...) Expand all Loading... |
| 365 self.assertEquals(touch_scroll_events, | 393 self.assertEquals(touch_scroll_events, |
| 366 ref_latency_stats.touch_scroll_events) | 394 ref_latency_stats.touch_scroll_events) |
| 367 self.assertEquals(js_touch_scroll_events, | 395 self.assertEquals(js_touch_scroll_events, |
| 368 ref_latency_stats.js_touch_scroll_events) | 396 ref_latency_stats.js_touch_scroll_events) |
| 369 self.assertEquals(ComputeMouseWheelScrollLatency(mouse_wheel_scroll_events), | 397 self.assertEquals(ComputeMouseWheelScrollLatency(mouse_wheel_scroll_events), |
| 370 ref_latency_stats.mouse_wheel_scroll_latency) | 398 ref_latency_stats.mouse_wheel_scroll_latency) |
| 371 self.assertEquals(ComputeTouchScrollLatency(touch_scroll_events), | 399 self.assertEquals(ComputeTouchScrollLatency(touch_scroll_events), |
| 372 ref_latency_stats.touch_scroll_latency) | 400 ref_latency_stats.touch_scroll_latency) |
| 373 self.assertEquals(ComputeTouchScrollLatency(js_touch_scroll_events), | 401 self.assertEquals(ComputeTouchScrollLatency(js_touch_scroll_events), |
| 374 ref_latency_stats.js_touch_scroll_latency) | 402 ref_latency_stats.js_touch_scroll_latency) |
| OLD | NEW |