1 /*
2 * Copyright (c) Huawei Technologies Co., Ltd. 2023. All rights reserved.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16 #include "bytrace_event_parser.h"
17 #include "app_start_filter.h"
18 #include "binder_filter.h"
19 #include "cpu_filter.h"
20 #include "filter_filter.h"
21 #include "irq_filter.h"
22 #include "measure_filter.h"
23 #include "parting_string.h"
24 #include "process_filter.h"
25 #include "slice_filter.h"
26 #include "stat_filter.h"
27 #include "string_to_numerical.h"
28 #include "thread_state_flag.h"
29 #include "ts_common.h"
30 namespace SysTuning {
31 namespace TraceStreamer {
32 namespace {
GetFunctionName(const std::string_view & text,const std::string_view & delimiter)33 std::string GetFunctionName(const std::string_view &text, const std::string_view &delimiter)
34 {
35 std::string str("");
36 if (delimiter.empty()) {
37 return str;
38 }
39
40 std::size_t foundIndex = text.find(delimiter);
41 if (foundIndex != std::string::npos) {
42 std::size_t funIndex = foundIndex + delimiter.size();
43 str = std::string(text.substr(funIndex, text.size() - funIndex));
44 }
45 return str;
46 }
47 } // namespace
48
BytraceEventParser(TraceDataCache * dataCache,const TraceStreamerFilters * filter)49 BytraceEventParser::BytraceEventParser(TraceDataCache *dataCache, const TraceStreamerFilters *filter)
50 : EventParserBase(dataCache, filter), printEventParser_(traceDataCache_, streamFilters_)
51 {
52 printEventParser_.SetTraceType(TRACE_FILETYPE_BY_TRACE);
53 eventToFunctionMap_ = {
54 {config_.eventNameMap_.at(TRACE_EVENT_TASK_RENAME),
55 bind(&BytraceEventParser::TaskRenameEvent, this, std::placeholders::_1, std::placeholders::_2)},
56 {config_.eventNameMap_.at(TRACE_EVENT_TASK_NEWTASK),
57 bind(&BytraceEventParser::TaskNewtaskEvent, this, std::placeholders::_1, std::placeholders::_2)},
58 {config_.eventNameMap_.at(TRACE_EVENT_SCHED_SWITCH),
59 bind(&BytraceEventParser::SchedSwitchEvent, this, std::placeholders::_1, std::placeholders::_2)},
60 {config_.eventNameMap_.at(TRACE_EVENT_SCHED_BLOCKED_REASON),
61 bind(&BytraceEventParser::BlockedReason, this, std::placeholders::_1, std::placeholders::_2)},
62 {config_.eventNameMap_.at(TRACE_EVENT_SCHED_WAKEUP),
63 bind(&BytraceEventParser::SchedWakeupEvent, this, std::placeholders::_1, std::placeholders::_2)},
64 {config_.eventNameMap_.at(TRACE_EVENT_SCHED_WAKING),
65 bind(&BytraceEventParser::SchedWakingEvent, this, std::placeholders::_1, std::placeholders::_2)},
66 {config_.eventNameMap_.at(TRACE_EVENT_SCHED_WAKEUP_NEW),
67 bind(&BytraceEventParser::SchedWakeupEvent, this, std::placeholders::_1, std::placeholders::_2)},
68 {config_.eventNameMap_.at(TRACE_EVENT_PROCESS_EXIT),
69 bind(&BytraceEventParser::ProcessExitEvent, this, std::placeholders::_1, std::placeholders::_2)},
70 {config_.eventNameMap_.at(TRACE_EVENT_IPI_ENTRY),
71 bind(&BytraceEventParser::IpiEntryEvent, this, std::placeholders::_1, std::placeholders::_2)},
72 {config_.eventNameMap_.at(TRACE_EVENT_IPI_EXIT),
73 bind(&BytraceEventParser::IpiExitEvent, this, std::placeholders::_1, std::placeholders::_2)},
74 };
75 InterruptEventInitialization();
76 ClockEventInitialization();
77 CpuEventInitialization();
78 RegulatorEventInitialization();
79 BinderEventInitialization();
80 StackEventsInitialization();
81 eventList_.reserve(maxBuffSize_);
82 }
83
InterruptEventInitialization()84 void BytraceEventParser::InterruptEventInitialization()
85 {
86 // Interrupt and soft interrupt event initialization
87 eventToFunctionMap_.emplace(
88 config_.eventNameMap_.at(TRACE_EVENT_IRQ_HANDLER_ENTRY),
89 bind(&BytraceEventParser::IrqHandlerEntryEvent, this, std::placeholders::_1, std::placeholders::_2));
90 eventToFunctionMap_.emplace(
91 config_.eventNameMap_.at(TRACE_EVENT_IRQ_HANDLER_EXIT),
92 bind(&BytraceEventParser::IrqHandlerExitEvent, this, std::placeholders::_1, std::placeholders::_2));
93 eventToFunctionMap_.emplace(
94 config_.eventNameMap_.at(TRACE_EVENT_SOFTIRQ_RAISE),
95 bind(&BytraceEventParser::SoftIrqRaiseEvent, this, std::placeholders::_1, std::placeholders::_2));
96 eventToFunctionMap_.emplace(
97 config_.eventNameMap_.at(TRACE_EVENT_SOFTIRQ_ENTRY),
98 bind(&BytraceEventParser::SoftIrqEntryEvent, this, std::placeholders::_1, std::placeholders::_2));
99 eventToFunctionMap_.emplace(
100 config_.eventNameMap_.at(TRACE_EVENT_SOFTIRQ_EXIT),
101 bind(&BytraceEventParser::SoftIrqExitEvent, this, std::placeholders::_1, std::placeholders::_2));
102 eventToFunctionMap_.emplace(
103 config_.eventNameMap_.at(TRACE_EVENT_DMA_FENCE_INIT),
104 bind(&BytraceEventParser::DmaFenceEvent, this, std::placeholders::_1, std::placeholders::_2));
105 eventToFunctionMap_.emplace(
106 config_.eventNameMap_.at(TRACE_EVENT_DMA_FENCE_DESTROY),
107 bind(&BytraceEventParser::DmaFenceEvent, this, std::placeholders::_1, std::placeholders::_2));
108 eventToFunctionMap_.emplace(
109 config_.eventNameMap_.at(TRACE_EVENT_DMA_FENCE_ENABLE),
110 bind(&BytraceEventParser::DmaFenceEvent, this, std::placeholders::_1, std::placeholders::_2));
111 eventToFunctionMap_.emplace(
112 config_.eventNameMap_.at(TRACE_EVENT_DMA_FENCE_SIGNALED),
113 bind(&BytraceEventParser::DmaFenceEvent, this, std::placeholders::_1, std::placeholders::_2));
114 }
115
ClockEventInitialization()116 void BytraceEventParser::ClockEventInitialization()
117 {
118 // Clock event initialization
119 eventToFunctionMap_.emplace(
120 config_.eventNameMap_.at(TRACE_EVENT_CLOCK_SET_RATE),
121 bind(&BytraceEventParser::SetRateEvent, this, std::placeholders::_1, std::placeholders::_2));
122 eventToFunctionMap_.emplace(
123 config_.eventNameMap_.at(TRACE_EVENT_CLOCK_ENABLE),
124 bind(&BytraceEventParser::ClockEnableEvent, this, std::placeholders::_1, std::placeholders::_2));
125 eventToFunctionMap_.emplace(
126 config_.eventNameMap_.at(TRACE_EVENT_CLOCK_DISABLE),
127 bind(&BytraceEventParser::ClockDisableEvent, this, std::placeholders::_1, std::placeholders::_2));
128 }
129
CpuEventInitialization()130 void BytraceEventParser::CpuEventInitialization()
131 {
132 eventToFunctionMap_.emplace(
133 config_.eventNameMap_.at(TRACE_EVENT_CPU_IDLE),
134 bind(&BytraceEventParser::CpuIdleEvent, this, std::placeholders::_1, std::placeholders::_2));
135 eventToFunctionMap_.emplace(
136 config_.eventNameMap_.at(TRACE_EVENT_CPU_FREQUENCY),
137 bind(&BytraceEventParser::CpuFrequencyEvent, this, std::placeholders::_1, std::placeholders::_2));
138 eventToFunctionMap_.emplace(
139 config_.eventNameMap_.at(TRACE_EVENT_CPU_FREQUENCY_LIMITS),
140 bind(&BytraceEventParser::CpuFrequencyLimitsEvent, this, std::placeholders::_1, std::placeholders::_2));
141 }
142
RegulatorEventInitialization()143 void BytraceEventParser::RegulatorEventInitialization()
144 {
145 // Initialize regulator related events
146 eventToFunctionMap_.emplace(
147 config_.eventNameMap_.at(TRACE_EVENT_REGULATOR_SET_VOLTAGE),
148 bind(&BytraceEventParser::RegulatorSetVoltageEvent, this, std::placeholders::_1, std::placeholders::_2));
149 eventToFunctionMap_.emplace(config_.eventNameMap_.at(TRACE_EVENT_REGULATOR_SET_VOLTAGE_COMPLETE),
150 bind(&BytraceEventParser::RegulatorSetVoltageCompleteEvent, this, std::placeholders::_1,
151 std::placeholders::_2));
152 eventToFunctionMap_.emplace(
153 config_.eventNameMap_.at(TRACE_EVENT_REGULATOR_DISABLE),
154 bind(&BytraceEventParser::RegulatorDisableEvent, this, std::placeholders::_1, std::placeholders::_2));
155 eventToFunctionMap_.emplace(
156 config_.eventNameMap_.at(TRACE_EVENT_REGULATOR_DISABLE_COMPLETE),
157 bind(&BytraceEventParser::RegulatorDisableCompleteEvent, this, std::placeholders::_1, std::placeholders::_2));
158 }
159
BinderEventInitialization()160 void BytraceEventParser::BinderEventInitialization()
161 {
162 // Binder event initialization
163 eventToFunctionMap_.emplace(
164 config_.eventNameMap_.at(TRACE_EVENT_BINDER_TRANSACTION),
165 bind(&BytraceEventParser::BinderTransaction, this, std::placeholders::_1, std::placeholders::_2));
166 eventToFunctionMap_.emplace(
167 config_.eventNameMap_.at(TRACE_EVENT_BINDER_TRANSACTION_RECEIVED),
168 bind(&BytraceEventParser::BinderTransactionReceived, this, std::placeholders::_1, std::placeholders::_2));
169 eventToFunctionMap_.emplace(
170 config_.eventNameMap_.at(TRACE_EVENT_BINDER_TRANSACTION_ALLOC_BUF),
171 bind(&BytraceEventParser::BinderTransactionAllocBufEvent, this, std::placeholders::_1, std::placeholders::_2));
172 }
173
StackEventsInitialization()174 void BytraceEventParser::StackEventsInitialization()
175 {
176 // Call stack Events
177 eventToFunctionMap_.emplace(
178 config_.eventNameMap_.at(TRACE_EVENT_TRACING_MARK_WRITE),
179 bind(&BytraceEventParser::TracingMarkWriteOrPrintEvent, this, std::placeholders::_1, std::placeholders::_2));
180 eventToFunctionMap_.emplace(
181 config_.eventNameMap_.at(TRACE_EVENT_PRINT),
182 bind(&BytraceEventParser::TracingMarkWriteOrPrintEvent, this, std::placeholders::_1, std::placeholders::_2));
183 eventToFunctionMap_.emplace(
184 config_.eventNameMap_.at(TRACE_EVENT_WORKQUEUE_EXECUTE_START),
185 bind(&BytraceEventParser::WorkqueueExecuteStartEvent, this, std::placeholders::_1, std::placeholders::_2));
186 eventToFunctionMap_.emplace(
187 config_.eventNameMap_.at(TRACE_EVENT_WORKQUEUE_EXECUTE_END),
188 bind(&BytraceEventParser::WorkqueueExecuteEndEvent, this, std::placeholders::_1, std::placeholders::_2));
189 }
190
SchedSwitchEvent(const ArgsMap & args,const BytraceLine & line) const191 bool BytraceEventParser::SchedSwitchEvent(const ArgsMap &args, const BytraceLine &line) const
192 {
193 if (args.empty() || args.size() < MIN_SCHED_SWITCH_ARGS_COUNT) {
194 TS_LOGW("Failed to parse sched_switch event, no args or args size < 6, argsStr=%s.", line.argsStr.data());
195 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_SCHED_SWITCH, STAT_EVENT_DATA_INVALID);
196 return false;
197 }
198 auto prevCommStr = std::string_view(args.at("prev_comm"));
199 auto nextCommStr = std::string_view(args.at("next_comm"));
200 auto prevPrioValue = base::StrToInt<int32_t>(args.at("prev_prio"));
201 auto nextPrioValue = base::StrToInt<int32_t>(args.at("next_prio"));
202 auto prevPidValue = base::StrToInt<uint32_t>(args.at("prev_pid"));
203 auto nextPidValue = base::StrToInt<uint32_t>(args.at("next_pid"));
204 DataIndex nextInfo = INVALID_DATAINDEX;
205 auto nextInfoIt = args.find("next_info");
206 if (nextInfoIt != args.end()) {
207 nextInfo = traceDataCache_->GetDataIndex(std::string_view(args.at("next_info")));
208 }
209 if (!(prevPidValue.has_value() && prevPrioValue.has_value() && nextPidValue.has_value() &&
210 nextPrioValue.has_value())) {
211 TS_LOGD("Failed to parse sched_switch event");
212 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_SCHED_SWITCH, STAT_EVENT_DATA_INVALID);
213 return false;
214 }
215 auto prevStateStr = args.at("prev_state");
216 auto threadState = ThreadStateFlag(prevStateStr.c_str());
217 uint64_t prevState = threadState.State();
218 if (threadState.IsInvalid()) {
219 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_SCHED_SWITCH, STAT_EVENT_DATA_INVALID);
220 }
221 uint32_t nextInternalTid = 0;
222 uint32_t uprevtid = 0;
223 nextInternalTid =
224 streamFilters_->processFilter_->UpdateOrCreateThreadWithName(line.ts, nextPidValue.value(), nextCommStr);
225
226 if (!prevCommStr.empty()) {
227 uprevtid =
228 streamFilters_->processFilter_->UpdateOrCreateThreadWithName(line.ts, prevPidValue.value(), prevCommStr);
229 } else {
230 uprevtid = streamFilters_->processFilter_->UpdateOrCreateThread(line.ts, prevPidValue.value());
231 }
232 streamFilters_->cpuFilter_->InsertSwitchEvent(line.ts, line.cpu, uprevtid, prevPrioValue.value(), prevState,
233 nextInternalTid, nextPrioValue.value(), nextInfo);
234 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_SCHED_SWITCH, STAT_EVENT_RECEIVED);
235 return true;
236 }
BlockedReason(const ArgsMap & args,const BytraceLine & line) const237 bool BytraceEventParser::BlockedReason(const ArgsMap &args, const BytraceLine &line) const
238 {
239 if (args.empty() || args.size() < MIN_BLOCKED_REASON_ARGS_COUNT) {
240 TS_LOGD("Failed to parse blocked_reason event, no args or args size < %d", MIN_BLOCKED_REASON_ARGS_COUNT);
241 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_SCHED_BLOCKED_REASON, STAT_EVENT_DATA_INVALID);
242 return false;
243 }
244 auto tid = base::StrToInt<int32_t>(args.at("pid"));
245 auto iowaitIt = args.find("iowait");
246 if (iowaitIt == args.end()) {
247 iowaitIt = args.find("io_wait");
248 }
249 auto iowait = base::StrToInt<int32_t>(iowaitIt->second);
250 uint32_t delayValue = INVALID_UINT32;
251 if (args.find("delay") != args.end()) {
252 auto delay = base::StrToInt<int32_t>(args.at("delay"));
253 delayValue = delay.has_value() ? delay.value() : INVALID_UINT32;
254 }
255 auto caller = traceDataCache_->GetDataIndex(std::string_view(args.at("caller")));
256 if (!(tid.has_value() && iowait.has_value())) {
257 TS_LOGD("Failed to parse blocked_reason event");
258 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_SCHED_BLOCKED_REASON, STAT_EVENT_DATA_INVALID);
259 return false;
260 }
261 auto iTid = streamFilters_->processFilter_->UpdateOrCreateThread(line.ts, tid.value());
262 if (streamFilters_->cpuFilter_->InsertBlockedReasonEvent(line.cpu, iTid, iowait.value(), caller, delayValue)) {
263 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_SCHED_BLOCKED_REASON, STAT_EVENT_RECEIVED);
264 } else {
265 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_SCHED_BLOCKED_REASON, STAT_EVENT_NOTMATCH);
266 }
267 return true;
268 }
269
TaskRenameEvent(const ArgsMap & args,const BytraceLine & line) const270 bool BytraceEventParser::TaskRenameEvent(const ArgsMap &args, const BytraceLine &line) const
271 {
272 if (args.empty() || args.size() < MIN_TASK_RENAME_ARGS_COUNT) {
273 TS_LOGD("Failed to parse task_rename event, no args or args size < 2");
274 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_TASK_RENAME, STAT_EVENT_DATA_INVALID);
275 return false;
276 }
277 auto prevCommStr = std::string_view(args.at("newcomm"));
278 auto pidValue = base::StrToInt<uint32_t>(args.at("pid"));
279 streamFilters_->processFilter_->UpdateOrCreateThreadWithName(line.ts, pidValue.value(), prevCommStr);
280 return true;
281 }
282
TaskNewtaskEvent(const ArgsMap & args,const BytraceLine & line) const283 bool BytraceEventParser::TaskNewtaskEvent(const ArgsMap &args, const BytraceLine &line) const
284 {
285 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_TASK_NEWTASK, STAT_EVENT_RECEIVED);
286 // the clone flag from txt trace from kernel original is HEX, but when it is converted from proto
287 // based trace, it will be OCT number, it is not stable, so we decide to ignore it
288 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_TASK_NEWTASK, STAT_EVENT_NOTSUPPORTED);
289 return true;
290 }
291
TracingMarkWriteOrPrintEvent(const ArgsMap & args,const BytraceLine & line)292 bool BytraceEventParser::TracingMarkWriteOrPrintEvent(const ArgsMap &args, const BytraceLine &line)
293 {
294 Unused(args);
295 return printEventParser_.ParsePrintEvent(line.task, line.ts, line.pid, line.argsStr.c_str(), line);
296 }
297 // prefer to use waking, unless no waking, can use wakeup
SchedWakeupEvent(const ArgsMap & args,const BytraceLine & line) const298 bool BytraceEventParser::SchedWakeupEvent(const ArgsMap &args, const BytraceLine &line) const
299 {
300 if (args.size() < MIN_SCHED_WAKEUP_ARGS_COUNT) {
301 TS_LOGD("Failed to parse SchedWakeupEvent event, no args or args size < 2");
302 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_SCHED_WAKEUP, STAT_EVENT_DATA_INVALID);
303 return false;
304 }
305 std::optional<uint32_t> wakePidValue = base::StrToInt<uint32_t>(args.at("pid"));
306 if (!wakePidValue.has_value()) {
307 TS_LOGD("Failed to convert wake_pid");
308 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_SCHED_WAKEUP, STAT_EVENT_DATA_INVALID);
309 return false;
310 }
311 auto instants = traceDataCache_->GetInstantsData();
312 InternalTid internalTid = streamFilters_->processFilter_->UpdateOrCreateThread(line.ts, wakePidValue.value_or(0));
313 streamFilters_->cpuFilter_->InsertWakeupEvent(line.ts, internalTid);
314
315 InternalTid wakeupFromPid = streamFilters_->processFilter_->UpdateOrCreateThread(line.ts, line.pid);
316
317 instants->AppendInstantEventData(line.ts, schedWakeupName_, internalTid, wakeupFromPid);
318 std::optional<uint32_t> targetCpu = base::StrToInt<uint32_t>(args.at("target_cpu"));
319 if (targetCpu.has_value()) {
320 traceDataCache_->GetRawData()->AppendRawData(line.ts, RAW_SCHED_WAKEUP, targetCpu.value(), wakeupFromPid);
321 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_SCHED_WAKEUP, STAT_EVENT_RECEIVED);
322 }
323 return true;
324 }
325
SchedWakingEvent(const ArgsMap & args,const BytraceLine & line) const326 bool BytraceEventParser::SchedWakingEvent(const ArgsMap &args, const BytraceLine &line) const
327 {
328 if (args.empty() || args.size() < MIN_SCHED_WAKING_ARGS_COUNT) {
329 TS_LOGD("Failed to parse sched_waking event, no args or args size < 4");
330 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_SCHED_WAKING, STAT_EVENT_DATA_INVALID);
331 return false;
332 }
333 std::optional<uint32_t> wakePidValue = base::StrToInt<uint32_t>(args.at("pid"));
334 if (!wakePidValue.has_value()) {
335 TS_LOGD("Failed to convert wake_pid");
336 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_SCHED_WAKING, STAT_EVENT_DATA_INVALID);
337 return false;
338 }
339 auto instants = traceDataCache_->GetInstantsData();
340 InternalTid internalTid = streamFilters_->processFilter_->UpdateOrCreateThread(line.ts, wakePidValue.value());
341 DataIndex wakeByPidStrIndex = traceDataCache_->GetDataIndex(line.task);
342 InternalTid internalTidWakeup =
343 streamFilters_->processFilter_->UpdateOrCreateThreadWithNameIndex(line.ts, line.pid, wakeByPidStrIndex);
344 InternalTid wakeupFromPid = streamFilters_->processFilter_->UpdateOrCreateThread(line.ts, line.pid);
345 streamFilters_->cpuFilter_->InsertWakeupEvent(line.ts, internalTid, true);
346 instants->AppendInstantEventData(line.ts, schedWakingName_, internalTid, wakeupFromPid);
347 std::optional<uint32_t> targetCpu = base::StrToInt<uint32_t>(args.at("target_cpu"));
348 if (targetCpu.has_value()) {
349 traceDataCache_->GetRawData()->AppendRawData(line.ts, RAW_SCHED_WAKING, targetCpu.value(), internalTidWakeup);
350 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_SCHED_WAKING, STAT_EVENT_RECEIVED);
351 }
352
353 return true;
354 }
355
CpuIdleEvent(const ArgsMap & args,const BytraceLine & line) const356 bool BytraceEventParser::CpuIdleEvent(const ArgsMap &args, const BytraceLine &line) const
357 {
358 if (args.empty() || args.size() < MIN_CPU_IDLE_ARGS_COUNT) {
359 TS_LOGD("Failed to parse cpu_idle event, no args or args size < 2");
360 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_CPU_IDLE, STAT_EVENT_DATA_INVALID);
361 return false;
362 }
363 std::optional<uint32_t> eventCpuValue = base::StrToInt<uint32_t>(args.at("cpu_id"));
364 std::optional<int64_t> newStateValue = base::StrToInt<int64_t>(args.at("state"));
365 if (!eventCpuValue.has_value()) {
366 TS_LOGD("Failed to convert event cpu");
367 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_CPU_IDLE, STAT_EVENT_DATA_INVALID);
368 return false;
369 }
370 if (!newStateValue.has_value()) {
371 TS_LOGD("Failed to convert state");
372 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_CPU_IDLE, STAT_EVENT_DATA_INVALID);
373 return false;
374 }
375 // Add cpu_idle event to raw_data_table
376 auto cpuidleNameIndex = traceDataCache_->GetDataIndex(line.eventName.c_str());
377 streamFilters_->cpuMeasureFilter_->AppendNewMeasureData(eventCpuValue.value(), cpuidleNameIndex, line.ts,
378 config_.GetStateValue(newStateValue.value()));
379 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_CPU_IDLE, STAT_EVENT_RECEIVED);
380 return true;
381 }
382
CpuFrequencyEvent(const ArgsMap & args,const BytraceLine & line) const383 bool BytraceEventParser::CpuFrequencyEvent(const ArgsMap &args, const BytraceLine &line) const
384 {
385 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_CPU_FREQUENCY, STAT_EVENT_RECEIVED);
386 if (args.empty() || args.size() < MIN_CPU_FREQUENCY_ARGS_COUNT) {
387 TS_LOGD("Failed to parse cpu_frequency event, no args or args size < 2");
388 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_CPU_FREQUENCY, STAT_EVENT_DATA_INVALID);
389 return false;
390 }
391 std::optional<uint32_t> eventCpuValue = base::StrToInt<uint32_t>(args.at("cpu_id"));
392 std::optional<int64_t> newStateValue = base::StrToInt<int64_t>(args.at("state"));
393
394 if (!newStateValue.has_value()) {
395 TS_LOGD("Failed to convert state");
396 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_CPU_FREQUENCY, STAT_EVENT_DATA_INVALID);
397 return false;
398 }
399 if (!eventCpuValue.has_value()) {
400 TS_LOGD("Failed to convert event cpu");
401 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_CPU_FREQUENCY, STAT_EVENT_DATA_INVALID);
402 return false;
403 }
404
405 auto cpuidleNameIndex = traceDataCache_->GetDataIndex(line.eventName.c_str());
406 streamFilters_->cpuMeasureFilter_->AppendNewMeasureData(eventCpuValue.value(), cpuidleNameIndex, line.ts,
407 newStateValue.value());
408 return true;
409 }
CpuFrequencyLimitsEvent(const ArgsMap & args,const BytraceLine & line) const410 bool BytraceEventParser::CpuFrequencyLimitsEvent(const ArgsMap &args, const BytraceLine &line) const
411 {
412 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_CPU_FREQUENCY_LIMITS, STAT_EVENT_RECEIVED);
413 if (args.empty() || args.size() < MIN_CPU_FREQUENCY_ARGS_COUNT) {
414 TS_LOGD("Failed to parse cpu_frequency event, no args or args size < 2");
415 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_CPU_FREQUENCY_LIMITS, STAT_EVENT_DATA_INVALID);
416 return false;
417 }
418 std::optional<uint32_t> eventCpuValue = base::StrToInt<uint32_t>(args.at("cpu_id"));
419
420 auto minIt = args.find("min");
421 if (minIt == args.end()) {
422 minIt = args.find("min_freq");
423 }
424 auto maxIt = args.find("max");
425 if (maxIt == args.end()) {
426 maxIt = args.find("max_freq");
427 }
428 std::optional<int64_t> minValue = base::StrToInt<int64_t>(minIt->second);
429 std::optional<int64_t> maxValue = base::StrToInt<int64_t>(maxIt->second);
430
431 if (!minValue.has_value()) {
432 TS_LOGD("Failed to get frequency minValue");
433 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_CPU_FREQUENCY_LIMITS, STAT_EVENT_DATA_INVALID);
434 return false;
435 }
436 if (!maxValue.has_value()) {
437 TS_LOGD("Failed to get frequency maxValue");
438 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_CPU_FREQUENCY_LIMITS, STAT_EVENT_DATA_INVALID);
439 return false;
440 }
441 if (!eventCpuValue.has_value()) {
442 TS_LOGD("Failed to get frequency cpu");
443 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_CPU_FREQUENCY_LIMITS, STAT_EVENT_DATA_INVALID);
444 return false;
445 }
446
447 streamFilters_->cpuMeasureFilter_->AppendNewMeasureData(eventCpuValue.value(), cpuFrequencyLimitMaxNameId, line.ts,
448 maxValue.value());
449 streamFilters_->cpuMeasureFilter_->AppendNewMeasureData(eventCpuValue.value(), cpuFrequencyLimitMinNameId, line.ts,
450 minValue.value());
451 return true;
452 }
453
WorkqueueExecuteStartEvent(const ArgsMap & args,const BytraceLine & line) const454 bool BytraceEventParser::WorkqueueExecuteStartEvent(const ArgsMap &args, const BytraceLine &line) const
455 {
456 Unused(args);
457 auto splitStr = GetFunctionName(line.argsStr, "function ");
458 auto splitStrIndex = traceDataCache_->GetDataIndex(splitStr);
459 size_t result =
460 streamFilters_->sliceFilter_->BeginSlice(line.task, line.ts, line.pid, 0, workQueueId_, splitStrIndex);
461 traceDataCache_->GetInternalSlicesData()->AppendDistributeInfo();
462 if (result != INVALID_UINT32) {
463 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_WORKQUEUE_EXECUTE_START, STAT_EVENT_RECEIVED);
464 return true;
465 } else {
466 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_WORKQUEUE_EXECUTE_START, STAT_EVENT_DATA_LOST);
467 return false;
468 }
469 }
470
WorkqueueExecuteEndEvent(const ArgsMap & args,const BytraceLine & line) const471 bool BytraceEventParser::WorkqueueExecuteEndEvent(const ArgsMap &args, const BytraceLine &line) const
472 {
473 Unused(args);
474 if (streamFilters_->sliceFilter_->EndSlice(line.ts, line.pid, 0, workQueueId_)) {
475 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_WORKQUEUE_EXECUTE_END, STAT_EVENT_RECEIVED);
476 return true;
477 } else {
478 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_WORKQUEUE_EXECUTE_END, STAT_EVENT_NOTMATCH);
479 return false;
480 }
481 }
482
ProcessExitEvent(const ArgsMap & args,const BytraceLine & line) const483 bool BytraceEventParser::ProcessExitEvent(const ArgsMap &args, const BytraceLine &line) const
484 {
485 if (args.empty() || args.size() < MIN_PROCESS_EXIT_ARGS_COUNT) {
486 TS_LOGD("Failed to parse process_exit event, no args or args size < 2");
487 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_PROCESS_EXIT, STAT_EVENT_DATA_INVALID);
488 return false;
489 }
490 auto comm = std::string_view(args.at("comm"));
491 auto pid = base::StrToInt<uint32_t>(args.at("pid"));
492 if (!pid.has_value()) {
493 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_PROCESS_EXIT, STAT_EVENT_DATA_INVALID);
494 return false;
495 }
496 auto itid = streamFilters_->processFilter_->UpdateOrCreateThreadWithName(line.ts, pid.value(), comm);
497 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_PROCESS_EXIT, STAT_EVENT_RECEIVED);
498 if (streamFilters_->cpuFilter_->InsertProcessExitEvent(line.ts, line.cpu, itid)) {
499 return true;
500 } else {
501 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_PROCESS_EXIT, STAT_EVENT_NOTMATCH);
502 return false;
503 }
504 }
505
SetRateEvent(const ArgsMap & args,const BytraceLine & line) const506 bool BytraceEventParser::SetRateEvent(const ArgsMap &args, const BytraceLine &line) const
507 {
508 if (args.empty() || args.size() < MIN_CLOCK_SET_RATE_ARGS_COUNT) {
509 TS_LOGD("Failed to parse clock_set_rate event, no args or args size < 3");
510 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_CLOCK_SET_RATE, STAT_EVENT_DATA_INVALID);
511 return false;
512 }
513 auto name = std::string_view(args.at("name"));
514 auto state = base::StrToInt<int64_t>(args.at("state"));
515 uint64_t cpu = 0;
516 DataIndex nameIndex = traceDataCache_->GetDataIndex(name);
517 streamFilters_->clockRateFilter_->AppendNewMeasureData(cpu, nameIndex, line.ts, state.value());
518 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_CLOCK_SET_RATE, STAT_EVENT_RECEIVED);
519 return true;
520 }
521
ClockEnableEvent(const ArgsMap & args,const BytraceLine & line) const522 bool BytraceEventParser::ClockEnableEvent(const ArgsMap &args, const BytraceLine &line) const
523 {
524 if (args.empty() || args.size() < MIN_CLOCK_ENABLE_ARGS_COUNT) {
525 TS_LOGD("Failed to parse clock_enable event, no args or args size < 3");
526 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_CLOCK_ENABLE, STAT_EVENT_DATA_INVALID);
527 return false;
528 }
529 auto name = std::string_view(args.at("name"));
530 auto state = base::StrToInt<int64_t>(args.at("state"));
531 auto cpuId = base::StrToInt<uint64_t>(args.at("cpu_id"));
532 DataIndex nameIndex = traceDataCache_->GetDataIndex(name);
533 streamFilters_->clockEnableFilter_->AppendNewMeasureData(cpuId.value(), nameIndex, line.ts, state.value());
534 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_CLOCK_ENABLE, STAT_EVENT_RECEIVED);
535 return true;
536 }
ClockDisableEvent(const ArgsMap & args,const BytraceLine & line) const537 bool BytraceEventParser::ClockDisableEvent(const ArgsMap &args, const BytraceLine &line) const
538 {
539 if (args.empty() || args.size() < MIN_CLOCK_DISABLE_ARGS_COUNT) {
540 TS_LOGD("Failed to parse clock_disable event, no args or args size < 3");
541 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_CLOCK_DISABLE, STAT_EVENT_DATA_INVALID);
542 return false;
543 }
544 auto name = std::string_view(args.at("name"));
545 auto state = base::StrToInt<int64_t>(args.at("state"));
546 auto cpuId = base::StrToInt<uint64_t>(args.at("cpu_id"));
547 DataIndex nameIndex = traceDataCache_->GetDataIndex(name);
548 streamFilters_->clockDisableFilter_->AppendNewMeasureData(cpuId.value(), nameIndex, line.ts, state.value());
549 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_CLOCK_DISABLE, STAT_EVENT_RECEIVED);
550 return true;
551 }
552
RegulatorSetVoltageEvent(const ArgsMap & args,const BytraceLine & line) const553 bool BytraceEventParser::RegulatorSetVoltageEvent(const ArgsMap &args, const BytraceLine &line) const
554 {
555 Unused(args);
556 Unused(line);
557 traceDataCache_->GetStatAndInfo()->IncreaseStat(TRACE_EVENT_REGULATOR_SET_VOLTAGE, STAT_EVENT_RECEIVED);
558 traceDataCache_->GetStatAndInfo()->IncreaseStat(TRACE_EVENT_REGULATOR_SET_VOLTAGE, STAT_EVENT_NOTSUPPORTED);
559 return true;
560 }
RegulatorSetVoltageCompleteEvent(const ArgsMap & args,const BytraceLine & line) const561 bool BytraceEventParser::RegulatorSetVoltageCompleteEvent(const ArgsMap &args, const BytraceLine &line) const
562 {
563 Unused(args);
564 Unused(line);
565 traceDataCache_->GetStatAndInfo()->IncreaseStat(TRACE_EVENT_REGULATOR_SET_VOLTAGE_COMPLETE, STAT_EVENT_RECEIVED);
566 traceDataCache_->GetStatAndInfo()->IncreaseStat(TRACE_EVENT_REGULATOR_SET_VOLTAGE_COMPLETE,
567 STAT_EVENT_NOTSUPPORTED);
568 return true;
569 }
RegulatorDisableEvent(const ArgsMap & args,const BytraceLine & line) const570 bool BytraceEventParser::RegulatorDisableEvent(const ArgsMap &args, const BytraceLine &line) const
571 {
572 Unused(args);
573 Unused(line);
574 traceDataCache_->GetStatAndInfo()->IncreaseStat(TRACE_EVENT_REGULATOR_DISABLE, STAT_EVENT_RECEIVED);
575 traceDataCache_->GetStatAndInfo()->IncreaseStat(TRACE_EVENT_REGULATOR_DISABLE, STAT_EVENT_NOTSUPPORTED);
576 return true;
577 }
RegulatorDisableCompleteEvent(const ArgsMap & args,const BytraceLine & line) const578 bool BytraceEventParser::RegulatorDisableCompleteEvent(const ArgsMap &args, const BytraceLine &line) const
579 {
580 Unused(args);
581 Unused(line);
582 traceDataCache_->GetStatAndInfo()->IncreaseStat(TRACE_EVENT_REGULATOR_DISABLE_COMPLETE, STAT_EVENT_RECEIVED);
583 traceDataCache_->GetStatAndInfo()->IncreaseStat(TRACE_EVENT_REGULATOR_DISABLE_COMPLETE, STAT_EVENT_NOTSUPPORTED);
584 return true;
585 }
586
IpiEntryEvent(const ArgsMap & args,const BytraceLine & line) const587 bool BytraceEventParser::IpiEntryEvent(const ArgsMap &args, const BytraceLine &line) const
588 {
589 Unused(args);
590 traceDataCache_->GetStatAndInfo()->IncreaseStat(TRACE_EVENT_IPI_ENTRY, STAT_EVENT_RECEIVED);
591 streamFilters_->irqFilter_->IpiHandlerEntry(line.ts, line.cpu, traceDataCache_->GetDataIndex(line.argsStr));
592 return true;
593 }
IpiExitEvent(const ArgsMap & args,const BytraceLine & line) const594 bool BytraceEventParser::IpiExitEvent(const ArgsMap &args, const BytraceLine &line) const
595 {
596 Unused(args);
597 traceDataCache_->GetStatAndInfo()->IncreaseStat(TRACE_EVENT_IPI_EXIT, STAT_EVENT_RECEIVED);
598 streamFilters_->irqFilter_->IpiHandlerExit(line.ts, line.cpu);
599 return true;
600 }
IrqHandlerEntryEvent(const ArgsMap & args,const BytraceLine & line) const601 bool BytraceEventParser::IrqHandlerEntryEvent(const ArgsMap &args, const BytraceLine &line) const
602 {
603 if (args.empty() || args.size() < MIN_IRQ_HANDLER_ENTRY_ARGS_COUNT) {
604 TS_LOGD("Failed to parse irq_handler_entry event, no args or args size < 2");
605 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_IRQ_HANDLER_ENTRY, STAT_EVENT_DATA_INVALID);
606 return false;
607 }
608 traceDataCache_->GetStatAndInfo()->IncreaseStat(TRACE_EVENT_IRQ_HANDLER_ENTRY, STAT_EVENT_RECEIVED);
609 auto name = std::string_view(args.at("name"));
610 streamFilters_->irqFilter_->IrqHandlerEntry(line.ts, line.cpu, traceDataCache_->GetDataIndex(name));
611 return true;
612 }
IrqHandlerExitEvent(const ArgsMap & args,const BytraceLine & line) const613 bool BytraceEventParser::IrqHandlerExitEvent(const ArgsMap &args, const BytraceLine &line) const
614 {
615 if (args.empty() || args.size() < MIN_IRQ_HANDLER_EXIT_ARGS_COUNT) {
616 TS_LOGD("Failed to parse irq_handler_exit event, no args or args size < 2");
617 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_IRQ_HANDLER_EXIT, STAT_EVENT_DATA_INVALID);
618 return false;
619 }
620 traceDataCache_->GetStatAndInfo()->IncreaseStat(TRACE_EVENT_IRQ_HANDLER_EXIT, STAT_EVENT_RECEIVED);
621 uint32_t ret = (args.at("ret") == "handled") ? 1 : 0;
622 auto irq = base::StrToInt<uint32_t>(args.at("irq"));
623 streamFilters_->irqFilter_->IrqHandlerExit(line.ts, line.cpu, irq.value(), ret);
624 return true;
625 }
SoftIrqRaiseEvent(const ArgsMap & args,const BytraceLine & line) const626 bool BytraceEventParser::SoftIrqRaiseEvent(const ArgsMap &args, const BytraceLine &line) const
627 {
628 Unused(args);
629 Unused(line);
630 traceDataCache_->GetStatAndInfo()->IncreaseStat(TRACE_EVENT_SOFTIRQ_RAISE, STAT_EVENT_RECEIVED);
631 traceDataCache_->GetStatAndInfo()->IncreaseStat(TRACE_EVENT_SOFTIRQ_RAISE, STAT_EVENT_NOTSUPPORTED);
632 return true;
633 }
SoftIrqEntryEvent(const ArgsMap & args,const BytraceLine & line) const634 bool BytraceEventParser::SoftIrqEntryEvent(const ArgsMap &args, const BytraceLine &line) const
635 {
636 if (args.empty() || args.size() < MIN_SOFTIRQ_ENTRY_ARGS_COUNT) {
637 TS_LOGD("Failed to parse softirq_entry event, no args or args size < 2");
638 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_SOFTIRQ_ENTRY, STAT_EVENT_DATA_INVALID);
639 return false;
640 }
641 traceDataCache_->GetStatAndInfo()->IncreaseStat(TRACE_EVENT_SOFTIRQ_ENTRY, STAT_EVENT_RECEIVED);
642 auto vec = base::StrToInt<uint32_t>(args.at("vec"));
643 streamFilters_->irqFilter_->SoftIrqEntry(line.ts, line.cpu, vec.value());
644 return true;
645 }
SoftIrqExitEvent(const ArgsMap & args,const BytraceLine & line) const646 bool BytraceEventParser::SoftIrqExitEvent(const ArgsMap &args, const BytraceLine &line) const
647 {
648 if (args.empty() || args.size() < MIN_SOFTIRQ_EXIT_ARGS_COUNT) {
649 TS_LOGD("Failed to parse softirq_exit event, no args or args size < 2");
650 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_SOFTIRQ_EXIT, STAT_EVENT_DATA_INVALID);
651 return false;
652 }
653 traceDataCache_->GetStatAndInfo()->IncreaseStat(TRACE_EVENT_SOFTIRQ_EXIT, STAT_EVENT_RECEIVED);
654 auto vec = base::StrToInt<uint32_t>(args.at("vec"));
655 streamFilters_->irqFilter_->SoftIrqExit(line.ts, line.cpu, vec.value());
656 return true;
657 }
DmaFenceEvent(const ArgsMap & args,const BytraceLine & line) const658 bool BytraceEventParser::DmaFenceEvent(const ArgsMap &args, const BytraceLine &line) const
659 {
660 if (args.empty() || args.size() < MIN_DMA_FENCE_ARGS_COUNT) {
661 TS_LOGD("Failed to dma fence event,no args or args size <4");
662 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_DMA_FENCE, STAT_EVENT_DATA_INVALID);
663 return false;
664 }
665 traceDataCache_->GetStatAndInfo()->IncreaseStat(TRACE_EVENT_DMA_FENCE, STAT_EVENT_RECEIVED);
666 auto driverStr = std::string_view(args.at("driver"));
667 auto timelineStr = std::string_view(args.at("timeline"));
668 auto context = base::StrToInt<uint32_t>(args.at("context"));
669 auto seqno = base::StrToInt<uint32_t>(args.at("seqno"));
670 if (timelineStr.empty() || !(context.has_value()) || !(seqno.has_value())) {
671 TS_LOGD("Failed to dma fence event,timelineStr or context or seqno is empty");
672 return false;
673 }
674 DmaFenceRow dmaFenceRow = {line.ts,
675 0,
676 traceDataCache_->GetDataIndex(line.eventName),
677 traceDataCache_->GetDataIndex(driverStr),
678 traceDataCache_->GetDataIndex(timelineStr),
679 context.value(),
680 seqno.value()};
681 streamFilters_->sliceFilter_->DmaFence(dmaFenceRow);
682 return true;
683 }
BinderTransaction(const ArgsMap & args,const BytraceLine & line) const684 bool BytraceEventParser::BinderTransaction(const ArgsMap &args, const BytraceLine &line) const
685 {
686 if (args.empty() || args.size() < MIN_BINDER_TRANSACTION_ARGS_COUNT) {
687 TS_LOGD("Failed to parse binder_transaction event, no args or args size < 7");
688 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_BINDER_TRANSACTION, STAT_EVENT_DATA_INVALID);
689 return false;
690 }
691 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_BINDER_TRANSACTION, STAT_EVENT_RECEIVED);
692 auto transactionId = base::StrToInt<int64_t>(args.at("transaction"));
693 auto destNode = base::StrToInt<uint32_t>(args.at("dest_node"));
694 auto destProc = base::StrToInt<uint32_t>(args.at("dest_proc"));
695 auto destThread = base::StrToInt<uint32_t>(args.at("dest_thread"));
696 auto isReply = base::StrToInt<uint32_t>(args.at("reply"));
697 auto flags = base::StrToInt<uint32_t>(args.at("flags"), base::INTEGER_RADIX_TYPE_HEX);
698 auto codeStr = base::StrToInt<uint32_t>(args.at("code"), base::INTEGER_RADIX_TYPE_HEX);
699 TS_LOGD("ts:%" PRIu64 ", pid:%u, destNode:%u, destTgid:%u, destTid:%u, transactionId:%" PRIu64
700 ", isReply:%u flags:%u, code:%u",
701 line.ts, line.pid, destNode.value(), destProc.value(), destThread.value(), transactionId.value(),
702 isReply.value(), flags.value(), codeStr.value());
703 streamFilters_->binderFilter_->SendTraction(line.ts, line.pid, transactionId.value(), destNode.value(),
704 destProc.value(), destThread.value(), isReply.value(), flags.value(),
705 codeStr.value());
706 if (traceDataCache_->BinderRunnableTraceEnabled() && transactionId.has_value() && flags.has_value() &&
707 !streamFilters_->binderFilter_->IsAsync(flags.value())) {
708 streamFilters_->cpuFilter_->InsertRunnableBinderEvent(transactionId.value(),
709 streamFilters_->processFilter_->GetInternalTid(line.pid));
710 }
711 return true;
712 }
BinderTransactionReceived(const ArgsMap & args,const BytraceLine & line) const713 bool BytraceEventParser::BinderTransactionReceived(const ArgsMap &args, const BytraceLine &line) const
714 {
715 if (args.empty() || args.size() < MIN_BINDER_TRANSACTION_RECEIVED_ARGS_COUNT) {
716 TS_LOGD("Failed to parse binder_transaction_received event, no args or args size < 1");
717 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_BINDER_TRANSACTION_RECEIVED, STAT_EVENT_DATA_INVALID);
718 return false;
719 }
720 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_BINDER_TRANSACTION_RECEIVED, STAT_EVENT_RECEIVED);
721 auto transactionId = base::StrToInt<int64_t>(args.at("transaction"));
722 streamFilters_->binderFilter_->ReceiveTraction(line.ts, line.pid, transactionId.value());
723 if (traceDataCache_->BinderRunnableTraceEnabled() && transactionId.has_value()) {
724 streamFilters_->cpuFilter_->InsertRunnableBinderRecvEvent(
725 transactionId.value(), streamFilters_->processFilter_->GetInternalTid(line.pid));
726 }
727 TS_LOGD("ts:%" PRIu64 ", pid:%u, transactionId:%" PRIu64 "", line.ts, line.pid, transactionId.value());
728 return true;
729 }
BinderTransactionAllocBufEvent(const ArgsMap & args,const BytraceLine & line) const730 bool BytraceEventParser::BinderTransactionAllocBufEvent(const ArgsMap &args, const BytraceLine &line) const
731 {
732 if (args.empty() || args.size() < MIN_BINDER_TRANSACTION_ALLOC_BUF_ARGS_COUNT) {
733 TS_LOGD("Failed to parse binder_transaction_alloc_buf event, no args or args size < 3");
734 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_BINDER_TRANSACTION_ALLOC_BUF, STAT_EVENT_DATA_INVALID);
735 return false;
736 }
737 streamFilters_->statFilter_->IncreaseStat(TRACE_EVENT_BINDER_TRANSACTION_ALLOC_BUF, STAT_EVENT_RECEIVED);
738 auto dataSize = base::StrToInt<uint64_t>(args.at("data_size"));
739 auto offsetsSize = base::StrToInt<uint64_t>(args.at("offsets_size"));
740 streamFilters_->binderFilter_->TransactionAllocBuf(line.ts, line.pid, dataSize.value(), offsetsSize.value());
741 TS_LOGD("dataSize:%" PRIu64 ", offsetSize:%" PRIu64 "", dataSize.value(), offsetsSize.value());
742 return true;
743 }
ParseDataItem(const BytraceLine & line)744 void BytraceEventParser::ParseDataItem(const BytraceLine &line)
745 {
746 eventList_.emplace_back(std::make_unique<EventInfo>(line.ts, line));
747 size_t maxQueue = 2;
748 if (eventList_.size() < maxBuffSize_ * maxQueue) {
749 return;
750 }
751 auto cmp = [](const std::unique_ptr<EventInfo> &a, const std::unique_ptr<EventInfo> &b) {
752 return a->eventTimestamp < b->eventTimestamp;
753 };
754 std::stable_sort(eventList_.begin(), eventList_.end(), cmp);
755 auto endOfList = eventList_.begin() + maxBuffSize_;
756 for (auto itor = eventList_.begin(); itor != endOfList; itor++) {
757 EventInfo *event = itor->get();
758 BeginFilterEvents(event);
759 itor->reset();
760 }
761 eventList_.erase(eventList_.begin(), endOfList);
762 }
763
GetDataSegArgs(const BytraceLine & bufLine,ArgsMap & args) const764 void BytraceEventParser::GetDataSegArgs(const BytraceLine &bufLine, ArgsMap &args) const
765 {
766 int32_t len = bufLine.argsStr.size();
767 int32_t first = -1;
768 int32_t second = -1;
769 for (int32_t i = 0; i < len; i++) {
770 if (bufLine.argsStr[i] == ' ') {
771 if (first == -1) {
772 continue;
773 }
774 if (second != -1) {
775 args.emplace(bufLine.argsStr.substr(first, second - 1 - first),
776 bufLine.argsStr.substr(second, i - second));
777 second = -1;
778 } else {
779 args.emplace("name", bufLine.argsStr.substr(first, i - first));
780 }
781 first = -1;
782 } else {
783 if (first == -1) {
784 first = i;
785 }
786 if (bufLine.argsStr[i] == '=') {
787 second = i + 1;
788 }
789 }
790 }
791 if (second != -1) {
792 args.emplace(bufLine.argsStr.substr(first, second - 1 - first), bufLine.argsStr.substr(second, len - second));
793 return;
794 }
795 if (first != -1) {
796 args.emplace("name", bufLine.argsStr.substr(first, len - first));
797 }
798 }
799
FilterAllEvents()800 void BytraceEventParser::FilterAllEvents()
801 {
802 auto cmp = [](const std::unique_ptr<EventInfo> &a, const std::unique_ptr<EventInfo> &b) {
803 return a->eventTimestamp < b->eventTimestamp;
804 };
805 std::stable_sort(eventList_.begin(), eventList_.end(), cmp);
806 while (eventList_.size()) {
807 int32_t size = std::min(maxBuffSize_, eventList_.size());
808 auto endOfList = eventList_.begin() + size;
809 for (auto itor = eventList_.begin(); itor != endOfList; itor++) {
810 EventInfo *event = itor->get();
811 BeginFilterEvents(event);
812 itor->reset();
813 }
814 eventList_.erase(eventList_.begin(), endOfList);
815 }
816 eventList_.clear();
817 streamFilters_->cpuFilter_->Finish();
818 traceDataCache_->dataDict_.Finish();
819 traceDataCache_->UpdataZeroThreadInfo();
820 if (traceDataCache_->AppStartTraceEnabled()) {
821 streamFilters_->appStartupFilter_->FilterAllAPPStartupData();
822 }
823 traceDataCache_->GetThreadStateData()->SortAllRowByTs();
824 }
825
BeginFilterEvents(EventInfo * event)826 void BytraceEventParser::BeginFilterEvents(EventInfo *event)
827 {
828 auto it = eventToFunctionMap_.find(event->line.eventName);
829 if (it != eventToFunctionMap_.end()) {
830 uint32_t tgid = event->line.tgid;
831 ArgsMap args;
832 GetDataSegArgs(event->line, args);
833 if (tgid) {
834 streamFilters_->processFilter_->UpdateOrCreateThreadWithPidAndName(event->line.pid, tgid, event->line.task);
835 } else {
836 // When tgid is zero, only use tid create thread
837 streamFilters_->processFilter_->GetOrCreateThreadWithPid(event->line.pid, tgid);
838 }
839 if (it->second(args, event->line)) {
840 traceDataCache_->UpdateTraceTime(event->line.ts);
841 }
842 } else {
843 traceDataCache_->GetStatAndInfo()->IncreaseStat(TRACE_EVENT_OTHER, STAT_EVENT_NOTSUPPORTED);
844 TS_LOGD("UnRecognizable event name:%s", event->line.eventName.c_str());
845 }
846 }
847
Clear()848 void BytraceEventParser::Clear()
849 {
850 const_cast<TraceStreamerFilters *>(streamFilters_)->FilterClear();
851 printEventParser_.Finish();
852 }
853 } // namespace TraceStreamer
854 } // namespace SysTuning
855