diff options
Diffstat (limited to 'src/backends/reference')
-rw-r--r-- | src/backends/reference/RefLayerSupport.cpp | 30 | ||||
-rw-r--r-- | src/backends/reference/RefLayerSupport.hpp | 5 | ||||
-rw-r--r-- | src/backends/reference/RefWorkloadFactory.cpp | 6 | ||||
-rw-r--r-- | src/backends/reference/RefWorkloadFactory.hpp | 3 | ||||
-rw-r--r-- | src/backends/reference/backend.mk | 3 | ||||
-rw-r--r-- | src/backends/reference/test/RefLayerTests.cpp | 7 | ||||
-rw-r--r-- | src/backends/reference/workloads/CMakeLists.txt | 6 | ||||
-rw-r--r-- | src/backends/reference/workloads/Mean.hpp | 22 | ||||
-rw-r--r-- | src/backends/reference/workloads/Reduce.cpp (renamed from src/backends/reference/workloads/Mean.cpp) | 48 | ||||
-rw-r--r-- | src/backends/reference/workloads/Reduce.hpp | 24 | ||||
-rw-r--r-- | src/backends/reference/workloads/RefMeanWorkload.cpp | 9 | ||||
-rw-r--r-- | src/backends/reference/workloads/RefReduceWorkload.cpp | 42 | ||||
-rw-r--r-- | src/backends/reference/workloads/RefReduceWorkload.hpp | 23 | ||||
-rw-r--r-- | src/backends/reference/workloads/RefWorkloads.hpp | 1 |
14 files changed, 182 insertions, 47 deletions
diff --git a/src/backends/reference/RefLayerSupport.cpp b/src/backends/reference/RefLayerSupport.cpp index bdaaafb0af..992ae71f97 100644 --- a/src/backends/reference/RefLayerSupport.cpp +++ b/src/backends/reference/RefLayerSupport.cpp @@ -1706,6 +1706,36 @@ bool RefLayerSupport::IsRankSupported(const TensorInfo& input, "Reference rank: input type not supported."); } +bool RefLayerSupport::IsReduceSupported(const TensorInfo& input, + const TensorInfo& output, + const ReduceDescriptor& descriptor, + Optional<std::string&> reasonIfUnsupported) const +{ + IgnoreUnused(descriptor); + bool supported = true; + std::array<DataType,7> supportedTypes = + { + DataType::BFloat16, + DataType::Float32, + DataType::Float16, + DataType::QAsymmS8, + DataType::QAsymmU8, + DataType::QSymmS16, + DataType::Signed32 + }; + + supported &= CheckSupportRule(TypeAnyOf(input, supportedTypes), reasonIfUnsupported, + "Reference Reduce: input type not supported"); + + supported &= CheckSupportRule(TypeAnyOf(output, supportedTypes), reasonIfUnsupported, + "Reference Reduce: output type not supported"); + + supported &= CheckSupportRule(TypesAreEqual(input, output), reasonIfUnsupported, + "Reference Reduce: input and output types not matching"); + + return supported; +} + bool RefLayerSupport::IsReshapeSupported(const TensorInfo& input, const TensorInfo& output, const ReshapeDescriptor& descriptor, diff --git a/src/backends/reference/RefLayerSupport.hpp b/src/backends/reference/RefLayerSupport.hpp index 6b6440833e..b75b778f7a 100644 --- a/src/backends/reference/RefLayerSupport.hpp +++ b/src/backends/reference/RefLayerSupport.hpp @@ -275,6 +275,11 @@ public: const TensorInfo& output, Optional<std::string&> reasonIfUnsupported = EmptyOptional()) const override; + bool IsReduceSupported(const TensorInfo& input, + const TensorInfo& output, + const ReduceDescriptor& descriptor, + Optional<std::string&> reasonIfUnsupported = EmptyOptional()) const override; + bool IsReshapeSupported(const TensorInfo& input, const TensorInfo& output, const ReshapeDescriptor& descriptor, diff --git a/src/backends/reference/RefWorkloadFactory.cpp b/src/backends/reference/RefWorkloadFactory.cpp index 468aeb3877..fde6c863c3 100644 --- a/src/backends/reference/RefWorkloadFactory.cpp +++ b/src/backends/reference/RefWorkloadFactory.cpp @@ -580,6 +580,12 @@ std::unique_ptr<IWorkload> RefWorkloadFactory::CreateRank(const RankQueueDescrip return std::make_unique<RefRankWorkload>(descriptor, info); } +std::unique_ptr<IWorkload> RefWorkloadFactory::CreateReduce(const ReduceQueueDescriptor& descriptor, + const WorkloadInfo& info) const +{ + return std::make_unique<RefReduceWorkload>(descriptor, info); +} + std::unique_ptr<IWorkload> RefWorkloadFactory::CreateReshape(const ReshapeQueueDescriptor& descriptor, const WorkloadInfo& info) const { diff --git a/src/backends/reference/RefWorkloadFactory.hpp b/src/backends/reference/RefWorkloadFactory.hpp index 41cefd34ce..c22d87fa43 100644 --- a/src/backends/reference/RefWorkloadFactory.hpp +++ b/src/backends/reference/RefWorkloadFactory.hpp @@ -223,6 +223,9 @@ public: std::unique_ptr<IWorkload> CreateRank(const RankQueueDescriptor& descriptor, const WorkloadInfo& info) const override; + std::unique_ptr<IWorkload> CreateReduce(const ReduceQueueDescriptor& descriptor, + const WorkloadInfo& info) const override; + std::unique_ptr<IWorkload> CreateReshape(const ReshapeQueueDescriptor& descriptor, const WorkloadInfo& info) const override; diff --git a/src/backends/reference/backend.mk b/src/backends/reference/backend.mk index b4aa3a0953..96765097e4 100644 --- a/src/backends/reference/backend.mk +++ b/src/backends/reference/backend.mk @@ -38,11 +38,11 @@ BACKEND_SOURCES := \ workloads/InstanceNorm.cpp \ workloads/LogSoftmax.cpp \ workloads/LstmUtils.cpp \ - workloads/Mean.cpp \ workloads/Concatenate.cpp \ workloads/Pad.cpp \ workloads/Pooling2d.cpp \ workloads/PreluImpl.cpp \ + workloads/Reduce.cpp \ workloads/RefActivationWorkload.cpp \ workloads/RefArgMinMaxWorkload.cpp \ workloads/RefBatchNormalizationWorkload.cpp \ @@ -81,6 +81,7 @@ BACKEND_SOURCES := \ workloads/RefPreluWorkload.cpp \ workloads/RefQLstmWorkload.cpp \ workloads/RefQuantizeWorkload.cpp \ + workloads/RefReduceWorkload.cpp \ workloads/RefReshapeWorkload.cpp \ workloads/RefResizeBilinearWorkload.cpp \ workloads/RefResizeWorkload.cpp \ diff --git a/src/backends/reference/test/RefLayerTests.cpp b/src/backends/reference/test/RefLayerTests.cpp index 502e0cb84d..d5e0f8290b 100644 --- a/src/backends/reference/test/RefLayerTests.cpp +++ b/src/backends/reference/test/RefLayerTests.cpp @@ -2234,4 +2234,11 @@ ARMNN_AUTO_TEST_CASE_WITH_THF(LogicalOrBroadcast2, LogicalOrBroadcast2Test) ARMNN_AUTO_TEST_CASE_WITH_THF(LogicalAndBroadcast3, LogicalAndBroadcast3Test) ARMNN_AUTO_TEST_CASE_WITH_THF(LogicalOrBroadcast3, LogicalOrBroadcast3Test) +// ReduceSum +ARMNN_AUTO_TEST_CASE_WITH_THF(ReduceSumFloat32, ReduceSumSimpleTest<DataType::Float32>) +ARMNN_AUTO_TEST_CASE_WITH_THF(ReduceSumSingleAxisFloat32_1, ReduceSumSingleAxisTest1<DataType::Float32>) +ARMNN_AUTO_TEST_CASE_WITH_THF(ReduceSumSingleAxisFloat32_2, ReduceSumSingleAxisTest2<DataType::Float32>) +ARMNN_AUTO_TEST_CASE_WITH_THF(ReduceSumSingleAxisFloat32_3, ReduceSumSingleAxisTest3<DataType::Float32>) +ARMNN_AUTO_TEST_CASE_WITH_THF(ReduceSumMultipleAxisFloat32, ReduceSumMultipleAxisTest<DataType::Float32>) + BOOST_AUTO_TEST_SUITE_END() diff --git a/src/backends/reference/workloads/CMakeLists.txt b/src/backends/reference/workloads/CMakeLists.txt index 1b20e5bf2d..1f4298be5d 100644 --- a/src/backends/reference/workloads/CMakeLists.txt +++ b/src/backends/reference/workloads/CMakeLists.txt @@ -44,8 +44,6 @@ list(APPEND armnnRefBackendWorkloads_sources LstmUtils.hpp LstmUtils.cpp Maximum.hpp - Mean.cpp - Mean.hpp Concatenate.hpp Concatenate.cpp Minimum.hpp @@ -55,6 +53,8 @@ list(APPEND armnnRefBackendWorkloads_sources Pooling2d.hpp PreluImpl.cpp PreluImpl.hpp + Reduce.cpp + Reduce.hpp RefActivationWorkload.cpp RefActivationWorkload.hpp RefArgMinMaxWorkload.cpp @@ -132,6 +132,8 @@ list(APPEND armnnRefBackendWorkloads_sources RefQLstmWorkload.cpp RefQLstmWorkload.hpp RefRankWorkload.hpp + RefReduceWorkload.cpp + RefReduceWorkload.hpp RefReshapeWorkload.cpp RefReshapeWorkload.hpp RefResizeBilinearWorkload.cpp diff --git a/src/backends/reference/workloads/Mean.hpp b/src/backends/reference/workloads/Mean.hpp deleted file mode 100644 index dfb0302bf9..0000000000 --- a/src/backends/reference/workloads/Mean.hpp +++ /dev/null @@ -1,22 +0,0 @@ -// -// Copyright © 2017 Arm Ltd. All rights reserved. -// SPDX-License-Identifier: MIT -// - -#pragma once - -#include "armnn/DescriptorsFwd.hpp" -#include "armnn/Tensor.hpp" -#include "BaseIterator.hpp" - -#include <vector> - -namespace armnn -{ -void Mean(const TensorInfo& inputInfo, - const TensorInfo& outputInfo, - const std::vector<unsigned int>& axis, - Decoder<float>& input, - Encoder<float>& output); -} //namespace armnn - diff --git a/src/backends/reference/workloads/Mean.cpp b/src/backends/reference/workloads/Reduce.cpp index fe34efe0c7..5375c7163a 100644 --- a/src/backends/reference/workloads/Mean.cpp +++ b/src/backends/reference/workloads/Reduce.cpp @@ -1,13 +1,14 @@ // -// Copyright © 2017 Arm Ltd. All rights reserved. +// Copyright © 2021 Arm Ltd and Contributors. All rights reserved. // SPDX-License-Identifier: MIT // -#include "Mean.hpp" -#include <backendsCommon/WorkloadData.hpp> +#include "Reduce.hpp" #include <armnn/utility/NumericCast.hpp> +#include <backendsCommon/WorkloadData.hpp> + #include <cmath> #include <cstddef> #include <functional> @@ -15,6 +16,7 @@ namespace armnn { + bool NextIndex(const unsigned int numDims, const armnn::TensorShape& dims, std::vector<unsigned int>& current) { unsigned int carry = 1; @@ -64,18 +66,16 @@ unsigned int ReducedOutputOffset(const unsigned int numDims, } return offset; } -} // namespace -namespace armnn -{ -void Mean(const armnn::TensorInfo& inputInfo, - const armnn::TensorInfo& outputInfo, - const std::vector<unsigned int>& axis, - Decoder<float>& input, - Encoder<float>& output) -{ - unsigned int inputNumDims = inputInfo.GetNumDimensions(); +void Reduce(const TensorInfo& inputInfo, + const TensorInfo& outputInfo, + Decoder<float>& input, + Encoder<float>& output, + const std::vector<uint32_t> axis, + const ReduceOperation reduceOperation) +{ + unsigned int inputNumDims = inputInfo.GetNumDimensions(); unsigned int outputNumDims = outputInfo.GetNumDimensions(); armnn::TensorShape outputDims = outputInfo.GetShape(); @@ -106,10 +106,10 @@ void Mean(const armnn::TensorInfo& inputInfo, std::vector<unsigned int> resolvedAxis = axis; if (resolvedAxis.empty()) { - for (unsigned int idx = 0; idx < inputNumDims; ++idx) - { - resolvedAxis.push_back(idx); - } + for (unsigned int idx = 0; idx < inputNumDims; ++idx) + { + resolvedAxis.push_back(idx); + } } auto numResolvedAxis = armnn::numeric_cast<unsigned int>(resolvedAxis.size()); @@ -129,15 +129,23 @@ void Mean(const armnn::TensorInfo& inputInfo, { unsigned int current = inputDims[resolvedAxis[idx]]; ARMNN_ASSERT(armnn::numeric_cast<float>(current) < - (std::numeric_limits<float>::max() / armnn::numeric_cast<float>(numElementsInAxis))); + (std::numeric_limits<float>::max() / armnn::numeric_cast<float>(numElementsInAxis))); numElementsInAxis *= current; } if (numElementsInAxis > 0) { for (unsigned int idx = 0; idx < numOutputs; ++idx) { output[idx]; - output.Set(tempSum[idx] / armnn::numeric_cast<float>(numElementsInAxis)); + if (reduceOperation == ReduceOperation::Sum) + { + output.Set(tempSum[idx]); + } + else if (reduceOperation == ReduceOperation::Mean) + { + output.Set(tempSum[idx] / armnn::numeric_cast<float>(numElementsInAxis)); + } } } } -} //namespace armnn + +} //namespace armnn
\ No newline at end of file diff --git a/src/backends/reference/workloads/Reduce.hpp b/src/backends/reference/workloads/Reduce.hpp new file mode 100644 index 0000000000..ad777adcf5 --- /dev/null +++ b/src/backends/reference/workloads/Reduce.hpp @@ -0,0 +1,24 @@ +// +// Copyright © 2021 Arm Ltd and Contributors. All rights reserved. +// SPDX-License-Identifier: MIT +// + +#pragma once + +#include "BaseIterator.hpp" +#include "Decoders.hpp" +#include "Encoders.hpp" + +#include <armnn/Tensor.hpp> + +namespace armnn +{ + +void Reduce(const TensorInfo& inputInfo, + const TensorInfo& outputInfo, + Decoder<float>& input, + Encoder<float>& output, + const std::vector<uint32_t> axis, + const ReduceOperation reduceOperation); + +} //namespace armnn diff --git a/src/backends/reference/workloads/RefMeanWorkload.cpp b/src/backends/reference/workloads/RefMeanWorkload.cpp index 375ab395be..00e59bca4c 100644 --- a/src/backends/reference/workloads/RefMeanWorkload.cpp +++ b/src/backends/reference/workloads/RefMeanWorkload.cpp @@ -5,7 +5,7 @@ #include "RefMeanWorkload.hpp" -#include "Mean.hpp" +#include "Reduce.hpp" #include "RefWorkloadUtils.hpp" #include "Profiling.hpp" @@ -28,7 +28,12 @@ void RefMeanWorkload::Execute() const auto inputDecoder = MakeDecoder<float>(inputInfo, m_Data.m_Inputs[0]->Map()); auto outputEncoder = MakeEncoder<float>(outputInfo, m_Data.m_Outputs[0]->Map()); - Mean(inputInfo, outputInfo, m_Data.m_Parameters.m_Axis, *inputDecoder, *outputEncoder); + Reduce(inputInfo, + outputInfo, + *inputDecoder, + *outputEncoder, + m_Data.m_Parameters.m_Axis, + armnn::ReduceOperation::Mean); } } //namespace armnn diff --git a/src/backends/reference/workloads/RefReduceWorkload.cpp b/src/backends/reference/workloads/RefReduceWorkload.cpp new file mode 100644 index 0000000000..7a46ff9ffc --- /dev/null +++ b/src/backends/reference/workloads/RefReduceWorkload.cpp @@ -0,0 +1,42 @@ +// +// Copyright © 2020 Samsung Electronics Co Ltd and Contributors. All rights reserved. +// SPDX-License-Identifier: MIT +// + +#include "RefReduceWorkload.hpp" + +#include "Reduce.hpp" +#include "RefWorkloadUtils.hpp" +#include "BaseIterator.hpp" +#include "Profiling.hpp" + +namespace armnn +{ + +RefReduceWorkload::RefReduceWorkload( + const ReduceQueueDescriptor& descriptor, + const WorkloadInfo& info) + : BaseWorkload<ReduceQueueDescriptor>(descriptor, info) {} + +void RefReduceWorkload::Execute() const +{ + ARMNN_SCOPED_PROFILING_EVENT(Compute::CpuRef, "RefReduceWorkload_Execute"); + + const TensorInfo& inputInfo = GetTensorInfo(m_Data.m_Inputs[0]); + const TensorInfo& outputInfo = GetTensorInfo(m_Data.m_Outputs[0]); + + std::unique_ptr<Decoder<float>> decoderPtr = MakeDecoder<float>(inputInfo, m_Data.m_Inputs[0]->Map()); + Decoder<float>& decoder = *decoderPtr; + + std::unique_ptr<Encoder<float>> encoderPtr = MakeEncoder<float>(outputInfo, m_Data.m_Outputs[0]->Map()); + Encoder<float>& encoder = *encoderPtr; + + Reduce(inputInfo, + outputInfo, + decoder, + encoder, + m_Data.m_Parameters.m_vAxis, + m_Data.m_Parameters.m_ReduceOperation); +} + +} //namespace armnn diff --git a/src/backends/reference/workloads/RefReduceWorkload.hpp b/src/backends/reference/workloads/RefReduceWorkload.hpp new file mode 100644 index 0000000000..1d551acb4a --- /dev/null +++ b/src/backends/reference/workloads/RefReduceWorkload.hpp @@ -0,0 +1,23 @@ +// +// Copyright © 2020 Samsung Electronics Co Ltd and Contributors. All rights reserved. +// SPDX-License-Identifier: MIT +// + +#pragma once + +#include <backendsCommon/Workload.hpp> +#include <backendsCommon/WorkloadData.hpp> + +namespace armnn +{ + +class RefReduceWorkload : public BaseWorkload<ReduceQueueDescriptor> +{ +public: + explicit RefReduceWorkload(const ReduceQueueDescriptor& descriptor, + const WorkloadInfo& info); + + virtual void Execute() const override; +}; + +} //namespace armnn diff --git a/src/backends/reference/workloads/RefWorkloads.hpp b/src/backends/reference/workloads/RefWorkloads.hpp index 390b2a8d55..989644f633 100644 --- a/src/backends/reference/workloads/RefWorkloads.hpp +++ b/src/backends/reference/workloads/RefWorkloads.hpp @@ -54,6 +54,7 @@ #include "RefQLstmWorkload.hpp" #include "RefQuantizeWorkload.hpp" #include "RefRankWorkload.hpp" +#include "RefReduceWorkload.hpp" #include "RefReshapeWorkload.hpp" #include "RefResizeBilinearWorkload.hpp" #include "RefResizeWorkload.hpp" |