aboutsummaryrefslogtreecommitdiff
path: root/src/backends/tosaReference
diff options
context:
space:
mode:
authorMatthew Sloyan <matthew.sloyan@arm.com>2022-10-28 18:02:17 +0100
committerMatthew Sloyan <matthew.sloyan@arm.com>2022-11-02 15:08:37 +0000
commit164bf4f29f6f1b2a3e6714ef4f5a21fc0fd16c2b (patch)
treee7296130a787578e1be4d3a93de46a9c466944b4 /src/backends/tosaReference
parent2e950f4fa774ac995230addea898f3b11bf146cc (diff)
downloadarmnn-164bf4f29f6f1b2a3e6714ef4f5a21fc0fd16c2b.tar.gz
IVGCVSW-7164 Implement TosaRefBackend::OptimizeSubgraphView
* Added TosaRefBackend::OptimizeSubgraphView implementation. * Generalised TosaRefLayerSupport::IsLayerSupported to work with any operator. * Changed TosaCommon.hpp utils to inline functions. * Added source files for TosaMappings.hpp and AdditionOperator.hpp. * Fixed multiple defines issue with HALF_ROUND_STYLE and HALF_ROUND_TIES_TO_EVEN. Signed-off-by: Matthew Sloyan <matthew.sloyan@arm.com> Change-Id: Ib2576ec3fb97faa3a2256b2fb93ec16ac8745760
Diffstat (limited to 'src/backends/tosaReference')
-rw-r--r--src/backends/tosaReference/TosaRefBackend.cpp45
-rw-r--r--src/backends/tosaReference/TosaRefLayerSupport.cpp35
-rw-r--r--src/backends/tosaReference/test/CMakeLists.txt1
-rw-r--r--src/backends/tosaReference/test/TosaRefOptimizedNetworkTests.cpp54
4 files changed, 121 insertions, 14 deletions
diff --git a/src/backends/tosaReference/TosaRefBackend.cpp b/src/backends/tosaReference/TosaRefBackend.cpp
index 093802958b..688cf93b49 100644
--- a/src/backends/tosaReference/TosaRefBackend.cpp
+++ b/src/backends/tosaReference/TosaRefBackend.cpp
@@ -9,6 +9,7 @@
#include "TosaRefLayerSupport.hpp"
#include "TosaRefTensorHandleFactory.hpp"
+#include <tosaCommon/TosaMappings.hpp>
#include <armnn/BackendRegistry.hpp>
#include <armnn/backends/IBackendContext.hpp>
#include <armnn/backends/IMemoryManager.hpp>
@@ -21,6 +22,13 @@
namespace armnn
{
+// Utility function to construct a valid Deleter for TosaSerializationHandler ptrs passed back to ArmNN
+template <typename T>
+void DeleteAsType(const void* const blob)
+{
+ delete static_cast<const T*>(blob);
+}
+
const BackendId& TosaRefBackend::GetIdStatic()
{
static const BackendId s_Id{TosaRefBackendId()};
@@ -75,11 +83,44 @@ OptimizationViews TosaRefBackend::OptimizeSubgraphView(const SubgraphView& subgr
const ModelOptions& modelOptions) const
{
OptimizationViews optimizationViews(modelOptions);
- optimizationViews.AddUntouchedSubgraph(SubgraphView(subgraph));
-
+ auto handler = std::make_unique<TosaSerializationHandler>();
+
+ auto it = subgraph.endIConnectable();
+ while (it != subgraph.beginIConnectable())
+ {
+ --it;
+ Layer &base = *(PolymorphicDowncast<Layer*>(*it));
+
+ if(base.GetType() == armnn::LayerType::Input ||
+ base.GetType() == armnn::LayerType::Output)
+ {
+ continue;
+ }
+
+ tosa::TosaSerializationBasicBlock* mappings = GetTosaMappingFromLayer(&base);
+ handler.get()->GetBlocks().push_back(mappings);
+ }
+
+ auto compiledBlob =
+ std::make_unique<PreCompiledObjectPtr>(handler.release(), DeleteAsType<TosaSerializationHandler>);
+
+ IConnectableLayer* preCompiledLayer = optimizationViews.GetINetwork()->AddPrecompiledLayer(
+ PreCompiledDescriptor(subgraph.GetNumInputSlots(), subgraph.GetNumOutputSlots()),
+ std::move(*compiledBlob),
+ armnn::Optional<BackendId>(GetId()),
+ "TOSA_Pre_Compiled_Layer");
+
+ // Copy the output tensor infos from sub-graph
+ for (unsigned int i = 0; i < subgraph.GetNumOutputSlots(); i++)
+ {
+ preCompiledLayer->GetOutputSlot(i).SetTensorInfo(subgraph.GetIOutputSlot(i)->GetTensorInfo());
+ }
+
+ optimizationViews.AddSubstitution({ std::move(subgraph), SubgraphView(preCompiledLayer) });
return optimizationViews;
}
+
std::vector<ITensorHandleFactory::FactoryId> TosaRefBackend::GetHandleFactoryPreferences() const
{
return std::vector<ITensorHandleFactory::FactoryId> { TosaRefTensorHandleFactory::GetIdStatic() };
diff --git a/src/backends/tosaReference/TosaRefLayerSupport.cpp b/src/backends/tosaReference/TosaRefLayerSupport.cpp
index 18530bb535..f5f34a814b 100644
--- a/src/backends/tosaReference/TosaRefLayerSupport.cpp
+++ b/src/backends/tosaReference/TosaRefLayerSupport.cpp
@@ -95,25 +95,36 @@ bool TosaRefLayerSupport::IsLayerSupported(const LayerType& type,
IgnoreUnused(lstmParamsInfo);
IgnoreUnused(quantizedLstmInputParamsInfo);
- // Setup Inputs
- const auto input0 = infos[0];
- const TensorInfo* ptr0 = &input0;
- const auto input1 = infos[1];
- const TensorInfo* ptr1 = &input1;
- std::vector<const TensorInfo*> inputInfos = {ptr0, ptr1};
-
- // Setup Outputs
- const auto output = infos[2];
- const TensorInfo* ptr2 = &output;
- std::vector<const TensorInfo*> outputInfos = {ptr2};
+ std::vector<const TensorInfo*> inputInfos;
+ std::vector<const TensorInfo*> outputInfos;
+
+ switch (type)
+ {
+ case LayerType::Addition:
+ // Setup inputs and outputs
+ inputInfos.push_back(&infos[0]);
+ inputInfos.push_back(&infos[1]);
+ outputInfos.push_back(&infos[2]);
+ break;
+ case LayerType::Input:
+ case LayerType::Output:
+ return true;
+ default:
+ break;
+ }
auto mappings = GetTosaMapping(type, inputInfos, outputInfos, descriptor);
+ if (mappings->GetName() == "")
+ {
+ // There currently isn't a TOSA mapping for this layer, as the default was returned.
+ return false;
+ }
// Loop through block and get each tensor and operator
for (long unsigned int i = 0; i < mappings->GetOperators().size(); ++i)
{
// While looping over operators check for op_UNKNOWN which is unsupported
- if (mappings->GetOperators()[i]->GetOp() == tosa::Op_UNKNOWN) { return false;}
+ if (mappings->GetOperators()[i]->GetOp() == tosa::Op_UNKNOWN) { return false; }
// Loop over operators and get GetInput/OutputTensorNames, loop over resulting names and
// use GetTensorByName to pass pointers to tensors on to the IsTosaLayerSupported()
diff --git a/src/backends/tosaReference/test/CMakeLists.txt b/src/backends/tosaReference/test/CMakeLists.txt
index 8366901605..627a1836e1 100644
--- a/src/backends/tosaReference/test/CMakeLists.txt
+++ b/src/backends/tosaReference/test/CMakeLists.txt
@@ -6,6 +6,7 @@
list(APPEND armnnTosaRefBackendUnitTests_sources
TosaRefLayerTests.cpp
TosaRefLayerSupportTests.cpp
+ TosaRefOptimizedNetworkTests.cpp
)
add_library(armnnTosaRefBackendUnitTests OBJECT ${armnnTosaRefBackendUnitTests_sources})
diff --git a/src/backends/tosaReference/test/TosaRefOptimizedNetworkTests.cpp b/src/backends/tosaReference/test/TosaRefOptimizedNetworkTests.cpp
new file mode 100644
index 0000000000..64b6805d2c
--- /dev/null
+++ b/src/backends/tosaReference/test/TosaRefOptimizedNetworkTests.cpp
@@ -0,0 +1,54 @@
+//
+// Copyright © 2022 Arm Ltd and Contributors. All rights reserved.
+// SPDX-License-Identifier: MIT
+//
+
+#include <armnn/INetwork.hpp>
+
+#include <GraphUtils.hpp>
+#include <TestUtils.hpp>
+
+#include <doctest/doctest.h>
+
+TEST_SUITE("TosaReferenceOptimizedNetwork")
+{
+
+TEST_CASE("SimpleSupportedOptimizedNetwork")
+{
+ armnn::IRuntime::CreationOptions options;
+ armnn::IRuntimePtr runtime(armnn::IRuntime::Create(options));
+ armnn::INetworkPtr network(armnn::INetwork::Create());
+
+ auto inputLayer1 = network->AddInputLayer(0, "input_1");
+ auto inputLayer2 = network->AddInputLayer(1, "input_2");
+ auto addLayer = network->AddAdditionLayer("add");
+ auto outputLayer = network->AddOutputLayer(2, "output");
+
+ armnn::TensorInfo tensorInfo{{4}, armnn::DataType::Float32};
+
+ inputLayer1->GetOutputSlot(0).Connect(addLayer->GetInputSlot(0));
+ inputLayer1->GetOutputSlot(0).SetTensorInfo(tensorInfo);
+
+ inputLayer2->GetOutputSlot(0).Connect(addLayer->GetInputSlot(1));
+ inputLayer2->GetOutputSlot(0).SetTensorInfo(tensorInfo);
+
+ addLayer->GetOutputSlot(0).Connect(outputLayer->GetInputSlot(0));
+ addLayer->GetOutputSlot(0).SetTensorInfo(tensorInfo);
+
+ std::vector<armnn::BackendId> backends = { "TosaRef" };
+
+ armnn::OptimizerOptions optimizedOptions;
+ armnn::IOptimizedNetworkPtr optNet = Optimize(*network, backends, runtime->GetDeviceSpec(), optimizedOptions);
+ CHECK(optNet);
+
+ armnn::Graph& graph = GetGraphForTesting(optNet.get());
+
+ // Check graph layer sequence to ensure that the network has been replaced with a PreCompiledLayer
+ CHECK(CheckSequence(graph.cbegin(), graph.cend(),
+ &IsLayerOfType<armnn::InputLayer>,
+ &IsLayerOfType<armnn::InputLayer>,
+ &IsLayerOfType<armnn::PreCompiledLayer>,
+ &IsLayerOfType<armnn::OutputLayer>));
+}
+
+}