blob: dd70af4b39351cfa104cb11b6392ae61b6048700 [file] [log] [blame]
Keith Davis02356de2019-08-26 18:28:17 +01001//
2// Copyright © 2017 Arm Ltd. All rights reserved.
3// SPDX-License-Identifier: MIT
4//
5
6#pragma once
7
8#include "ProfilingStateMachine.hpp"
9#include "ProfilingConnectionFactory.hpp"
FinnWilliamsArmce2d9d12019-09-18 10:28:16 +010010#include "CounterDirectory.hpp"
Matteo Martincighe0e6efc2019-10-04 17:17:42 +010011#include "ICounterValues.hpp"
Matteo Martincigh54fb9572019-10-02 12:50:57 +010012#include "CommandHandler.hpp"
13#include "BufferManager.hpp"
14#include "SendCounterPacket.hpp"
Matteo Martincighe8485382019-10-10 14:08:21 +010015#include "PeriodicCounterCapture.hpp"
Matteo Martincigh54fb9572019-10-02 12:50:57 +010016#include "ConnectionAcknowledgedCommandHandler.hpp"
Matteo Martincigh8efc5002019-10-10 14:30:29 +010017#include "RequestCounterDirectoryCommandHandler.hpp"
Matteo Martincighe8485382019-10-10 14:08:21 +010018#include "PeriodicCounterSelectionCommandHandler.hpp"
Keith Davis02356de2019-08-26 18:28:17 +010019
20namespace armnn
21{
22
23namespace profiling
24{
25
Matteo Martincigh54fb9572019-10-02 12:50:57 +010026class ProfilingService : public IReadWriteCounterValues
Keith Davis02356de2019-08-26 18:28:17 +010027{
28public:
Matteo Martincigha84edee2019-10-02 12:50:57 +010029 using ExternalProfilingOptions = Runtime::CreationOptions::ExternalProfilingOptions;
Matteo Martincigh54fb9572019-10-02 12:50:57 +010030 using IProfilingConnectionFactoryPtr = std::unique_ptr<IProfilingConnectionFactory>;
Matteo Martincigha84edee2019-10-02 12:50:57 +010031 using IProfilingConnectionPtr = std::unique_ptr<IProfilingConnection>;
32 using CounterIndices = std::vector<std::atomic<uint32_t>*>;
33 using CounterValues = std::list<std::atomic<uint32_t>>;
Keith Davis02356de2019-08-26 18:28:17 +010034
Matteo Martincigha84edee2019-10-02 12:50:57 +010035 // Getter for the singleton instance
36 static ProfilingService& Instance()
37 {
38 static ProfilingService instance;
39 return instance;
40 }
41
42 // Resets the profiling options, optionally clears the profiling service entirely
43 void ResetExternalProfilingOptions(const ExternalProfilingOptions& options, bool resetProfilingService = false);
44
Matteo Martincigh54fb9572019-10-02 12:50:57 +010045 // Updates the profiling service, making it transition to a new state if necessary
46 void Update();
Keith Davis02356de2019-08-26 18:28:17 +010047
Matteo Martincigha84edee2019-10-02 12:50:57 +010048 // Getters for the profiling service state
FinnWilliamsArmce2d9d12019-09-18 10:28:16 +010049 const ICounterDirectory& GetCounterDirectory() const;
Keith Davis02356de2019-08-26 18:28:17 +010050 ProfilingState GetCurrentState() const;
Matteo Martincighe8485382019-10-10 14:08:21 +010051 bool IsCounterRegistered(uint16_t counterUid) const override;
Matteo Martincigha84edee2019-10-02 12:50:57 +010052 uint16_t GetCounterCount() const override;
53 uint32_t GetCounterValue(uint16_t counterUid) const override;
Keith Davis02356de2019-08-26 18:28:17 +010054
Matteo Martincigha84edee2019-10-02 12:50:57 +010055 // Setters for the profiling service state
56 void SetCounterValue(uint16_t counterUid, uint32_t value) override;
57 uint32_t AddCounterValue(uint16_t counterUid, uint32_t value) override;
58 uint32_t SubtractCounterValue(uint16_t counterUid, uint32_t value) override;
59 uint32_t IncrementCounterValue(uint16_t counterUid) override;
60 uint32_t DecrementCounterValue(uint16_t counterUid) override;
FinnWilliamsArmf6e534a2019-09-16 15:45:42 +010061
Keith Davis02356de2019-08-26 18:28:17 +010062private:
Matteo Martincigh54fb9572019-10-02 12:50:57 +010063 // Copy/move constructors/destructors and copy/move assignment operators are deleted
Matteo Martincigha84edee2019-10-02 12:50:57 +010064 ProfilingService(const ProfilingService&) = delete;
65 ProfilingService(ProfilingService&&) = delete;
66 ProfilingService& operator=(const ProfilingService&) = delete;
67 ProfilingService& operator=(ProfilingService&&) = delete;
Keith Davis02356de2019-08-26 18:28:17 +010068
Matteo Martincigh54fb9572019-10-02 12:50:57 +010069 // Initialization/reset functions
Matteo Martincigha84edee2019-10-02 12:50:57 +010070 void Initialize();
71 void InitializeCounterValue(uint16_t counterUid);
Matteo Martincigh54fb9572019-10-02 12:50:57 +010072 void Reset();
Matteo Martincigha84edee2019-10-02 12:50:57 +010073
Matteo Martincighe8485382019-10-10 14:08:21 +010074 // Helper function
75 void CheckCounterUid(uint16_t counterUid) const;
76
Matteo Martincigh54fb9572019-10-02 12:50:57 +010077 // Profiling service components
Matteo Martincigha84edee2019-10-02 12:50:57 +010078 ExternalProfilingOptions m_Options;
FinnWilliamsArmce2d9d12019-09-18 10:28:16 +010079 CounterDirectory m_CounterDirectory;
Matteo Martincigh54fb9572019-10-02 12:50:57 +010080 IProfilingConnectionFactoryPtr m_ProfilingConnectionFactory;
Matteo Martincigha84edee2019-10-02 12:50:57 +010081 IProfilingConnectionPtr m_ProfilingConnection;
82 ProfilingStateMachine m_StateMachine;
83 CounterIndices m_CounterIndex;
84 CounterValues m_CounterValues;
Matteo Martincigh54fb9572019-10-02 12:50:57 +010085 CommandHandlerRegistry m_CommandHandlerRegistry;
86 PacketVersionResolver m_PacketVersionResolver;
87 CommandHandler m_CommandHandler;
88 BufferManager m_BufferManager;
89 SendCounterPacket m_SendCounterPacket;
Matteo Martincighe8485382019-10-10 14:08:21 +010090 Holder m_Holder;
91 PeriodicCounterCapture m_PeriodicCounterCapture;
Matteo Martincigh54fb9572019-10-02 12:50:57 +010092 ConnectionAcknowledgedCommandHandler m_ConnectionAcknowledgedCommandHandler;
Matteo Martincigh8efc5002019-10-10 14:30:29 +010093 RequestCounterDirectoryCommandHandler m_RequestCounterDirectoryCommandHandler;
Matteo Martincighe8485382019-10-10 14:08:21 +010094 PeriodicCounterSelectionCommandHandler m_PeriodicCounterSelectionCommandHandler;
Matteo Martincigh54fb9572019-10-02 12:50:57 +010095
96protected:
97 // Default constructor/destructor kept protected for testing
98 ProfilingService()
99 : m_Options()
100 , m_CounterDirectory()
101 , m_ProfilingConnectionFactory(new ProfilingConnectionFactory())
102 , m_ProfilingConnection()
103 , m_StateMachine()
104 , m_CounterIndex()
105 , m_CounterValues()
106 , m_CommandHandlerRegistry()
107 , m_PacketVersionResolver()
108 , m_CommandHandler(1000,
109 false,
110 m_CommandHandlerRegistry,
111 m_PacketVersionResolver)
112 , m_BufferManager()
113 , m_SendCounterPacket(m_StateMachine, m_BufferManager)
Matteo Martincighe8485382019-10-10 14:08:21 +0100114 , m_PeriodicCounterCapture(m_Holder, m_SendCounterPacket, *this)
Matteo Martincigh54fb9572019-10-02 12:50:57 +0100115 , m_ConnectionAcknowledgedCommandHandler(1,
116 m_PacketVersionResolver.ResolvePacketVersion(1).GetEncodedValue(),
117 m_StateMachine)
Matteo Martincigh8efc5002019-10-10 14:30:29 +0100118 , m_RequestCounterDirectoryCommandHandler(3,
119 m_PacketVersionResolver.ResolvePacketVersion(3).GetEncodedValue(),
120 m_CounterDirectory,
121 m_SendCounterPacket,
122 m_StateMachine)
Matteo Martincighe8485382019-10-10 14:08:21 +0100123 , m_PeriodicCounterSelectionCommandHandler(4,
124 m_PacketVersionResolver.ResolvePacketVersion(4).GetEncodedValue(),
125 m_Holder,
126 m_PeriodicCounterCapture,
127 *this,
128 m_SendCounterPacket,
129 m_StateMachine)
Matteo Martincigh54fb9572019-10-02 12:50:57 +0100130 {
131 // Register the "Connection Acknowledged" command handler
132 m_CommandHandlerRegistry.RegisterFunctor(&m_ConnectionAcknowledgedCommandHandler);
Matteo Martincigh8efc5002019-10-10 14:30:29 +0100133
134 // Register the "Request Counter Directory" command handler
135 m_CommandHandlerRegistry.RegisterFunctor(&m_RequestCounterDirectoryCommandHandler);
Matteo Martincighe8485382019-10-10 14:08:21 +0100136
137 // Register the "Periodic Counter Selection" command handler
138 m_CommandHandlerRegistry.RegisterFunctor(&m_PeriodicCounterSelectionCommandHandler);
Matteo Martincigh54fb9572019-10-02 12:50:57 +0100139 }
140 ~ProfilingService() = default;
141
Matteo Martincighd0613b52019-10-09 16:47:04 +0100142 // Protected methods for testing
Matteo Martincigh54fb9572019-10-02 12:50:57 +0100143 void SwapProfilingConnectionFactory(ProfilingService& instance,
144 IProfilingConnectionFactory* other,
145 IProfilingConnectionFactory*& backup)
146 {
147 BOOST_ASSERT(instance.m_ProfilingConnectionFactory);
148 BOOST_ASSERT(other);
149
150 backup = instance.m_ProfilingConnectionFactory.release();
151 instance.m_ProfilingConnectionFactory.reset(other);
152 }
Matteo Martincighd0613b52019-10-09 16:47:04 +0100153 IProfilingConnection* GetProfilingConnection(ProfilingService& instance)
154 {
155 return instance.m_ProfilingConnection.get();
156 }
Matteo Martincigh8efc5002019-10-10 14:30:29 +0100157 void TransitionToState(ProfilingService& instance, ProfilingState newState)
158 {
159 instance.m_StateMachine.TransitionToState(newState);
160 }
Matteo Martincighe8485382019-10-10 14:08:21 +0100161 void WaitForPacketSent(ProfilingService& instance)
162 {
163 return instance.m_SendCounterPacket.WaitForPacketSent();
164 }
Keith Davis02356de2019-08-26 18:28:17 +0100165};
166
167} // namespace profiling
168
Matteo Martincigha84edee2019-10-02 12:50:57 +0100169} // namespace armnn