1-- 2-- Copyright 2024 The Android Open Source Project 3-- 4-- Licensed under the Apache License, Version 2.0 (the "License"); 5-- you may not use this file except in compliance with the License. 6-- You may obtain a copy of the License at 7-- 8-- https://www.apache.org/licenses/LICENSE-2.0 9-- 10-- Unless required by applicable law or agreed to in writing, software 11-- distributed under the License is distributed on an "AS IS" BASIS, 12-- WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13-- See the License for the specific language governing permissions and 14-- limitations under the License. 15-- 16 17CREATE PERFETTO FUNCTION _extract_freezer_pid( 18 name STRING 19) 20RETURNS LONG AS 21SELECT 22 cast_int!(reverse(str_split(reverse(str_split($name, ' ', 1)), ':', 0))); 23 24-- Converts a pid to a upid using the timestamp of occurence of an event from 25-- |pid| to disambiguate duplicate pids. 26-- 27-- This is still best effort because it relies on having information about 28-- process start and end in the trace. In the edge case that we are missing this, 29-- it best effort returns the last upid. 30CREATE PERFETTO FUNCTION _pid_to_upid( 31 -- Pid to convert from. 32 pid LONG, 33 -- Timestamp of an event from the |pid|. 34 event_ts TIMESTAMP 35) 36-- Returns the converted upid. 37RETURNS LONG AS 38WITH 39 process_lifetime AS ( 40 SELECT 41 pid, 42 upid, 43 coalesce(start_ts, trace_start()) AS start_ts, 44 coalesce(end_ts, trace_end()) AS end_ts 45 FROM process 46 ) 47SELECT 48 upid 49FROM process_lifetime 50WHERE 51 pid = $pid AND $event_ts BETWEEN start_ts AND end_ts 52ORDER BY 53 upid DESC 54LIMIT 1; 55 56-- Translate unfreeze reason from INT to STRING. 57-- See: frameworks/proto_logging/stats/atoms.proto 58CREATE PERFETTO FUNCTION _translate_unfreeze_reason( 59 reason LONG 60) 61RETURNS STRING AS 62SELECT 63 CASE 64 WHEN $reason = 0 65 THEN 'none' 66 WHEN $reason = 1 67 THEN 'activity' 68 WHEN $reason = 2 69 THEN 'finish_receiver' 70 WHEN $reason = 3 71 THEN 'start_receiver' 72 WHEN $reason = 4 73 THEN 'bind_service' 74 WHEN $reason = 5 75 THEN 'unbind_service' 76 WHEN $reason = 6 77 THEN 'start_service' 78 WHEN $reason = 7 79 THEN 'get_provider' 80 WHEN $reason = 8 81 THEN 'remove_provider' 82 WHEN $reason = 9 83 THEN 'ui_visibility' 84 WHEN $reason = 10 85 THEN 'allowlist' 86 WHEN $reason = 11 87 THEN 'process_begin' 88 WHEN $reason = 12 89 THEN 'process_end' 90 WHEN $reason = 13 91 THEN 'trim_memory' 92 WHEN $reason = 15 93 THEN 'ping' 94 WHEN $reason = 16 95 THEN 'file_locks' 96 WHEN $reason = 17 97 THEN 'file_lock_check_failure' 98 WHEN $reason = 18 99 THEN 'binder_txns' 100 WHEN $reason = 19 101 THEN 'feature_flags' 102 WHEN $reason = 20 103 THEN 'short_fgs_timeout' 104 WHEN $reason = 21 105 THEN 'system_init' 106 WHEN $reason = 22 107 THEN 'backup' 108 WHEN $reason = 23 109 THEN 'shell' 110 WHEN $reason = 24 111 THEN 'remove_task' 112 WHEN $reason = 25 113 THEN 'uid_idle' 114 WHEN $reason = 26 115 THEN 'stop_service' 116 WHEN $reason = 27 117 THEN 'executing_service' 118 WHEN $reason = 28 119 THEN 'restriction_change' 120 WHEN $reason = 29 121 THEN 'component_disabled' 122 ELSE NULL 123 END; 124 125-- All frozen processes and their frozen duration. 126CREATE PERFETTO TABLE android_freezer_events ( 127 -- Upid of frozen process 128 upid JOINID(process.id), 129 -- Pid of frozen process 130 pid LONG, 131 -- Timestamp process was frozen. 132 ts TIMESTAMP, 133 -- Duration process was frozen for. 134 dur DURATION, 135 -- Unfreeze reason Integer. 136 unfreeze_reason_int LONG, 137 -- Unfreeze reason String. 138 unfreeze_reason_str STRING 139) AS 140WITH 141 freeze AS ( 142 SELECT 143 ts, 144 _extract_freezer_pid(name) AS pid, 145 _pid_to_upid(_extract_freezer_pid(name), ts) AS upid, 146 'freeze' AS type, 147 NULL AS unfreeze_reason 148 FROM slice 149 WHERE 150 name GLOB 'Freeze *:*' 151 ), 152 unfreeze AS ( 153 SELECT 154 ts, 155 _extract_freezer_pid(name) AS pid, 156 _pid_to_upid(_extract_freezer_pid(name), ts) AS upid, 157 'unfreeze' AS type, 158 str_split(name, ' ', 2) AS unfreeze_reason 159 FROM slice 160 WHERE 161 name GLOB 'Unfreeze *:*' 162 ), 163 merged AS ( 164 SELECT 165 * 166 FROM freeze 167 UNION ALL 168 SELECT 169 * 170 FROM unfreeze 171 ), 172 starts AS ( 173 SELECT 174 type, 175 upid, 176 pid, 177 ts, 178 coalesce(lead(ts) OVER (PARTITION BY upid ORDER BY ts), trace_end()) - ts AS dur, 179 cast_int!(lead(unfreeze_reason) OVER (PARTITION BY upid ORDER BY ts)) AS unfreeze_reason 180 FROM merged 181 ) 182SELECT 183 upid, 184 pid, 185 ts, 186 dur, 187 unfreeze_reason AS unfreeze_reason_int, 188 _translate_unfreeze_reason(unfreeze_reason) AS unfreeze_reason_str 189FROM starts 190WHERE 191 starts.type = 'freeze' AND upid IS NOT NULL; 192