diff options
Diffstat (limited to 'src/backends/neon')
6 files changed, 97 insertions, 35 deletions
diff --git a/src/backends/neon/workloads/NeonConvolution2dWorkload.cpp b/src/backends/neon/workloads/NeonConvolution2dWorkload.cpp index 586b9c9849..879bb747a1 100644 --- a/src/backends/neon/workloads/NeonConvolution2dWorkload.cpp +++ b/src/backends/neon/workloads/NeonConvolution2dWorkload.cpp @@ -1,5 +1,5 @@ // -// Copyright © 2017 Arm Ltd and Contributors. All rights reserved. +// Copyright © 2017,2022 Arm Ltd and Contributors. All rights reserved. // SPDX-License-Identifier: MIT // @@ -90,11 +90,11 @@ NeonConvolution2dWorkload::NeonConvolution2dWorkload( output.info()->set_data_layout(aclDataLayout); m_KernelTensor = std::make_unique<arm_compute::Tensor>(); - BuildArmComputeTensor(*m_KernelTensor, m_Data.m_Weight->GetTensorInfo(), m_Data.m_Parameters.m_DataLayout); + BuildArmComputeTensor(*m_KernelTensor, info.m_InputTensorInfos[1], m_Data.m_Parameters.m_DataLayout); if (m_Data.m_Parameters.m_BiasEnabled) { m_BiasTensor = std::make_unique<arm_compute::Tensor>(); - BuildArmComputeTensor(*m_BiasTensor, m_Data.m_Bias->GetTensorInfo(), m_Data.m_Parameters.m_DataLayout); + BuildArmComputeTensor(*m_BiasTensor, info.m_InputTensorInfos[2], m_Data.m_Parameters.m_DataLayout); } arm_compute::PadStrideInfo padStrideInfo = BuildArmComputePadStrideInfo(m_Data.m_Parameters); @@ -130,11 +130,12 @@ NeonConvolution2dWorkload::NeonConvolution2dWorkload( detailsInfo.m_InputTensorInfos = info.m_InputTensorInfos; detailsInfo.m_OutputTensorInfos = info.m_OutputTensorInfos; - detailsInfo.m_WeightsTensorInfo = armnn::Optional<armnn::TensorInfo>(descriptor.m_Weight->GetTensorInfo()); + detailsInfo.m_WeightsTensorInfo = armnn::Optional<armnn::TensorInfo>(info.m_InputTensorInfos[1]); detailsInfo.m_ConvolutionMethod = armnn::Optional<std::string>(GetConvolutionMethodString(m_ConvolutionMethod)); + if (descriptor.m_Parameters.m_BiasEnabled) { - detailsInfo.m_BiasTensorInfo = armnn::Optional<armnn::TensorInfo>(descriptor.m_Bias->GetTensorInfo()); + detailsInfo.m_BiasTensorInfo = armnn::Optional<armnn::TensorInfo>(info.m_InputTensorInfos[2]); } // Report Profiling Details @@ -146,22 +147,31 @@ NeonConvolution2dWorkload::NeonConvolution2dWorkload( m_ConvolutionLayer.reset(convolutionLayer.release()); ARMNN_ASSERT(m_ConvolutionLayer); - - InitializeArmComputeTensorData(*m_KernelTensor, m_Data.m_Weight); + m_KernelTensorInfo = info.m_InputTensorInfos[1]; if (m_Data.m_Parameters.m_BiasEnabled) { - InitializeArmComputeTensorData(*m_BiasTensor, m_Data.m_Bias); + m_BiasTensorInfo = info.m_InputTensorInfos[2]; } - - m_ConvolutionLayer->prepare(); - FreeTensorIfUnused(m_KernelTensor); - FreeTensorIfUnused(m_BiasTensor); } void NeonConvolution2dWorkload::Execute() const { ARMNN_SCOPED_PROFILING_EVENT_NEON_GUID("NeonConvolution2dWorkload_Execute", this->GetGuid()); + // The constant tensors may not be fully in place until the workload is Executed + if (!prepared) + { + InitializeArmComputeTensorData(*m_KernelTensor, m_KernelTensorInfo, m_Data.m_Inputs[1]); + + if (m_Data.m_Parameters.m_BiasEnabled) + { + InitializeArmComputeTensorData(*m_BiasTensor, m_BiasTensorInfo, m_Data.m_Inputs[2]); + } + m_ConvolutionLayer->prepare(); + FreeTensorIfUnused(m_KernelTensor); + FreeTensorIfUnused(m_BiasTensor); + prepared = true; + } m_ConvolutionLayer->run(); } diff --git a/src/backends/neon/workloads/NeonConvolution2dWorkload.hpp b/src/backends/neon/workloads/NeonConvolution2dWorkload.hpp index e833f2ac66..4e5c1cf5ed 100644 --- a/src/backends/neon/workloads/NeonConvolution2dWorkload.hpp +++ b/src/backends/neon/workloads/NeonConvolution2dWorkload.hpp @@ -1,5 +1,5 @@ // -// Copyright © 2017 Arm Ltd and Contributors. All rights reserved. +// Copyright © 2017,2022 Arm Ltd and Contributors. All rights reserved. // SPDX-License-Identifier: MIT // @@ -41,10 +41,12 @@ public: private: std::unique_ptr<arm_compute::IFunction> m_ConvolutionLayer; - std::unique_ptr<arm_compute::Tensor> m_KernelTensor; - std::unique_ptr<arm_compute::Tensor> m_BiasTensor; - + mutable std::unique_ptr<arm_compute::Tensor> m_KernelTensor; + mutable std::unique_ptr<arm_compute::Tensor> m_BiasTensor; + TensorInfo m_KernelTensorInfo; + TensorInfo m_BiasTensorInfo; arm_compute::ConvolutionMethod m_ConvolutionMethod; + mutable bool prepared = false; }; } //namespace armnn diff --git a/src/backends/neon/workloads/NeonDepthwiseConvolutionWorkload.cpp b/src/backends/neon/workloads/NeonDepthwiseConvolutionWorkload.cpp index e2d0a8200f..00d9d3340e 100644 --- a/src/backends/neon/workloads/NeonDepthwiseConvolutionWorkload.cpp +++ b/src/backends/neon/workloads/NeonDepthwiseConvolutionWorkload.cpp @@ -1,5 +1,5 @@ // -// Copyright © 2017 Arm Ltd and Contributors. All rights reserved. +// Copyright © 2017,2022 Arm Ltd and Contributors. All rights reserved. // SPDX-License-Identifier: MIT // @@ -141,10 +141,10 @@ NeonDepthwiseConvolutionWorkload::NeonDepthwiseConvolutionWorkload( detailsInfo.m_InputTensorInfos = info.m_InputTensorInfos; detailsInfo.m_OutputTensorInfos = info.m_OutputTensorInfos; - detailsInfo.m_WeightsTensorInfo = armnn::Optional<armnn::TensorInfo>(descriptor.m_Weight->GetTensorInfo()); + detailsInfo.m_WeightsTensorInfo = armnn::Optional<armnn::TensorInfo>(info.m_InputTensorInfos[1]); if (descriptor.m_Parameters.m_BiasEnabled) { - detailsInfo.m_BiasTensorInfo = armnn::Optional<armnn::TensorInfo>(descriptor.m_Bias->GetTensorInfo()); + detailsInfo.m_BiasTensorInfo = armnn::Optional<armnn::TensorInfo>(info.m_InputTensorInfos[2]); } // Report Profiling Details diff --git a/src/backends/neon/workloads/NeonFullyConnectedWorkload.cpp b/src/backends/neon/workloads/NeonFullyConnectedWorkload.cpp index 0b91eb37c2..7bb23f870b 100644 --- a/src/backends/neon/workloads/NeonFullyConnectedWorkload.cpp +++ b/src/backends/neon/workloads/NeonFullyConnectedWorkload.cpp @@ -1,5 +1,5 @@ // -// Copyright © 2017 Arm Ltd and Contributors. All rights reserved. +// Copyright © 2017,2022 Arm Ltd and Contributors. All rights reserved. // SPDX-License-Identifier: MIT // @@ -70,15 +70,15 @@ NeonFullyConnectedWorkload::NeonFullyConnectedWorkload(const FullyConnectedQueue // Copy the weights' tensor into arm_compute tensor. m_WeightsTensor = std::make_unique<arm_compute::Tensor>(); - BuildArmComputeTensor(*m_WeightsTensor, m_Data.m_Weight->GetTensorInfo()); - InitializeArmComputeTensorData(*m_WeightsTensor, m_Data.m_Weight); - + m_WeightsTensorInfo = info.m_InputTensorInfos[1]; + BuildArmComputeTensor(*m_WeightsTensor, m_WeightsTensorInfo); + if (m_Data.m_Parameters.m_BiasEnabled) { // Copy the biases tensor into arm_compute tensor. m_BiasesTensor = std::make_unique<arm_compute::Tensor>(); - BuildArmComputeTensor(*m_BiasesTensor, m_Data.m_Bias->GetTensorInfo()); - InitializeArmComputeTensorData(*m_BiasesTensor, m_Data.m_Bias); + m_BiasesTensorInfo = info.m_InputTensorInfos[2]; + BuildArmComputeTensor(*m_BiasesTensor, m_BiasesTensorInfo); } const arm_compute::ActivationLayerInfo activationInfo = ConvertAdditionalInfoToAclActivationLayerInfo(descriptor); @@ -94,10 +94,10 @@ NeonFullyConnectedWorkload::NeonFullyConnectedWorkload(const FullyConnectedQueue detailsInfo.m_InputTensorInfos = info.m_InputTensorInfos; detailsInfo.m_OutputTensorInfos = info.m_OutputTensorInfos; - detailsInfo.m_WeightsTensorInfo = armnn::Optional<armnn::TensorInfo>(descriptor.m_Weight->GetTensorInfo()); + detailsInfo.m_WeightsTensorInfo = armnn::Optional<armnn::TensorInfo>(info.m_InputTensorInfos[1]); if (descriptor.m_Parameters.m_BiasEnabled) { - detailsInfo.m_BiasTensorInfo = armnn::Optional<armnn::TensorInfo>(descriptor.m_Bias->GetTensorInfo()); + detailsInfo.m_BiasTensorInfo = armnn::Optional<armnn::TensorInfo>(info.m_InputTensorInfos[2]); } // Report Profiling Details @@ -107,14 +107,25 @@ NeonFullyConnectedWorkload::NeonFullyConnectedWorkload(const FullyConnectedQueue this->GetGuid()); // Force Compute Library to perform the necessary copying and reshaping. - m_FullyConnectedLayer->prepare(); - FreeTensorIfUnused(m_WeightsTensor); - FreeTensorIfUnused(m_BiasesTensor); } void NeonFullyConnectedWorkload::Execute() const { ARMNN_SCOPED_PROFILING_EVENT_NEON_GUID("NeonFullyConnectedWorkload_Execute", this->GetGuid()); + // The constant tensors may not be fully in place until the workload is Executed + if (!prepared) + { + InitializeArmComputeTensorData(*m_WeightsTensor, m_WeightsTensorInfo, m_Data.m_Inputs[1]); + + if (m_Data.m_Parameters.m_BiasEnabled) + { + InitializeArmComputeTensorData(*m_BiasesTensor, m_BiasesTensorInfo, m_Data.m_Inputs[2]); + } + m_FullyConnectedLayer->prepare(); + FreeTensorIfUnused(m_WeightsTensor); + FreeTensorIfUnused(m_BiasesTensor); + prepared = true; + } m_FullyConnectedLayer->run(); } diff --git a/src/backends/neon/workloads/NeonFullyConnectedWorkload.hpp b/src/backends/neon/workloads/NeonFullyConnectedWorkload.hpp index 944731d7bd..d5bb932c6e 100644 --- a/src/backends/neon/workloads/NeonFullyConnectedWorkload.hpp +++ b/src/backends/neon/workloads/NeonFullyConnectedWorkload.hpp @@ -1,5 +1,5 @@ // -// Copyright © 2017 Arm Ltd and Contributors. All rights reserved. +// Copyright © 2017,2022 Arm Ltd and Contributors. All rights reserved. // SPDX-License-Identifier: MIT // @@ -29,13 +29,16 @@ class NeonFullyConnectedWorkload : public NeonBaseWorkload<FullyConnectedQueueDe public: NeonFullyConnectedWorkload(const FullyConnectedQueueDescriptor& descriptor, const WorkloadInfo& info, std::shared_ptr<arm_compute::MemoryManagerOnDemand>& memoryManager); + virtual void Execute() const override; private: std::unique_ptr<arm_compute::IFunction> m_FullyConnectedLayer; - std::unique_ptr<arm_compute::Tensor> m_WeightsTensor; - std::unique_ptr<arm_compute::Tensor> m_BiasesTensor; - + mutable std::unique_ptr<arm_compute::Tensor> m_WeightsTensor; + mutable std::unique_ptr<arm_compute::Tensor> m_BiasesTensor; + TensorInfo m_WeightsTensorInfo; + TensorInfo m_BiasesTensorInfo; + mutable bool prepared = false; }; } //namespace armnn diff --git a/src/backends/neon/workloads/NeonWorkloadUtils.hpp b/src/backends/neon/workloads/NeonWorkloadUtils.hpp index f9c3718e14..9f8bb9540e 100644 --- a/src/backends/neon/workloads/NeonWorkloadUtils.hpp +++ b/src/backends/neon/workloads/NeonWorkloadUtils.hpp @@ -1,5 +1,5 @@ // -// Copyright © 2022 Arm Ltd and Contributors. All rights reserved. +// Copyright © 2017,2022 Arm Ltd and Contributors. All rights reserved. // SPDX-License-Identifier: MIT // #pragma once @@ -58,6 +58,42 @@ void CopyArmComputeTensorData(arm_compute::Tensor& dstTensor, const T* srcData) } inline void InitializeArmComputeTensorData(arm_compute::Tensor& tensor, + TensorInfo tensorInfo, + const ITensorHandle* handle) +{ + ARMNN_ASSERT(handle); + + switch(tensorInfo.GetDataType()) + { + case DataType::Float16: + CopyArmComputeTensorData(tensor, reinterpret_cast<const armnn::Half*>(handle->Map())); + break; + case DataType::Float32: + CopyArmComputeTensorData(tensor, reinterpret_cast<const float*>(handle->Map())); + break; + case DataType::QAsymmU8: + CopyArmComputeTensorData(tensor, reinterpret_cast<const uint8_t*>(handle->Map())); + break; + case DataType::QSymmS8: + case DataType::QAsymmS8: + CopyArmComputeTensorData(tensor, reinterpret_cast<const int8_t*>(handle->Map())); + break; + case DataType::Signed32: + CopyArmComputeTensorData(tensor, reinterpret_cast<const int32_t*>(handle->Map())); + break; + case DataType::QSymmS16: + CopyArmComputeTensorData(tensor, reinterpret_cast<const int16_t*>(handle->Map())); + break; + case DataType::BFloat16: + CopyArmComputeTensorData(tensor, reinterpret_cast<const armnn::BFloat16*>(handle->Map())); + break; + default: + // Throw exception; assertion not called in release build. + throw Exception("Unexpected tensor type during InitializeArmComputeTensorData()."); + } +}; + +inline void InitializeArmComputeTensorData(arm_compute::Tensor& tensor, const ConstTensorHandle* handle) { ARMNN_ASSERT(handle); |