| 781 | } |
| 782 | |
| 783 | Status LoadedNetwork::EnqueueWorkload(const InputTensors& inputTensors, |
| 784 | const OutputTensors& outputTensors, |
| 785 | std::vector<ImportedInputId> preImportedInputIds, |
| 786 | std::vector<ImportedOutputId> preImportedOutputIds) |
| 787 | { |
| 788 | const Graph& graph = m_OptimizedNetwork->pOptimizedNetworkImpl->GetGraph(); |
| 789 | |
| 790 | // Walk graph to determine the order of execution. |
| 791 | if (graph.GetNumLayers() < 2) |
| 792 | { |
| 793 | ARMNN_LOG(warning) << "IRuntime::EnqueueWorkload()::Less than two nodes in graph"; |
| 794 | return Status::Failure; |
| 795 | } |
| 796 | |
| 797 | // Data that must be kept alive for the entire execution of the workload. |
| 798 | WorkloadData workloadData(inputTensors, outputTensors); |
| 799 | |
| 800 | // Input tensors can be provided as parameters or pre imported. Either way the number of |
| 801 | // tensors should match the number of inputs. |
| 802 | if (graph.GetNumInputs() != (inputTensors.size() + preImportedInputIds.size())) |
| 803 | { |
| 804 | throw InvalidArgumentException("Number of inputs provided does not match network."); |
| 805 | } |
| 806 | |
| 807 | // For each input to the network, call EnqueueInput with the data passed by the user. |
| 808 | { |
| 809 | ARMNN_SCOPED_PROFILING_EVENT(Compute::Undefined, "PrepareInputs"); |
| 810 | m_InputQueue.clear(); |
| 811 | m_InputQueue.reserve(graph.GetNumInputs()); |
| 812 | |
| 813 | unsigned int inputIndex = 0; |
| 814 | unsigned int importedInputIdIndex = 0; |
| 815 | std::sort(preImportedInputIds.begin(), preImportedInputIds.end()); |
| 816 | for (const BindableLayer* inputLayer : graph.GetInputLayers()) |
| 817 | { |
| 818 | if (importedInputIdIndex < preImportedInputIds.size() && |
| 819 | inputIndex == preImportedInputIds[importedInputIdIndex]) |
| 820 | { |
| 821 | // Only replace tensorhandles if they have not already been replaced |
| 822 | if (!m_IsInputImported[inputIndex]) |
| 823 | { |
| 824 | auto outputTensorHandle = m_PreImportedInputHandles[inputIndex].m_TensorHandle.get(); |
| 825 | |
| 826 | for (const auto& workloadInfo: m_InputWorkloadSlotPairs[inputLayer->GetBindingId()]) |
| 827 | { |
| 828 | auto workload = m_WorkloadQueue[workloadInfo.m_WorkloadIndex].get(); |
| 829 | workload->ReplaceInputTensorHandle(outputTensorHandle, workloadInfo.m_SlotIndex); |
| 830 | } |
| 831 | m_IsInputImported[inputIndex] = true; |
| 832 | } |
| 833 | importedInputIdIndex++; |
| 834 | } |
| 835 | else |
| 836 | { |
| 837 | if (m_IsInputImported[inputIndex]) |
| 838 | { |
| 839 | OutputHandler& handler = const_cast<OutputHandler&>(inputLayer->GetOutputHandler(0)); |
| 840 |
nothing calls this directly
no test coverage detected