blob: 02d93c3caa19c5ddaaf4dcdaf8cfde7741b22c8d [file] [log] [blame]
Finn Williamse63a0262019-10-22 10:30:49 +01001//
2// Copyright © 2019 Arm Ltd. All rights reserved.
3// SPDX-License-Identifier: MIT
4//
5
Finn Williams8a2b4682020-02-26 10:25:26 +00006#include <TimelineCaptureCommandHandler.hpp>
7#include <TimelineDirectoryCaptureCommandHandler.hpp>
8#include <TimelineDecoder.hpp>
Finn Williamse63a0262019-10-22 10:30:49 +01009
10#include <CommandHandlerFunctor.hpp>
11#include <ProfilingService.hpp>
12#include <PacketBuffer.hpp>
13#include <TimelinePacketWriterFactory.hpp>
14
15#include <boost/test/test_tools.hpp>
16#include <boost/test/unit_test_suite.hpp>
17
18BOOST_AUTO_TEST_SUITE(TimelineDecoderTests)
19
20using namespace armnn;
Finn Williams8a2b4682020-02-26 10:25:26 +000021using namespace timelinedecoder;
Finn Williamse63a0262019-10-22 10:30:49 +010022
23void SendTimelinePacketToCommandHandler(const unsigned char* packetBuffer,
24 profiling::CommandHandlerFunctor &CommandHandler)
25{
26 uint32_t uint32_t_size = sizeof(uint32_t);
27 unsigned int offset = 0;
28
29 uint32_t header[2];
30 header[0] = profiling::ReadUint32(packetBuffer, offset);
31 offset += uint32_t_size;
32 header[1] = profiling::ReadUint32(packetBuffer, offset);
33 offset += uint32_t_size;
Finn Williamse63a0262019-10-22 10:30:49 +010034 uint32_t PacketDataLength = header[1] & 0x00FFFFFF;
35
Matteo Martincigh34a407d2019-11-06 15:30:54 +000036 auto uniquePacketData = std::make_unique<unsigned char[]>(PacketDataLength);
Finn Williamse63a0262019-10-22 10:30:49 +010037 std::memcpy(uniquePacketData.get(), packetBuffer + offset, PacketDataLength);
38
Matteo Martincigh34a407d2019-11-06 15:30:54 +000039 armnn::profiling::Packet packet(header[0], PacketDataLength, uniquePacketData);
40
41 BOOST_CHECK(std::memcmp(packetBuffer + offset, packet.GetData(), packet.GetLength()) == 0);
Finn Williamse63a0262019-10-22 10:30:49 +010042
43 CommandHandler(packet);
44}
45
Finn Williams510f6182020-02-21 11:14:08 +000046void PushEntity(TimelineDecoder::Model& model, const ITimelineDecoder::Entity entity)
47{
48 model.m_Entities.emplace_back(entity);
49}
50
51void PushEventClass(TimelineDecoder::Model& model, const ITimelineDecoder::EventClass eventClass)
52{
53 model.m_EventClasses.emplace_back(eventClass);
54}
55
56void PushEvent(TimelineDecoder::Model& model, const ITimelineDecoder::Event event)
57{
58 model.m_Events.emplace_back(event);
59}
60
61void PushLabel(TimelineDecoder::Model& model, const ITimelineDecoder::Label label)
62{
63 model.m_Labels.emplace_back(label);
64}
65
66void PushRelationship(TimelineDecoder::Model& model, const ITimelineDecoder::Relationship relationship)
67{
68 model.m_Relationships.emplace_back(relationship);
69}
70
Matteo Martincigh34a407d2019-11-06 15:30:54 +000071BOOST_AUTO_TEST_CASE(TimelineDirectoryTest)
Finn Williamse63a0262019-10-22 10:30:49 +010072{
Matteo Martincigh34a407d2019-11-06 15:30:54 +000073 uint32_t uint8_t_size = sizeof(uint8_t);
Finn Williamse63a0262019-10-22 10:30:49 +010074 uint32_t uint32_t_size = sizeof(uint32_t);
Matteo Martincigh34a407d2019-11-06 15:30:54 +000075 uint32_t uint64_t_size = sizeof(uint64_t);
76 uint32_t threadId_size = sizeof(std::thread::id);
Finn Williamse63a0262019-10-22 10:30:49 +010077
78 profiling::BufferManager bufferManager(5);
79 profiling::TimelinePacketWriterFactory timelinePacketWriterFactory(bufferManager);
80
81 std::unique_ptr<profiling::ISendTimelinePacket> sendTimelinePacket =
82 timelinePacketWriterFactory.GetSendTimelinePacket();
83
84 profiling::PacketVersionResolver packetVersionResolver;
85
Finn Williams8a2b4682020-02-26 10:25:26 +000086 TimelineDirectoryCaptureCommandHandler timelineDirectoryCaptureCommandHandler(
Finn Williamse63a0262019-10-22 10:30:49 +010087 1, 0, packetVersionResolver.ResolvePacketVersion(1, 0).GetEncodedValue(), true);
88
89 sendTimelinePacket->SendTimelineMessageDirectoryPackage();
90 sendTimelinePacket->Commit();
91
92 std::vector<profiling::SwTraceMessage> swTraceBufferMessages;
93
94 unsigned int offset = uint32_t_size * 2;
95
96 std::unique_ptr<profiling::IPacketBuffer> packetBuffer = bufferManager.GetReadableBuffer();
97
Matteo Martincigh34a407d2019-11-06 15:30:54 +000098 uint8_t readStreamVersion = ReadUint8(packetBuffer, offset);
99 BOOST_CHECK(readStreamVersion == 4);
100 offset += uint8_t_size;
101 uint8_t readPointerBytes = ReadUint8(packetBuffer, offset);
102 BOOST_CHECK(readPointerBytes == uint64_t_size);
103 offset += uint8_t_size;
104 uint8_t readThreadIdBytes = ReadUint8(packetBuffer, offset);
105 BOOST_CHECK(readThreadIdBytes == threadId_size);
106 offset += uint8_t_size;
107
Finn Williamse63a0262019-10-22 10:30:49 +0100108 uint32_t declarationSize = profiling::ReadUint32(packetBuffer, offset);
109 offset += uint32_t_size;
110 for(uint32_t i = 0; i < declarationSize; ++i)
111 {
112 swTraceBufferMessages.push_back(profiling::ReadSwTraceMessage(packetBuffer->GetReadableData(), offset));
113 }
114
115 SendTimelinePacketToCommandHandler(packetBuffer->GetReadableData(), timelineDirectoryCaptureCommandHandler);
116
117 for(uint32_t index = 0; index < declarationSize; ++index)
118 {
119 profiling::SwTraceMessage& bufferMessage = swTraceBufferMessages[index];
120 profiling::SwTraceMessage& handlerMessage = timelineDirectoryCaptureCommandHandler.m_SwTraceMessages[index];
121
Matteo Martincigh34a407d2019-11-06 15:30:54 +0000122 BOOST_CHECK(bufferMessage.m_Name == handlerMessage.m_Name);
123 BOOST_CHECK(bufferMessage.m_UiName == handlerMessage.m_UiName);
124 BOOST_CHECK(bufferMessage.m_Id == handlerMessage.m_Id);
Finn Williamse63a0262019-10-22 10:30:49 +0100125
Matteo Martincigh34a407d2019-11-06 15:30:54 +0000126 BOOST_CHECK(bufferMessage.m_ArgTypes.size() == handlerMessage.m_ArgTypes.size());
127 for(uint32_t i = 0; i < bufferMessage.m_ArgTypes.size(); ++i)
Finn Williamse63a0262019-10-22 10:30:49 +0100128 {
Matteo Martincigh34a407d2019-11-06 15:30:54 +0000129 BOOST_CHECK(bufferMessage.m_ArgTypes[i] == handlerMessage.m_ArgTypes[i]);
Finn Williamse63a0262019-10-22 10:30:49 +0100130 }
131
Matteo Martincigh34a407d2019-11-06 15:30:54 +0000132 BOOST_CHECK(bufferMessage.m_ArgNames.size() == handlerMessage.m_ArgNames.size());
133 for(uint32_t i = 0; i < bufferMessage.m_ArgNames.size(); ++i)
Finn Williamse63a0262019-10-22 10:30:49 +0100134 {
Matteo Martincigh34a407d2019-11-06 15:30:54 +0000135 BOOST_CHECK(bufferMessage.m_ArgNames[i] == handlerMessage.m_ArgNames[i]);
Finn Williamse63a0262019-10-22 10:30:49 +0100136 }
137 }
138}
139
140BOOST_AUTO_TEST_CASE(TimelineCaptureTest)
141{
Finn Williams510f6182020-02-21 11:14:08 +0000142 unsigned int threadIdSize = sizeof(std::thread::id);
Finn Williamse63a0262019-10-22 10:30:49 +0100143 profiling::BufferManager bufferManager(50);
144 profiling::TimelinePacketWriterFactory timelinePacketWriterFactory(bufferManager);
145
146 std::unique_ptr<profiling::ISendTimelinePacket> sendTimelinePacket =
147 timelinePacketWriterFactory.GetSendTimelinePacket();
148
149 profiling::PacketVersionResolver packetVersionResolver;
150
Finn Williams510f6182020-02-21 11:14:08 +0000151 TimelineDecoder timelineDecoder;
152 const TimelineDecoder::Model& model = timelineDecoder.GetModel();
Finn Williamse63a0262019-10-22 10:30:49 +0100153
Finn Williams8a2b4682020-02-26 10:25:26 +0000154 TimelineCaptureCommandHandler timelineCaptureCommandHandler(
Finn Williams510f6182020-02-21 11:14:08 +0000155 1, 1, packetVersionResolver.ResolvePacketVersion(1, 1).GetEncodedValue(), timelineDecoder, threadIdSize);
Finn Williamse63a0262019-10-22 10:30:49 +0100156
Keith Davis97da5e22020-03-05 16:25:28 +0000157 using Status = ITimelineDecoder::TimelineStatus;
158 BOOST_CHECK(timelineDecoder.SetEntityCallback(PushEntity) == Status::TimelineStatus_Success);
159 BOOST_CHECK(timelineDecoder.SetEventClassCallback(PushEventClass) == Status::TimelineStatus_Success);
160 BOOST_CHECK(timelineDecoder.SetEventCallback(PushEvent) == Status::TimelineStatus_Success);
161 BOOST_CHECK(timelineDecoder.SetLabelCallback(PushLabel) == Status::TimelineStatus_Success);
162 BOOST_CHECK(timelineDecoder.SetRelationshipCallback(PushRelationship) == Status::TimelineStatus_Success);
Finn Williamse63a0262019-10-22 10:30:49 +0100163
Keith Davis97da5e22020-03-05 16:25:28 +0000164 const uint64_t entityGuid = 111111u;
Finn Williams510f6182020-02-21 11:14:08 +0000165 const uint64_t eventClassGuid = 22222u;
166 const uint64_t timestamp = 33333u;
167 const uint64_t eventGuid = 44444u;
Finn Williamse63a0262019-10-22 10:30:49 +0100168
Finn Williams510f6182020-02-21 11:14:08 +0000169 const std::thread::id threadId = std::this_thread::get_id();
Finn Williamse63a0262019-10-22 10:30:49 +0100170
Finn Williams510f6182020-02-21 11:14:08 +0000171 // need to do a bit of work here to extract the value from threadId
172 unsigned char* uCharThreadId = new unsigned char[threadIdSize]();;
173 uint64_t uint64ThreadId;
Finn Williamse63a0262019-10-22 10:30:49 +0100174
Finn Williams510f6182020-02-21 11:14:08 +0000175 profiling::WriteBytes(uCharThreadId, 0, &threadId, threadIdSize);
Finn Williamse63a0262019-10-22 10:30:49 +0100176
Finn Williams510f6182020-02-21 11:14:08 +0000177 if (threadIdSize == 4)
178 {
179 uint64ThreadId = profiling::ReadUint32(uCharThreadId, 0);
180 }
181 else if (threadIdSize == 8)
182 {
183 uint64ThreadId = profiling::ReadUint64(uCharThreadId, 0);
184 }
185 delete[] uCharThreadId;
186
187 const uint64_t labelGuid = 66666u;
Finn Williamse63a0262019-10-22 10:30:49 +0100188 std::string labelName = "test_label";
189
Finn Williams510f6182020-02-21 11:14:08 +0000190 const uint64_t relationshipGuid = 77777u;
191 const uint64_t headGuid = 888888u;
192 const uint64_t tailGuid = 999999u;
Finn Williamse63a0262019-10-22 10:30:49 +0100193
194 for (int i = 0; i < 10; ++i)
195 {
196 // Send entity
197 sendTimelinePacket->SendTimelineEntityBinaryPacket(entityGuid);
198 sendTimelinePacket->Commit();
199 SendTimelinePacketToCommandHandler(bufferManager.GetReadableBuffer()->GetReadableData(),
200 timelineCaptureCommandHandler);
201
202 // Send event class
203 sendTimelinePacket->SendTimelineEventClassBinaryPacket(eventClassGuid);
204 sendTimelinePacket->Commit();
205 SendTimelinePacketToCommandHandler(bufferManager.GetReadableBuffer()->GetReadableData(),
206 timelineCaptureCommandHandler);
207
208 // Send event
209 sendTimelinePacket->SendTimelineEventBinaryPacket(timestamp, threadId, eventGuid);
210 sendTimelinePacket->Commit();
211 SendTimelinePacketToCommandHandler(bufferManager.GetReadableBuffer()->GetReadableData(),
212 timelineCaptureCommandHandler);
213
214 // Send label
215 sendTimelinePacket->SendTimelineLabelBinaryPacket(labelGuid, labelName);
216 sendTimelinePacket->Commit();
217 SendTimelinePacketToCommandHandler(bufferManager.GetReadableBuffer()->GetReadableData(),
218 timelineCaptureCommandHandler);
219
220 // Send relationship
221 profiling::ProfilingRelationshipType relationshipType = profiling::ProfilingRelationshipType::DataLink;
222 sendTimelinePacket->SendTimelineRelationshipBinaryPacket(relationshipType,
223 relationshipGuid,
224 headGuid,
225 tailGuid);
226 sendTimelinePacket->Commit();
227 SendTimelinePacketToCommandHandler(bufferManager.GetReadableBuffer()->GetReadableData(),
228 timelineCaptureCommandHandler);
229 }
230
Finn Williams510f6182020-02-21 11:14:08 +0000231 for (unsigned long i = 0; i < 10; ++i)
Finn Williamse63a0262019-10-22 10:30:49 +0100232 {
Finn Williams510f6182020-02-21 11:14:08 +0000233 BOOST_CHECK(model.m_Entities[i].m_Guid == entityGuid);
Finn Williamse63a0262019-10-22 10:30:49 +0100234
Finn Williams510f6182020-02-21 11:14:08 +0000235 BOOST_CHECK(model.m_EventClasses[i].m_Guid == eventClassGuid);
Finn Williamse63a0262019-10-22 10:30:49 +0100236
Finn Williams510f6182020-02-21 11:14:08 +0000237 BOOST_CHECK(model.m_Events[i].m_TimeStamp == timestamp);
238 BOOST_CHECK(model.m_Events[i].m_ThreadId == uint64ThreadId);
239 BOOST_CHECK(model.m_Events[i].m_Guid == eventGuid);
Finn Williamse63a0262019-10-22 10:30:49 +0100240
Finn Williams510f6182020-02-21 11:14:08 +0000241 BOOST_CHECK(model.m_Labels[i].m_Guid == labelGuid);
242 BOOST_CHECK(model.m_Labels[i].m_Name == labelName);
Finn Williamse63a0262019-10-22 10:30:49 +0100243
Finn Williams510f6182020-02-21 11:14:08 +0000244 BOOST_CHECK(model.m_Relationships[i].m_RelationshipType == ITimelineDecoder::RelationshipType::DataLink);
245 BOOST_CHECK(model.m_Relationships[i].m_Guid == relationshipGuid);
246 BOOST_CHECK(model.m_Relationships[i].m_HeadGuid == headGuid);
247 BOOST_CHECK(model.m_Relationships[i].m_TailGuid == tailGuid);
Finn Williamse63a0262019-10-22 10:30:49 +0100248 }
Finn Williamse63a0262019-10-22 10:30:49 +0100249}
250
251BOOST_AUTO_TEST_SUITE_END()