1 /* 2 * Copyright (c) 2021 Huawei Device Co., Ltd. 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 #ifndef HTRACE_PARSER_H 17 #define HTRACE_PARSER_H 18 #include <cstdint> 19 #include <limits> 20 #include <map> 21 #include <stdexcept> 22 #include <string> 23 #include <thread> 24 #include "common_types.h" 25 #include "common_types.pbreader.h" 26 #include "ebpf_data_parser.h" 27 #include "file.h" 28 #include "htrace_clock_detail_parser.h" 29 #include "htrace_cpu_detail_parser.h" 30 #include "htrace_cpu_data_parser.h" 31 #include "htrace_disk_io_parser.h" 32 #include "htrace_file_header.h" 33 #include "htrace_hidump_parser.h" 34 #include "htrace_hilog_parser.h" 35 #include "htrace_hisysevent_parser.h" 36 #include "htrace_js_memory_parser.h" 37 #include "htrace_mem_parser.h" 38 #include "htrace_native_hook_parser.h" 39 #include "htrace_network_parser.h" 40 #include "htrace_process_parser.h" 41 #include "htrace_symbols_detail_parser.h" 42 #include "log.h" 43 #include "parser_base.h" 44 #include "perf_data_parser.h" 45 #include "proto_reader_help.h" 46 #include "string_help.h" 47 #include "symbols_file.h" 48 #include "trace_data/trace_data_cache.h" 49 #include "trace_streamer_filters.h" 50 #include "ts_common.h" 51 52 namespace SysTuning { 53 namespace TraceStreamer { 54 using namespace SysTuning::base; 55 using namespace OHOS::Developtools::HiPerf; 56 class HtraceParser : public ParserBase, public HtracePluginTimeParser { 57 public: 58 HtraceParser(TraceDataCache* dataCache, const TraceStreamerFilters* filters); 59 ~HtraceParser(); 60 void ParseTraceDataSegment(std::unique_ptr<uint8_t[]> bufferStr, size_t size, bool isFinish = false) override; 61 bool ReparseSymbolFilesAndResymbolization(std::string& symbolsPath, std::vector<std::string>& symbolsPaths); 62 void WaitForParserEnd(); 63 void EnableFileSeparate(bool enabled); 64 void ParserFileSO(std::string& directory, const std::vector<std::string>& relativeFilePaths); 65 void TraceDataSegmentEnd(bool isSplitFile); 66 void StoreTraceDataSegment(std::unique_ptr<uint8_t[]> bufferStr, size_t size, int32_t isFinish); GetTraceDataHtrace()67 const auto& GetTraceDataHtrace() 68 { 69 return mTraceDataHtrace_; 70 } GetProfilerHeader()71 auto GetProfilerHeader() 72 { 73 return profilerTraceFileHeader_; 74 } ClearNativehookData()75 auto ClearNativehookData() 76 { 77 htraceNativeHookParser_->FinishSplitNativeHook(); 78 } GetDataSourceType()79 auto GetDataSourceType() 80 { 81 return dataSourceType_; 82 } GetJsMemoryData()83 auto GetJsMemoryData() 84 { 85 return jsMemoryParser_.get(); 86 } GetArkTsConfigData()87 auto GetArkTsConfigData() 88 { 89 return arkTsConfigData_; 90 } ClearTraceDataHtrace()91 auto ClearTraceDataHtrace() 92 { 93 perfDataParser_->ClearPerfSplitResult(); 94 ebpfDataParser_->ClearEbpfSplitResult(); 95 processedDataLen_ = 0; 96 perfProcessedLen_ = 0; 97 splitFileOffset_ = 0; 98 hasGotHeader_ = false; 99 hasInitEbpfPublicData_ = false; 100 parsedEbpfOver_ = false; 101 return mTraceDataHtrace_.clear(); 102 } GetPerfSplitResult()103 const auto& GetPerfSplitResult() 104 { 105 return perfDataParser_->GetPerfSplitResult(); 106 } GetEbpfDataParser()107 const auto& GetEbpfDataParser() 108 { 109 return ebpfDataParser_; 110 } 111 void WaitForParserSplitedHtraceEnd(); 112 113 private: 114 bool ParseDataRecursively(std::deque<uint8_t>::iterator& packagesBegin, size_t& currentLength); 115 bool ParseHiperfData(std::deque<uint8_t>::iterator& packagesBegin, size_t& currentLength); 116 void ParseTraceDataItem(const std::string& buffer) override; 117 void FilterData(HtraceDataSegment& seg, bool isSplitFile); 118 void ParserData(HtraceDataSegment& dataSeg, bool isSplitFile); 119 120 private: 121 #if IS_WASM 122 bool ParseSDKData(); 123 #endif 124 void InitPluginNameIndex(); 125 bool GetHeaderAndUpdateLengthMark(std::deque<uint8_t>::iterator& packagesBegin, size_t& currentLength); 126 bool ParseSegLengthAndEnsureSegDataEnough(std::deque<uint8_t>::iterator& packagesBegin, size_t& currentLength); 127 void ParseMemory(const ProtoReader::ProfilerPluginData_Reader& pluginDataZero, HtraceDataSegment& dataSeg); 128 void ParseMemoryConfig(HtraceDataSegment& dataSeg, const ProtoReader::ProfilerPluginData_Reader& pluginDataZero); 129 void ParseHilog(HtraceDataSegment& dataSeg); 130 void ParseFtrace(HtraceDataSegment& dataSeg); 131 void ParseFPS(HtraceDataSegment& dataSeg); 132 void ParseCpuUsage(HtraceDataSegment& dataSeg); 133 void ParseNetwork(HtraceDataSegment& dataSeg); 134 void ParseDiskIO(HtraceDataSegment& dataSeg); 135 void ParseProcess(HtraceDataSegment& dataSeg); 136 void ParseHisysevent(HtraceDataSegment& dataSeg); 137 void ParseHisyseventConfig(HtraceDataSegment& dataSeg); 138 void ParseJSMemory(HtraceDataSegment& dataSeg, bool isSplitFile); 139 void ParseNativeHookConfig(HtraceDataSegment& dataSeg); 140 void ParseNativeHook(HtraceDataSegment& dataSeg, bool isSplitFile); 141 void ParseJSMemoryConfig(HtraceDataSegment& dataSeg); 142 void ParseThread(); 143 int32_t GetNextSegment(); 144 void FilterThread(); 145 bool CalcEbpfCutOffset(std::deque<uint8_t>::iterator& packagesBegin, size_t& currentLength); 146 bool SpliteConfigData(const std::string& pluginName, const HtraceDataSegment& dataSeg); 147 bool InitProfilerTraceFileHeader(); 148 void ParseDataByPluginName(HtraceDataSegment& dataSeg, 149 DataIndex pulginNameIndex, 150 const ProtoReader::ProfilerPluginData_Reader& pluginDataZero, 151 bool isSplitFile); 152 bool SpliteDataBySegment(DataIndex pluginNameIndex, HtraceDataSegment& dataSeg); 153 ProfilerTraceFileHeader profilerTraceFileHeader_; 154 uint32_t profilerDataType_ = ProfilerTraceFileHeader::UNKNOW_TYPE; 155 uint64_t profilerDataLength_ = 0; 156 ProfilerPluginDataHeader profilerPluginData_; 157 uint64_t htraceCurentLength_ = 0; 158 char standalonePluginName_[ProfilerTraceFileHeader::PLUGIN_MODULE_NAME_MAX + 1] = ""; 159 bool hasGotSegLength_ = false; 160 bool hasGotHeader_ = false; 161 uint32_t nextLength_ = 0; 162 const size_t packetSegLength_ = 4; 163 const size_t packetHeaderLength_ = 1024; 164 TraceDataCache* traceDataCache_; 165 std::unique_ptr<HtraceCpuDetailParser> htraceCpuDetailParser_; 166 std::unique_ptr<HtraceSymbolsDetailParser> htraceSymbolsDetailParser_; 167 std::unique_ptr<HtraceMemParser> htraceMemParser_; 168 std::unique_ptr<HtraceClockDetailParser> htraceClockDetailParser_; 169 std::unique_ptr<HtraceHiLogParser> htraceHiLogParser_; 170 std::unique_ptr<HtraceNativeHookParser> htraceNativeHookParser_; 171 std::unique_ptr<HtraceHidumpParser> htraceHidumpParser_; 172 std::unique_ptr<HtraceCpuDataParser> cpuUsageParser_; 173 std::unique_ptr<HtraceNetworkParser> networkParser_; 174 std::unique_ptr<HtraceDiskIOParser> diskIOParser_; 175 std::unique_ptr<HtraceProcessParser> processParser_; 176 std::unique_ptr<HtraceHisyseventParser> hisyseventParser_; 177 std::unique_ptr<HtraceJSMemoryParser> jsMemoryParser_; 178 std::unique_ptr<PerfDataParser> perfDataParser_; 179 std::unique_ptr<EbpfDataParser> ebpfDataParser_; 180 std::unique_ptr<HtraceDataSegment[]> dataSegArray_; 181 std::atomic<bool> filterThreadStarted_{false}; 182 const int32_t maxSegArraySize = 10000; 183 int32_t rawDataHead_ = 0; 184 bool toExit_ = false; 185 bool exited_ = false; 186 int32_t filterHead_ = 0; 187 int32_t parseHead_ = 0; 188 size_t htraceLength_ = 1024; 189 const int32_t sleepDur_ = 100; 190 bool parseThreadStarted_ = false; 191 int32_t parserThreadCount_ = 0; 192 std::mutex htraceDataSegMux_ = {}; 193 ClockId dataSourceTypeTraceClockid_ = TS_CLOCK_UNKNOW; 194 ClockId dataSourceTypeMemClockid_ = TS_CLOCK_UNKNOW; 195 ClockId dataSourceTypeHilogClockid_ = TS_CLOCK_UNKNOW; 196 ClockId dataSourceTypeNativeHookClockid_ = TS_CLOCK_UNKNOW; 197 ClockId dataSourceTypeFpsClockid_ = TS_CLOCK_UNKNOW; 198 ClockId dataSourceTypeNetworkClockid_ = TS_CLOCK_UNKNOW; 199 ClockId dataSourceTypeDiskioClockid_ = TS_CLOCK_UNKNOW; 200 ClockId dataSourceTypeCpuClockid_ = TS_CLOCK_UNKNOW; 201 ClockId dataSourceTypeProcessClockid_ = TS_CLOCK_UNKNOW; 202 ClockId dataSourceTypeHisyseventClockid_ = TS_CLOCK_UNKNOW; 203 ClockId dataSourceTypeJSMemoryClockid_ = TS_CLOCK_UNKNOW; 204 std::vector<std::unique_ptr<SymbolsFile>> symbolsFiles_; 205 std::map<int32_t, int32_t> mTraceDataHtrace_ = {}; 206 std::string traceDataHtrace_ = ""; 207 uint64_t splitFileOffset_ = 0; 208 uint64_t processedDataLen_ = 0; 209 uint64_t perfProcessedLen_ = 0; 210 uint64_t parsedFileOffset_ = 0; 211 bool hasInitEbpfPublicData_ = false; 212 bool parsedEbpfOver_ = false; 213 uint32_t dataSourceType_ = INVALID_UINT32; 214 std::string arkTsConfigData_ = ""; 215 std::string lenBuffer_ = ""; 216 std::set<DataIndex> nativeHookPluginIndex_ = {}; 217 std::set<DataIndex> ftracePluginIndex_ = {}; 218 std::set<DataIndex> hilogPluginIndex_ = {}; 219 DataIndex hisyseventPluginIndex_; 220 DataIndex nativeHookConfigIndex_; 221 DataIndex memPluginIndex_; 222 std::set<DataIndex> hidumpPluginIndex_ = {}; 223 DataIndex cpuPluginIndex_; 224 DataIndex networkPluginIndex_; 225 DataIndex diskioPluginIndex_; 226 DataIndex processPluginIndex_; 227 DataIndex hisyseventPluginConfigIndex_; 228 DataIndex arktsPluginIndex_; 229 DataIndex arktsPluginConfigIndex_; 230 DataIndex memoryPluginConfigIndex_; 231 std::set<DataIndex> supportPluginNameIndex_ = {}; 232 }; 233 } // namespace TraceStreamer 234 } // namespace SysTuning 235 236 #endif // HTRACE_PARSER_H_ 237