1*3e777be0SXin Li // 2*3e777be0SXin Li // Copyright © 2020 Arm Ltd. All rights reserved. 3*3e777be0SXin Li // SPDX-License-Identifier: MIT 4*3e777be0SXin Li // 5*3e777be0SXin Li 6*3e777be0SXin Li #pragma once 7*3e777be0SXin Li 8*3e777be0SXin Li #include <queue> 9*3e777be0SXin Li #include <thread> 10*3e777be0SXin Li #include <mutex> 11*3e777be0SXin Li #include <condition_variable> 12*3e777be0SXin Li 13*3e777be0SXin Li #include "ArmnnDriver.hpp" 14*3e777be0SXin Li #include "ArmnnDriverImpl.hpp" 15*3e777be0SXin Li 16*3e777be0SXin Li #include <CpuExecutor.h> 17*3e777be0SXin Li #include <armnn/ArmNN.hpp> 18*3e777be0SXin Li 19*3e777be0SXin Li namespace armnn_driver 20*3e777be0SXin Li { 21*3e777be0SXin Li using TimePoint = std::chrono::steady_clock::time_point; 22*3e777be0SXin Li 23*3e777be0SXin Li template<template <typename HalVersion> class PreparedModel, typename HalVersion, typename CallbackContext> 24*3e777be0SXin Li class RequestThread_1_3 25*3e777be0SXin Li { 26*3e777be0SXin Li public: 27*3e777be0SXin Li /// Constructor creates the thread 28*3e777be0SXin Li RequestThread_1_3(); 29*3e777be0SXin Li 30*3e777be0SXin Li /// Destructor terminates the thread 31*3e777be0SXin Li ~RequestThread_1_3(); 32*3e777be0SXin Li 33*3e777be0SXin Li /// Add a message to the thread queue. 34*3e777be0SXin Li /// @param[in] model pointer to the prepared model handling the request 35*3e777be0SXin Li /// @param[in] memPools pointer to the memory pools vector for the tensors 36*3e777be0SXin Li /// @param[in] inputTensors pointer to the input tensors for the request 37*3e777be0SXin Li /// @param[in] outputTensors pointer to the output tensors for the request 38*3e777be0SXin Li /// @param[in] callback the android notification callback 39*3e777be0SXin Li void PostMsg(PreparedModel<HalVersion>* model, 40*3e777be0SXin Li std::shared_ptr<std::vector<::android::nn::RunTimePoolInfo>>& memPools, 41*3e777be0SXin Li std::shared_ptr<armnn::InputTensors>& inputTensors, 42*3e777be0SXin Li std::shared_ptr<armnn::OutputTensors>& outputTensors, 43*3e777be0SXin Li CallbackContext callbackContext); 44*3e777be0SXin Li 45*3e777be0SXin Li private: 46*3e777be0SXin Li RequestThread_1_3(const RequestThread_1_3&) = delete; 47*3e777be0SXin Li RequestThread_1_3& operator=(const RequestThread_1_3&) = delete; 48*3e777be0SXin Li 49*3e777be0SXin Li /// storage for a prepared model and args for the asyncExecute call 50*3e777be0SXin Li struct AsyncExecuteData 51*3e777be0SXin Li { AsyncExecuteDataarmnn_driver::RequestThread_1_3::AsyncExecuteData52*3e777be0SXin Li AsyncExecuteData(PreparedModel<HalVersion>* model, 53*3e777be0SXin Li std::shared_ptr<std::vector<::android::nn::RunTimePoolInfo>>& memPools, 54*3e777be0SXin Li std::shared_ptr<armnn::InputTensors>& inputTensors, 55*3e777be0SXin Li std::shared_ptr<armnn::OutputTensors>& outputTensors, 56*3e777be0SXin Li CallbackContext callbackContext) 57*3e777be0SXin Li : m_Model(model) 58*3e777be0SXin Li , m_MemPools(memPools) 59*3e777be0SXin Li , m_InputTensors(inputTensors) 60*3e777be0SXin Li , m_OutputTensors(outputTensors) 61*3e777be0SXin Li , m_CallbackContext(callbackContext) 62*3e777be0SXin Li { 63*3e777be0SXin Li } 64*3e777be0SXin Li 65*3e777be0SXin Li PreparedModel<HalVersion>* m_Model; 66*3e777be0SXin Li std::shared_ptr<std::vector<::android::nn::RunTimePoolInfo>> m_MemPools; 67*3e777be0SXin Li std::shared_ptr<armnn::InputTensors> m_InputTensors; 68*3e777be0SXin Li std::shared_ptr<armnn::OutputTensors> m_OutputTensors; 69*3e777be0SXin Li CallbackContext m_CallbackContext; 70*3e777be0SXin Li }; 71*3e777be0SXin Li enum class ThreadMsgType 72*3e777be0SXin Li { 73*3e777be0SXin Li EXIT, // exit the thread 74*3e777be0SXin Li REQUEST // user request to process 75*3e777be0SXin Li }; 76*3e777be0SXin Li 77*3e777be0SXin Li /// storage for the thread message type and data 78*3e777be0SXin Li struct ThreadMsg 79*3e777be0SXin Li { ThreadMsgarmnn_driver::RequestThread_1_3::ThreadMsg80*3e777be0SXin Li ThreadMsg(ThreadMsgType msgType, 81*3e777be0SXin Li std::shared_ptr<AsyncExecuteData>& msgData) 82*3e777be0SXin Li : type(msgType) 83*3e777be0SXin Li , data(msgData) 84*3e777be0SXin Li { 85*3e777be0SXin Li } 86*3e777be0SXin Li 87*3e777be0SXin Li ThreadMsgType type; 88*3e777be0SXin Li std::shared_ptr<AsyncExecuteData> data; 89*3e777be0SXin Li }; 90*3e777be0SXin Li 91*3e777be0SXin Li /// Add a prepared thread message to the thread queue. 92*3e777be0SXin Li /// @param[in] threadMsg the message to add to the queue 93*3e777be0SXin Li void PostMsg(std::shared_ptr<ThreadMsg>& pThreadMsg, V1_3::Priority priority = V1_3::Priority::MEDIUM); 94*3e777be0SXin Li 95*3e777be0SXin Li /// Entry point for the request thread 96*3e777be0SXin Li void Process(); 97*3e777be0SXin Li 98*3e777be0SXin Li std::unique_ptr<std::thread> m_Thread; 99*3e777be0SXin Li std::queue<std::shared_ptr<ThreadMsg>> m_HighPriorityQueue; 100*3e777be0SXin Li std::queue<std::shared_ptr<ThreadMsg>> m_MediumPriorityQueue; 101*3e777be0SXin Li std::queue<std::shared_ptr<ThreadMsg>> m_LowPriorityQueue; 102*3e777be0SXin Li std::mutex m_Mutex; 103*3e777be0SXin Li std::condition_variable m_Cv; 104*3e777be0SXin Li }; 105*3e777be0SXin Li 106*3e777be0SXin Li } // namespace armnn_driver 107