ArmNN
 21.11
NeonBackend Class Reference

#include <NeonBackend.hpp>

Inheritance diagram for NeonBackend:
IBackendInternal IBackend

Public Member Functions

 NeonBackend ()=default
 
 ~NeonBackend ()=default
 
const BackendIdGetId () const override
 
IBackendInternal::IMemoryManagerUniquePtr CreateMemoryManager () const override
 
IWorkloadFactoryPtr CreateWorkloadFactory (const IBackendInternal::IMemoryManagerSharedPtr &memoryManager=nullptr) const override
 
IWorkloadFactoryPtr CreateWorkloadFactory (class TensorHandleFactoryRegistry &tensorHandleFactoryRegistry) const override
 
IWorkloadFactoryPtr CreateWorkloadFactory (const IMemoryManagerSharedPtr &memoryManager, const ModelOptions &modelOptions) const override
 
IWorkloadFactoryPtr CreateWorkloadFactory (class TensorHandleFactoryRegistry &tensorHandleFactoryRegistry, const ModelOptions &modelOptions) const override
 
IBackendInternal::IBackendContextPtr CreateBackendContext (const IRuntime::CreationOptions &) const override
 Create the runtime context of the backend. More...
 
IBackendInternal::IBackendProfilingContextPtr CreateBackendProfilingContext (const IRuntime::CreationOptions &, IBackendProfilingPtr &backendProfiling) override
 Create context specifically used for profiling interaction from backends. More...
 
IBackendInternal::ILayerSupportSharedPtr GetLayerSupport () const override
 
IBackendInternal::ILayerSupportSharedPtr GetLayerSupport (const ModelOptions &modelOptions) const override
 
OptimizationViews OptimizeSubgraphView (const SubgraphView &subgraph) const override
 
std::vector< ITensorHandleFactory::FactoryIdGetHandleFactoryPreferences () const override
 (Optional) Returns a vector of supported TensorHandleFactory ids in preference order. More...
 
void RegisterTensorHandleFactories (class TensorHandleFactoryRegistry &registry) override
 (Optional) Register TensorHandleFactories Either this method or CreateMemoryManager() and IWorkloadFactory::CreateTensor()/IWorkloadFactory::CreateSubtensor() methods must be implemented. More...
 
IBackendInternal::IBackendSpecificModelContextPtr CreateBackendSpecificModelContext (const ModelOptions &modelOptions) const override
 
BackendCapabilities GetCapabilities () const override
 Returns a BackendCapability if the backend lists the capability The BackendCapability must then be inspected to check whether or not that BackendCapability is supported Otherwise returns an EmptyOptional if the BackendCapability is unlisted. More...
 
std::unique_ptr< ICustomAllocatorGetDefaultAllocator () const override
 Returns the default memory allocator for the backend. More...
 
- Public Member Functions inherited from IBackendInternal
 ~IBackendInternal () override=default
 Allow backends created by the factory function to be destroyed through IBackendInternal. More...
 
virtual IWorkloadFactoryPtr CreateWorkloadFactory (class TensorHandleFactoryRegistry &tensorHandleFactoryRegistry, const ModelOptions &modelOptions, MemorySourceFlags inputFlags, MemorySourceFlags outputFlags) const
 
virtual OptimizationViews OptimizeSubgraphView (const SubgraphView &subgraph, const ModelOptions &modelOptions) const
 
bool SupportsTensorAllocatorAPI () const
 
ITensorHandleFactory::FactoryId GetBackwardCompatibleFavoriteHandleFactory ()
 
virtual void RegisterTensorHandleFactories (class TensorHandleFactoryRegistry &registry, MemorySourceFlags inputFlags, MemorySourceFlags outputFlags)
 (Optional) Register TensorHandleFactories Either this method or CreateMemoryManager() and IWorkloadFactory::CreateTensor()/IWorkloadFactory::CreateSubtensor() methods must be implemented. More...
 
virtual bool HasCapability (BackendCapability) const
 Returns true if backend support the capability false otherwise. More...
 
virtual bool UseCustomMemoryAllocator (std::shared_ptr< ICustomAllocator > allocator, armnn::Optional< std::string &> errMsg)
 Signals the backend to use a custom memory allocator provided by the user. More...
 
virtual unsigned int GetNumberOfCacheFiles () const
 Returns the number of files cached if backend supports caching. More...
 

Static Public Member Functions

static const BackendIdGetIdStatic ()
 
- Static Public Member Functions inherited from IBackendInternal
static constexpr BackendVersion GetApiVersion ()
 Returns the version of the Backend API. More...
 

Additional Inherited Members

- Public Types inherited from IBackendInternal
using IWorkloadFactoryPtr = std::unique_ptr< IWorkloadFactory >
 
using IBackendContextPtr = std::unique_ptr< IBackendContext >
 
using IBackendProfilingContextPtr = std::shared_ptr< armnn::profiling::IBackendProfilingContext >
 This is the bridge between backend and backend profiling we'll keep it in the backend namespace. More...
 
using IBackendProfilingPtr = std::unique_ptr< armnn::profiling::IBackendProfiling >
 
using OptimizationPtr = std::unique_ptr< Optimization >
 
using Optimizations = std::vector< OptimizationPtr >
 
using ILayerSupportSharedPtr = std::shared_ptr< ILayerSupport >
 
using IBackendSpecificModelContextPtr = std::shared_ptr< IBackendModelContext >
 
using IMemoryManagerUniquePtr = std::unique_ptr< IMemoryManager >
 
using IMemoryManagerSharedPtr = std::shared_ptr< IMemoryManager >
 
- Protected Member Functions inherited from IBackendInternal
 IBackendInternal ()=default
 Creation must be done through a specific backend interface. More...
 
- Protected Member Functions inherited from IBackend
 IBackend ()
 
virtual ~IBackend ()
 

Detailed Description

Definition at line 26 of file NeonBackend.hpp.

Constructor & Destructor Documentation

◆ NeonBackend()

NeonBackend ( )
default

◆ ~NeonBackend()

~NeonBackend ( )
default

Member Function Documentation

◆ CreateBackendContext()

IBackendInternal::IBackendContextPtr CreateBackendContext ( const IRuntime::CreationOptions ) const
overridevirtual

Create the runtime context of the backend.

Implementations may return a default-constructed IBackendContextPtr if no context is needed at runtime. Implementations must throw BackendUnavailableException if the backend cannot be used (for example, necessary accelerator hardware is not present). The default implementation always returns a default-constructed pointer.

Reimplemented from IBackendInternal.

Definition at line 96 of file NeonBackend.cpp.

Referenced by NeonBackend::GetId().

97 {
98  return IBackendContextPtr{};
99 }
std::unique_ptr< IBackendContext > IBackendContextPtr

◆ CreateBackendProfilingContext()

IBackendInternal::IBackendProfilingContextPtr CreateBackendProfilingContext ( const IRuntime::CreationOptions creationOptions,
IBackendProfilingPtr backendProfiling 
)
overridevirtual

Create context specifically used for profiling interaction from backends.

Reimplemented from IBackendInternal.

Definition at line 101 of file NeonBackend.cpp.

Referenced by NeonBackend::GetId().

103 {
105 }
std::shared_ptr< armnn::profiling::IBackendProfilingContext > IBackendProfilingContextPtr
This is the bridge between backend and backend profiling we&#39;ll keep it in the backend namespace...

◆ CreateBackendSpecificModelContext()

IBackendInternal::IBackendSpecificModelContextPtr CreateBackendSpecificModelContext ( const ModelOptions modelOptions) const
overridevirtual

Reimplemented from IBackendInternal.

Definition at line 107 of file NeonBackend.cpp.

Referenced by NeonBackend::CreateWorkloadFactory(), NeonBackend::GetId(), and NeonBackend::GetLayerSupport().

109 {
110  return IBackendSpecificModelContextPtr{new NeonBackendModelContext{modelOptions}};
111 }
std::shared_ptr< IBackendModelContext > IBackendSpecificModelContextPtr

◆ CreateMemoryManager()

IBackendInternal::IMemoryManagerUniquePtr CreateMemoryManager ( ) const
overridevirtual

Reimplemented from IBackendInternal.

Definition at line 50 of file NeonBackend.cpp.

References BaseMemoryManager::Offset.

Referenced by NeonBackend::GetId().

51 {
52  return std::make_unique<NeonMemoryManager>(std::make_unique<arm_compute::Allocator>(),
54 }

◆ CreateWorkloadFactory() [1/4]

IBackendInternal::IWorkloadFactoryPtr CreateWorkloadFactory ( const IBackendInternal::IMemoryManagerSharedPtr memoryManager = nullptr) const
overridevirtual

Implements IBackendInternal.

Definition at line 56 of file NeonBackend.cpp.

Referenced by NeonBackend::GetId().

58 {
59  return std::make_unique<NeonWorkloadFactory>(
60  PolymorphicPointerDowncast<NeonMemoryManager>(memoryManager));
61 }

◆ CreateWorkloadFactory() [2/4]

IBackendInternal::IWorkloadFactoryPtr CreateWorkloadFactory ( class TensorHandleFactoryRegistry tensorHandleFactoryRegistry) const
overridevirtual

Reimplemented from IBackendInternal.

Definition at line 70 of file NeonBackend.cpp.

References BaseMemoryManager::Offset, TensorHandleFactoryRegistry::RegisterFactory(), and TensorHandleFactoryRegistry::RegisterMemoryManager().

72 {
73  auto memoryManager = std::make_shared<NeonMemoryManager>(std::make_unique<arm_compute::Allocator>(),
75 
76  tensorHandleFactoryRegistry.RegisterMemoryManager(memoryManager);
77  tensorHandleFactoryRegistry.RegisterFactory(std::make_unique<NeonTensorHandleFactory>(memoryManager));
78 
79  return std::make_unique<NeonWorkloadFactory>(
80  PolymorphicPointerDowncast<NeonMemoryManager>(memoryManager));
81 }

◆ CreateWorkloadFactory() [3/4]

IBackendInternal::IWorkloadFactoryPtr CreateWorkloadFactory ( const IMemoryManagerSharedPtr memoryManager,
const ModelOptions modelOptions 
) const
overridevirtual

Reimplemented from IBackendInternal.

Definition at line 63 of file NeonBackend.cpp.

References NeonBackend::CreateBackendSpecificModelContext().

65 {
66  return std::make_unique<NeonWorkloadFactory>(
67  PolymorphicPointerDowncast<NeonMemoryManager>(memoryManager), CreateBackendSpecificModelContext(modelOptions));
68 }
IBackendInternal::IBackendSpecificModelContextPtr CreateBackendSpecificModelContext(const ModelOptions &modelOptions) const override

◆ CreateWorkloadFactory() [4/4]

IBackendInternal::IWorkloadFactoryPtr CreateWorkloadFactory ( class TensorHandleFactoryRegistry tensorHandleFactoryRegistry,
const ModelOptions modelOptions 
) const
overridevirtual

Reimplemented from IBackendInternal.

Definition at line 83 of file NeonBackend.cpp.

References NeonBackend::CreateBackendSpecificModelContext(), BaseMemoryManager::Offset, TensorHandleFactoryRegistry::RegisterFactory(), and TensorHandleFactoryRegistry::RegisterMemoryManager().

85 {
86  auto memoryManager = std::make_shared<NeonMemoryManager>(std::make_unique<arm_compute::Allocator>(),
88 
89  tensorHandleFactoryRegistry.RegisterMemoryManager(memoryManager);
90  tensorHandleFactoryRegistry.RegisterFactory(std::make_unique<NeonTensorHandleFactory>(memoryManager));
91 
92  return std::make_unique<NeonWorkloadFactory>(
93  PolymorphicPointerDowncast<NeonMemoryManager>(memoryManager), CreateBackendSpecificModelContext(modelOptions));
94 }
IBackendInternal::IBackendSpecificModelContextPtr CreateBackendSpecificModelContext(const ModelOptions &modelOptions) const override

◆ GetCapabilities()

BackendCapabilities GetCapabilities ( ) const
inlineoverridevirtual

Returns a BackendCapability if the backend lists the capability The BackendCapability must then be inspected to check whether or not that BackendCapability is supported Otherwise returns an EmptyOptional if the BackendCapability is unlisted.

Reimplemented from IBackendInternal.

Definition at line 64 of file NeonBackend.hpp.

References armnn::cpuAccCapabilities, and NeonBackend::GetDefaultAllocator().

65  {
66  return cpuAccCapabilities;
67  };
const BackendCapabilities cpuAccCapabilities("CpuAcc", { {"NonConstWeights", false}, {"AsyncExecution", false}, {"ProtectedContentAllocation", false}, {"ConstantTensorsAsInputs", false}, {"PreImportIOTensors", false}, {"ExternallyManagedMemory", true}, {"MultiAxisPacking", false}, {"SingleAxisPacking", true} })

◆ GetDefaultAllocator()

std::unique_ptr< ICustomAllocator > GetDefaultAllocator ( ) const
overridevirtual

Returns the default memory allocator for the backend.

Returns
- Returns unique pointer to the Default Allocator of the Backend

Reimplemented from IBackendInternal.

Definition at line 431 of file NeonBackend.cpp.

Referenced by NeonBackend::GetCapabilities().

432 {
433  return std::make_unique<DefaultAllocator>();
434 }

◆ GetHandleFactoryPreferences()

std::vector< ITensorHandleFactory::FactoryId > GetHandleFactoryPreferences ( ) const
overridevirtual

(Optional) Returns a vector of supported TensorHandleFactory ids in preference order.

Reimplemented from IBackendInternal.

Definition at line 417 of file NeonBackend.cpp.

References NeonTensorHandleFactory::GetIdStatic().

Referenced by NeonBackend::GetId().

418 {
419  return std::vector<ITensorHandleFactory::FactoryId>() = { NeonTensorHandleFactory::GetIdStatic() };
420 }
static const FactoryId & GetIdStatic()

◆ GetId()

◆ GetIdStatic()

const BackendId & GetIdStatic ( )
static

Definition at line 44 of file NeonBackend.cpp.

References armnn::NeonBackendId().

Referenced by NeonBackend::GetId().

45 {
46  static const BackendId s_Id{NeonBackendId()};
47  return s_Id;
48 }
constexpr const char * NeonBackendId()

◆ GetLayerSupport() [1/2]

IBackendInternal::ILayerSupportSharedPtr GetLayerSupport ( ) const
overridevirtual

Implements IBackendInternal.

Definition at line 113 of file NeonBackend.cpp.

Referenced by NeonBackend::GetId().

114 {
115  static ILayerSupportSharedPtr layerSupport
116  {
118  };
119  return layerSupport;
120 }
std::shared_ptr< IBackendModelContext > IBackendSpecificModelContextPtr
std::shared_ptr< ILayerSupport > ILayerSupportSharedPtr

◆ GetLayerSupport() [2/2]

IBackendInternal::ILayerSupportSharedPtr GetLayerSupport ( const ModelOptions modelOptions) const
overridevirtual

Reimplemented from IBackendInternal.

Definition at line 122 of file NeonBackend.cpp.

References NeonBackend::CreateBackendSpecificModelContext().

123 {
124  static ILayerSupportSharedPtr layerSupport
125  {
126  new NeonLayerSupport(CreateBackendSpecificModelContext(modelOptions))
127  };
128  return layerSupport;
129 }
IBackendInternal::IBackendSpecificModelContextPtr CreateBackendSpecificModelContext(const ModelOptions &modelOptions) const override
std::shared_ptr< ILayerSupport > ILayerSupportSharedPtr

◆ OptimizeSubgraphView()

OptimizationViews OptimizeSubgraphView ( const SubgraphView subgraph) const
overridevirtual

Reimplemented from IBackendInternal.

Definition at line 131 of file NeonBackend.cpp.

References armnn::Activation, armnn::Addition, OptimizationViews::AddUntouchedSubgraph(), armnn::BatchNormalization, SubgraphView::begin(), Layer::BeginOutputSlots(), armnn::Convolution2d, armnn::DepthwiseConvolution2d, armnn::Division, SubgraphView::end(), Layer::EndOutputSlots(), armnn::FullyConnected, Layer::GetAdditionalInformation(), InputSlot::GetConnectedOutputSlot(), Layer::GetGuid(), Layer::GetInputSlot(), Layer::GetName(), LayerWithParameters< Parameters >::GetParameters(), OptimizationViews::GetSubstitutions(), OutputSlot::GetTensorInfo(), Layer::GetType(), BatchNormalizationLayer::m_Beta, DepthwiseConvolution2dLayer::m_Bias, Convolution2dLayer::m_Bias, FullyConnectedLayer::m_Bias, Convolution2dDescriptor::m_BiasEnabled, DepthwiseConvolution2dDescriptor::m_BiasEnabled, BatchNormalizationLayer::m_Gamma, BatchNormalizationLayer::m_Mean, BatchNormalizationLayer::m_Variance, DepthwiseConvolution2dLayer::m_Weight, Convolution2dLayer::m_Weight, FullyConnectedLayer::m_Weight, armnn::Multiplication, armnn::NeonAdditionWorkloadValidate(), armnn::NeonBatchNormalizationValidate(), armnn::NeonConvolution2dWorkloadValidate(), armnn::NeonDepthwiseConvolutionWorkloadValidate(), armnn::NeonDivisionWorkloadValidate(), armnn::NeonFullyConnectedWorkloadValidate(), armnn::NeonMultiplicationWorkloadValidate(), armnn::NeonSubtractionWorkloadValidate(), armnn::Reduce, armnn::ReportUntouchedLayers(), and armnn::Subtraction.

Referenced by NeonBackend::GetId().

132 {
133  OptimizationViews optimizationViews;
134 
135  auto it = subgraph.end();
136  std::map<LayerGuid, Layer*> untouched;
137 
138  while (it != subgraph.begin())
139  {
140  --it;
141  Layer& base = **it;
142  untouched.insert({base.GetGuid(), &base});
143  }
144 
145  it = subgraph.end();
146  while (it != subgraph.begin())
147  {
148  --it;
149  Layer& base = **it;
150 
151  // Fuse activation into previous layer if supported by backend
152  if ((base.GetType() == LayerType::DepthwiseConvolution2d || base.GetType() == LayerType::Convolution2d
153  || base.GetType() == LayerType::BatchNormalization || base.GetType() == LayerType::FullyConnected
154  || base.GetType() == LayerType::Addition || base.GetType() == LayerType::Multiplication
155  || base.GetType() == LayerType::Subtraction || base.GetType() == LayerType::Division)
156  && (base.GetAdditionalInformation<ActivationDescriptor>() == nullptr))
157  {
158  for (auto output = base.BeginOutputSlots(); output != base.EndOutputSlots(); ++output)
159  {
160  if (output->GetNumConnections() == 1)
161  {
162  for (auto&& childInput : output->GetConnections())
163  {
164  if ((childInput->GetOwningLayer().GetType() == LayerType::Activation) &&
165  (checkDataTypeInputandOutput(childInput->GetOwningLayer())))
166  {
167  Layer& child = childInput->GetOwningLayer();
168 
169  auto* activationLayer = PolymorphicDowncast<ActivationLayer*>(&child);
170 
171  const std::string name = std::string("fused-") + child.GetName() + std::string("-into-") +
172  base.GetName();
173 
174  // Get params from activation layer
175  ActivationDescriptor activationDesc = activationLayer->GetParameters();
176 
177  if (base.GetType() == LayerType::Convolution2d)
178  {
179  Convolution2dLayer* baseLayer = PolymorphicDowncast<Convolution2dLayer*>(&base);
180 
181  Optional<TensorInfo> biases;
182 
183  if (baseLayer->GetParameters().m_BiasEnabled)
184  {
185  biases = baseLayer->m_Bias->GetTensorInfo();
186  }
187 
189  baseLayer->GetInputSlot(0).GetConnectedOutputSlot()->GetTensorInfo(),
190  activationLayer->GetInputSlot(0).GetConnectedOutputSlot()->GetTensorInfo(),
191  baseLayer->GetParameters(),
192  baseLayer->m_Weight->GetTensorInfo(),
193  biases,
194  false,
195  &activationDesc);
196 
197  if (status)
198  {
199  FuseLayerWithWeightsAndBiases<Convolution2dLayer>(optimizationViews,
200  baseLayer,
201  activationLayer,
202  activationDesc,
203  name);
204  untouched.erase(baseLayer->GetGuid());
205  untouched.erase(activationLayer->GetGuid());
206  }
207  }
208  else if (base.GetType() == LayerType::DepthwiseConvolution2d)
209  {
210  DepthwiseConvolution2dLayer* baseLayer =
211  PolymorphicDowncast<DepthwiseConvolution2dLayer*>(&base);
212 
213  Optional<TensorInfo> biases;
214 
215  if (baseLayer->GetParameters().m_BiasEnabled)
216  {
217  biases = baseLayer->m_Bias->GetTensorInfo();
218  }
219 
221  baseLayer->GetInputSlot(0).GetConnectedOutputSlot()->GetTensorInfo(),
222  activationLayer->GetInputSlot(0).GetConnectedOutputSlot()->GetTensorInfo(),
223  baseLayer->GetParameters(),
224  baseLayer->m_Weight->GetTensorInfo(),
225  biases,
226  &activationDesc);
227 
228  if (status)
229  {
230  FuseLayerWithWeightsAndBiases<DepthwiseConvolution2dLayer>(optimizationViews,
231  baseLayer,
232  activationLayer,
233  activationDesc,
234  name);
235  untouched.erase(baseLayer->GetGuid());
236  untouched.erase(activationLayer->GetGuid());
237  }
238  }
239  else if (base.GetType() == LayerType::FullyConnected)
240  {
241  FullyConnectedLayer* baseLayer = PolymorphicDowncast<FullyConnectedLayer*>(&base);
242 
244  baseLayer->GetInputSlot(0).GetConnectedOutputSlot()->GetTensorInfo(),
245  activationLayer->GetInputSlot(0).GetConnectedOutputSlot()->GetTensorInfo(),
246  baseLayer->m_Weight->GetTensorInfo(),
247  baseLayer->m_Bias->GetTensorInfo(),
248  baseLayer->GetParameters(),
249  &activationDesc);
250 
251  if (status)
252  {
253  FuseLayerWithWeightsAndBiases<FullyConnectedLayer>(optimizationViews,
254  baseLayer,
255  activationLayer,
256  activationDesc,
257  name);
258  untouched.erase(baseLayer->GetGuid());
259  untouched.erase(activationLayer->GetGuid());
260  }
261  }
262  else if (base.GetType() == LayerType::BatchNormalization)
263  {
264  BatchNormalizationLayer* baseLayer =
265  PolymorphicDowncast<BatchNormalizationLayer*>(&base);
266 
268  baseLayer->GetInputSlot(0).GetConnectedOutputSlot()->GetTensorInfo(),
269  activationLayer->GetInputSlot(0).GetConnectedOutputSlot()->GetTensorInfo(),
270  baseLayer->m_Mean->GetTensorInfo(),
271  baseLayer->m_Variance->GetTensorInfo(),
272  baseLayer->m_Beta->GetTensorInfo(),
273  baseLayer->m_Gamma->GetTensorInfo(),
274  baseLayer->GetParameters(),
275  &activationDesc);
276 
277  if (status)
278  {
279  BatchNormalizationLayer* replacementLayer =
280  FuseLayerWithParameters<BatchNormalizationLayer>(
281  optimizationViews,
282  baseLayer,
283  activationLayer,
284  activationDesc,
285  name);
286 
287  replacementLayer->m_Beta = std::move(baseLayer->m_Beta);
288  replacementLayer->m_Gamma = std::move(baseLayer->m_Gamma);
289  replacementLayer->m_Mean = std::move(baseLayer->m_Mean);
290  replacementLayer->m_Variance = std::move(baseLayer->m_Variance);
291  untouched.erase(baseLayer->GetGuid());
292  untouched.erase(activationLayer->GetGuid());
293  }
294  }
295  else if (base.GetType() == LayerType::Addition)
296  {
297  AdditionLayer* baseLayer = PolymorphicDowncast<AdditionLayer*>(&base);
298 
300  baseLayer->GetInputSlot(0).GetConnectedOutputSlot()->GetTensorInfo(),
301  baseLayer->GetInputSlot(1).GetConnectedOutputSlot()->GetTensorInfo(),
302  activationLayer->GetInputSlot(0).GetConnectedOutputSlot()->GetTensorInfo(),
303  &activationDesc);
304 
305  if (status)
306  {
307  FuseLayerWithoutParameters<AdditionLayer>(optimizationViews,
308  baseLayer,
309  activationLayer,
310  activationDesc,
311  name);
312  untouched.erase(baseLayer->GetGuid());
313  untouched.erase(activationLayer->GetGuid());
314  }
315  }
316  else if (base.GetType() == LayerType::Division)
317  {
318  DivisionLayer* baseLayer = PolymorphicDowncast<DivisionLayer*>(&base);
319 
321  baseLayer->GetInputSlot(0).GetConnectedOutputSlot()->GetTensorInfo(),
322  baseLayer->GetInputSlot(1).GetConnectedOutputSlot()->GetTensorInfo(),
323  activationLayer->GetInputSlot(0).GetConnectedOutputSlot()->GetTensorInfo(),
324  &activationDesc);
325 
326  if (status)
327  {
328  FuseLayerWithoutParameters<DivisionLayer>(optimizationViews,
329  baseLayer,
330  activationLayer,
331  activationDesc,
332  name);
333  untouched.erase(baseLayer->GetGuid());
334  untouched.erase(activationLayer->GetGuid());
335  }
336  }
337  else if (base.GetType() == LayerType::Multiplication)
338  {
339  MultiplicationLayer* baseLayer = PolymorphicDowncast<MultiplicationLayer*>(&base);
340 
342  baseLayer->GetInputSlot(0).GetConnectedOutputSlot()->GetTensorInfo(),
343  baseLayer->GetInputSlot(1).GetConnectedOutputSlot()->GetTensorInfo(),
344  activationLayer->GetInputSlot(0).GetConnectedOutputSlot()->GetTensorInfo(),
345  &activationDesc);
346 
347  if (status)
348  {
349  FuseLayerWithoutParameters<MultiplicationLayer>(optimizationViews,
350  baseLayer,
351  activationLayer,
352  activationDesc,
353  name);
354  untouched.erase(baseLayer->GetGuid());
355  untouched.erase(activationLayer->GetGuid());
356  }
357  }
358  else if (base.GetType() == LayerType::Subtraction)
359  {
360  SubtractionLayer* baseLayer = PolymorphicDowncast<SubtractionLayer*>(&base);
361 
363  baseLayer->GetInputSlot(0).GetConnectedOutputSlot()->GetTensorInfo(),
364  baseLayer->GetInputSlot(1).GetConnectedOutputSlot()->GetTensorInfo(),
365  activationLayer->GetInputSlot(0).GetConnectedOutputSlot()->GetTensorInfo(),
366  &activationDesc);
367 
368  if (status)
369  {
370  FuseLayerWithoutParameters<SubtractionLayer>(optimizationViews,
371  baseLayer,
372  activationLayer,
373  activationDesc,
374  name);
375  untouched.erase(baseLayer->GetGuid());
376  untouched.erase(activationLayer->GetGuid());
377  }
378  }
379  }
380  }
381  }
382  }
383  }
384 
385  // Separate reduce layer with multiple axes into multiple reduce layers with 1 axis.
386  if (base.GetType() == LayerType::Reduce)
387  {
388  ReduceLayer* baseLayer = PolymorphicDowncast<ReduceLayer*>(&base);
389  ReduceDescriptor reduceDescriptor = baseLayer->GetParameters();
390 
391  if (!reduceDescriptor.m_vAxis.empty() && reduceDescriptor.m_vAxis.size() > 1)
392  {
393  // Add new layers to the graph and connect them.
394  std::vector<Layer*> layers = ChainReduceLayers<ReduceLayer>(optimizationViews,
395  baseLayer,
396  reduceDescriptor);
397 
398  // Replace existing baselayer with new subgraph.
399  ReplaceLayers<ReduceLayer>(optimizationViews, baseLayer, layers);
400  untouched.erase(baseLayer->GetGuid());
401  }
402  }
403  }
404 
405  if (optimizationViews.GetSubstitutions().empty())
406  {
407  optimizationViews.AddUntouchedSubgraph(SubgraphView(subgraph));
408  }
409  else
410  {
411  ReportUntouchedLayers(optimizationViews, untouched);
412  }
413 
414  return optimizationViews;
415 }
arm_compute::Status NeonBatchNormalizationValidate(const TensorInfo &input, const TensorInfo &output, const TensorInfo &mean, const TensorInfo &var, const TensorInfo &beta, const TensorInfo &gamma, const BatchNormalizationDescriptor &descriptor, const ActivationDescriptor *activationDescriptor)
void ReportUntouchedLayers(OptimizationViews &optimizationViews, std::map< LayerGuid, Layer *> untouched)
arm_compute::Status NeonDepthwiseConvolutionWorkloadValidate(const TensorInfo &input, const TensorInfo &output, const DepthwiseConvolution2dDescriptor &descriptor, const TensorInfo &weights, const Optional< TensorInfo > &biases, const ActivationDescriptor *activationDescriptor)
arm_compute::Status NeonFullyConnectedWorkloadValidate(const TensorInfo &input, const TensorInfo &output, const TensorInfo &weights, const TensorInfo &biases, const FullyConnectedDescriptor &descriptor, const ActivationDescriptor *activationDescriptor)
arm_compute::Status NeonAdditionWorkloadValidate(const TensorInfo &input0, const TensorInfo &input1, const TensorInfo &output, const ActivationDescriptor *activationDescriptor)
arm_compute::Status NeonSubtractionWorkloadValidate(const TensorInfo &input0, const TensorInfo &input1, const TensorInfo &output, const ActivationDescriptor *activationDescriptor)
Status
enumeration
Definition: Types.hpp:29
arm_compute::Status NeonConvolution2dWorkloadValidate(const TensorInfo &input, const TensorInfo &output, const Convolution2dDescriptor &descriptor, const TensorInfo &weights, const Optional< TensorInfo > &biases, bool isFastMathEnabled, const ActivationDescriptor *activationDescriptor)
arm_compute::Status NeonDivisionWorkloadValidate(const TensorInfo &input0, const TensorInfo &input1, const TensorInfo &output, const ActivationDescriptor *activationDescriptor)
arm_compute::Status NeonMultiplicationWorkloadValidate(const TensorInfo &input0, const TensorInfo &input1, const TensorInfo &output, const ActivationDescriptor *activationDescriptor)

◆ RegisterTensorHandleFactories()

void RegisterTensorHandleFactories ( class TensorHandleFactoryRegistry )
overridevirtual

(Optional) Register TensorHandleFactories Either this method or CreateMemoryManager() and IWorkloadFactory::CreateTensor()/IWorkloadFactory::CreateSubtensor() methods must be implemented.

Reimplemented from IBackendInternal.

Definition at line 422 of file NeonBackend.cpp.

References BaseMemoryManager::Offset, TensorHandleFactoryRegistry::RegisterFactory(), and TensorHandleFactoryRegistry::RegisterMemoryManager().

Referenced by NeonBackend::GetId().

423 {
424  auto memoryManager = std::make_shared<NeonMemoryManager>(std::make_unique<arm_compute::Allocator>(),
426 
427  registry.RegisterMemoryManager(memoryManager);
428  registry.RegisterFactory(std::make_unique<NeonTensorHandleFactory>(memoryManager));
429 }

The documentation for this class was generated from the following files: