196class cTestListener:
public ISignalListening::ISignalsListener,
197 public ISignalListening::ISignalListener
200 using tSignal = std::pair<ISignalRegistry::tSignalAttributes, std::vector<cTestSignalValueNs>>;
201 using tSignals = std::map<adtf::util::cString, tSignal>;
211 virtual ~cTestListener()
213 m_pSignalListening->UnregisterSignalsListener(*
this);
215 for (
const auto& strSignal: m_oRequestedSignals)
217 const auto itSignal = m_oSignals.find(strSignal.c_str());
218 if (itSignal != m_oSignals.end())
220 m_pSignalListening->CancelSignalUpdates(itSignal->second.first.nSignalID, *
this);
225 virtual void SignalAdded(
const ISignalRegistry::tSignalAttributes& sSignalAttributes)
override
228 std::scoped_lock oSignalsGuard(m_oSignalsMutex);
230 m_oIdMap[sSignalAttributes.nSignalID] = m_oSignals.emplace(adtf::util::cString(sSignalAttributes.strName), tSignal{sSignalAttributes, {}}).first;
232 if (m_oRequestedSignals.find(sSignalAttributes.strName) != m_oRequestedSignals.end())
234 THROW_IF_FAILED(m_pSignalListening->RequestSignalUpdates(sSignalAttributes.nSignalID, *
this));
238 m_oSignalsChanged.notify_all();
241 virtual void SignalRemoved(
const ISignalRegistry::tSignalAttributes& sSignalAttributes)
override
244 std::scoped_lock oGuard(m_oSignalsMutex);
245 m_oSignals.erase(sSignalAttributes.strName);
248 m_oSignalsChanged.notify_all();
251 virtual void SignalUpdated(ISignalRegistry::tSignalID nSignalID,
const ISignalRegistry::tSignalValueNs& sValue)
override
253 std::scoped_lock oGuard(m_oSignalsMutex);
258 void ForEachSignal(std::function<
void(
typename tSignals::reference&)> fnCallback)
260 std::scoped_lock oSignalsGuard(m_oSignalsMutex);
261 for (
auto& oSignal : m_oSignals)
267 tSignals GetCurrentSignals()
269 std::scoped_lock oSignalsGuard(m_oSignalsMutex);
273 size_t GetUpdateCount(
const char* strSignal)
275 std::scoped_lock oSignalsGuard(m_oSignalsMutex);
276 return m_oSignals.at(strSignal).second.size();
279 void RequestUpdates(
const char* strSignal)
281 std::optional<ISignalRegistry::tSignalID> nId;
284 std::scoped_lock oSignalsGuard(m_oSignalsMutex);
285 m_oRequestedSignals.insert(strSignal);
287 const auto itSignal = m_oSignals.find(strSignal);
288 if (itSignal != m_oSignals.end())
290 nId = itSignal->second.first.nSignalID;
296 THROW_IF_FAILED(m_pSignalListening->RequestSignalUpdates(*nId, *
this));
300 void CancelUpdates(
const char* strSignal)
302 std::optional<ISignalRegistry::tSignalID> nId;
305 std::scoped_lock oSignalsGuard(m_oSignalsMutex);
306 m_oRequestedSignals.erase(strSignal);
307 const auto itSignal = m_oSignals.find(strSignal);
308 if (itSignal != m_oSignals.end())
310 nId = itSignal->second.first.nSignalID;
316 m_pSignalListening->CancelSignalUpdates(*nId, *
this);
320 bool WaitForUpdates(std::chrono::seconds nMaxSeconds,
size_t nUpdateCountEachSignal)
322 auto oBeginTimePoint = std::chrono::steady_clock::now();
323 while (std::chrono::duration_cast<std::chrono::seconds>(std::chrono::steady_clock::now() - oBeginTimePoint) < nMaxSeconds)
325 const size_t oCurrentCount = m_oUpdateCount;
326 if (oCurrentCount < nUpdateCountEachSignal * m_oSignals.size())
328 std::this_thread::sleep_for(std::chrono::milliseconds(100));
335 const size_t oLastCount = m_oUpdateCount;
336 return (oLastCount >= nUpdateCountEachSignal * m_oSignals.size());
339 bool WaitForSignal(
const char* strName, std::chrono::nanoseconds tmTimeout)
341 std::unique_lock oLock(m_oSignalsMutex);
342 return m_oSignalsChanged.wait_for(oLock, tmTimeout, [&] {
return m_oSignals.count(strName) > 0 ;});
346 adtf::ucom::object_ptr<ISignalListening> m_pSignalListening;
347 mutable std::recursive_mutex m_oSignalsMutex;
348 std::condition_variable_any m_oSignalsChanged;
350 std::unordered_map<ISignalRegistry::tSignalID, tSignals::iterator> m_oIdMap;
351 std::unordered_set<std::string> m_oRequestedSignals;
352 std::atomic<size_t> m_oUpdateCount;