1 //
2 // Copyright © 2021 Arm Ltd and Contributors. All rights reserved.
3 // SPDX-License-Identifier: MIT
4 //
5
6 #include "ChannelShuffleTestImpl.hpp"
7
8 #include <DataTypeUtils.hpp>
9 #include <armnnTestUtils/TensorCopyUtils.hpp>
10 #include <armnnTestUtils/WorkloadTestUtils.hpp>
11
12 namespace
13 {
14
15 template<typename T, size_t NumDims>
ChannelShuffleTestImpl(armnn::IWorkloadFactory & workloadFactory,const armnn::IBackendInternal::IMemoryManagerSharedPtr & memoryManager,const armnn::ITensorHandleFactory & tensorHandleFactory,armnn::ChannelShuffleDescriptor descriptor,armnn::TensorInfo inputTensorInfo,armnn::TensorInfo outputTensorInfo,const std::vector<T> & inputData,const std::vector<T> & outputExpectedData)16 LayerTestResult<T, NumDims> ChannelShuffleTestImpl(
17 armnn::IWorkloadFactory& workloadFactory,
18 const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager,
19 const armnn::ITensorHandleFactory& tensorHandleFactory,
20 armnn::ChannelShuffleDescriptor descriptor,
21 armnn::TensorInfo inputTensorInfo,
22 armnn::TensorInfo outputTensorInfo,
23 const std::vector<T>& inputData,
24 const std::vector<T>& outputExpectedData)
25 {
26 IgnoreUnused(memoryManager);
27 std::vector<T> actualOutput(outputTensorInfo.GetNumElements());
28
29 std::unique_ptr<armnn::ITensorHandle> inputHandle = tensorHandleFactory.CreateTensorHandle(inputTensorInfo);
30 std::unique_ptr<armnn::ITensorHandle> outputHandle = tensorHandleFactory.CreateTensorHandle(outputTensorInfo);
31
32 armnn::ChannelShuffleQueueDescriptor data;
33 data.m_Parameters = descriptor;
34 armnn::WorkloadInfo info;
35 AddInputToWorkload(data, info, inputTensorInfo, inputHandle.get());
36 AddOutputToWorkload(data, info, outputTensorInfo, outputHandle.get());
37
38 std::unique_ptr<armnn::IWorkload> workload
39 = workloadFactory.CreateWorkload(armnn::LayerType::ChannelShuffle, data, info);
40
41 inputHandle->Allocate();
42 outputHandle->Allocate();
43
44 CopyDataToITensorHandle(inputHandle.get(), inputData.data());
45
46 workload->Execute();
47
48 CopyDataFromITensorHandle(actualOutput.data(), outputHandle.get());
49
50 return LayerTestResult<T, NumDims>(actualOutput,
51 outputExpectedData,
52 outputHandle->GetShape(),
53 outputTensorInfo.GetShape());
54 }
55 } // anonymous namespace
56
57 template<armnn::DataType ArmnnType, typename T>
SimpleChannelShuffleTest(armnn::IWorkloadFactory & workloadFactory,const armnn::IBackendInternal::IMemoryManagerSharedPtr & memoryManager,const armnn::ITensorHandleFactory & tensorHandleFactory)58 LayerTestResult<T, 4> SimpleChannelShuffleTest(
59 armnn::IWorkloadFactory& workloadFactory,
60 const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager,
61 const armnn::ITensorHandleFactory& tensorHandleFactory)
62 {
63 armnn::TensorInfo inputTensorInfo;
64 armnn::TensorInfo outputTensorInfo;
65
66 unsigned int inputShape[] = { 1,9,1,1 };
67 unsigned int outputShape[] = { 1,9,1,1 };
68
69 armnn::ChannelShuffleDescriptor descriptor;
70 descriptor.m_Axis = 1;
71 descriptor.m_NumGroups = 3;
72
73 inputTensorInfo = armnn::TensorInfo(4, inputShape, ArmnnType);
74 inputTensorInfo.SetQuantizationScale(1.0f);
75 outputTensorInfo = armnn::TensorInfo(4, outputShape, ArmnnType);
76 outputTensorInfo.SetQuantizationScale(1.0f);
77
78 auto input = ConvertToDataType<ArmnnType>(
79 {
80 0.0f, 1.0f, 2.0f, 3.0f, 4.0f, 5.0f, 6.0f, 7.0f, 8.0f
81 },
82 inputTensorInfo);
83 auto outputExpected = ConvertToDataType<ArmnnType>(
84 {
85 0.0f, 3.0f, 6.0f, 1.0f, 4.0f, 7.0f, 2.0f, 5.0f, 8.0f
86 },
87 outputTensorInfo);
88
89 return ChannelShuffleTestImpl<T, 4>(
90 workloadFactory,
91 memoryManager,
92 tensorHandleFactory,
93 descriptor,
94 inputTensorInfo,
95 outputTensorInfo,
96 input,
97 outputExpected);
98 }
99
100 template<armnn::DataType ArmnnType, typename T>
ChannelShuffle2DTest(armnn::IWorkloadFactory & workloadFactory,const armnn::IBackendInternal::IMemoryManagerSharedPtr & memoryManager,const armnn::ITensorHandleFactory & tensorHandleFactory)101 LayerTestResult<T, 2> ChannelShuffle2DTest(
102 armnn::IWorkloadFactory& workloadFactory,
103 const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager,
104 const armnn::ITensorHandleFactory& tensorHandleFactory)
105 {
106 armnn::TensorInfo inputTensorInfo;
107 armnn::TensorInfo outputTensorInfo;
108
109 unsigned int inputShape[] = { 3, 12 };
110 unsigned int outputShape[] = { 3, 12 };
111
112 armnn::ChannelShuffleDescriptor descriptor;
113 descriptor.m_Axis = 1;
114 descriptor.m_NumGroups = 3;
115
116 inputTensorInfo = armnn::TensorInfo(2, inputShape, ArmnnType);
117 inputTensorInfo.SetQuantizationScale(1.0f);
118 outputTensorInfo = armnn::TensorInfo(2, outputShape, ArmnnType);
119 outputTensorInfo.SetQuantizationScale(1.0f);
120
121 auto input = ConvertToDataType<ArmnnType>(
122 {
123 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11,
124 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23,
125 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35
126 },
127 inputTensorInfo);
128
129 auto outputExpected = ConvertToDataType<ArmnnType>(
130 {
131 0, 4, 8, 1, 5, 9, 2, 6, 10, 3, 7, 11,
132 12, 16, 20, 13, 17, 21, 14, 18, 22, 15, 19, 23,
133 24, 28, 32, 25, 29, 33, 26, 30, 34, 27, 31, 35
134 },
135 outputTensorInfo);
136
137 return ChannelShuffleTestImpl<T, 2>(
138 workloadFactory,
139 memoryManager,
140 tensorHandleFactory,
141 descriptor,
142 inputTensorInfo,
143 outputTensorInfo,
144 input,
145 outputExpected);
146 }
147
148 template<armnn::DataType ArmnnType, typename T>
ChannelShuffle4DTest(armnn::IWorkloadFactory & workloadFactory,const armnn::IBackendInternal::IMemoryManagerSharedPtr & memoryManager,const armnn::ITensorHandleFactory & tensorHandleFactory)149 LayerTestResult<T, 4> ChannelShuffle4DTest(
150 armnn::IWorkloadFactory& workloadFactory,
151 const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager,
152 const armnn::ITensorHandleFactory& tensorHandleFactory)
153 {
154 armnn::TensorInfo inputTensorInfo;
155 armnn::TensorInfo outputTensorInfo;
156
157 unsigned int inputShape[] = { 2, 9, 1, 2 };
158 unsigned int outputShape[] = { 2, 9, 1, 2 };
159
160 armnn::ChannelShuffleDescriptor descriptor;
161 descriptor.m_Axis = 1;
162 descriptor.m_NumGroups = 3;
163
164 inputTensorInfo = armnn::TensorInfo(4, inputShape, ArmnnType);
165 inputTensorInfo.SetQuantizationScale(1.0f);
166 outputTensorInfo = armnn::TensorInfo(4, outputShape, ArmnnType);
167 outputTensorInfo.SetQuantizationScale(1.0f);
168
169 auto input = ConvertToDataType<ArmnnType>(
170 {
171 0.0f, 1.0f,
172 2.0f, 3.0f,
173 4.0f, 5.0f,
174
175 6.0f, 7.0f,
176 8.0f, 9.0f,
177 10.0f, 11.0f,
178
179 12.0f, 13.0f,
180 14.0f, 15.0f,
181 16.0f, 17.0f,
182
183 18.0f, 19.0f,
184 20.0f, 21.0f,
185 22.0f, 23.0f,
186
187 24.0f, 25.0f,
188 26.0f, 27.0f,
189 28.0f, 29.0f,
190
191 30.0f, 31.0f,
192 32.0f, 33.0f,
193 34.0f, 35.0f
194 },
195 inputTensorInfo);
196
197 auto outputExpected = ConvertToDataType<ArmnnType>(
198 {
199 0.0f, 1.0f,
200 6.0f, 7.0f,
201 12.0f, 13.0f,
202 2.0f, 3.0f,
203 8.0f, 9.0f,
204 14.0f, 15.0f,
205 4.0f, 5.0f,
206 10.0f, 11.0f,
207 16.0f, 17.0f,
208
209 18.0f, 19.0f,
210 24.0f, 25.0f,
211 30.0f, 31.0f,
212 20.0f, 21.0f,
213 26.0f, 27.0f,
214 32.0f, 33.0f,
215 22.0f, 23.0f,
216 28.0f, 29.0f,
217 34.0f, 35.0f
218 },
219 outputTensorInfo);
220
221 return ChannelShuffleTestImpl<T, 4>(
222 workloadFactory,
223 memoryManager,
224 tensorHandleFactory,
225 descriptor,
226 inputTensorInfo,
227 outputTensorInfo,
228 input,
229 outputExpected);
230 }
231
232 //
233 // Explicit template specializations
234 //
235
236 template LayerTestResult<armnn::ResolveType<armnn::DataType::Float32>, 4>
237 SimpleChannelShuffleTest<armnn::DataType::Float32>(
238 armnn::IWorkloadFactory& workloadFactory,
239 const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager,
240 const armnn::ITensorHandleFactory& tensorHandleFactory);
241
242 template LayerTestResult<armnn::ResolveType<armnn::DataType::QAsymmU8>, 4>
243 SimpleChannelShuffleTest<armnn::DataType::QAsymmU8>(
244 armnn::IWorkloadFactory& workloadFactory,
245 const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager,
246 const armnn::ITensorHandleFactory& tensorHandleFactory);
247
248 template LayerTestResult<armnn::ResolveType<armnn::DataType::QAsymmS8>, 4>
249 SimpleChannelShuffleTest<armnn::DataType::QAsymmS8>(
250 armnn::IWorkloadFactory& workloadFactory,
251 const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager,
252 const armnn::ITensorHandleFactory& tensorHandleFactory);
253
254 template LayerTestResult<armnn::ResolveType<armnn::DataType::Float32>, 2>
255 ChannelShuffle2DTest<armnn::DataType::Float32>(
256 armnn::IWorkloadFactory& workloadFactory,
257 const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager,
258 const armnn::ITensorHandleFactory& tensorHandleFactory);
259
260 template LayerTestResult<armnn::ResolveType<armnn::DataType::QAsymmU8>, 2>
261 ChannelShuffle2DTest<armnn::DataType::QAsymmU8>(
262 armnn::IWorkloadFactory& workloadFactory,
263 const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager,
264 const armnn::ITensorHandleFactory& tensorHandleFactory);
265
266 template LayerTestResult<armnn::ResolveType<armnn::DataType::QAsymmS8>, 2>
267 ChannelShuffle2DTest<armnn::DataType::QAsymmS8>(
268 armnn::IWorkloadFactory& workloadFactory,
269 const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager,
270 const armnn::ITensorHandleFactory& tensorHandleFactory);
271
272 template LayerTestResult<armnn::ResolveType<armnn::DataType::Float32>, 4>
273 ChannelShuffle4DTest<armnn::DataType::Float32>(
274 armnn::IWorkloadFactory& workloadFactory,
275 const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager,
276 const armnn::ITensorHandleFactory& tensorHandleFactory);
277
278 template LayerTestResult<armnn::ResolveType<armnn::DataType::QAsymmU8>, 4>
279 ChannelShuffle4DTest<armnn::DataType::QAsymmU8>(
280 armnn::IWorkloadFactory& workloadFactory,
281 const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager,
282 const armnn::ITensorHandleFactory& tensorHandleFactory);
283
284 template LayerTestResult<armnn::ResolveType<armnn::DataType::QAsymmS8>, 4>
285 ChannelShuffle4DTest<armnn::DataType::QAsymmS8>(
286 armnn::IWorkloadFactory& workloadFactory,
287 const armnn::IBackendInternal::IMemoryManagerSharedPtr& memoryManager,
288 const armnn::ITensorHandleFactory& tensorHandleFactory);