1# Copyright 2014 The Chromium Authors. All rights reserved. 2# Use of this source code is governed by a BSD-style license that can be 3# found in the LICENSE file. 4 5import logging 6 7from telemetry.timeline import bounds 8from telemetry.value import scalar 9from telemetry.web_perf import timeline_interaction_record as tir_module 10from telemetry.web_perf.metrics import timeline_based_metric 11from telemetry.web_perf.metrics import v8_stats as v8_stats_module 12 13 14class FastMetric(timeline_based_metric.TimelineBasedMetric): 15 def __init__(self): 16 super(FastMetric, self).__init__() 17 18 def AddResults(self, model, renderer_thread, interaction_records, results): 19 """Add 11 results: duration, cpu_time, and idle_time, 20 incremental_marking, incremental_marking_outside_idle, 21 scavenger, scavenger_outside_idle, 22 mark_compactor, mark_compactor_outside_idle, 23 total_garbage_collection, 24 total_garbage_collection_outside_idle 25 26 duration is the total wall time for |interaction_records|. 27 cpu_time is the renderer thread time that intersects |interaction_records|. 28 idle time is wall time for |interaction_records| for which renderer slices 29 do not overlap. Note that unscheduled renderer thread time is not 30 counted. Idle time is time for which there was nothing to do. 31 incremental_marking is the total thread duration spent in incremental 32 marking steps. 33 incremental_marking_outside_idle is the thread duration spent in incremental 34 marking steps outside of idle notifications. 35 scavenger is the total thread duration spent in scavenges. 36 scavenger_outside_idle is the thread duration spent in scavenges outside of 37 idle notifications. 38 mark_compactor is the total thread duration spent in mark-sweep-compactor. 39 mark_compactor_outside_idle is the thread duration spent in 40 mark-sweep-compactor outside of idle notifications. 41 total_garbage_collection is the total thread duration spend in garbage 42 collection 43 total_garbage_collection_outside_idle is the total thread duration spend in 44 garbage collection outside of idle notification. 45 46 Args: 47 model: a TimelineModule instance 48 renderer_thread: a telemetry.timeline.thread.Thread() instance 49 interaction_records: an iterable of TimelineInteractionRecord instances 50 results: an instance of page.PageTestResults 51 """ 52 self.VerifyNonOverlappedRecords(interaction_records) 53 54 duration = sum(r.end - r.start for r in interaction_records) 55 results.AddValue(scalar.ScalarValue( 56 results.current_page, 'fast-duration', 'ms', duration)) 57 58 try: 59 cpu_time = sum( 60 r.GetOverlappedThreadTimeForSlice(s) 61 for r in interaction_records 62 for s in renderer_thread.toplevel_slices) 63 except tir_module.NoThreadTimeDataException: 64 logging.warning( 65 'Main thread cpu_time cannot be computed for records %s since ' 66 'trace does not contain thread time data.', 67 repr(interaction_records)) 68 else: 69 results.AddValue(scalar.ScalarValue( 70 results.current_page, 'fast-cpu_time', 'ms', cpu_time)) 71 72 idle_time = duration - sum( 73 bounds.Bounds.GetOverlap(r.start, r.end, s.start, s.end) 74 for r in interaction_records 75 for s in renderer_thread.toplevel_slices) 76 results.AddValue(scalar.ScalarValue( 77 results.current_page, 'fast-idle_time', 'ms', idle_time)) 78 79 v8_stats = v8_stats_module.V8Stats(renderer_thread, interaction_records) 80 81 for event_stats in v8_stats.all_event_stats: 82 results.AddValue(scalar.ScalarValue( 83 results.current_page, 'fast-' + event_stats.result_name, 'ms', 84 event_stats.thread_duration, 85 event_stats.result_description)) 86 results.AddValue(scalar.ScalarValue( 87 results.current_page, 88 'fast-' + event_stats.result_name + '_outside_idle', 'ms', 89 event_stats.thread_duration_outside_idle, 90 event_stats.result_description + 'outside of idle notifications')) 91 92 results.AddValue(scalar.ScalarValue( 93 results.current_page, 'fast-total_garbage_collection', 'ms', 94 v8_stats.total_gc_thread_duration, 95 'Total thread duration of all garbage collection events')) 96 97 results.AddValue(scalar.ScalarValue( 98 results.current_page, 'fast-total_garbage_collection_outside_idle', 99 'ms', v8_stats.total_gc_thread_duration_outside_idle, 100 'Total thread duration of all garbage collection events outside of idle' 101 'notifications')) 102