1 /* 2 * Copyright (C) 2017 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #ifndef ANDROID_ML_NN_RUNTIME_MANAGER_H 18 #define ANDROID_ML_NN_RUNTIME_MANAGER_H 19 20 #include "HalInterfaces.h" 21 #include "Utils.h" 22 23 #include <map> 24 #include <unordered_set> 25 #include <vector> 26 27 namespace android { 28 namespace nn { 29 30 class ModelBuilder; 31 32 class Device { 33 public: 34 Device(const std::string& name, const sp<IDevice>& device) : mName(name), mInterface(device) {} 35 sp<IDevice> getInterface() { return mInterface; } 36 const std::string& getName() const { return mName; } 37 // Returns true if succesfully initialized. 38 bool initialize(); 39 40 void getSupportedOperations(const Model& hidlModel, hidl_vec<bool>* supportedOperations) const; 41 42 PerformanceInfo getFloat32Performance() const { return mFloat32Performance; } 43 PerformanceInfo getQuantized8Performance() const { return mQuantized8Performance; } 44 45 private: 46 std::string mName; 47 sp<IDevice> mInterface; 48 PerformanceInfo mFloat32Performance; 49 PerformanceInfo mQuantized8Performance; 50 51 #ifdef NN_DEBUGGABLE 52 // For debugging: behavior of IDevice::getSupportedOperations for SampleDriver. 53 // 0 - all operations reported by IDevice::getSupportedOperations() supported 54 // 1 - some operations reported by IDevice::getSupportedOperations() supported 55 uint32_t mSupported = 0; 56 #endif // NN_DEBUGGABLE 57 }; 58 59 // Manages the NN HAL devices. Only one instance of this class will exist. 60 // Use get() to retrieve it. 61 class DeviceManager { 62 public: 63 const std::vector<std::shared_ptr<Device>>& getDrivers() const { 64 if (mUseCpuOnly) { 65 return mNoDevices; 66 } 67 return mDevices; 68 } 69 70 // For testing only: 71 void setUseCpuOnly(bool useCpuOnly) { mUseCpuOnly = useCpuOnly; } 72 73 // How to handle graph partitioning? 74 // 0 - Don't do graph partitioning. 75 // 1 - Do graph partitioning; but fall back to non-partitioned 76 // execution if there is a partitioning failure. 77 // 2 - Do graph partitioning, and rely on it; there is no fallback. 78 enum { 79 kPartitioningNo = 0, 80 kPartitioningWithFallback = 1, 81 kPartitioningWithoutFallback = 2 82 }; 83 uint32_t getPartitioning() const { return mPartitioning; } 84 static bool partitioningAllowsFallback(uint32_t partitioning) { 85 return partitioning == kPartitioningWithFallback; 86 } 87 88 // Returns the singleton manager. 89 static DeviceManager* get(); 90 91 private: 92 // Builds the list of available drivers and queries their capabilities. 93 DeviceManager(); 94 95 // Adds a device for the manager to use. 96 void registerDevice(const char* name, const sp<IDevice>& device); 97 98 void findAvailableDevices(); 99 100 // List of all the devices we discovered. 101 std::vector<std::shared_ptr<Device>> mDevices; 102 103 // We leave this one always empty. To be used when mUseCpuOnly is true. 104 std::vector<std::shared_ptr<Device>> mNoDevices; 105 106 // If true, we'll ignore the drivers that are on the device and run everything 107 // on the CPU. 108 bool mUseCpuOnly = false; 109 110 static const uint32_t kPartitioningDefault = kPartitioningWithFallback; 111 uint32_t mPartitioning = kPartitioningDefault; 112 }; 113 114 } // namespace nn 115 } // namespace android 116 117 #endif // ANDROID_ML_NN_RUNTIME_MANAGER_H 118