diff options
author | Sadik Armagan <sadik.armagan@arm.com> | 2021-03-25 07:46:55 +0000 |
---|---|---|
committer | Sadik Armagan <sadik.armagan@arm.com> | 2021-03-25 07:46:55 +0000 |
commit | f0a6dec75832604d5ab18242dc216852821a8279 (patch) | |
tree | ff25e64c62c63975a54abd16a8bff744be70d7c0 /src/armnnSerializer | |
parent | 16fb1a2d9c1d3d80c0f0b6ab549919fbabd2a0b9 (diff) | |
download | armnn-f0a6dec75832604d5ab18242dc216852821a8279.tar.gz |
IVGCVSW-5736 and IVGCVSW-5743 'NonConstWeights: Update front-end and TfLiteDelegate support for FullyConnected Operator'
* Added front-end support for non-const weights for FULLY_CONNECTED operator
* Added FULLY_CONNECTED end-to-end test
* Updated FULLY_CONNECTED operator support in TfLite Arm NN Delegate for non-const weights
* Updated the version numbers
Signed-off-by: Sadik Armagan <sadik.armagan@arm.com>
Change-Id: Iffa5b9aa9297aca4c02d923cce4636c88ac21faa
Diffstat (limited to 'src/armnnSerializer')
-rw-r--r-- | src/armnnSerializer/ArmnnSchema.fbs | 1 | ||||
-rw-r--r-- | src/armnnSerializer/ArmnnSchema_generated.h | 14 | ||||
-rw-r--r-- | src/armnnSerializer/Serializer.cpp | 24 | ||||
-rw-r--r-- | src/armnnSerializer/test/SerializerTests.cpp | 48 |
4 files changed, 74 insertions, 13 deletions
diff --git a/src/armnnSerializer/ArmnnSchema.fbs b/src/armnnSerializer/ArmnnSchema.fbs index e2b3a3c288..88d66f76f5 100644 --- a/src/armnnSerializer/ArmnnSchema.fbs +++ b/src/armnnSerializer/ArmnnSchema.fbs @@ -321,6 +321,7 @@ table FullyConnectedLayer { table FullyConnectedDescriptor { biasEnabled:bool = false; transposeWeightsMatrix:bool = false; + constantWeights:bool = true; } table GatherLayer { diff --git a/src/armnnSerializer/ArmnnSchema_generated.h b/src/armnnSerializer/ArmnnSchema_generated.h index 524ffb0182..99ab0dc78a 100644 --- a/src/armnnSerializer/ArmnnSchema_generated.h +++ b/src/armnnSerializer/ArmnnSchema_generated.h @@ -3504,7 +3504,8 @@ struct FullyConnectedDescriptor FLATBUFFERS_FINAL_CLASS : private flatbuffers::T typedef FullyConnectedDescriptorBuilder Builder; enum FlatBuffersVTableOffset FLATBUFFERS_VTABLE_UNDERLYING_TYPE { VT_BIASENABLED = 4, - VT_TRANSPOSEWEIGHTSMATRIX = 6 + VT_TRANSPOSEWEIGHTSMATRIX = 6, + VT_CONSTANTWEIGHTS = 8 }; bool biasEnabled() const { return GetField<uint8_t>(VT_BIASENABLED, 0) != 0; @@ -3512,10 +3513,14 @@ struct FullyConnectedDescriptor FLATBUFFERS_FINAL_CLASS : private flatbuffers::T bool transposeWeightsMatrix() const { return GetField<uint8_t>(VT_TRANSPOSEWEIGHTSMATRIX, 0) != 0; } + bool constantWeights() const { + return GetField<uint8_t>(VT_CONSTANTWEIGHTS, 1) != 0; + } bool Verify(flatbuffers::Verifier &verifier) const { return VerifyTableStart(verifier) && VerifyField<uint8_t>(verifier, VT_BIASENABLED) && VerifyField<uint8_t>(verifier, VT_TRANSPOSEWEIGHTSMATRIX) && + VerifyField<uint8_t>(verifier, VT_CONSTANTWEIGHTS) && verifier.EndTable(); } }; @@ -3530,6 +3535,9 @@ struct FullyConnectedDescriptorBuilder { void add_transposeWeightsMatrix(bool transposeWeightsMatrix) { fbb_.AddElement<uint8_t>(FullyConnectedDescriptor::VT_TRANSPOSEWEIGHTSMATRIX, static_cast<uint8_t>(transposeWeightsMatrix), 0); } + void add_constantWeights(bool constantWeights) { + fbb_.AddElement<uint8_t>(FullyConnectedDescriptor::VT_CONSTANTWEIGHTS, static_cast<uint8_t>(constantWeights), 1); + } explicit FullyConnectedDescriptorBuilder(flatbuffers::FlatBufferBuilder &_fbb) : fbb_(_fbb) { start_ = fbb_.StartTable(); @@ -3545,8 +3553,10 @@ struct FullyConnectedDescriptorBuilder { inline flatbuffers::Offset<FullyConnectedDescriptor> CreateFullyConnectedDescriptor( flatbuffers::FlatBufferBuilder &_fbb, bool biasEnabled = false, - bool transposeWeightsMatrix = false) { + bool transposeWeightsMatrix = false, + bool constantWeights = true) { FullyConnectedDescriptorBuilder builder_(_fbb); + builder_.add_constantWeights(constantWeights); builder_.add_transposeWeightsMatrix(transposeWeightsMatrix); builder_.add_biasEnabled(biasEnabled); return builder_.Finish(); diff --git a/src/armnnSerializer/Serializer.cpp b/src/armnnSerializer/Serializer.cpp index 0586700ada..ae9ddf29f2 100644 --- a/src/armnnSerializer/Serializer.cpp +++ b/src/armnnSerializer/Serializer.cpp @@ -1118,12 +1118,8 @@ void SerializerStrategy::SerializeQuantizeLayer(const armnn::IConnectableLayer * void SerializerStrategy::SerializeFullyConnectedLayer(const armnn::IConnectableLayer* layer, const armnn::FullyConnectedDescriptor& fullyConnectedDescriptor, const std::vector<armnn::ConstTensor>& constants, - const char* name) + const char*) { - IgnoreUnused(name); - - const armnn::ConstTensor& weights = constants.at(0); - // Create FlatBuffer BaseLayer auto flatBufferBaseLayer = CreateLayerBase(layer, serializer::LayerType::LayerType_FullyConnected); @@ -1131,17 +1127,23 @@ void SerializerStrategy::SerializeFullyConnectedLayer(const armnn::IConnectableL auto flatBufferDescriptor = serializer::CreateFullyConnectedDescriptor(m_flatBufferBuilder, fullyConnectedDescriptor.m_BiasEnabled, - fullyConnectedDescriptor.m_TransposeWeightMatrix); + fullyConnectedDescriptor.m_TransposeWeightMatrix, + fullyConnectedDescriptor.m_ConstantWeights); // Create FlatBuffer weights data - auto flatBufferWeights = CreateConstTensorInfo(weights); - + flatbuffers::Offset<serializer::ConstTensor> flatBufferWeights; // Create FlatBuffer bias data flatbuffers::Offset<serializer::ConstTensor> flatBufferBiases; - if (fullyConnectedDescriptor.m_BiasEnabled) + if (fullyConnectedDescriptor.m_ConstantWeights && !constants.empty()) { - armnn::ConstTensor biases = constants.at(1); - flatBufferBiases = CreateConstTensorInfo(biases); + armnn::ConstTensor weights = constants.at(0); + flatBufferWeights = CreateConstTensorInfo(weights); + + if (fullyConnectedDescriptor.m_BiasEnabled) + { + armnn::ConstTensor biases = constants.at(1); + flatBufferBiases = CreateConstTensorInfo(biases); + } } // Create FlatBuffer FullyConnectedLayer diff --git a/src/armnnSerializer/test/SerializerTests.cpp b/src/armnnSerializer/test/SerializerTests.cpp index f261731a75..d7c10cb599 100644 --- a/src/armnnSerializer/test/SerializerTests.cpp +++ b/src/armnnSerializer/test/SerializerTests.cpp @@ -748,6 +748,7 @@ BOOST_AUTO_TEST_CASE(SerializeFullyConnected) armnn::FullyConnectedDescriptor descriptor; descriptor.m_BiasEnabled = true; descriptor.m_TransposeWeightMatrix = false; + descriptor.m_ConstantWeights = true; armnn::INetworkPtr network = armnn::INetwork::Create(); armnn::IConnectableLayer* const inputLayer = network->AddInputLayer(0); @@ -773,6 +774,53 @@ BOOST_AUTO_TEST_CASE(SerializeFullyConnected) deserializedNetwork->ExecuteStrategy(verifier); } +BOOST_AUTO_TEST_CASE(SerializeFullyConnectedWeightsAsInputs) +{ + const std::string layerName("fullyConnected_weights_as_inputs"); + const armnn::TensorInfo inputInfo ({ 2, 5, 1, 1 }, armnn::DataType::Float32); + const armnn::TensorInfo outputInfo({ 2, 3 }, armnn::DataType::Float32); + + const armnn::TensorInfo weightsInfo({ 5, 3 }, armnn::DataType::Float32); + const armnn::TensorInfo biasesInfo ({ 3 }, armnn::DataType::Float32); + + armnn::Optional<armnn::ConstTensor> weights = armnn::EmptyOptional(); + armnn::Optional<armnn::ConstTensor> bias = armnn::EmptyOptional(); + + armnn::FullyConnectedDescriptor descriptor; + descriptor.m_BiasEnabled = true; + descriptor.m_TransposeWeightMatrix = false; + descriptor.m_ConstantWeights = false; + + armnn::INetworkPtr network = armnn::INetwork::Create(); + armnn::IConnectableLayer* const inputLayer = network->AddInputLayer(0); + armnn::IConnectableLayer* const weightsInputLayer = network->AddInputLayer(1); + armnn::IConnectableLayer* const biasInputLayer = network->AddInputLayer(2); + armnn::IConnectableLayer* const fullyConnectedLayer = + network->AddFullyConnectedLayer(descriptor, + weights, + bias, + layerName.c_str()); + armnn::IConnectableLayer* const outputLayer = network->AddOutputLayer(0); + + inputLayer->GetOutputSlot(0).Connect(fullyConnectedLayer->GetInputSlot(0)); + weightsInputLayer->GetOutputSlot(0).Connect(fullyConnectedLayer->GetInputSlot(1)); + biasInputLayer->GetOutputSlot(0).Connect(fullyConnectedLayer->GetInputSlot(2)); + fullyConnectedLayer->GetOutputSlot(0).Connect(outputLayer->GetInputSlot(0)); + + inputLayer->GetOutputSlot(0).SetTensorInfo(inputInfo); + weightsInputLayer->GetOutputSlot(0).SetTensorInfo(weightsInfo); + biasInputLayer->GetOutputSlot(0).SetTensorInfo(biasesInfo); + fullyConnectedLayer->GetOutputSlot(0).SetTensorInfo(outputInfo); + + armnn::INetworkPtr deserializedNetwork = DeserializeNetwork(SerializeNetwork(*network)); + BOOST_CHECK(deserializedNetwork); + + const std::vector<armnn::ConstTensor> constants {}; + LayerVerifierBaseWithDescriptorAndConstants<armnn::FullyConnectedDescriptor> verifier( + layerName, {inputInfo, weightsInfo, biasesInfo}, {outputInfo}, descriptor, constants); + deserializedNetwork->ExecuteStrategy(verifier); +} + BOOST_AUTO_TEST_CASE(SerializeGather) { using GatherDescriptor = armnn::GatherDescriptor; |