• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 //
2 // Copyright © 2019 Arm Ltd and Contributors. All rights reserved.
3 // SPDX-License-Identifier: MIT
4 //
5 
6 #include "CommandHandler.hpp"
7 #include "ProfilingService.hpp"
8 
9 #include <common/include/Logging.hpp>
10 
11 #if defined(ARMNN_DISABLE_THREADS)
12 #include <common/include/IgnoreUnused.hpp>
13 #endif
14 
15 namespace arm
16 {
17 
18 namespace pipe
19 {
20 
Start(IProfilingConnection & profilingConnection)21 void CommandHandler::Start(IProfilingConnection& profilingConnection)
22 {
23     if (IsRunning())
24     {
25         return;
26     }
27 
28 #if !defined(ARMNN_DISABLE_THREADS)
29     if (m_CommandThread.joinable())
30     {
31         m_CommandThread.join();
32     }
33 #endif
34 
35     m_IsRunning.store(true);
36     m_KeepRunning.store(true);
37 #if !defined(ARMNN_DISABLE_THREADS)
38     m_CommandThread = std::thread(&CommandHandler::HandleCommands, this, std::ref(profilingConnection));
39 #else
40     IgnoreUnused(profilingConnection);
41 #endif
42 }
43 
Stop()44 void CommandHandler::Stop()
45 {
46     m_KeepRunning.store(false);
47 
48 #if !defined(ARMNN_DISABLE_THREADS)
49     if (m_CommandThread.joinable())
50     {
51         m_CommandThread.join();
52     }
53 #endif
54 }
55 
HandleCommands(IProfilingConnection & profilingConnection)56 void CommandHandler::HandleCommands(IProfilingConnection& profilingConnection)
57 {
58     do
59     {
60         try
61         {
62             arm::pipe::Packet packet = profilingConnection.ReadPacket(m_Timeout.load());
63 
64             if (packet.IsEmpty())
65             {
66                 // Nothing to do, continue
67                 continue;
68             }
69 
70             arm::pipe::Version version = m_PacketVersionResolver.ResolvePacketVersion(packet.GetPacketFamily(),
71                                                                                       packet.GetPacketId());
72 
73             arm::pipe::CommandHandlerFunctor* commandHandlerFunctor =
74                 m_CommandHandlerRegistry.GetFunctor(packet.GetPacketFamily(),
75                                                     packet.GetPacketId(),
76                                                     version.GetEncodedValue());
77             ARM_PIPE_ASSERT(commandHandlerFunctor);
78             commandHandlerFunctor->operator()(packet);
79         }
80         catch (const arm::pipe::TimeoutException&)
81         {
82             if (m_StopAfterTimeout.load())
83             {
84                 m_KeepRunning.store(false);
85             }
86         }
87         catch (const arm::pipe::ProfilingException& e)
88         {
89             // Log the error and continue
90             ARM_PIPE_LOG(warning) << "An error has occurred when handling a command: " << e.what();
91             // Did we get here because the socket failed?
92             if ( !profilingConnection.IsOpen() )
93             {
94                 // We're going to stop processing commands.
95                 // This will leave the thread idle. There is no mechanism to restart the profiling service when the
96                 // connection is lost.
97                 m_KeepRunning.store(false);
98             }
99         }
100         catch (...)
101         {
102             // Log the error and continue
103             ARM_PIPE_LOG(warning) << "An unknown error has occurred when handling a command";
104             // Did we get here because the socket failed?
105             if ( !profilingConnection.IsOpen() )
106             {
107                 // We're going to stop processing commands.
108                 // This will leave the thread idle. There is no mechanism to restart the profiling service when the
109                 // connection is lost.
110                 m_KeepRunning.store(false);
111             }
112         }
113     }
114     while (m_KeepRunning.load());
115 
116     m_IsRunning.store(false);
117 }
118 
119 } // namespace pipe
120 
121 } // namespace arm
122