aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorSadik Armagan <sadik.armagan@arm.com>2020-05-27 13:40:58 +0100
committerSadik Armagan <sadik.armagan@arm.com>2020-05-27 12:41:44 +0000
commit9fabf4336bb1e966f3fa192106dcb46562deebcd (patch)
tree1e10d48ec718b68efe50dbb6e0d22c77d5cb5ee8 /src
parent855a47b1b0a78c839a674cc1e61d0668b8c4e349 (diff)
downloadarmnn-9fabf4336bb1e966f3fa192106dcb46562deebcd.tar.gz
IVGCVSW-4200 Add CL EXP Workload
IVGCVSW-4203 Add Neon EXP Workload * Added CL EXP operator workload * Added EXP test suite * Enabled EXP tests on ACL and Ref Signed-off-by: Sadik Armagan <sadik.armagan@arm.com> Change-Id: I793d31af1b2e3fe86b0bec6d9e5de503c5dab970
Diffstat (limited to 'src')
-rw-r--r--src/backends/backendsCommon/common.mk1
-rw-r--r--src/backends/backendsCommon/test/CMakeLists.txt2
-rw-r--r--src/backends/backendsCommon/test/LayerTests.hpp1
-rw-r--r--src/backends/backendsCommon/test/layerTests/ExpTestImpl.cpp185
-rw-r--r--src/backends/backendsCommon/test/layerTests/ExpTestImpl.hpp33
-rw-r--r--src/backends/cl/ClLayerSupport.cpp45
-rw-r--r--src/backends/cl/ClWorkloadFactory.cpp42
-rw-r--r--src/backends/cl/backend.mk1
-rw-r--r--src/backends/cl/test/ClLayerTests.cpp8
-rw-r--r--src/backends/cl/workloads/CMakeLists.txt2
-rw-r--r--src/backends/cl/workloads/ClExpWorkload.cpp45
-rw-r--r--src/backends/cl/workloads/ClExpWorkload.hpp28
-rw-r--r--src/backends/cl/workloads/ClWorkloads.hpp1
-rw-r--r--src/backends/neon/test/NeonLayerTests.cpp6
-rw-r--r--src/backends/neon/workloads/CMakeLists.txt2
-rw-r--r--src/backends/reference/test/RefLayerTests.cpp14
16 files changed, 375 insertions, 41 deletions
diff --git a/src/backends/backendsCommon/common.mk b/src/backends/backendsCommon/common.mk
index 450313f8d7..47e88214af 100644
--- a/src/backends/backendsCommon/common.mk
+++ b/src/backends/backendsCommon/common.mk
@@ -54,6 +54,7 @@ COMMON_TEST_SOURCES := \
test/layerTests/DequantizeTestImpl.cpp \
test/layerTests/DivisionTestImpl.cpp \
test/layerTests/ElementwiseUnaryTestImpl.cpp \
+ test/layerTests/ExpTestImpl.cpp \
test/layerTests/FakeQuantizationTestImpl.cpp \
test/layerTests/FloorTestImpl.cpp \
test/layerTests/FullyConnectedTestImpl.cpp \
diff --git a/src/backends/backendsCommon/test/CMakeLists.txt b/src/backends/backendsCommon/test/CMakeLists.txt
index 0679050c16..81372dab3a 100644
--- a/src/backends/backendsCommon/test/CMakeLists.txt
+++ b/src/backends/backendsCommon/test/CMakeLists.txt
@@ -91,6 +91,8 @@ list(APPEND armnnBackendsCommonUnitTests_sources
layerTests/ElementwiseTestImpl.hpp
layerTests/ElementwiseUnaryTestImpl.cpp
layerTests/ElementwiseUnaryTestImpl.hpp
+ layerTests/ExpTestImpl.cpp
+ layerTests/ExpTestImpl.hpp
layerTests/FakeQuantizationTestImpl.cpp
layerTests/FakeQuantizationTestImpl.hpp
layerTests/FloorTestImpl.cpp
diff --git a/src/backends/backendsCommon/test/LayerTests.hpp b/src/backends/backendsCommon/test/LayerTests.hpp
index 247ed12048..3589056220 100644
--- a/src/backends/backendsCommon/test/LayerTests.hpp
+++ b/src/backends/backendsCommon/test/LayerTests.hpp
@@ -25,6 +25,7 @@
#include <backendsCommon/test/layerTests/DetectionPostProcessTestImpl.hpp>
#include <backendsCommon/test/layerTests/DivisionTestImpl.hpp>
#include <backendsCommon/test/layerTests/ElementwiseUnaryTestImpl.hpp>
+#include <backendsCommon/test/layerTests/ExpTestImpl.hpp>
#include <backendsCommon/test/layerTests/FakeQuantizationTestImpl.hpp>
#include <backendsCommon/test/layerTests/FloorTestImpl.hpp>
#include <backendsCommon/test/layerTests/FullyConnectedTestImpl.hpp>
diff --git a/src/backends/backendsCommon/test/layerTests/ExpTestImpl.cpp b/src/backends/backendsCommon/test/layerTests/ExpTestImpl.cpp
new file mode 100644
index 0000000000..6e68ade1a4
--- /dev/null
+++ b/src/backends/backendsCommon/test/layerTests/ExpTestImpl.cpp
@@ -0,0 +1,185 @@
+//
+// Copyright © 2020 Arm Ltd. All rights reserved.
+// SPDX-License-Identifier: MIT
+//
+
+#include "ExpTestImpl.hpp"
+#include "ElementwiseUnaryTestImpl.hpp"
+
+template<armnn::DataType ArmnnType, typename T>
+LayerTestResult<T, 2> Exp2dTest(
+ armnn::IWorkloadFactory& workloadFactory,
+ const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager)
+{
+ const unsigned int inputShape[] = { 2, 2 };
+
+ std::vector<float> inputValues
+ {
+ 3.0f, 2.0f,
+ 1.0f, 1.1f
+ };
+
+ std::vector<float> expectedOutputValues
+ {
+ 20.085536923188f, 7.389056098931f,
+ 2.718281828459f, 3.004166023946f
+ };
+
+ return ElementwiseUnaryTestHelper<2, ArmnnType>(
+ workloadFactory,
+ memoryManager,
+ armnn::UnaryOperation::Exp,
+ inputShape,
+ inputValues,
+ inputShape,
+ expectedOutputValues);
+}
+
+template<armnn::DataType ArmnnType, typename T>
+LayerTestResult<T, 3> Exp3dTest(
+ armnn::IWorkloadFactory& workloadFactory,
+ const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager)
+{
+ const unsigned int inputShape[] = { 3, 1, 2 };
+
+ std::vector<float> inputValues
+ {
+ 5.0f, 4.0f,
+ 3.0f, 2.0f,
+ 1.0f, 1.1f
+ };
+
+ std::vector<float> expectedOutputValues
+ {
+ 148.413159102577f, 54.598150033144f,
+ 20.085536923188f, 7.389056098931f,
+ 2.718281828459f, 3.004166023946f
+ };
+
+ return ElementwiseUnaryTestHelper<3, ArmnnType>(
+ workloadFactory,
+ memoryManager,
+ armnn::UnaryOperation::Exp,
+ inputShape,
+ inputValues,
+ inputShape,
+ expectedOutputValues);
+}
+
+template<armnn::DataType ArmnnType, typename T>
+LayerTestResult<T, 2> ExpZeroTest(
+ armnn::IWorkloadFactory& workloadFactory,
+ const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager)
+{
+ const unsigned int inputShape[] = { 1, 2 };
+
+ std::vector<float> inputValues
+ {
+ 0.f, 0.f
+ };
+
+ std::vector<float> expectedOutputValues
+ {
+ 1.0f, 1.0f
+ };
+
+ return ElementwiseUnaryTestHelper<2, ArmnnType>(
+ workloadFactory,
+ memoryManager,
+ armnn::UnaryOperation::Exp,
+ inputShape,
+ inputValues,
+ inputShape,
+ expectedOutputValues);
+}
+
+template<armnn::DataType ArmnnType, typename T>
+LayerTestResult<T, 2> ExpNegativeTest(
+ armnn::IWorkloadFactory& workloadFactory,
+ const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager)
+{
+ const unsigned int inputShape[] = { 1, 2 };
+
+ std::vector<float> inputValues
+ {
+ -5.9f, -5.8f
+ };
+
+ std::vector<float> expectedOutputValues
+ {
+ 0.0027394448187683684f, 0.0030275547453758153f,
+ };
+
+ return ElementwiseUnaryTestHelper<2, ArmnnType>(
+ workloadFactory,
+ memoryManager,
+ armnn::UnaryOperation::Exp,
+ inputShape,
+ inputValues,
+ inputShape,
+ expectedOutputValues);
+}
+
+//
+// Explicit template specializations
+//
+
+template LayerTestResult<armnn::ResolveType<armnn::DataType::Float32>, 2>
+Exp2dTest<armnn::DataType::Float32>(
+ armnn::IWorkloadFactory& workloadFactory,
+ const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager);
+
+template LayerTestResult<armnn::ResolveType<armnn::DataType::Float16>, 2>
+Exp2dTest<armnn::DataType::Float16>(
+ armnn::IWorkloadFactory& workloadFactory,
+ const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager);
+
+template LayerTestResult<armnn::ResolveType<armnn::DataType::QAsymmS8>, 2>
+Exp2dTest<armnn::DataType::QAsymmS8>(
+ armnn::IWorkloadFactory& workloadFactory,
+ const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager);
+
+template LayerTestResult<armnn::ResolveType<armnn::DataType::QAsymmU8>, 2>
+Exp2dTest<armnn::DataType::QAsymmU8>(
+ armnn::IWorkloadFactory& workloadFactory,
+ const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager);
+
+template LayerTestResult<armnn::ResolveType<armnn::DataType::QSymmS16>, 2>
+Exp2dTest<armnn::DataType::QSymmS16>(
+ armnn::IWorkloadFactory& workloadFactory,
+ const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager);
+
+template LayerTestResult<armnn::ResolveType<armnn::DataType::Float32>, 3>
+Exp3dTest<armnn::DataType::Float32>(
+ armnn::IWorkloadFactory& workloadFactory,
+ const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager);
+
+template LayerTestResult<armnn::ResolveType<armnn::DataType::Float16>, 3>
+Exp3dTest<armnn::DataType::Float16>(
+ armnn::IWorkloadFactory& workloadFactory,
+ const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager);
+
+template LayerTestResult<armnn::ResolveType<armnn::DataType::QAsymmS8>, 3>
+Exp3dTest<armnn::DataType::QAsymmS8>(
+ armnn::IWorkloadFactory& workloadFactory,
+ const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager);
+
+template LayerTestResult<armnn::ResolveType<armnn::DataType::QAsymmU8>, 3>
+Exp3dTest<armnn::DataType::QAsymmU8>(
+ armnn::IWorkloadFactory& workloadFactory,
+ const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager);
+
+template LayerTestResult<armnn::ResolveType<armnn::DataType::QSymmS16>, 3>
+Exp3dTest<armnn::DataType::QSymmS16>(
+ armnn::IWorkloadFactory& workloadFactory,
+ const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager);
+
+template LayerTestResult<armnn::ResolveType<armnn::DataType::Float32>, 2>
+ExpZeroTest<armnn::DataType::Float32>(
+ armnn::IWorkloadFactory& workloadFactory,
+ const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager);
+
+template LayerTestResult<armnn::ResolveType<armnn::DataType::Float32>, 2>
+ExpNegativeTest<armnn::DataType::Float32>(
+ armnn::IWorkloadFactory& workloadFactory,
+ const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager); \ No newline at end of file
diff --git a/src/backends/backendsCommon/test/layerTests/ExpTestImpl.hpp b/src/backends/backendsCommon/test/layerTests/ExpTestImpl.hpp
new file mode 100644
index 0000000000..2d49ba9863
--- /dev/null
+++ b/src/backends/backendsCommon/test/layerTests/ExpTestImpl.hpp
@@ -0,0 +1,33 @@
+//
+// Copyright © 2020 Arm Ltd. All rights reserved.
+// SPDX-License-Identifier: MIT
+//
+
+#pragma once
+
+#include "LayerTestResult.hpp"
+
+#include <ResolveType.hpp>
+
+#include <armnn/backends/IBackendInternal.hpp>
+#include <backendsCommon/WorkloadFactory.hpp>
+
+template<armnn::DataType ArmnnType, typename T = armnn::ResolveType<ArmnnType>>
+LayerTestResult<T, 2> Exp2dTest(
+ armnn::IWorkloadFactory& workloadFactory,
+ const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager);
+
+template<armnn::DataType ArmnnType, typename T = armnn::ResolveType<ArmnnType>>
+LayerTestResult<T, 3> Exp3dTest(
+ armnn::IWorkloadFactory& workloadFactory,
+ const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager);
+
+template<armnn::DataType ArmnnType, typename T = armnn::ResolveType<ArmnnType>>
+LayerTestResult<T, 2> ExpZeroTest(
+ armnn::IWorkloadFactory& workloadFactory,
+ const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager);
+
+template<armnn::DataType ArmnnType, typename T = armnn::ResolveType<ArmnnType>>
+LayerTestResult<T, 2> ExpNegativeTest(
+ armnn::IWorkloadFactory& workloadFactory,
+ const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager);
diff --git a/src/backends/cl/ClLayerSupport.cpp b/src/backends/cl/ClLayerSupport.cpp
index 7418dbd9e4..c8d3816a4c 100644
--- a/src/backends/cl/ClLayerSupport.cpp
+++ b/src/backends/cl/ClLayerSupport.cpp
@@ -31,6 +31,7 @@
#include "workloads/ClDepthwiseConvolutionWorkload.hpp"
#include "workloads/ClDequantizeWorkload.hpp"
#include "workloads/ClDivisionFloatWorkload.hpp"
+#include "workloads/ClExpWorkload.hpp"
#include "workloads/ClFloorFloatWorkload.hpp"
#include "workloads/ClFullyConnectedWorkload.hpp"
#include "workloads/ClInstanceNormalizationWorkload.hpp"
@@ -399,29 +400,31 @@ bool ClLayerSupport::IsElementwiseUnarySupported(const TensorInfo& input,
const ElementwiseUnaryDescriptor& descriptor,
Optional<std::string&> reasonIfUnsupported) const
{
- if (descriptor.m_Operation == UnaryOperation::Abs)
+ switch(descriptor.m_Operation)
{
- FORWARD_WORKLOAD_VALIDATE_FUNC(ClAbsWorkloadValidate,
- reasonIfUnsupported,
- input,
- output);
- }
- else if (descriptor.m_Operation == UnaryOperation::Rsqrt)
- {
- FORWARD_WORKLOAD_VALIDATE_FUNC(ClRsqrtWorkloadValidate,
- reasonIfUnsupported,
- input,
- output);
- }
- else if (descriptor.m_Operation == UnaryOperation::Neg)
- {
- FORWARD_WORKLOAD_VALIDATE_FUNC(ClNegWorkloadValidate,
- reasonIfUnsupported,
- input,
- output);
+ case UnaryOperation::Abs:
+ FORWARD_WORKLOAD_VALIDATE_FUNC(ClAbsWorkloadValidate,
+ reasonIfUnsupported,
+ input,
+ output);
+ case UnaryOperation::Exp:
+ FORWARD_WORKLOAD_VALIDATE_FUNC(ClExpWorkloadValidate,
+ reasonIfUnsupported,
+ input,
+ output);
+ case UnaryOperation::Neg:
+ FORWARD_WORKLOAD_VALIDATE_FUNC(ClNegWorkloadValidate,
+ reasonIfUnsupported,
+ input,
+ output);
+ case UnaryOperation::Rsqrt:
+ FORWARD_WORKLOAD_VALIDATE_FUNC(ClRsqrtWorkloadValidate,
+ reasonIfUnsupported,
+ input,
+ output);
+ default:
+ return false;
}
-
- return false;
}
bool ClLayerSupport::IsFloorSupported(const TensorInfo& input,
diff --git a/src/backends/cl/ClWorkloadFactory.cpp b/src/backends/cl/ClWorkloadFactory.cpp
index 50a867ca2c..cabc3466aa 100644
--- a/src/backends/cl/ClWorkloadFactory.cpp
+++ b/src/backends/cl/ClWorkloadFactory.cpp
@@ -249,27 +249,31 @@ std::unique_ptr<IWorkload> ClWorkloadFactory::CreateDivision(const DivisionQueue
std::unique_ptr<IWorkload> ClWorkloadFactory::CreateElementwiseUnary(const ElementwiseUnaryQueueDescriptor& descriptor,
const WorkloadInfo& info) const
{
- if (descriptor.m_Parameters.m_Operation == UnaryOperation::Abs)
+ switch(descriptor.m_Parameters.m_Operation)
{
- AbsQueueDescriptor absQueueDescriptor;
- absQueueDescriptor.m_Inputs = descriptor.m_Inputs;
- absQueueDescriptor.m_Outputs = descriptor.m_Outputs;
-
- return MakeWorkload<ClAbsWorkload>(absQueueDescriptor, info);
- }
- else if (descriptor.m_Parameters.m_Operation == UnaryOperation::Rsqrt)
- {
- RsqrtQueueDescriptor rsqrtQueueDescriptor;
- rsqrtQueueDescriptor.m_Inputs = descriptor.m_Inputs;
- rsqrtQueueDescriptor.m_Outputs = descriptor.m_Outputs;
-
- return MakeWorkload<ClRsqrtWorkload>(rsqrtQueueDescriptor, info);
+ case UnaryOperation::Abs:
+ {
+ AbsQueueDescriptor absQueueDescriptor;
+ absQueueDescriptor.m_Inputs = descriptor.m_Inputs;
+ absQueueDescriptor.m_Outputs = descriptor.m_Outputs;
+
+ return std::make_unique<ClAbsWorkload>(absQueueDescriptor, info);
+ }
+ case UnaryOperation::Exp:
+ return std::make_unique<ClExpWorkload>(descriptor, info);
+ case UnaryOperation::Neg:
+ return std::make_unique<ClNegWorkload>(descriptor, info);
+ case UnaryOperation::Rsqrt:
+ {
+ RsqrtQueueDescriptor rsqrtQueueDescriptor;
+ rsqrtQueueDescriptor.m_Inputs = descriptor.m_Inputs;
+ rsqrtQueueDescriptor.m_Outputs = descriptor.m_Outputs;
+
+ return std::make_unique<ClRsqrtWorkload>(rsqrtQueueDescriptor, info);
+ }
+ default:
+ return nullptr;
}
- else if (descriptor.m_Parameters.m_Operation == UnaryOperation::Neg)
- {
- return MakeWorkload<ClNegWorkload>(descriptor, info);
- }
- return MakeWorkload<NullWorkload, NullWorkload>(descriptor, info);
}
std::unique_ptr<IWorkload> ClWorkloadFactory::CreateEqual(const EqualQueueDescriptor& descriptor,
diff --git a/src/backends/cl/backend.mk b/src/backends/cl/backend.mk
index f18f8f03a2..740aee6d67 100644
--- a/src/backends/cl/backend.mk
+++ b/src/backends/cl/backend.mk
@@ -38,6 +38,7 @@ BACKEND_SOURCES := \
workloads/ClDepthwiseConvolutionWorkload.cpp \
workloads/ClDequantizeWorkload.cpp \
workloads/ClDivisionFloatWorkload.cpp \
+ workloads/ClExpWorkload.cpp \
workloads/ClFloorFloatWorkload.cpp \
workloads/ClFullyConnectedWorkload.cpp \
workloads/ClInstanceNormalizationWorkload.cpp \
diff --git a/src/backends/cl/test/ClLayerTests.cpp b/src/backends/cl/test/ClLayerTests.cpp
index 1c433a85c5..e6492f612a 100644
--- a/src/backends/cl/test/ClLayerTests.cpp
+++ b/src/backends/cl/test/ClLayerTests.cpp
@@ -1119,6 +1119,14 @@ ARMNN_AUTO_TEST_CASE(NegNegative, NegNegativeTest<DataType::Float32>)
ARMNN_AUTO_TEST_CASE(Neg2dFloat16, Neg2dTest<DataType::Float16>)
ARMNN_AUTO_TEST_CASE(Neg3dFloat16, Neg3dTest<DataType::Float16>)
+// Exp
+ARMNN_AUTO_TEST_CASE(Exp2d, Exp2dTest<DataType::Float32>)
+ARMNN_AUTO_TEST_CASE(Exo3d, Exp3dTest<DataType::Float32>)
+ARMNN_AUTO_TEST_CASE(ExpZero, ExpZeroTest<DataType::Float32>)
+ARMNN_AUTO_TEST_CASE(ExpNegative, ExpNegativeTest<DataType::Float32>)
+ARMNN_AUTO_TEST_CASE(Exp2dFloat16, Exp2dTest<DataType::Float16>)
+ARMNN_AUTO_TEST_CASE(Exp3dFloat16, Exp3dTest<DataType::Float16>)
+
#if defined(ARMNNREF_ENABLED)
// The ARMNN_COMPARE_REF_AUTO_TEST_CASE and the ARMNN_COMPARE_REF_FIXTURE_TEST_CASE test units are not available
diff --git a/src/backends/cl/workloads/CMakeLists.txt b/src/backends/cl/workloads/CMakeLists.txt
index 6d0aa792a1..7d9df07ed9 100644
--- a/src/backends/cl/workloads/CMakeLists.txt
+++ b/src/backends/cl/workloads/CMakeLists.txt
@@ -36,6 +36,8 @@ list(APPEND armnnClBackendWorkloads_sources
ClDequantizeWorkload.hpp
ClDivisionFloatWorkload.cpp
ClDivisionFloatWorkload.hpp
+ ClExpWorkload.cpp
+ ClExpWorkload.hpp
ClFloorFloatWorkload.cpp
ClFloorFloatWorkload.hpp
ClFullyConnectedWorkload.cpp
diff --git a/src/backends/cl/workloads/ClExpWorkload.cpp b/src/backends/cl/workloads/ClExpWorkload.cpp
new file mode 100644
index 0000000000..5b5e0a5f0c
--- /dev/null
+++ b/src/backends/cl/workloads/ClExpWorkload.cpp
@@ -0,0 +1,45 @@
+//
+// Copyright © 2020 Arm Ltd. All rights reserved.
+// SPDX-License-Identifier: MIT
+//
+
+#include "ClExpWorkload.hpp"
+
+#include "ClWorkloadUtils.hpp"
+
+#include <aclCommon/ArmComputeTensorUtils.hpp>
+#include <armnn/utility/PolymorphicDowncast.hpp>
+
+#include <cl/ClTensorHandle.hpp>
+
+#include <boost/cast.hpp>
+
+namespace armnn
+{
+
+arm_compute::Status ClExpWorkloadValidate(const TensorInfo& input, const TensorInfo& output)
+{
+ const arm_compute::TensorInfo aclInput = armcomputetensorutils::BuildArmComputeTensorInfo(input);
+ const arm_compute::TensorInfo aclOutput = armcomputetensorutils::BuildArmComputeTensorInfo(output);
+
+ return arm_compute::CLExpLayer::validate(&aclInput, &aclOutput);
+}
+
+ClExpWorkload::ClExpWorkload(const ElementwiseUnaryQueueDescriptor& descriptor, const WorkloadInfo& info)
+ : BaseWorkload<ElementwiseUnaryQueueDescriptor>(descriptor, info)
+{
+ m_Data.ValidateInputsOutputs("ClExpWorkload", 1, 1);
+
+ arm_compute::ICLTensor& input = PolymorphicDowncast<ClTensorHandle*>(m_Data.m_Inputs[0])->GetTensor();
+ arm_compute::ICLTensor& output = PolymorphicDowncast<ClTensorHandle*>(m_Data.m_Outputs[0])->GetTensor();
+
+ m_ExpLayer.configure(&input, &output);
+}
+
+void ClExpWorkload::Execute() const
+{
+ ARMNN_SCOPED_PROFILING_EVENT_CL("ClExpWorkload_Execute");
+ RunClFunction(m_ExpLayer, CHECK_LOCATION());
+}
+
+} // namespace armnn
diff --git a/src/backends/cl/workloads/ClExpWorkload.hpp b/src/backends/cl/workloads/ClExpWorkload.hpp
new file mode 100644
index 0000000000..c35aebbeb9
--- /dev/null
+++ b/src/backends/cl/workloads/ClExpWorkload.hpp
@@ -0,0 +1,28 @@
+//
+// Copyright © 2020 Arm Ltd. All rights reserved.
+// SPDX-License-Identifier: MIT
+//
+
+#pragma once
+
+#include <backendsCommon/Workload.hpp>
+
+#include <arm_compute/core/Error.h>
+#include <arm_compute/runtime/CL/functions/CLElementWiseUnaryLayer.h>
+
+namespace armnn
+{
+
+arm_compute::Status ClExpWorkloadValidate(const TensorInfo& input, const TensorInfo& output);
+
+class ClExpWorkload : public BaseWorkload<ElementwiseUnaryQueueDescriptor>
+{
+public:
+ ClExpWorkload(const ElementwiseUnaryQueueDescriptor& descriptor, const WorkloadInfo& info);
+ virtual void Execute() const override;
+
+private:
+ mutable arm_compute::CLExpLayer m_ExpLayer;
+};
+
+} // namespace armnn
diff --git a/src/backends/cl/workloads/ClWorkloads.hpp b/src/backends/cl/workloads/ClWorkloads.hpp
index 7b3ce439be..1ae9a91b88 100644
--- a/src/backends/cl/workloads/ClWorkloads.hpp
+++ b/src/backends/cl/workloads/ClWorkloads.hpp
@@ -17,6 +17,7 @@
#include "ClDepthwiseConvolutionWorkload.hpp"
#include "ClDequantizeWorkload.hpp"
#include "ClDivisionFloatWorkload.hpp"
+#include "ClExpWorkload.hpp"
#include "ClFloorFloatWorkload.hpp"
#include "ClFullyConnectedWorkload.hpp"
#include "ClInstanceNormalizationWorkload.hpp"
diff --git a/src/backends/neon/test/NeonLayerTests.cpp b/src/backends/neon/test/NeonLayerTests.cpp
index e8f0f78bab..0e0558b763 100644
--- a/src/backends/neon/test/NeonLayerTests.cpp
+++ b/src/backends/neon/test/NeonLayerTests.cpp
@@ -1209,6 +1209,12 @@ ARMNN_AUTO_TEST_CASE(Neg3d, Neg3dTest<DataType::Float32>)
ARMNN_AUTO_TEST_CASE(NegZero, NegZeroTest<DataType::Float32>)
ARMNN_AUTO_TEST_CASE(NegNegative, NegNegativeTest<DataType::Float32>)
+// Exp
+ARMNN_AUTO_TEST_CASE(Exp2d, Exp2dTest<DataType::Float32>)
+ARMNN_AUTO_TEST_CASE(Exo3d, Exp3dTest<DataType::Float32>)
+ARMNN_AUTO_TEST_CASE(ExpZero, ExpZeroTest<DataType::Float32>)
+ARMNN_AUTO_TEST_CASE(ExpNegative, ExpNegativeTest<DataType::Float32>)
+
#if defined(ARMNNREF_ENABLED)
// The ARMNN_COMPARE_REF_AUTO_TEST_CASE and the ARMNN_COMPARE_REF_FIXTURE_TEST_CASE test units are not available
diff --git a/src/backends/neon/workloads/CMakeLists.txt b/src/backends/neon/workloads/CMakeLists.txt
index f3b08ecb5d..6b3fe67f1f 100644
--- a/src/backends/neon/workloads/CMakeLists.txt
+++ b/src/backends/neon/workloads/CMakeLists.txt
@@ -110,7 +110,7 @@ list(APPEND armnnNeonBackendWorkloads_sources
NeonWorkloadUtils.hpp
)
-add_library(armnnNeonBackendWorkloads OBJECT ${armnnNeonBackendWorkloads_sources} NeonExpWorkload.cpp NeonExpWorkload.hpp)
+add_library(armnnNeonBackendWorkloads OBJECT ${armnnNeonBackendWorkloads_sources})
target_include_directories(armnnNeonBackendWorkloads PRIVATE ${PROJECT_SOURCE_DIR}/src/armnn)
target_include_directories(armnnNeonBackendWorkloads PRIVATE ${PROJECT_SOURCE_DIR}/src/armnnUtils)
target_include_directories(armnnNeonBackendWorkloads PRIVATE ${PROJECT_SOURCE_DIR}/src/backends)
diff --git a/src/backends/reference/test/RefLayerTests.cpp b/src/backends/reference/test/RefLayerTests.cpp
index fc30b0d9a5..0250299c81 100644
--- a/src/backends/reference/test/RefLayerTests.cpp
+++ b/src/backends/reference/test/RefLayerTests.cpp
@@ -2008,4 +2008,18 @@ ARMNN_AUTO_TEST_CASE(Neg3dQuantisedAsymm8, Neg3dTest<DataType::QAsymmU8>)
ARMNN_AUTO_TEST_CASE(Neg2dQuantisedSymm16, Neg2dTest<DataType::QSymmS16>)
ARMNN_AUTO_TEST_CASE(Neg3dQuantisedSymm16, Neg3dTest<DataType::QSymmS16>)
+// Exp
+ARMNN_AUTO_TEST_CASE(Exp2d, Exp2dTest<DataType::Float32>)
+ARMNN_AUTO_TEST_CASE(Exo3d, Exp3dTest<DataType::Float32>)
+ARMNN_AUTO_TEST_CASE(ExpZero, ExpZeroTest<DataType::Float32>)
+ARMNN_AUTO_TEST_CASE(ExpNegative, ExpNegativeTest<DataType::Float32>)
+ARMNN_AUTO_TEST_CASE(Exp2dFloat16, Exp2dTest<DataType::Float16>)
+ARMNN_AUTO_TEST_CASE(Exp3dFloat16, Exp3dTest<DataType::Float16>)
+ARMNN_AUTO_TEST_CASE(Exp2dQuantisedAsymmS8, Exp2dTest<DataType::QAsymmS8>)
+ARMNN_AUTO_TEST_CASE(Exp3dQuantisedAsymmS8, Exp3dTest<DataType::QAsymmS8>)
+ARMNN_AUTO_TEST_CASE(Exp2dQuantisedAsymm8, Exp2dTest<DataType::QAsymmU8>)
+ARMNN_AUTO_TEST_CASE(Exp3dQuantisedAsymm8, Exp3dTest<DataType::QAsymmU8>)
+ARMNN_AUTO_TEST_CASE(Exp2dQuantisedSymm16, Exp2dTest<DataType::QSymmS16>)
+ARMNN_AUTO_TEST_CASE(Exp3dQuantisedSymm16, Exp3dTest<DataType::QSymmS16>)
+
BOOST_AUTO_TEST_SUITE_END()