36 std::string& outReasonIfUnsupported)
43 std::string& outReasonIfUnsupported,
54 void NeonWorkloadFactory::SetNumberOfThreads()
56 if (m_ModelContextPtr)
58 const unsigned int MIN_THREADS = 1;
59 const unsigned int MAX_THREADS = 64;
66 if (numberOfThreads != 0 && numberOfThreads >= MIN_THREADS && numberOfThreads <= MAX_THREADS)
68 arm_compute::Scheduler::get().set_num_threads(numberOfThreads);
74 : m_MemoryManager(memoryManager), m_ModelContextPtr(
IBackendInternal::IBackendSpecificModelContextPtr{})
81 : m_MemoryManager(memoryManager), m_ModelContextPtr(modelContextPtr)
88 unsigned int const* subTensorOrigin)
const
90 const arm_compute::TensorShape shape = armcomputetensorutils::BuildArmComputeTensorShape(subTensorShape);
98 coords.set(i, armnn::numeric_cast<int>(subTensorOrigin[revertedIndex]));
101 const arm_compute::TensorShape parentShape = armcomputetensorutils::BuildArmComputeTensorShape(parent.
GetShape());
102 if (!::arm_compute::error_on_invalid_subtensor(__func__, __FILE__, __LINE__, parentShape, coords, shape))
107 return std::make_unique<NeonSubTensorHandle>(
108 PolymorphicDowncast<IAclTensorHandle*>(&parent), shape, coords);
112 const bool IsMemoryManaged)
const
114 auto tensorHandle = std::make_unique<NeonTensorHandle>(tensorInfo);
117 tensorHandle->SetMemoryGroup(m_MemoryManager->GetInterLayerMemoryGroup());
124 const bool IsMemoryManaged)
const
126 auto tensorHandle = std::make_unique<NeonTensorHandle>(tensorInfo, dataLayout);
129 tensorHandle->SetMemoryGroup(m_MemoryManager->GetInterLayerMemoryGroup());
142 auto activationQueueDescriptor = PolymorphicDowncast<const ActivationQueueDescriptor*>(&descriptor);
143 return std::make_unique<NeonActivationWorkload>(*activationQueueDescriptor,
info);
147 auto additionQueueDescriptor = PolymorphicDowncast<const AdditionQueueDescriptor*>(&descriptor);
148 return std::make_unique<NeonAdditionWorkload>(*additionQueueDescriptor,
info);
152 auto argMinMaxQueueDescriptor = PolymorphicDowncast<const ArgMinMaxQueueDescriptor*>(&descriptor);
153 return std::make_unique<NeonArgMinMaxWorkload>(*argMinMaxQueueDescriptor,
info);
157 auto batchMatMulQueueDescriptor = PolymorphicDowncast<const BatchMatMulQueueDescriptor*>(&descriptor);
158 bool isFastMathEnabled =
false;
159 if (m_ModelContextPtr)
161 if (m_ModelContextPtr.get() !=
nullptr)
170 return std::make_unique<NeonBatchMatMulWorkload>(*batchMatMulQueueDescriptor,
info, isFastMathEnabled);
174 auto batchNormalizationQueueDescriptor
175 = PolymorphicDowncast<const BatchNormalizationQueueDescriptor*>(&descriptor);
176 return std::make_unique<NeonBatchNormalizationWorkload>(*batchNormalizationQueueDescriptor,
info);
180 auto batchToSpaceNdQueueDescriptor
181 = PolymorphicDowncast<const BatchToSpaceNdQueueDescriptor*>(&descriptor);
182 return std::make_unique<NeonBatchToSpaceNdWorkload>(*batchToSpaceNdQueueDescriptor,
info);
186 auto castQueueDescriptor = PolymorphicDowncast<const CastQueueDescriptor*>(&descriptor);
187 return std::make_unique<NeonCastWorkload>(*castQueueDescriptor,
info);
191 auto channelShuffleQueueDescriptor = PolymorphicDowncast<const ChannelShuffleQueueDescriptor*>(&descriptor);
192 return std::make_unique<NeonChannelShuffleWorkload>(*channelShuffleQueueDescriptor,
info);
196 auto comparisonQueueDescriptor = PolymorphicDowncast<const ComparisonQueueDescriptor*>(&descriptor);
197 return std::make_unique<NeonComparisonWorkload>(*comparisonQueueDescriptor,
info);
201 auto concatQueueDescriptor = PolymorphicDowncast<const ConcatQueueDescriptor*>(&descriptor);
202 return std::make_unique<NeonConcatWorkload>(*concatQueueDescriptor,
info);
206 auto constantQueueDescriptor = PolymorphicDowncast<const ConstantQueueDescriptor*>(&descriptor);
207 return std::make_unique<NeonConstantWorkload>(*constantQueueDescriptor,
info);
211 auto convertFp16ToFp32QueueDescriptor
212 = PolymorphicDowncast<const ConvertFp16ToFp32QueueDescriptor*>(&descriptor);
213 return std::make_unique<NeonConvertFp16ToFp32Workload>(*convertFp16ToFp32QueueDescriptor,
info);
217 auto convertFp32ToFp16QueueDescriptor
218 = PolymorphicDowncast<const ConvertFp32ToFp16QueueDescriptor*>(&descriptor);
219 return std::make_unique<NeonConvertFp32ToFp16Workload>(*convertFp32ToFp16QueueDescriptor,
info);
223 auto convolution2dQueueDescriptor = PolymorphicDowncast<const Convolution2dQueueDescriptor*>(&descriptor);
224 bool isFastMathEnabled =
false;
225 if (m_ModelContextPtr)
227 if (m_ModelContextPtr.get() !=
nullptr)
236 return std::make_unique<NeonConvolution2dWorkload>(*convolution2dQueueDescriptor,
238 m_MemoryManager->GetIntraLayerManager(),
243 auto convolution3dQueueDescriptor = PolymorphicDowncast<const Convolution3dQueueDescriptor*>(&descriptor);
244 bool isFastMathEnabled =
false;
245 if (m_ModelContextPtr)
247 if (m_ModelContextPtr.get() !=
nullptr)
256 return std::make_unique<NeonConvolution3dWorkload>(*convolution3dQueueDescriptor,
258 m_MemoryManager->GetIntraLayerManager(),
263 auto debugQueueDescriptor = PolymorphicDowncast<const DebugQueueDescriptor*>(&descriptor);
264 return MakeWorkloadHelper<NullWorkload, NullWorkload>(*debugQueueDescriptor,
info);
268 auto depthToSpaceQueueDescriptor = PolymorphicDowncast<const DepthToSpaceQueueDescriptor*>(&descriptor);
269 return std::make_unique<NeonDepthToSpaceWorkload>(*depthToSpaceQueueDescriptor,
info);
273 auto depthwiseConvolution2dQueueDescriptor
274 = PolymorphicDowncast<const DepthwiseConvolution2dQueueDescriptor*>(&descriptor);
275 return std::make_unique<NeonDepthwiseConvolutionWorkload>(*depthwiseConvolution2dQueueDescriptor,
info);
279 auto dequantizeQueueDescriptor = PolymorphicDowncast<const DequantizeQueueDescriptor*>(&descriptor);
280 return std::make_unique<NeonDequantizeWorkload>(*dequantizeQueueDescriptor,
info);
284 auto detectionPostProcessQueueDescriptor
285 = PolymorphicDowncast<const DetectionPostProcessQueueDescriptor*>(&descriptor);
286 return MakeWorkloadHelper<NullWorkload, NullWorkload>(*detectionPostProcessQueueDescriptor,
info);
290 auto divisionQueueDescriptor = PolymorphicDowncast<const DivisionQueueDescriptor*>(&descriptor);
291 return std::make_unique<NeonDivisionWorkload>(*divisionQueueDescriptor,
info);
295 auto elementwiseBinaryQueueDescriptor
296 = PolymorphicDowncast<const ElementwiseBinaryQueueDescriptor*>(&descriptor);
297 switch (elementwiseBinaryQueueDescriptor->m_Parameters.m_Operation)
304 return std::make_unique<NeonAdditionWorkload>(additionQueueDescriptor,
info);
311 return std::make_unique<NeonDivisionWorkload>(divisionQueueDescriptor,
info);
318 return std::make_unique<NeonMaximumWorkload>(maximumQueueDescriptor,
info);
325 return std::make_unique<NeonMinimumWorkload>(minimumQueueDescriptor,
info);
332 return std::make_unique<NeonMultiplicationWorkload>(multiplicationQueueDescriptor,
info);
337 return std::make_unique<NeonElementwiseBinaryWorkload>(*elementwiseBinaryQueueDescriptor,
info);
344 return std::make_unique<NeonSubtractionWorkload>(subtractionQueueDescriptor,
info);
352 auto elementwiseUnaryQueueDescriptor
353 = PolymorphicDowncast<const ElementwiseUnaryQueueDescriptor*>(&descriptor);
354 switch(elementwiseUnaryQueueDescriptor->m_Parameters.m_Operation)
359 absQueueDescriptor.
m_Inputs = elementwiseUnaryQueueDescriptor->m_Inputs;
360 absQueueDescriptor.
m_Outputs = elementwiseUnaryQueueDescriptor->m_Outputs;
361 return std::make_unique<NeonAbsWorkload>(absQueueDescriptor,
info);
364 return std::make_unique<NeonExpWorkload>(*elementwiseUnaryQueueDescriptor,
info);
366 return std::make_unique<NeonLogicalNotWorkload>(*elementwiseUnaryQueueDescriptor,
info);
368 return std::make_unique<NeonLogWorkload>(*elementwiseUnaryQueueDescriptor,
info);
370 return std::make_unique<NeonNegWorkload>(*elementwiseUnaryQueueDescriptor,
info);
374 rsqrtQueueDescriptor.
m_Inputs = elementwiseUnaryQueueDescriptor->m_Inputs;
375 rsqrtQueueDescriptor.
m_Outputs = elementwiseUnaryQueueDescriptor->m_Outputs;
376 return std::make_unique<NeonRsqrtWorkload>(rsqrtQueueDescriptor,
info);
379 return std::make_unique<NeonSinWorkload>(*elementwiseUnaryQueueDescriptor,
info);
381 return std::make_unique<NeonSqrtWorkload>(*elementwiseUnaryQueueDescriptor,
info);
388 auto fillQueueDescriptor = PolymorphicDowncast<const FillQueueDescriptor*>(&descriptor);
389 return std::make_unique<NeonFillWorkload>(*fillQueueDescriptor,
info);
393 auto floorQueueDescriptor = PolymorphicDowncast<const FloorQueueDescriptor*>(&descriptor);
394 return MakeWorkloadHelper<NeonFloorFloatWorkload, NullWorkload>(*floorQueueDescriptor,
info);
398 auto fullyConnectedQueueDescriptor = PolymorphicDowncast<const FullyConnectedQueueDescriptor*>(&descriptor);
399 return std::make_unique<NeonFullyConnectedWorkload>(*fullyConnectedQueueDescriptor,
401 m_MemoryManager->GetIntraLayerManager());
405 auto fusedQueueDescriptor = PolymorphicDowncast<const FusedQueueDescriptor*>(&descriptor);
406 return std::make_unique<NeonFusedWorkload>(*fusedQueueDescriptor,
info);
410 auto gatherQueueDescriptor = PolymorphicDowncast<const GatherQueueDescriptor*>(&descriptor);
411 return std::make_unique<NeonGatherWorkload>(*gatherQueueDescriptor,
info);
415 auto gatherNdQueueDescriptor = PolymorphicDowncast<const GatherNdQueueDescriptor*>(&descriptor);
416 return std::make_unique<NeonGatherNdWorkload>(*gatherNdQueueDescriptor,
info);
420 auto inputQueueDescriptor = PolymorphicDowncast<const InputQueueDescriptor*>(&descriptor);
421 return std::make_unique<CopyMemGenericWorkload>(*inputQueueDescriptor,
info);
425 auto instanceNormalizationQueueDescriptor
426 = PolymorphicDowncast<const InstanceNormalizationQueueDescriptor*>(&descriptor);
427 return std::make_unique<NeonInstanceNormalizationWorkload>(*instanceNormalizationQueueDescriptor,
info);
431 auto l2NormalizationQueueDescriptor
432 = PolymorphicDowncast<const L2NormalizationQueueDescriptor*>(&descriptor);
433 return MakeWorkloadHelper<NeonL2NormalizationFloatWorkload, NullWorkload>
434 (*l2NormalizationQueueDescriptor,
info, m_MemoryManager->GetIntraLayerManager());
438 auto logSoftmaxQueueDescriptor = PolymorphicDowncast<const LogSoftmaxQueueDescriptor*>(&descriptor);
439 return std::make_unique<NeonLogSoftmaxWorkload>(*logSoftmaxQueueDescriptor,
441 m_MemoryManager->GetIntraLayerManager());
445 auto logicalBinaryQueueDescriptor = PolymorphicDowncast<const LogicalBinaryQueueDescriptor*>(&descriptor);
446 switch(logicalBinaryQueueDescriptor->m_Parameters.m_Operation)
449 return std::make_unique<NeonLogicalAndWorkload>(*logicalBinaryQueueDescriptor,
info);
451 return std::make_unique<NeonLogicalOrWorkload>(*logicalBinaryQueueDescriptor,
info);
458 auto lstmQueueDescriptor = PolymorphicDowncast<const LstmQueueDescriptor*>(&descriptor);
459 return MakeWorkloadHelper<NeonLstmFloatWorkload, NullWorkload>(*lstmQueueDescriptor,
info);
463 auto maximumQueueDescriptor = PolymorphicDowncast<const MaximumQueueDescriptor*>(&descriptor);
464 return std::make_unique<NeonMaximumWorkload>(*maximumQueueDescriptor,
info);
468 auto meanQueueDescriptor = PolymorphicDowncast<const MeanQueueDescriptor*>(&descriptor);
469 return std::make_unique<NeonMeanWorkload>(*meanQueueDescriptor,
info);
473 auto memCopyQueueDescriptor = PolymorphicDowncast<const MemCopyQueueDescriptor*>(&descriptor);
474 if (memCopyQueueDescriptor->m_Inputs.empty() || !memCopyQueueDescriptor->m_Inputs[0])
478 return MakeWorkloadHelper<CopyMemGenericWorkload, CopyMemGenericWorkload>(*memCopyQueueDescriptor,
info);
482 auto memImportQueueDescriptor = PolymorphicDowncast<const MemImportQueueDescriptor*>(&descriptor);
483 if (memImportQueueDescriptor->m_Inputs.empty() || !memImportQueueDescriptor->m_Inputs[0])
487 return std::make_unique<ImportMemGenericWorkload>(*memImportQueueDescriptor,
info);
491 auto minimumQueueDescriptor = PolymorphicDowncast<const MinimumQueueDescriptor*>(&descriptor);
492 return std::make_unique<NeonMinimumWorkload>(*minimumQueueDescriptor,
info);
496 auto multiplicationQueueDescriptor = PolymorphicDowncast<const MultiplicationQueueDescriptor*>(&descriptor);
497 return std::make_unique<NeonMultiplicationWorkload>(*multiplicationQueueDescriptor,
info);
501 auto normalizationQueueDescriptor = PolymorphicDowncast<const NormalizationQueueDescriptor*>(&descriptor);
502 return MakeWorkloadHelper<NeonNormalizationFloatWorkload, NullWorkload>
503 (*normalizationQueueDescriptor,
info, m_MemoryManager->GetIntraLayerManager());
507 auto outputQueueDescriptor = PolymorphicDowncast<const OutputQueueDescriptor*>(&descriptor);
508 return std::make_unique<CopyMemGenericWorkload>(*outputQueueDescriptor,
info);
512 auto padQueueDescriptor = PolymorphicDowncast<const PadQueueDescriptor*>(&descriptor);
513 return std::make_unique<NeonPadWorkload>(*padQueueDescriptor,
info);
517 auto permuteQueueDescriptor = PolymorphicDowncast<const PermuteQueueDescriptor*>(&descriptor);
518 return std::make_unique<NeonPermuteWorkload>(*permuteQueueDescriptor,
info);
522 auto pooling2dQueueDescriptor = PolymorphicDowncast<const Pooling2dQueueDescriptor*>(&descriptor);
523 return std::make_unique<NeonPooling2dWorkload>(*pooling2dQueueDescriptor,
info);
527 auto pooling3dQueueDescriptor = PolymorphicDowncast<const Pooling3dQueueDescriptor*>(&descriptor);
528 return std::make_unique<NeonPooling3dWorkload>(*pooling3dQueueDescriptor,
info);
532 auto preCompiledQueueDescriptor = PolymorphicDowncast<const PreCompiledQueueDescriptor*>(&descriptor);
533 return MakeWorkloadHelper<NullWorkload, NullWorkload>(*preCompiledQueueDescriptor,
info);
537 auto preluQueueDescriptor = PolymorphicDowncast<const PreluQueueDescriptor*>(&descriptor);
538 return std::make_unique<NeonPreluWorkload>(*preluQueueDescriptor,
info);
542 auto qLstmQueueDescriptor = PolymorphicDowncast<const QLstmQueueDescriptor*>(&descriptor);
543 return std::make_unique<NeonQLstmWorkload>(*qLstmQueueDescriptor,
info);
547 auto quantizeQueueDescriptor = PolymorphicDowncast<const QuantizeQueueDescriptor*>(&descriptor);
548 return std::make_unique<NeonQuantizeWorkload>(*quantizeQueueDescriptor,
info);
552 auto quantizedLstmQueueDescriptor = PolymorphicDowncast<const QuantizedLstmQueueDescriptor*>(&descriptor);
553 return std::make_unique<NeonQuantizedLstmWorkload>(*quantizedLstmQueueDescriptor,
info);
557 auto rankQueueDescriptor = PolymorphicDowncast<const RankQueueDescriptor*>(&descriptor);
558 return std::make_unique<NeonRankWorkload>(*rankQueueDescriptor,
info);
562 auto reduceQueueDescriptor = PolymorphicDowncast<const ReduceQueueDescriptor*>(&descriptor);
563 return std::make_unique<NeonReduceWorkload>(*reduceQueueDescriptor,
info);
567 auto reshapeQueueDescriptor = PolymorphicDowncast<const ReshapeQueueDescriptor*>(&descriptor);
568 return std::make_unique<NeonReshapeWorkload>(*reshapeQueueDescriptor,
info);
572 auto resizeQueueDescriptor = PolymorphicDowncast<const ResizeQueueDescriptor*>(&descriptor);
573 return std::make_unique<NeonResizeWorkload>(*resizeQueueDescriptor,
info);
577 auto reverseV2QueueDescriptor = PolymorphicDowncast<const ReverseV2QueueDescriptor*>(&descriptor);
578 return std::make_unique<NeonReverseV2Workload>(*reverseV2QueueDescriptor,
info);
582 auto sliceQueueDescriptor = PolymorphicDowncast<const SliceQueueDescriptor*>(&descriptor);
583 return std::make_unique<NeonSliceWorkload>(*sliceQueueDescriptor,
info);
587 auto softmaxQueueDescriptor = PolymorphicDowncast<const SoftmaxQueueDescriptor*>(&descriptor);
588 return std::make_unique<NeonSoftmaxWorkload>(*softmaxQueueDescriptor,
590 m_MemoryManager->GetIntraLayerManager());
594 auto spaceToBatchNdQueueDescriptor
595 = PolymorphicDowncast<const SpaceToBatchNdQueueDescriptor*>(&descriptor);
596 return std::make_unique<NeonSpaceToBatchNdWorkload>(*spaceToBatchNdQueueDescriptor,
info);
600 auto spaceToDepthQueueDescriptor = PolymorphicDowncast<const SpaceToDepthQueueDescriptor*>(&descriptor);
601 return std::make_unique<NeonSpaceToDepthWorkload>(*spaceToDepthQueueDescriptor,
info);
605 auto splitterQueueDescriptor = PolymorphicDowncast<const SplitterQueueDescriptor*>(&descriptor);
606 return std::make_unique<NeonSplitterWorkload>(*splitterQueueDescriptor,
info);
610 auto stackQueueDescriptor = PolymorphicDowncast<const StackQueueDescriptor*>(&descriptor);
611 return std::make_unique<NeonStackWorkload>(*stackQueueDescriptor,
info);
615 auto stridedSliceQueueDescriptor = PolymorphicDowncast<const StridedSliceQueueDescriptor*>(&descriptor);
616 return std::make_unique<NeonStridedSliceWorkload>(*stridedSliceQueueDescriptor,
info);
620 auto subtractionQueueDescriptor = PolymorphicDowncast<const SubtractionQueueDescriptor*>(&descriptor);
621 return std::make_unique<NeonSubtractionWorkload>(*subtractionQueueDescriptor,
info);
625 auto tileQueueDescriptor = PolymorphicDowncast<const TileQueueDescriptor*>(&descriptor);
626 return std::make_unique<NeonTileWorkload>(*tileQueueDescriptor,
info);
630 auto transposeQueueDescriptor = PolymorphicDowncast<const TransposeQueueDescriptor*>(&descriptor);
631 return std::make_unique<NeonTransposeWorkload>(*transposeQueueDescriptor,
info);
635 auto transposeConvolution2dQueueDescriptor
636 = PolymorphicDowncast<const TransposeConvolution2dQueueDescriptor*>(&descriptor);
637 return std::make_unique<NeonTransposeConvolution2dWorkload>(*transposeConvolution2dQueueDescriptor,
639 m_MemoryManager->GetIntraLayerManager());
643 auto desc = PolymorphicDowncast<const UnidirectionalSequenceLstmQueueDescriptor*>(&descriptor);
651 return std::make_unique<NeonUnidirectionalSequenceLstmFloatWorkload>(*desc,
info);
655 return std::make_unique<NeonUnidirectionalSequenceLstmWorkload>(*desc,
info);