15c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci/* 25c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci * Copyright (C) 2018 The Android Open Source Project 35c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci * 45c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci * Licensed under the Apache License, Version 2.0 (the "License"); 55c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci * you may not use this file except in compliance with the License. 65c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci * You may obtain a copy of the License at 75c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci * 85c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci * http://www.apache.org/licenses/LICENSE-2.0 95c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci * 105c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci * Unless required by applicable law or agreed to in writing, software 115c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci * distributed under the License is distributed on an "AS IS" BASIS, 125c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 135c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci * See the License for the specific language governing permissions and 145c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci * limitations under the License. 155c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci */ 165c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci 175c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci#include "src/tracing/test/fake_packet.h" 185c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci 195c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci#include <ostream> 205c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci 215c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci#include "perfetto/base/logging.h" 225c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci#include "perfetto/protozero/proto_utils.h" 235c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci#include "perfetto/tracing/core/shared_memory_abi.h" 245c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci#include "src/tracing/core/trace_buffer.h" 255c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci 265c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucciusing protozero::proto_utils::ParseVarInt; 275c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucciusing protozero::proto_utils::WriteVarInt; 285c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci 295c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tuccinamespace perfetto { 305c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci 315c59901a5b3934c5eec083dd78645e093425d44bPrimiano TucciFakePacketFragment::FakePacketFragment(size_t size, char prefix) { 325c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci // |size| has to be at least == 2, because one byte will be taken just by the 335c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci // varint header. 345c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci PERFETTO_CHECK(size > 1); 355c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci 365c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci // Finding the |payload_size| from |size| is quite tricky: 375c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci // A packet with 127 bytes of payload requires: 385c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci // 1B header (to represent the number 127 in varint) + 127 = 128 bytes. 395c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci // A packet with 128 bytes payload requires: 405c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci // 2B header (to represent the number 128 in varint) + 128 = 130 bytes. 415c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci // So the only way to generate a packet of 129 bytes in total we need to 425c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci // generate a redundant varint header of 2 bytes + 127 bytes of payload. 435c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci if (size <= 128) { 445c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci header_[0] = static_cast<uint8_t>(size - 1); 455c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci header_size_ = 1; 465c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci payload_.resize(size - 1); 475c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci } else if (size == 129) { 485c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci header_[0] = 0x80 | 127; 495c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci header_size_ = 2; 505c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci payload_.resize(127); 515c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci } else { 525c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci WriteVarInt(size - 2, &header_[0]); 535c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci header_size_ = 2; 545c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci payload_.resize(size - 2); 555c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci } 565c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci // Fills the payload as follow: X00-X01-X02 (where X == |prefix|); 575c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci for (size_t i = 0; i < payload_.size(); i++) { 585c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci switch (i % 4) { 595c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci case 0: 605c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci payload_[i] = prefix; 615c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci break; 625c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci case 1: 635c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci payload_[i] = '0' + ((i / 4 / 10) % 10); 645c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci break; 655c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci case 2: 665c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci payload_[i] = '0' + ((i / 4) % 10); 675c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci break; 685c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci case 3: 695c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci payload_[i] = '-'; 705c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci break; 715c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci } 725c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci } 735c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci} 745c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci 755c59901a5b3934c5eec083dd78645e093425d44bPrimiano TucciFakePacketFragment::FakePacketFragment(const void* payload, 765c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci size_t payload_size) { 775c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci PERFETTO_CHECK(payload_size <= 4096 - 2); 785c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci payload_.assign(reinterpret_cast<const char*>(payload), payload_size); 795c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci uint8_t* end = WriteVarInt(payload_.size(), &header_[0]); 803cbb10a30c000fcd2cd4658dd215778422c7bbb1Primiano Tucci header_size_ = static_cast<size_t>(end - &header_[0]); 815c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci} 825c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci 835c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tuccivoid FakePacketFragment::CopyInto(std::vector<uint8_t>* data) const { 845c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci data->insert(data->end(), &header_[0], &header_[0] + header_size_); 855c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci data->insert(data->end(), payload_.begin(), payload_.end()); 865c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci} 875c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci 885c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tuccisize_t FakePacketFragment::GetSizeHeader() const { 895c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci uint64_t size = 0; 905c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci ParseVarInt(&header_[0], &header_[0] + header_size_, &size); 915c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci return static_cast<size_t>(size); 925c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci} 935c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci 945c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tuccibool FakePacketFragment::operator==(const FakePacketFragment& o) const { 955c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci if (payload_ != o.payload_) 965c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci return false; 975c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci PERFETTO_CHECK(GetSizeHeader() == o.GetSizeHeader()); 985c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci return true; 995c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci} 1005c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci 1015c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tuccistd::ostream& operator<<(std::ostream& os, const FakePacketFragment& packet) { 1025c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci return os << "{len:" << packet.payload().size() << ", payload:\"" 1035c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci << packet.payload() << "\"}"; 1045c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci} 1055c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci 1066214c8fcc26c19f1b6c9f677d353988ee3d4fac1Hector DearmanFakeChunk::FakeChunk(TraceBuffer* t, ProducerID p, WriterID w, ChunkID c) 1075c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci : trace_buffer_{t}, producer_id{p}, writer_id{w}, chunk_id{c} {} 1085c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci 1095c59901a5b3934c5eec083dd78645e093425d44bPrimiano TucciFakeChunk& FakeChunk::AddPacket(size_t size, char seed, uint8_t packet_flag) { 1105c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci PERFETTO_DCHECK(size <= 4096); 1115c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci PERFETTO_CHECK( 1125c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci !(packet_flag & 1135c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci SharedMemoryABI::ChunkHeader::kFirstPacketContinuesFromPrevChunk) || 1145c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci num_packets == 0); 1155c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci PERFETTO_CHECK( 1165c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci !(flags & SharedMemoryABI::ChunkHeader::kLastPacketContinuesOnNextChunk)); 1175c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci flags |= packet_flag; 1185c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci FakePacketFragment(size, seed).CopyInto(&data); 1195c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci num_packets++; 1205c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci return *this; 1215c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci} 1225c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci 1235c59901a5b3934c5eec083dd78645e093425d44bPrimiano TucciFakeChunk& FakeChunk::AddPacket(std::initializer_list<uint8_t> raw) { 1245c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci data.insert(data.end(), raw.begin(), raw.end()); 1255c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci num_packets++; 1265c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci return *this; 1275c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci} 1285c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci 1297b14f6565cb61ee17b4b8937073f5245e757af56Primiano TucciFakeChunk& FakeChunk::IncrementNumPackets() { 1307b14f6565cb61ee17b4b8937073f5245e757af56Primiano Tucci num_packets++; 1317b14f6565cb61ee17b4b8937073f5245e757af56Primiano Tucci return *this; 1327b14f6565cb61ee17b4b8937073f5245e757af56Primiano Tucci} 1337b14f6565cb61ee17b4b8937073f5245e757af56Primiano Tucci 1345c59901a5b3934c5eec083dd78645e093425d44bPrimiano TucciFakeChunk& FakeChunk::ClearBytes(size_t offset, size_t len) { 1355c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci PERFETTO_DCHECK(offset + len <= data.size()); 1365c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci memset(data.data() + offset, 0, len); 1375c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci return *this; 1385c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci} 1395c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci 14009db827c202e5f23895ab278b7e360ba34152d77Primiano TucciFakeChunk& FakeChunk::SetUID(uid_t u) { 14109db827c202e5f23895ab278b7e360ba34152d77Primiano Tucci uid = u; 14209db827c202e5f23895ab278b7e360ba34152d77Primiano Tucci return *this; 14309db827c202e5f23895ab278b7e360ba34152d77Primiano Tucci} 14409db827c202e5f23895ab278b7e360ba34152d77Primiano Tucci 1455c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tuccisize_t FakeChunk::CopyIntoTraceBuffer() { 14609db827c202e5f23895ab278b7e360ba34152d77Primiano Tucci trace_buffer_->CopyChunkUntrusted(producer_id, uid, writer_id, chunk_id, 1475c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci num_packets, flags, data.data(), 1485c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci data.size()); 1496214c8fcc26c19f1b6c9f677d353988ee3d4fac1Hector Dearman return data.size() + TraceBuffer::InlineChunkHeaderSize; 1505c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci} 1515c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci 1525c59901a5b3934c5eec083dd78645e093425d44bPrimiano Tucci} // namespace perfetto 153