1*89c4ff92SAndroid Build Coastguard Worker //
2*89c4ff92SAndroid Build Coastguard Worker // Copyright © 2017 Arm Ltd. All rights reserved.
3*89c4ff92SAndroid Build Coastguard Worker // SPDX-License-Identifier: MIT
4*89c4ff92SAndroid Build Coastguard Worker //
5*89c4ff92SAndroid Build Coastguard Worker
6*89c4ff92SAndroid Build Coastguard Worker #include "ProfilingStateMachine.hpp"
7*89c4ff92SAndroid Build Coastguard Worker
8*89c4ff92SAndroid Build Coastguard Worker #include <common/include/ProfilingException.hpp>
9*89c4ff92SAndroid Build Coastguard Worker
10*89c4ff92SAndroid Build Coastguard Worker #include <sstream>
11*89c4ff92SAndroid Build Coastguard Worker
12*89c4ff92SAndroid Build Coastguard Worker namespace arm
13*89c4ff92SAndroid Build Coastguard Worker {
14*89c4ff92SAndroid Build Coastguard Worker
15*89c4ff92SAndroid Build Coastguard Worker namespace pipe
16*89c4ff92SAndroid Build Coastguard Worker {
17*89c4ff92SAndroid Build Coastguard Worker
18*89c4ff92SAndroid Build Coastguard Worker namespace
19*89c4ff92SAndroid Build Coastguard Worker {
20*89c4ff92SAndroid Build Coastguard Worker
ThrowStateTransitionException(ProfilingState expectedState,ProfilingState newState)21*89c4ff92SAndroid Build Coastguard Worker void ThrowStateTransitionException(ProfilingState expectedState, ProfilingState newState)
22*89c4ff92SAndroid Build Coastguard Worker {
23*89c4ff92SAndroid Build Coastguard Worker std::stringstream ss;
24*89c4ff92SAndroid Build Coastguard Worker ss << "Cannot transition from state [" << GetProfilingStateName(expectedState) << "] "
25*89c4ff92SAndroid Build Coastguard Worker << "to state [" << GetProfilingStateName(newState) << "]";
26*89c4ff92SAndroid Build Coastguard Worker throw arm::pipe::ProfilingException(ss.str());
27*89c4ff92SAndroid Build Coastguard Worker }
28*89c4ff92SAndroid Build Coastguard Worker
29*89c4ff92SAndroid Build Coastguard Worker } // Anonymous namespace
30*89c4ff92SAndroid Build Coastguard Worker
GetCurrentState() const31*89c4ff92SAndroid Build Coastguard Worker ProfilingState ProfilingStateMachine::GetCurrentState() const
32*89c4ff92SAndroid Build Coastguard Worker {
33*89c4ff92SAndroid Build Coastguard Worker return m_State.load();
34*89c4ff92SAndroid Build Coastguard Worker }
35*89c4ff92SAndroid Build Coastguard Worker
TransitionToState(ProfilingState newState)36*89c4ff92SAndroid Build Coastguard Worker void ProfilingStateMachine::TransitionToState(ProfilingState newState)
37*89c4ff92SAndroid Build Coastguard Worker {
38*89c4ff92SAndroid Build Coastguard Worker ProfilingState currentState = m_State.load(std::memory_order::memory_order_relaxed);
39*89c4ff92SAndroid Build Coastguard Worker
40*89c4ff92SAndroid Build Coastguard Worker switch (newState)
41*89c4ff92SAndroid Build Coastguard Worker {
42*89c4ff92SAndroid Build Coastguard Worker case ProfilingState::Uninitialised:
43*89c4ff92SAndroid Build Coastguard Worker do
44*89c4ff92SAndroid Build Coastguard Worker {
45*89c4ff92SAndroid Build Coastguard Worker if (!IsOneOfStates(currentState, ProfilingState::Uninitialised))
46*89c4ff92SAndroid Build Coastguard Worker {
47*89c4ff92SAndroid Build Coastguard Worker ThrowStateTransitionException(currentState, newState);
48*89c4ff92SAndroid Build Coastguard Worker }
49*89c4ff92SAndroid Build Coastguard Worker }
50*89c4ff92SAndroid Build Coastguard Worker while (!m_State.compare_exchange_strong(currentState, newState, std::memory_order::memory_order_relaxed));
51*89c4ff92SAndroid Build Coastguard Worker break;
52*89c4ff92SAndroid Build Coastguard Worker case ProfilingState::NotConnected:
53*89c4ff92SAndroid Build Coastguard Worker do
54*89c4ff92SAndroid Build Coastguard Worker {
55*89c4ff92SAndroid Build Coastguard Worker if (!IsOneOfStates(currentState, ProfilingState::Uninitialised, ProfilingState::NotConnected,
56*89c4ff92SAndroid Build Coastguard Worker ProfilingState::Active, ProfilingState::WaitingForAck))
57*89c4ff92SAndroid Build Coastguard Worker {
58*89c4ff92SAndroid Build Coastguard Worker ThrowStateTransitionException(currentState, newState);
59*89c4ff92SAndroid Build Coastguard Worker }
60*89c4ff92SAndroid Build Coastguard Worker }
61*89c4ff92SAndroid Build Coastguard Worker while (!m_State.compare_exchange_strong(currentState, newState, std::memory_order::memory_order_relaxed));
62*89c4ff92SAndroid Build Coastguard Worker break;
63*89c4ff92SAndroid Build Coastguard Worker case ProfilingState::WaitingForAck:
64*89c4ff92SAndroid Build Coastguard Worker do
65*89c4ff92SAndroid Build Coastguard Worker {
66*89c4ff92SAndroid Build Coastguard Worker if (!IsOneOfStates(currentState, ProfilingState::NotConnected, ProfilingState::WaitingForAck))
67*89c4ff92SAndroid Build Coastguard Worker {
68*89c4ff92SAndroid Build Coastguard Worker ThrowStateTransitionException(currentState, newState);
69*89c4ff92SAndroid Build Coastguard Worker }
70*89c4ff92SAndroid Build Coastguard Worker }
71*89c4ff92SAndroid Build Coastguard Worker while (!m_State.compare_exchange_strong(currentState, newState, std::memory_order::memory_order_relaxed));
72*89c4ff92SAndroid Build Coastguard Worker break;
73*89c4ff92SAndroid Build Coastguard Worker case ProfilingState::Active:
74*89c4ff92SAndroid Build Coastguard Worker do
75*89c4ff92SAndroid Build Coastguard Worker {
76*89c4ff92SAndroid Build Coastguard Worker if (!IsOneOfStates(currentState, ProfilingState::WaitingForAck, ProfilingState::Active))
77*89c4ff92SAndroid Build Coastguard Worker {
78*89c4ff92SAndroid Build Coastguard Worker ThrowStateTransitionException(currentState, newState);
79*89c4ff92SAndroid Build Coastguard Worker }
80*89c4ff92SAndroid Build Coastguard Worker }
81*89c4ff92SAndroid Build Coastguard Worker while (!m_State.compare_exchange_strong(currentState, newState, std::memory_order::memory_order_relaxed));
82*89c4ff92SAndroid Build Coastguard Worker break;
83*89c4ff92SAndroid Build Coastguard Worker default:
84*89c4ff92SAndroid Build Coastguard Worker break;
85*89c4ff92SAndroid Build Coastguard Worker }
86*89c4ff92SAndroid Build Coastguard Worker }
87*89c4ff92SAndroid Build Coastguard Worker
Reset()88*89c4ff92SAndroid Build Coastguard Worker void ProfilingStateMachine::Reset()
89*89c4ff92SAndroid Build Coastguard Worker {
90*89c4ff92SAndroid Build Coastguard Worker m_State.store(ProfilingState::Uninitialised);
91*89c4ff92SAndroid Build Coastguard Worker }
92*89c4ff92SAndroid Build Coastguard Worker
93*89c4ff92SAndroid Build Coastguard Worker } // namespace pipe
94*89c4ff92SAndroid Build Coastguard Worker
95*89c4ff92SAndroid Build Coastguard Worker } // namespace arm
96