18 template<armnn::DataType DataType>
26 template<armnn::DataType DataType>
31 for (
unsigned int i=0; i < numInputs; i++)
36 for (
unsigned int o=0; o < numOutputs; o++)
45 template<
typename LayerType,
typename DescType =
typename LayerType::DescriptorType>
62 template<
typename LayerType>
79 struct DummyLayer<
armnn::BatchNormalizationLayer>
84 m_Layer->m_Mean = std::make_unique<armnn::ScopedCpuTensorHandle>(
86 m_Layer->m_Variance = std::make_unique<armnn::ScopedCpuTensorHandle>(
88 m_Layer->m_Beta = std::make_unique<armnn::ScopedCpuTensorHandle>(
90 m_Layer->m_Gamma = std::make_unique<armnn::ScopedCpuTensorHandle>(
103 struct DummyLayer<
armnn::BatchToSpaceNdLayer>
119 struct DummyLayer<
armnn::ConstantLayer, void>
151 struct DummyLayer<
armnn::ConcatLayer>
184 struct DummyLayer<
armnn::SplitterLayer>
200 template <
typename ConvolutionLayerType>
201 struct DummyConvolutionLayer
203 DummyConvolutionLayer()
205 typename ConvolutionLayerType::DescriptorType desc;
209 m_Layer->m_Weight = std::make_unique<armnn::ScopedCpuTensorHandle>(
211 m_Layer->m_Bias = std::make_unique<armnn::ScopedCpuTensorHandle>(
215 ~DummyConvolutionLayer()
224 struct DummyLayer<
armnn::Convolution2dLayer>
225 :
public DummyConvolutionLayer<armnn::Convolution2dLayer>
230 struct DummyLayer<armnn::DepthwiseConvolution2dLayer>
231 :
public DummyConvolutionLayer<armnn::DepthwiseConvolution2dLayer>
236 struct DummyLayer<armnn::TransposeConvolution2dLayer>
237 :
public DummyConvolutionLayer<armnn::TransposeConvolution2dLayer>
242 struct DummyLayer<armnn::DetectionPostProcessLayer>
247 m_Layer->m_Anchors = std::make_unique<armnn::ScopedCpuTensorHandle>(
259 template <
typename LstmLayerType>
260 struct DummyLstmLayer
264 typename LstmLayerType::DescriptorType desc;
265 desc.m_CifgEnabled =
false;
268 m_Layer->m_BasicParameters.m_InputToForgetWeights = std::make_unique<armnn::ScopedCpuTensorHandle>(
270 m_Layer->m_BasicParameters.m_InputToCellWeights = std::make_unique<armnn::ScopedCpuTensorHandle>(
272 m_Layer->m_BasicParameters.m_InputToOutputWeights = std::make_unique<armnn::ScopedCpuTensorHandle>(
274 m_Layer->m_BasicParameters.m_RecurrentToForgetWeights = std::make_unique<armnn::ScopedCpuTensorHandle>(
276 m_Layer->m_BasicParameters.m_RecurrentToCellWeights = std::make_unique<armnn::ScopedCpuTensorHandle>(
278 m_Layer->m_BasicParameters.m_RecurrentToOutputWeights = std::make_unique<armnn::ScopedCpuTensorHandle>(
280 m_Layer->m_BasicParameters.m_ForgetGateBias = std::make_unique<armnn::ScopedCpuTensorHandle>(
282 m_Layer->m_BasicParameters.m_CellBias = std::make_unique<armnn::ScopedCpuTensorHandle>(
284 m_Layer->m_BasicParameters.m_OutputGateBias = std::make_unique<armnn::ScopedCpuTensorHandle>(
287 m_Layer->m_CifgParameters.m_InputToInputWeights = std::make_unique<armnn::ScopedCpuTensorHandle>(
289 m_Layer->m_CifgParameters.m_RecurrentToInputWeights = std::make_unique<armnn::ScopedCpuTensorHandle>(
291 m_Layer->m_CifgParameters.m_CellToInputWeights = std::make_unique<armnn::ScopedCpuTensorHandle>(
293 m_Layer->m_CifgParameters.m_InputGateBias = std::make_unique<armnn::ScopedCpuTensorHandle>(
306 struct DummyLayer<armnn::LstmLayer>
307 :
public DummyLstmLayer<armnn::LstmLayer>
312 struct DummyLayer<armnn::QuantizedLstmLayer, void>
318 m_Layer->m_QuantizedLstmParameters.m_InputToInputWeights = std::make_unique<armnn::ScopedCpuTensorHandle>(
320 m_Layer->m_QuantizedLstmParameters.m_InputToForgetWeights = std::make_unique<armnn::ScopedCpuTensorHandle>(
322 m_Layer->m_QuantizedLstmParameters.m_InputToCellWeights = std::make_unique<armnn::ScopedCpuTensorHandle>(
324 m_Layer->m_QuantizedLstmParameters.m_InputToOutputWeights = std::make_unique<armnn::ScopedCpuTensorHandle>(
327 m_Layer->m_QuantizedLstmParameters.m_RecurrentToInputWeights = std::make_unique<armnn::ScopedCpuTensorHandle>(
329 m_Layer->m_QuantizedLstmParameters.m_RecurrentToForgetWeights = std::make_unique<armnn::ScopedCpuTensorHandle>(
331 m_Layer->m_QuantizedLstmParameters.m_RecurrentToCellWeights = std::make_unique<armnn::ScopedCpuTensorHandle>(
333 m_Layer->m_QuantizedLstmParameters.m_RecurrentToOutputWeights = std::make_unique<armnn::ScopedCpuTensorHandle>(
336 m_Layer->m_QuantizedLstmParameters.m_InputGateBias = std::make_unique<armnn::ScopedCpuTensorHandle>(
338 m_Layer->m_QuantizedLstmParameters.m_ForgetGateBias = std::make_unique<armnn::ScopedCpuTensorHandle>(
340 m_Layer->m_QuantizedLstmParameters.m_CellBias = std::make_unique<armnn::ScopedCpuTensorHandle>(
342 m_Layer->m_QuantizedLstmParameters.m_OutputGateBias = std::make_unique<armnn::ScopedCpuTensorHandle>(
355 struct DummyLayer<armnn::FullyConnectedLayer>
361 m_Layer->m_Weight = std::make_unique<armnn::ScopedCpuTensorHandle>(
374 template<armnn::LayerType>
377 #define DECLARE_LAYER_POLICY_CUSTOM_PARAM(name, descType) \ 378 template<armnn::DataType DataType> \ 379 struct LayerTypePolicy<armnn::LayerType::name, DataType> \ 381 using Type = armnn::name##Layer; \ 382 using Desc = descType; \ 383 using QueueDesc = armnn::name##QueueDescriptor; \ 384 constexpr static const char* NameStr = #name; \ 385 constexpr static const bool IsException = false; \ 387 static std::unique_ptr<armnn::IWorkload> MakeDummyWorkload(armnn::IWorkloadFactory *factory, \ 388 unsigned int nIn, unsigned int nOut) \ 391 armnn::WorkloadInfo info = MakeDummyWorkloadInfo<DataType>(nIn, nOut); \ 392 return factory->Create##name(desc, info); \ 398 #define DECLARE_LAYER_POLICY_1_PARAM(name) DECLARE_LAYER_POLICY_CUSTOM_PARAM(name, void) 402 #define DECLARE_LAYER_POLICY_2_PARAM(name) DECLARE_LAYER_POLICY_CUSTOM_PARAM(name, armnn::name##Descriptor) 405 #define DECLARE_LAYER_POLICY_EXCEPTION(name, descType) \ 406 template<armnn::DataType DataType> \ 407 struct LayerTypePolicy<armnn::LayerType::name, DataType> \ 409 using Type = armnn::name##Layer; \ 410 using Desc = descType; \ 411 constexpr static const char* NameStr = #name; \ 412 constexpr static const bool IsException = true; \ 414 static std::unique_ptr<armnn::IWorkload> MakeDummyWorkload(armnn::IWorkloadFactory *factory, \ 415 unsigned int nIn, unsigned int nOut) \ 417 IgnoreUnused(factory, nIn, nOut); \ 418 return std::unique_ptr<armnn::IWorkload>(); \ 422 #define DECLARE_LAYER_POLICY_EXCEPTION_1_PARAM(name) DECLARE_LAYER_POLICY_EXCEPTION(name, void) 423 #define DECLARE_LAYER_POLICY_EXCEPTION_2_PARAM(name) DECLARE_LAYER_POLICY_EXCEPTION(name, armnn::name##Descriptor) 426 template<armnn::LayerType Type, armnn::DataType DataType>
427 struct LayerTypePolicy;
546 template<armnn::LayerType Type>
553 template<armnn::LayerType Type>
560 unsigned int GetNumInputs<armnn::LayerType::Concat>(
const armnn::Layer& layer)
569 template<
typename FactoryType, armnn::DataType DataType, armnn::LayerType Type>
570 bool IsLayerSupportedTest(
FactoryType *factory, Tag<Type>)
572 using LayerPolicy = LayerTypePolicy<Type, DataType>;
573 using LayerType =
typename LayerPolicy::Type;
574 using LayerDesc =
typename LayerPolicy::Desc;
575 DummyLayer<LayerType, LayerDesc> layer;
577 if (LayerPolicy::IsException)
582 unsigned int numIn = GetNumInputs<Type>(*layer.m_Layer);
583 unsigned int numOut = GetNumOutputs<Type>(*layer.m_Layer);
586 DummyLayer<armnn::ConstantLayer, void> previousLayer;
589 previousLayer.m_Layer->GetOutputSlot(0).SetTensorInfo(output);
591 for (
unsigned int i = 0; i < numIn; i++)
593 armnn::IOutputSlot& previousLayerOutputSlot = previousLayer.m_Layer->GetOutputSlot(0);
595 previousLayerOutputSlot.
Connect(layerInputSlot);
598 for (
unsigned int i = 0; i < numOut; i++)
600 layer.m_Layer->GetOutputSlot(0).SetTensorInfo(output);
603 std::string layerName = LayerPolicy::NameStr;
604 std::string reasonIfUnsupported;
605 if (FactoryType::IsLayerSupported(*layer.m_Layer,
DataType, reasonIfUnsupported))
607 std::string errorMsg =
" layer expected support but found none.";
610 bool retVal = LayerPolicy::MakeDummyWorkload(factory, numIn, numOut).get() !=
nullptr;
611 BOOST_CHECK_MESSAGE(retVal, layerName << errorMsg);
620 catch(
const std::exception& e)
623 BOOST_TEST_ERROR(layerName <<
": " << errorMsg);
628 errorMsg =
"Unexpected error while testing support for ";
629 BOOST_TEST_ERROR(errorMsg << layerName);
635 std::string errorMsg =
"layer expected no support (giving reason: " + reasonIfUnsupported +
") but found some.";
638 bool retVal = LayerPolicy::MakeDummyWorkload(factory, numIn, numOut).get() ==
nullptr;
639 BOOST_CHECK_MESSAGE(retVal, layerName << errorMsg);
655 catch(
const std::exception& e)
658 BOOST_TEST_ERROR(layerName <<
": " << errorMsg);
663 errorMsg =
"Unexpected error while testing support for ";
664 BOOST_TEST_ERROR(errorMsg << layerName);
677 template<
typename FactoryType, armnn::DataType DataType, armnn::LayerType Type>
678 bool IsLayerSupportedTestsImpl(
FactoryType *factory, Tag<armnn::LayerType::LastLayer>)
680 return IsLayerSupportedTest<FactoryType, DataType, Type>(factory, Tag<Type>());
684 template<
typename FactoryType, armnn::DataType DataType, armnn::LayerType Type>
685 bool IsLayerSupportedTestsImpl(
FactoryType *factory, Tag<Type>)
687 bool v = IsLayerSupportedTest<FactoryType, DataType, Type>(factory, Tag<Type>());
690 IsLayerSupportedTestsImpl<FactoryType, DataType, NextType(Type)>
691 (factory, Tag<NextType(Type)>());
695 template<
typename FactoryType, armnn::DataType DataType>
698 return IsLayerSupportedTestsImpl<FactoryType, DataType>(factory, Tag<armnn::LayerType::FirstLayer>());
701 template<armnn::LayerType Type>
702 bool TestLayerTypeMatches()
704 using LayerPolicy = LayerTypePolicy<Type, armnn::DataType::Float32>;
705 using LayerType =
typename LayerPolicy::Type;
706 using LayerDesc =
typename LayerPolicy::Desc;
707 DummyLayer<LayerType, LayerDesc> layer;
709 std::stringstream ss;
710 ss << LayerPolicy::NameStr <<
" layer type mismatches expected layer type value.";
711 bool v = Type == layer.m_Layer->GetType();
712 BOOST_CHECK_MESSAGE(v, ss.str());
716 template<armnn::LayerType Type>
717 bool LayerTypeMatchesTestImpl(Tag<armnn::LayerType::LastLayer>)
719 return TestLayerTypeMatches<Type>();
722 template<armnn::LayerType Type>
723 bool LayerTypeMatchesTestImpl(Tag<Type>)
725 return TestLayerTypeMatches<Type>() &&
726 LayerTypeMatchesTestImpl<NextType(Type)>(Tag<NextType(Type)>());
729 template<
typename FactoryType,
typename LayerType, armnn::DataType InputDataType , armnn::DataType OutputDataType>
730 bool IsConvertLayerSupportedTests(std::string& reasonIfUnsupported)
741 input->GetOutputSlot(0).Connect(layer->GetInputSlot(0));
742 input->GetOutputHandler(0).SetTensorInfo(inputTensorInfo);
743 layer->GetOutputSlot(0).Connect(output->GetInputSlot(0));
744 layer->GetOutputHandler(0).SetTensorInfo(outputTensorInfo);
746 bool result = FactoryType::IsLayerSupported(*layer, InputDataType, reasonIfUnsupported);
751 template<
typename FactoryType, armnn::DataType InputDataType , armnn::DataType OutputDataType>
752 bool IsMeanLayerSupportedTests(std::string& reasonIfUnsupported)
755 static const std::vector<unsigned> axes = {1, 0};
766 input->GetOutputSlot(0).Connect(layer->
GetInputSlot(0));
767 input->GetOutputHandler(0).SetTensorInfo(inputTensorInfo);
771 bool result = FactoryType::IsLayerSupported(*layer, InputDataType, reasonIfUnsupported);
778 template<
typename FactoryType, armnn::DataType InputDataType , armnn::DataType OutputDataType>
779 bool IsMeanLayerNotSupportedTests(std::string& reasonIfUnsupported)
782 static const std::vector<unsigned> axes = {};
795 input->GetOutputSlot(0).Connect(layer->
GetInputSlot(0));
796 input->GetOutputHandler(0).SetTensorInfo(inputTensorInfo);
800 bool result = FactoryType::IsLayerSupported(*layer, InputDataType, reasonIfUnsupported);
A layer that the constant data can be bound to.
This layer represents a split operation.
float Dequantize(QuantizedType value, float scale, int32_t offset)
Dequantize an 8-bit data type into a floating point data type.
This layer represents a batch normalization operation.
A ViewsDescriptor for the SplitterLayer.
void Slice(const TensorInfo &inputInfo, const SliceDescriptor &descriptor, const void *inputData, void *outputData, unsigned int dataTypeSize)
unsigned int GetNumInputSlots() const override
Returns the number of connectable input slots.
void ArgMinMax(Decoder< float > &in, int32_t *out, const TensorInfo &inputTensorInfo, const TensorInfo &outputTensorInfo, ArgMinMaxFunction function, int axis)
LayerT * AddLayer(Args &&... args)
Adds a new layer, of type LayerType, to the graph constructed with the arguments passed.
int Connect(InputSlot &destination)
void EraseLayer(Iterator pos)
Deletes the layer at the specified position.
void Transpose(const armnn::TensorShape &dstShape, const armnn::PermutationVector &mappings, const void *src, void *dst, size_t dataTypeSize)
void DepthToSpace(const TensorInfo &inputInfo, const DepthToSpaceDescriptor &descriptor, const void *inputData, void *outputData, unsigned int dataTypeSize)
void FullyConnected(const TensorShape &rInputShape, Decoder< float > &rInputDecoder, const TensorShape &rOutputShape, Encoder< float > &rOutputEncoder, Decoder< float > &rWeightDecoder, Decoder< float > &rBiasDecoder, const bool biasEnabled, const unsigned int K, const bool transposeWeights)
Performs a matrix multiplication and optionally adds a bias.
This layer represents a detection postprocess operator.
Copyright (c) 2020 ARM Limited.
#define DECLARE_LAYER_POLICY_CUSTOM_PARAM(name, descType)
This layer represents a LSTM operation.
void IgnoreUnused(Ts &&...)
void FakeQuantization(const float *inputData, float *outputData, uint32_t numElements, float min, float max)
unsigned int GetNumOutputSlots() const override
Returns the number of connectable output slots.
A BatchToSpaceNdDescriptor for the BatchToSpaceNdLayer.
int LayerBindingId
Type of identifiers for bindable layers (inputs, outputs).
void Stack(const StackQueueDescriptor &data, std::vector< std::unique_ptr< Decoder< float >>> &inputs, Encoder< float > &output)
void Pad(const TensorInfo &inputInfo, const TensorInfo &outputInfo, std::vector< std::pair< unsigned int, unsigned int >> m_padList, const T *inputData, T *outData, const float padValue)
void Permute(const armnn::TensorShape &dstShape, const armnn::PermutationVector &mappings, const void *src, void *dst, size_t dataTypeSize)
const InputSlot & GetInputSlot(unsigned int index) const override
Get a const input slot handle by slot index.
std::vector< TensorInfo > m_InputTensorInfos
void DetectionPostProcess(const TensorInfo &boxEncodingsInfo, const TensorInfo &scoresInfo, const TensorInfo &anchorsInfo, const TensorInfo &detectionBoxesInfo, const TensorInfo &detectionClassesInfo, const TensorInfo &detectionScoresInfo, const TensorInfo &numDetectionsInfo, const DetectionPostProcessDescriptor &desc, Decoder< float > &boxEncodings, Decoder< float > &scores, Decoder< float > &anchors, float *detectionBoxes, float *detectionClasses, float *detectionScores, float *numDetections)
A layer user-provided data can be bound to (e.g. inputs, outputs).
This layer represents a fully connected operation.
An LstmDescriptor for the LstmLayer.
This layer represents a QuantizedLstm operation.
An output connection slot for a layer.
An OriginsDescriptor for the ConcatLayer.
#define DECLARE_LAYER_POLICY_EXCEPTION_2_PARAM(name)
A FullyConnectedDescriptor for the FullyConnectedLayer.
void Debug(const TensorInfo &inputInfo, const T *inputData, LayerGuid guid, const std::string &layerName, unsigned int slotIndex)
This layer represents a merge operation.
float Activation(float in, ActivationFunction function, float a, float b)
This layer represents a BatchToSpaceNd operation.
QuantizedType Quantize(float value, float scale, int32_t offset)
Quantize a floating point data type into an 8-bit data type.
std::vector< TensorInfo > m_OutputTensorInfos
void Resize(Decoder< float > &in, const TensorInfo &inputInfo, Encoder< float > &out, const TensorInfo &outputInfo, DataLayoutIndexed dataLayout, armnn::ResizeMethod resizeMethod, bool alignCorners)
void LogSoftmax(Decoder< float > &input, Encoder< float > &output, const TensorInfo &inputInfo, const LogSoftmaxDescriptor &descriptor)
void SpaceToBatchNd(const TensorInfo &inputInfo, const TensorInfo &outputInfo, const SpaceToBatchNdDescriptor ¶ms, Decoder< float > &inputData, Encoder< float > &outputData)
#define DECLARE_LAYER_POLICY_1_PARAM(name)
void SetTensorInfo(const TensorInfo &tensorInfo)
Sets the TensorInfo used by this output handler.
void StridedSlice(const TensorInfo &inputInfo, const StridedSliceDescriptor ¶ms, const void *inputData, void *outputData, unsigned int dataTypeSize)
const OutputHandler & GetOutputHandler(unsigned int i=0) const
ClWorkloadFactory FactoryType
A MeanDescriptor for the MeanLayer.
void Mean(const armnn::TensorInfo &inputInfo, const armnn::TensorInfo &outputInfo, const std::vector< unsigned int > &axis, Decoder< float > &input, Encoder< float > &output)
void Gather(const TensorInfo ¶msInfo, const TensorInfo &indicesInfo, const TensorInfo &outputInfo, Decoder< float > ¶ms, const int32_t *indices, Encoder< float > &output)
const OutputSlot & GetOutputSlot(unsigned int index=0) const override
Get the const output slot handle by slot index.
Contains information about inputs and outputs to a layer.
void SpaceToDepth(const TensorInfo &inputInfo, const TensorInfo &outputInfo, const SpaceToDepthDescriptor ¶ms, Decoder< float > &inputData, Encoder< float > &outputData)
#define DECLARE_LAYER_POLICY_2_PARAM(name)
This layer represents a mean operation.
void BatchToSpaceNd(const DataLayoutIndexed &dataLayout, const TensorInfo &inputTensorInfo, const TensorInfo &outputTensorInfo, const std::vector< unsigned int > &blockShape, const std::vector< std::pair< unsigned int, unsigned int >> &cropsData, Decoder< float > &inputDecoder, Encoder< float > &outputEncoder)
virtual int Connect(IInputSlot &destination)=0
void Pooling2d(Decoder< float > &rInputDecoder, Encoder< float > &rOutputEncoder, const TensorInfo &inputInfo, const TensorInfo &outputInfo, const Pooling2dDescriptor ¶ms)
Computes the Pooling2d operation.
void Splitter(const SplitterQueueDescriptor &data)
void Softmax(Decoder< float > &in, Encoder< float > &out, const TensorInfo &inputTensorInfo, float beta, int axis)
Computes the softmax function on some inputs, into outputs, with a shape given by tensorInfo...
A BatchNormalizationDescriptor for the BatchNormalizationLayer.