1 /* 2 * Copyright (C) 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 * http://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 17 #ifndef SRC_TRACE_PROCESSOR_IMPORTERS_ETM_ETM_V4_STREAM_H_ 18 #define SRC_TRACE_PROCESSOR_IMPORTERS_ETM_ETM_V4_STREAM_H_ 19 20 #include <cstdint> 21 #include <optional> 22 #include <vector> 23 24 #include "perfetto/base/status.h" 25 #include "perfetto/trace_processor/trace_blob_view.h" 26 #include "src/trace_processor/importers/common/trace_parser.h" 27 #include "src/trace_processor/importers/etm/opencsd.h" 28 #include "src/trace_processor/importers/perf/aux_data_tokenizer.h" 29 #include "src/trace_processor/importers/perf/perf_data_tokenizer.h" 30 #include "src/trace_processor/tables/etm_tables_py.h" 31 32 namespace perfetto::trace_processor { 33 class TraceProcessorContext; 34 namespace etm { 35 class FrameDecoder; 36 class EtmV4Stream : public perf_importer::AuxDataStream, public ITrcDataIn { 37 public: 38 EtmV4Stream(TraceProcessorContext* context, 39 FrameDecoder* frame_decoder, 40 tables::EtmV4ConfigurationTable::Id config_id); 41 42 ~EtmV4Stream() override; 43 44 ocsd_datapath_resp_t TraceDataIn(const ocsd_datapath_op_t op, 45 const ocsd_trc_index_t index, 46 const uint32_t dataBlockSize, 47 const uint8_t* pDataBlock, 48 uint32_t* numBytesProcessed) override; 49 50 base::Status Parse(perf_importer::AuxRecord aux, TraceBlobView data) override; 51 52 void OnDataLoss(uint64_t) override; 53 base::Status NotifyEndOfStream() override; 54 55 base::Status OnItraceStartRecord( 56 perf_importer::ItraceStartRecord start) override; 57 58 private: 59 struct SessionState { SessionStateSessionState60 explicit SessionState(tables::EtmV4SessionTable::Id in_session_id) 61 : session_id(in_session_id) {} 62 tables::EtmV4SessionTable::Id session_id; 63 std::vector<TraceBlobView> traces_; 64 }; 65 66 base::Status ParseFramedData(uint64_t offset, TraceBlobView data); 67 68 void StartChunkedTrace(); 69 void WriteChunkedTrace(const uint8_t* src, uint32_t size); 70 void EndChunkedTrace(); 71 72 void StartSession(std::optional<int64_t> start_ts); 73 void AddTrace(TraceBlobView trace); 74 void EndSession(); 75 76 TraceProcessorContext* const context_; 77 FrameDecoder* const frame_decoder_; 78 tables::EtmV4ConfigurationTable::Id config_id_; 79 80 bool stream_active_ = true; 81 ocsd_trc_index_t index_ = 0; 82 std::optional<SessionState> session_; 83 84 // For framed ETM data we get data in 16B or less chunks. This buffer is used 85 // to create a contiguous memory buffer out of that. 86 // 87 // TODO(carlscab): This could probably be made more efficient but keep in mind 88 // in the case of framed data we might get "spurious" starts, that is a start 89 // followed by no data before the end. Framed ETM data usually only contains 90 // data for one stream that means all the other streams will get such spurious 91 // starts. So we delay the creation of the builder to seeing actual data 92 std::vector<uint8_t> buffer_; 93 }; 94 95 } // namespace etm 96 } // namespace perfetto::trace_processor 97 98 #endif // SRC_TRACE_PROCESSOR_IMPORTERS_ETM_ETM_V4_STREAM_H_ 99