blob: 972916104e47037c139271c39821715ca6fdbbfd [file] [log] [blame]
Matteo Martincigh830101c2019-10-22 11:07:45 +01001//
2// Copyright © 2019 Arm Ltd. All rights reserved.
3// SPDX-License-Identifier: MIT
4//
5
6#include "TimelineUtilityMethods.hpp"
7#include "ProfilingService.hpp"
Matteo Martincigh102cdbd2019-10-28 11:42:50 +00008#include "LabelsAndEventClasses.hpp"
Matteo Martincigh830101c2019-10-22 11:07:45 +01009
10namespace armnn
11{
12
13namespace profiling
14{
15
Narumol Prangnawaratdf31cfe2019-11-22 11:26:06 +000016std::unique_ptr<TimelineUtilityMethods> TimelineUtilityMethods::GetTimelineUtils()
17{
18 if (ProfilingService::Instance().IsEnabled())
19 {
20 std::unique_ptr<ISendTimelinePacket> sendTimelinepacket = ProfilingService::Instance().GetSendTimelinePacket();
21 return std::make_unique<TimelineUtilityMethods>(sendTimelinepacket);
22 }
23 else
24 {
25 std::unique_ptr<TimelineUtilityMethods> empty;
26 return empty;
27 }
28}
29
30
Matteo Martincigh102cdbd2019-10-28 11:42:50 +000031void TimelineUtilityMethods::SendWellKnownLabelsAndEventClasses()
32{
33 // Send the "name" label, this call throws in case of error
Narumol Prangnawaratdf31cfe2019-11-22 11:26:06 +000034 m_SendTimelinePacket->SendTimelineLabelBinaryPacket(LabelsAndEventClasses::NAME_GUID,
35 LabelsAndEventClasses::NAME_LABEL);
Matteo Martincigh102cdbd2019-10-28 11:42:50 +000036
37 // Send the "type" label, this call throws in case of error
Narumol Prangnawaratdf31cfe2019-11-22 11:26:06 +000038 m_SendTimelinePacket->SendTimelineLabelBinaryPacket(LabelsAndEventClasses::TYPE_GUID,
39 LabelsAndEventClasses::TYPE_LABEL);
Matteo Martincigh102cdbd2019-10-28 11:42:50 +000040
41 // Send the "index" label, this call throws in case of error
Narumol Prangnawaratdf31cfe2019-11-22 11:26:06 +000042 m_SendTimelinePacket->SendTimelineLabelBinaryPacket(LabelsAndEventClasses::INDEX_GUID,
43 LabelsAndEventClasses::INDEX_LABEL);
44
45 // Send the "backendId" label, this call throws in case of error
46 m_SendTimelinePacket->SendTimelineLabelBinaryPacket(LabelsAndEventClasses::BACKENDID_GUID,
47 LabelsAndEventClasses::BACKENDID_LABEL);
48
49 // Send the "layer" label, this call throws in case of error
50 m_SendTimelinePacket->SendTimelineLabelBinaryPacket(LabelsAndEventClasses::LAYER_GUID,
51 LabelsAndEventClasses::LAYER);
52
53 // Send the "workload" label, this call throws in case of error
54 m_SendTimelinePacket->SendTimelineLabelBinaryPacket(LabelsAndEventClasses::WORKLOAD_GUID,
55 LabelsAndEventClasses::WORKLOAD);
56
57 // Send the "network" label, this call throws in case of error
58 m_SendTimelinePacket->SendTimelineLabelBinaryPacket(LabelsAndEventClasses::NETWORK_GUID,
59 LabelsAndEventClasses::NETWORK);
60
61 // Send the "connection" label, this call throws in case of error
62 m_SendTimelinePacket->SendTimelineLabelBinaryPacket(LabelsAndEventClasses::CONNECTION_GUID,
63 LabelsAndEventClasses::CONNECTION);
Matteo Martincigh102cdbd2019-10-28 11:42:50 +000064
David Monahan6198fe02019-12-02 08:35:43 +000065 // Send the "inference" label, this call throws in case of error
66 m_SendTimelinePacket->SendTimelineLabelBinaryPacket(LabelsAndEventClasses::INFERENCE_GUID,
67 LabelsAndEventClasses::INFERENCE);
68
69 // Send the "workload_execution" label, this call throws in case of error
70 m_SendTimelinePacket->SendTimelineLabelBinaryPacket(LabelsAndEventClasses::WORKLOAD_EXECUTION_GUID,
71 LabelsAndEventClasses::WORKLOAD_EXECUTION);
72
Matteo Martincigh102cdbd2019-10-28 11:42:50 +000073 // Send the "start of life" event class, this call throws in case of error
Narumol Prangnawaratdf31cfe2019-11-22 11:26:06 +000074 m_SendTimelinePacket->SendTimelineEventClassBinaryPacket(LabelsAndEventClasses::ARMNN_PROFILING_SOL_EVENT_CLASS);
Matteo Martincigh102cdbd2019-10-28 11:42:50 +000075
76 // Send the "end of life" event class, this call throws in case of error
Narumol Prangnawaratdf31cfe2019-11-22 11:26:06 +000077 m_SendTimelinePacket->SendTimelineEventClassBinaryPacket(LabelsAndEventClasses::ARMNN_PROFILING_EOL_EVENT_CLASS);
Matteo Martincigh102cdbd2019-10-28 11:42:50 +000078}
79
Narumol Prangnawaratd034e082019-10-30 12:48:31 +000080ProfilingDynamicGuid TimelineUtilityMethods::CreateNamedTypedEntity(const std::string& name, const std::string& type)
81{
82 // Check that the entity name is valid
83 if (name.empty())
84 {
85 throw InvalidArgumentException("Invalid entity name, the entity name cannot be empty");
86 }
87
88 // Check that the entity type is valid
89 if (type.empty())
90 {
91 throw InvalidArgumentException("Invalid entity type, the entity type cannot be empty");
92 }
93
94 // Generate dynamic GUID of the entity
95 ProfilingDynamicGuid entityGuid = ProfilingService::Instance().NextGuid();
96
Narumol Prangnawarat234d5252019-11-19 15:49:18 +000097 CreateNamedTypedEntity(entityGuid, name, type);
98
99 return entityGuid;
100}
101
Narumol Prangnawaratdf31cfe2019-11-22 11:26:06 +0000102void TimelineUtilityMethods::CreateNamedTypedEntity(ProfilingGuid entityGuid,
Narumol Prangnawarat234d5252019-11-19 15:49:18 +0000103 const std::string& name,
104 const std::string& type)
105{
106 // Check that the entity name is valid
107 if (name.empty())
108 {
109 throw InvalidArgumentException("Invalid entity name, the entity name cannot be empty");
110 }
111
112 // Check that the entity type is valid
113 if (type.empty())
114 {
115 throw InvalidArgumentException("Invalid entity type, the entity type cannot be empty");
116 }
117
Narumol Prangnawaratd034e082019-10-30 12:48:31 +0000118 // Send Entity Binary Packet of the entity to the external profiling service
Narumol Prangnawaratdf31cfe2019-11-22 11:26:06 +0000119 m_SendTimelinePacket->SendTimelineEntityBinaryPacket(entityGuid);
Narumol Prangnawaratd034e082019-10-30 12:48:31 +0000120
121 // Create name entity and send the relationship of the entity with the given name
122 NameEntity(entityGuid, name);
123
124 // Create type entity and send the relationship of the entity with the given type
125 TypeEntity(entityGuid, type);
Narumol Prangnawaratd034e082019-10-30 12:48:31 +0000126}
127
Narumol Prangnawaratdf31cfe2019-11-22 11:26:06 +0000128void TimelineUtilityMethods::CreateNamedTypedEntity(ProfilingGuid entityGuid,
129 const std::string& name,
130 ProfilingStaticGuid typeGuid)
131{
132 // Check that the entity name is valid
133 if (name.empty())
134 {
135 throw InvalidArgumentException("Invalid entity name, the entity name cannot be empty");
136 }
137
138 // Send Entity Binary Packet of the entity to the external profiling service
139 m_SendTimelinePacket->SendTimelineEntityBinaryPacket(entityGuid);
140
141 // Create name entity and send the relationship of the entity with the given name
142 NameEntity(entityGuid, name);
143
144 // Create type entity and send the relationship of the entity with the given type
145 MarkEntityWithType(entityGuid, typeGuid);
146}
147
Matteo Martincigh830101c2019-10-22 11:07:45 +0100148ProfilingStaticGuid TimelineUtilityMethods::DeclareLabel(const std::string& labelName)
149{
150 // Check that the label name is valid
151 if (labelName.empty())
152 {
153 // The label name is invalid
154 throw InvalidArgumentException("Invalid label name, the label name cannot be empty");
155 }
156
157 // Generate a static GUID for the given label name
158 ProfilingStaticGuid labelGuid = ProfilingService::Instance().GenerateStaticId(labelName);
159
160 // Send the new label to the external profiling service, this call throws in case of error
Narumol Prangnawaratdf31cfe2019-11-22 11:26:06 +0000161 m_SendTimelinePacket->SendTimelineLabelBinaryPacket(labelGuid, labelName);
Matteo Martincigh830101c2019-10-22 11:07:45 +0100162
163 return labelGuid;
164}
165
Narumol Prangnawaratdf31cfe2019-11-22 11:26:06 +0000166void TimelineUtilityMethods::MarkEntityWithLabel(ProfilingGuid entityGuid,
167 const std::string& labelName,
168 ProfilingStaticGuid labelTypeGuid)
Matteo Martincighc0401992019-10-28 15:24:34 +0000169{
Narumol Prangnawaratdf31cfe2019-11-22 11:26:06 +0000170 // Check that the label name is valid
171 if (labelName.empty())
Matteo Martincighc0401992019-10-28 15:24:34 +0000172 {
Narumol Prangnawaratdf31cfe2019-11-22 11:26:06 +0000173 // The label name is invalid
Matteo Martincighc0401992019-10-28 15:24:34 +0000174 throw InvalidArgumentException("Invalid entity name, the entity name cannot be empty");
175 }
176
Narumol Prangnawaratdf31cfe2019-11-22 11:26:06 +0000177 // Declare a label with the label's name, this call throws in case of error
178 ProfilingStaticGuid labelGuid = DeclareLabel(labelName);
Matteo Martincighc0401992019-10-28 15:24:34 +0000179
180 // Generate a GUID for the label relationship
Narumol Prangnawarat94a30882019-10-30 12:48:31 +0000181 ProfilingDynamicGuid relationshipGuid = ProfilingService::Instance().NextGuid();
Matteo Martincighc0401992019-10-28 15:24:34 +0000182
183 // Send the new label link to the external profiling service, this call throws in case of error
Narumol Prangnawaratdf31cfe2019-11-22 11:26:06 +0000184 m_SendTimelinePacket->SendTimelineRelationshipBinaryPacket(ProfilingRelationshipType::LabelLink,
185 relationshipGuid,
186 entityGuid,
187 labelGuid);
Matteo Martincighc0401992019-10-28 15:24:34 +0000188
189 // Generate a GUID for the label relationship
Narumol Prangnawarat94a30882019-10-30 12:48:31 +0000190 ProfilingDynamicGuid relationshipLabelGuid = ProfilingService::Instance().NextGuid();
Matteo Martincighc0401992019-10-28 15:24:34 +0000191
192 // Send the new label link to the external profiling service, this call throws in case of error
Narumol Prangnawaratdf31cfe2019-11-22 11:26:06 +0000193 m_SendTimelinePacket->SendTimelineRelationshipBinaryPacket(ProfilingRelationshipType::LabelLink,
194 relationshipLabelGuid,
195 relationshipGuid,
196 labelTypeGuid);
197}
198
199void TimelineUtilityMethods::MarkEntityWithType(ProfilingGuid entityGuid,
200 ProfilingStaticGuid typeNameGuid)
201{
202 // Generate a GUID for the label relationship
203 ProfilingDynamicGuid relationshipGuid = ProfilingService::Instance().NextGuid();
204
205 // Send the new label link to the external profiling service, this call throws in case of error
206 m_SendTimelinePacket->SendTimelineRelationshipBinaryPacket(ProfilingRelationshipType::LabelLink,
207 relationshipGuid,
208 entityGuid,
209 typeNameGuid);
210
211 // Generate a GUID for the label relationship
212 ProfilingDynamicGuid relationshipLabelGuid = ProfilingService::Instance().NextGuid();
213
214 // Send the new label link to the external profiling service, this call throws in case of error
215 m_SendTimelinePacket->SendTimelineRelationshipBinaryPacket(ProfilingRelationshipType::LabelLink,
216 relationshipLabelGuid,
217 relationshipGuid,
218 LabelsAndEventClasses::TYPE_GUID);
Matteo Martincighc0401992019-10-28 15:24:34 +0000219}
220
Narumol Prangnawaratd034e082019-10-30 12:48:31 +0000221void TimelineUtilityMethods::NameEntity(ProfilingGuid entityGuid, const std::string& name)
222{
Narumol Prangnawaratdf31cfe2019-11-22 11:26:06 +0000223 MarkEntityWithLabel(entityGuid, name, LabelsAndEventClasses::NAME_GUID);
Narumol Prangnawaratd034e082019-10-30 12:48:31 +0000224}
225
226void TimelineUtilityMethods::TypeEntity(ProfilingGuid entityGuid, const std::string& type)
227{
Narumol Prangnawaratdf31cfe2019-11-22 11:26:06 +0000228 MarkEntityWithLabel(entityGuid, type, LabelsAndEventClasses::TYPE_GUID);
Narumol Prangnawaratd034e082019-10-30 12:48:31 +0000229}
230
Narumol Prangnawarat94a30882019-10-30 12:48:31 +0000231ProfilingDynamicGuid TimelineUtilityMethods::CreateNamedTypedChildEntity(ProfilingGuid parentEntityGuid,
232 const std::string& entityName,
233 const std::string& entityType)
234{
235 // Check that the entity name is valid
236 if (entityName.empty())
237 {
238 // The entity name is invalid
239 throw InvalidArgumentException("Invalid entity name, the entity name cannot be empty");
240 }
241
242 // Check that the entity type is valid
243 if (entityType.empty())
244 {
245 // The entity type is invalid
246 throw InvalidArgumentException("Invalid entity type, the entity type cannot be empty");
247 }
248
249 // Create a named type entity from the given name and type, this call throws in case of error
250 ProfilingDynamicGuid childEntityGuid = CreateNamedTypedEntity(entityName, entityType);
251
252 // Generate a GUID for the retention link relationship
253 ProfilingDynamicGuid retentionLinkGuid = ProfilingService::Instance().NextGuid();
254
255 // Send the new retention link to the external profiling service, this call throws in case of error
Narumol Prangnawaratdf31cfe2019-11-22 11:26:06 +0000256 m_SendTimelinePacket->SendTimelineRelationshipBinaryPacket(ProfilingRelationshipType::RetentionLink,
257 retentionLinkGuid,
258 parentEntityGuid,
259 childEntityGuid);
Narumol Prangnawarat94a30882019-10-30 12:48:31 +0000260
261 return childEntityGuid;
262}
263
Narumol Prangnawaratdf31cfe2019-11-22 11:26:06 +0000264void TimelineUtilityMethods::CreateNamedTypedChildEntity(ProfilingGuid childEntityGuid,
Narumol Prangnawarat234d5252019-11-19 15:49:18 +0000265 ProfilingGuid parentEntityGuid,
266 const std::string& entityName,
267 const std::string& entityType)
268{
269 // Check that the entity name is valid
270 if (entityName.empty())
271 {
272 // The entity name is invalid
273 throw InvalidArgumentException("Invalid entity name, the entity name cannot be empty");
274 }
275
276 // Check that the entity type is valid
277 if (entityType.empty())
278 {
279 // The entity type is invalid
280 throw InvalidArgumentException("Invalid entity type, the entity type cannot be empty");
281 }
282
283 // Create a named type entity from the given guid, name and type, this call throws in case of error
284 CreateNamedTypedEntity(childEntityGuid, entityName, entityType);
285
286 // Generate a GUID for the retention link relationship
287 ProfilingDynamicGuid retentionLinkGuid = ProfilingService::Instance().NextGuid();
288
289 // Send the new retention link to the external profiling service, this call throws in case of error
Narumol Prangnawaratdf31cfe2019-11-22 11:26:06 +0000290 m_SendTimelinePacket->SendTimelineRelationshipBinaryPacket(ProfilingRelationshipType::RetentionLink,
291 retentionLinkGuid,
292 parentEntityGuid,
293 childEntityGuid);
294}
295
296void TimelineUtilityMethods::CreateNamedTypedChildEntity(ProfilingGuid childEntityGuid,
297 ProfilingGuid parentEntityGuid,
298 const std::string& entityName,
299 ProfilingStaticGuid typeGuid)
300{
301 // Check that the entity name is valid
302 if (entityName.empty())
303 {
304 // The entity name is invalid
305 throw InvalidArgumentException("Invalid entity name, the entity name cannot be empty");
306 }
307
308 // Create a named type entity from the given guid, name and type, this call throws in case of error
309 CreateNamedTypedEntity(childEntityGuid, entityName, typeGuid);
310
311 // Generate a GUID for the retention link relationship
312 ProfilingDynamicGuid retentionLinkGuid = ProfilingService::Instance().NextGuid();
313
314 // Send the new retention link to the external profiling service, this call throws in case of error
315 m_SendTimelinePacket->SendTimelineRelationshipBinaryPacket(ProfilingRelationshipType::RetentionLink,
316 retentionLinkGuid,
317 parentEntityGuid,
318 childEntityGuid);
319}
320
321ProfilingDynamicGuid TimelineUtilityMethods::CreateRelationship(ProfilingRelationshipType relationshipType,
322 ProfilingGuid headGuid,
323 ProfilingGuid tailGuid)
324{
325 // Generate a GUID for the relationship
326 ProfilingDynamicGuid relationshipGuid = ProfilingService::Instance().NextGuid();
327
328 // Send the new retention link to the external profiling service, this call throws in case of error
329 m_SendTimelinePacket->SendTimelineRelationshipBinaryPacket(relationshipType,
330 relationshipGuid,
331 headGuid,
332 tailGuid);
333 return relationshipGuid;
334}
335
336ProfilingDynamicGuid TimelineUtilityMethods::CreateConnectionRelationship(ProfilingRelationshipType relationshipType,
337 ProfilingGuid headGuid,
338 ProfilingGuid tailGuid)
339{
340 // Generate a GUID for the relationship
341 ProfilingDynamicGuid relationshipGuid = ProfilingService::Instance().NextGuid();
342
343 // Send the new retention link to the external profiling service, this call throws in case of error
344 m_SendTimelinePacket->SendTimelineRelationshipBinaryPacket(relationshipType,
345 relationshipGuid,
346 headGuid,
347 tailGuid);
348
349 MarkEntityWithType(relationshipGuid, LabelsAndEventClasses::CONNECTION_GUID);
350 return relationshipGuid;
351}
352
353void TimelineUtilityMethods::CreateTypedEntity(ProfilingGuid entityGuid, ProfilingStaticGuid entityTypeGuid)
354{
355 // Send Entity Binary Packet of the entity to the external profiling service
356 m_SendTimelinePacket->SendTimelineEntityBinaryPacket(entityGuid);
357
358 // Create type entity and send the relationship of the entity with the given type
359 MarkEntityWithType(entityGuid, entityTypeGuid);
Narumol Prangnawarat234d5252019-11-19 15:49:18 +0000360}
361
Matteo Martincigh5dc816e2019-11-04 14:05:28 +0000362ProfilingDynamicGuid TimelineUtilityMethods::RecordEvent(ProfilingGuid entityGuid, ProfilingStaticGuid eventClassGuid)
363{
364 // Take a timestamp
365 uint64_t timestamp = GetTimestamp();
366
367 // Get the thread id
368 std::thread::id threadId = std::this_thread::get_id();
369
370 // Generate a GUID for the event
371 ProfilingDynamicGuid eventGuid = ProfilingService::Instance().NextGuid();
372
373 // Send the new timeline event to the external profiling service, this call throws in case of error
Narumol Prangnawaratdf31cfe2019-11-22 11:26:06 +0000374 m_SendTimelinePacket->SendTimelineEventBinaryPacket(timestamp, threadId, eventGuid);
Matteo Martincigh5dc816e2019-11-04 14:05:28 +0000375
376 // Generate a GUID for the execution link
377 ProfilingDynamicGuid executionLinkId = ProfilingService::Instance().NextGuid();
378
379 // Send the new execution link to the external profiling service, this call throws in case of error
Narumol Prangnawaratdf31cfe2019-11-22 11:26:06 +0000380 m_SendTimelinePacket->SendTimelineRelationshipBinaryPacket(ProfilingRelationshipType::ExecutionLink,
381 executionLinkId,
382 entityGuid,
383 eventGuid);
Matteo Martincigh5dc816e2019-11-04 14:05:28 +0000384
385 // Generate a GUID for the data relationship link
386 ProfilingDynamicGuid eventClassLinkId = ProfilingService::Instance().NextGuid();
387
388 // Send the new data relationship link to the external profiling service, this call throws in case of error
Narumol Prangnawaratdf31cfe2019-11-22 11:26:06 +0000389 m_SendTimelinePacket->SendTimelineRelationshipBinaryPacket(ProfilingRelationshipType::DataLink,
390 eventClassLinkId,
391 eventGuid,
392 eventClassGuid);
Matteo Martincigh5dc816e2019-11-04 14:05:28 +0000393
394 return eventGuid;
395}
396
David Monahan6198fe02019-12-02 08:35:43 +0000397ProfilingDynamicGuid TimelineUtilityMethods::RecordWorkloadInferenceAndStartOfLifeEvent(ProfilingGuid workloadGuid,
398 ProfilingGuid inferenceGuid)
399{
400 ProfilingDynamicGuid workloadInferenceGuid = ProfilingService::Instance().NextGuid();
401 CreateTypedEntity(workloadInferenceGuid, LabelsAndEventClasses::WORKLOAD_EXECUTION_GUID);
402 CreateRelationship(ProfilingRelationshipType::RetentionLink, inferenceGuid, workloadInferenceGuid);
403 CreateRelationship(ProfilingRelationshipType::RetentionLink, workloadGuid, workloadInferenceGuid);
404 RecordEvent(workloadInferenceGuid, LabelsAndEventClasses::ARMNN_PROFILING_SOL_EVENT_CLASS);
405 return workloadInferenceGuid;
406}
407
408void TimelineUtilityMethods::RecordEndOfLifeEvent(ProfilingGuid entityGuid)
409{
410 RecordEvent(entityGuid, LabelsAndEventClasses::ARMNN_PROFILING_EOL_EVENT_CLASS);
411}
412
Matteo Martincigh830101c2019-10-22 11:07:45 +0100413} // namespace profiling
414
415} // namespace armnn