blob: 936b37fb316e316af772bfac024e8f04efb9dda1 [file] [log] [blame]
giuros01164a2722018-11-20 18:34:46 +00001/*
Michele Di Giorgio1e0208a2021-01-22 15:42:59 +00002 * Copyright (c) 2018-2021 Arm Limited.
giuros01164a2722018-11-20 18:34:46 +00003 *
4 * SPDX-License-Identifier: MIT
5 *
6 * Permission is hereby granted, free of charge, to any person obtaining a copy
7 * of this software and associated documentation files (the "Software"), to
8 * deal in the Software without restriction, including without limitation the
9 * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
10 * sell copies of the Software, and to permit persons to whom the Software is
11 * furnished to do so, subject to the following conditions:
12 *
13 * The above copyright notice and this permission notice shall be included in all
14 * copies or substantial portions of the Software.
15 *
16 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
19 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
22 * SOFTWARE.
23 */
giuros011e6e1b82019-05-14 16:12:53 +010024#include "arm_compute/runtime/CL/functions/CLElementwiseOperations.h"
25
Michele Di Giorgio237be032021-01-25 15:44:02 +000026#include "arm_compute/core/CL/CLKernelLibrary.h"
giuros01164a2722018-11-20 18:34:46 +000027#include "arm_compute/core/CL/ICLTensor.h"
Michele Di Giorgio237be032021-01-25 15:44:02 +000028#include "arm_compute/core/Types.h"
29#include "src/core/CL/ICLKernel.h"
Michele Di Giorgio1e0208a2021-01-22 15:42:59 +000030
Georgios Pinitas7891a732021-08-20 21:39:25 +010031#include "src/gpu/cl/operators/ClAdd.h"
32#include "src/gpu/cl/operators/ClElementwiseOperations.h"
33#include "src/gpu/cl/operators/ClSub.h"
giuros01164a2722018-11-20 18:34:46 +000034
giuros01164a2722018-11-20 18:34:46 +000035namespace arm_compute
36{
Michalis Spyrouad7515d2020-07-24 00:02:23 +010037struct CLArithmeticAddition::Impl
38{
Michele Di Giorgio1e0208a2021-01-22 15:42:59 +000039 const ICLTensor *src_0{ nullptr };
40 const ICLTensor *src_1{ nullptr };
41 ICLTensor *dst{ nullptr };
42 std::unique_ptr<opencl::ClAdd> op{ nullptr };
Michalis Spyrouad7515d2020-07-24 00:02:23 +010043};
44
45CLArithmeticAddition::CLArithmeticAddition()
Georgios Pinitas40f51a62020-11-21 03:04:18 +000046 : _impl(std::make_unique<Impl>())
Michalis Spyrouad7515d2020-07-24 00:02:23 +010047{
48}
49CLArithmeticAddition::CLArithmeticAddition(CLArithmeticAddition &&) = default;
50CLArithmeticAddition &CLArithmeticAddition::operator=(CLArithmeticAddition &&) = default;
51CLArithmeticAddition::~CLArithmeticAddition() = default;
52
53void CLArithmeticAddition::configure(ICLTensor *input1, ICLTensor *input2, ICLTensor *output, ConvertPolicy policy, const ActivationLayerInfo &act_info)
54{
55 configure(CLKernelLibrary::get().get_compile_context(), input1, input2, output, policy, act_info);
56}
57
58void CLArithmeticAddition::configure(const CLCompileContext &compile_context, const ICLTensor *input1, const ICLTensor *input2, ICLTensor *output, ConvertPolicy policy,
59 const ActivationLayerInfo &act_info)
60{
61 _impl->src_0 = input1;
62 _impl->src_1 = input2;
63 _impl->dst = output;
Michele Di Giorgio1e0208a2021-01-22 15:42:59 +000064 _impl->op = std::make_unique<opencl::ClAdd>();
Michalis Spyrouad7515d2020-07-24 00:02:23 +010065 _impl->op->configure(compile_context, input1->info(), input2->info(), output->info(), policy, act_info);
66}
67
68Status CLArithmeticAddition::validate(const ITensorInfo *input1, const ITensorInfo *input2, const ITensorInfo *output, ConvertPolicy policy, const ActivationLayerInfo &act_info)
69{
Michele Di Giorgio1e0208a2021-01-22 15:42:59 +000070 return opencl::ClAdd::validate(input1, input2, output, policy, act_info);
Michalis Spyrouad7515d2020-07-24 00:02:23 +010071}
72
73void CLArithmeticAddition::run()
74{
Georgios Pinitas0499dff2020-07-31 22:21:38 +010075 ITensorPack pack;
76 pack.add_tensor(TensorType::ACL_SRC_0, _impl->src_0);
77 pack.add_tensor(TensorType::ACL_SRC_1, _impl->src_1);
78 pack.add_tensor(TensorType::ACL_DST, _impl->dst);
Michalis Spyrouad7515d2020-07-24 00:02:23 +010079
Georgios Pinitas0499dff2020-07-31 22:21:38 +010080 _impl->op->run(pack);
Michalis Spyrouad7515d2020-07-24 00:02:23 +010081}
82
83struct CLArithmeticSubtraction::Impl
84{
Michele Di Giorgio4cfab182021-01-25 11:49:03 +000085 const ICLTensor *src_0{ nullptr };
86 const ICLTensor *src_1{ nullptr };
87 ICLTensor *dst{ nullptr };
88 std::unique_ptr<opencl::ClSub> op{ nullptr };
Michalis Spyrouad7515d2020-07-24 00:02:23 +010089};
90
91CLArithmeticSubtraction::CLArithmeticSubtraction()
Georgios Pinitas40f51a62020-11-21 03:04:18 +000092 : _impl(std::make_unique<Impl>())
Michalis Spyrouad7515d2020-07-24 00:02:23 +010093{
94}
95CLArithmeticSubtraction::CLArithmeticSubtraction(CLArithmeticSubtraction &&) = default;
96CLArithmeticSubtraction &CLArithmeticSubtraction::operator=(CLArithmeticSubtraction &&) = default;
97CLArithmeticSubtraction::~CLArithmeticSubtraction() = default;
98
99void CLArithmeticSubtraction::configure(const ICLTensor *input1, const ICLTensor *input2, ICLTensor *output, ConvertPolicy policy, const ActivationLayerInfo &act_info)
100{
101 configure(CLKernelLibrary::get().get_compile_context(), input1, input2, output, policy, act_info);
102}
103
104void CLArithmeticSubtraction::configure(const CLCompileContext &compile_context, const ICLTensor *input1, const ICLTensor *input2, ICLTensor *output, ConvertPolicy policy,
105 const ActivationLayerInfo &act_info)
106{
107 _impl->src_0 = input1;
108 _impl->src_1 = input2;
109 _impl->dst = output;
Michele Di Giorgio4cfab182021-01-25 11:49:03 +0000110 _impl->op = std::make_unique<opencl::ClSub>();
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100111 _impl->op->configure(compile_context, input1->info(), input2->info(), output->info(), policy, act_info);
112}
113
114Status CLArithmeticSubtraction::validate(const ITensorInfo *input1, const ITensorInfo *input2, const ITensorInfo *output, ConvertPolicy policy, const ActivationLayerInfo &act_info)
115{
Michele Di Giorgio4cfab182021-01-25 11:49:03 +0000116 return opencl::ClSub::validate(input1, input2, output, policy, act_info);
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100117}
118
119void CLArithmeticSubtraction::run()
120{
Georgios Pinitas0499dff2020-07-31 22:21:38 +0100121 ITensorPack pack;
122 pack.add_tensor(TensorType::ACL_SRC_0, _impl->src_0);
123 pack.add_tensor(TensorType::ACL_SRC_1, _impl->src_1);
124 pack.add_tensor(TensorType::ACL_DST, _impl->dst);
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100125
Georgios Pinitas0499dff2020-07-31 22:21:38 +0100126 _impl->op->run(pack);
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100127}
128
129struct CLArithmeticDivision::Impl
130{
Michele Di Giorgio237be032021-01-25 15:44:02 +0000131 const ICLTensor *src_0{ nullptr };
132 const ICLTensor *src_1{ nullptr };
133 ICLTensor *dst{ nullptr };
134 std::unique_ptr<opencl::ClElementwiseDivision> op{ nullptr };
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100135};
136
137CLArithmeticDivision::CLArithmeticDivision()
Georgios Pinitas40f51a62020-11-21 03:04:18 +0000138 : _impl(std::make_unique<Impl>())
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100139{
140}
141CLArithmeticDivision::CLArithmeticDivision(CLArithmeticDivision &&) = default;
142CLArithmeticDivision &CLArithmeticDivision::operator=(CLArithmeticDivision &&) = default;
143CLArithmeticDivision::~CLArithmeticDivision() = default;
144
145void CLArithmeticDivision::configure(ICLTensor *input1, ICLTensor *input2, ICLTensor *output, const ActivationLayerInfo &act_info)
146{
147 configure(CLKernelLibrary::get().get_compile_context(), input1, input2, output, act_info);
148}
149
150void CLArithmeticDivision::configure(const CLCompileContext &compile_context, const ICLTensor *input1, const ICLTensor *input2, ICLTensor *output, const ActivationLayerInfo &act_info)
151{
152 _impl->src_0 = input1;
153 _impl->src_1 = input2;
154 _impl->dst = output;
Michele Di Giorgio237be032021-01-25 15:44:02 +0000155 _impl->op = std::make_unique<opencl::ClElementwiseDivision>();
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100156 _impl->op->configure(compile_context, input1->info(), input2->info(), output->info(), act_info);
157}
158
159Status CLArithmeticDivision::validate(const ITensorInfo *input1, const ITensorInfo *input2, const ITensorInfo *output, const ActivationLayerInfo &act_info)
160{
Michele Di Giorgio237be032021-01-25 15:44:02 +0000161 return opencl::ClElementwiseDivision::validate(input1, input2, output, act_info);
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100162}
163
164void CLArithmeticDivision::run()
165{
Georgios Pinitas0499dff2020-07-31 22:21:38 +0100166 ITensorPack pack;
167 pack.add_tensor(TensorType::ACL_SRC_0, _impl->src_0);
168 pack.add_tensor(TensorType::ACL_SRC_1, _impl->src_1);
169 pack.add_tensor(TensorType::ACL_DST, _impl->dst);
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100170
Georgios Pinitas0499dff2020-07-31 22:21:38 +0100171 _impl->op->run(pack);
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100172}
173
174struct CLElementwiseMax::Impl
175{
Michele Di Giorgio237be032021-01-25 15:44:02 +0000176 const ICLTensor *src_0{ nullptr };
177 const ICLTensor *src_1{ nullptr };
178 ICLTensor *dst{ nullptr };
179 std::unique_ptr<opencl::ClElementwiseMax> op{ nullptr };
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100180};
181
182CLElementwiseMax::CLElementwiseMax()
Georgios Pinitas40f51a62020-11-21 03:04:18 +0000183 : _impl(std::make_unique<Impl>())
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100184{
185}
186CLElementwiseMax::CLElementwiseMax(CLElementwiseMax &&) = default;
187CLElementwiseMax &CLElementwiseMax::operator=(CLElementwiseMax &&) = default;
188CLElementwiseMax::~CLElementwiseMax() = default;
189
190void CLElementwiseMax::configure(ICLTensor *input1, ICLTensor *input2, ICLTensor *output, const ActivationLayerInfo &act_info)
191{
192 configure(CLKernelLibrary::get().get_compile_context(), input1, input2, output, act_info);
193}
194
195void CLElementwiseMax::configure(const CLCompileContext &compile_context, ICLTensor *input1, ICLTensor *input2, ICLTensor *output, const ActivationLayerInfo &act_info)
196{
197 _impl->src_0 = input1;
198 _impl->src_1 = input2;
199 _impl->dst = output;
Michele Di Giorgio237be032021-01-25 15:44:02 +0000200 _impl->op = std::make_unique<opencl::ClElementwiseMax>();
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100201 _impl->op->configure(compile_context, input1->info(), input2->info(), output->info(), act_info);
202}
203
204Status CLElementwiseMax::validate(const ITensorInfo *input1, const ITensorInfo *input2, const ITensorInfo *output, const ActivationLayerInfo &act_info)
205{
Michele Di Giorgio237be032021-01-25 15:44:02 +0000206 return opencl::ClElementwiseMax::validate(input1, input2, output, act_info);
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100207}
208
209void CLElementwiseMax::run()
210{
Georgios Pinitas0499dff2020-07-31 22:21:38 +0100211 ITensorPack pack;
212 pack.add_tensor(TensorType::ACL_SRC_0, _impl->src_0);
213 pack.add_tensor(TensorType::ACL_SRC_1, _impl->src_1);
214 pack.add_tensor(TensorType::ACL_DST, _impl->dst);
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100215
Georgios Pinitas0499dff2020-07-31 22:21:38 +0100216 _impl->op->run(pack);
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100217}
218
219struct CLElementwiseMin::Impl
220{
Michele Di Giorgio237be032021-01-25 15:44:02 +0000221 const ICLTensor *src_0{ nullptr };
222 const ICLTensor *src_1{ nullptr };
223 ICLTensor *dst{ nullptr };
224 std::unique_ptr<opencl::ClElementwiseMin> op{ nullptr };
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100225};
226
227CLElementwiseMin::CLElementwiseMin()
Georgios Pinitas40f51a62020-11-21 03:04:18 +0000228 : _impl(std::make_unique<Impl>())
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100229{
230}
231CLElementwiseMin::CLElementwiseMin(CLElementwiseMin &&) = default;
232CLElementwiseMin &CLElementwiseMin::operator=(CLElementwiseMin &&) = default;
233CLElementwiseMin::~CLElementwiseMin() = default;
234
235void CLElementwiseMin::configure(ICLTensor *input1, ICLTensor *input2, ICLTensor *output, const ActivationLayerInfo &act_info)
236{
237 configure(CLKernelLibrary::get().get_compile_context(), input1, input2, output, act_info);
238}
239
240void CLElementwiseMin::configure(const CLCompileContext &compile_context, ICLTensor *input1, ICLTensor *input2, ICLTensor *output, const ActivationLayerInfo &act_info)
241{
242 _impl->src_0 = input1;
243 _impl->src_1 = input2;
244 _impl->dst = output;
Michele Di Giorgio237be032021-01-25 15:44:02 +0000245 _impl->op = std::make_unique<opencl::ClElementwiseMin>();
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100246 _impl->op->configure(compile_context, input1->info(), input2->info(), output->info(), act_info);
247}
248
249Status CLElementwiseMin::validate(const ITensorInfo *input1, const ITensorInfo *input2, const ITensorInfo *output, const ActivationLayerInfo &act_info)
250{
Michele Di Giorgio237be032021-01-25 15:44:02 +0000251 return opencl::ClElementwiseMin::validate(input1, input2, output, act_info);
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100252}
253
254void CLElementwiseMin::run()
255{
Georgios Pinitas0499dff2020-07-31 22:21:38 +0100256 ITensorPack pack;
257 pack.add_tensor(TensorType::ACL_SRC_0, _impl->src_0);
258 pack.add_tensor(TensorType::ACL_SRC_1, _impl->src_1);
259 pack.add_tensor(TensorType::ACL_DST, _impl->dst);
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100260
Georgios Pinitas0499dff2020-07-31 22:21:38 +0100261 _impl->op->run(pack);
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100262}
263
264struct CLElementwiseSquaredDiff::Impl
265{
Michele Di Giorgio237be032021-01-25 15:44:02 +0000266 const ICLTensor *src_0{ nullptr };
267 const ICLTensor *src_1{ nullptr };
268 ICLTensor *dst{ nullptr };
269 std::unique_ptr<opencl::ClElementwiseSquaredDiff> op{ nullptr };
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100270};
271
272CLElementwiseSquaredDiff::CLElementwiseSquaredDiff()
Georgios Pinitas40f51a62020-11-21 03:04:18 +0000273 : _impl(std::make_unique<Impl>())
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100274{
275}
276CLElementwiseSquaredDiff::CLElementwiseSquaredDiff(CLElementwiseSquaredDiff &&) = default;
277CLElementwiseSquaredDiff &CLElementwiseSquaredDiff::operator=(CLElementwiseSquaredDiff &&) = default;
278CLElementwiseSquaredDiff::~CLElementwiseSquaredDiff() = default;
279
280void CLElementwiseSquaredDiff::configure(ICLTensor *input1, ICLTensor *input2, ICLTensor *output, const ActivationLayerInfo &act_info)
281{
282 configure(CLKernelLibrary::get().get_compile_context(), input1, input2, output, act_info);
283}
284
285void CLElementwiseSquaredDiff::configure(const CLCompileContext &compile_context, ICLTensor *input1, ICLTensor *input2, ICLTensor *output, const ActivationLayerInfo &act_info)
286{
287 _impl->src_0 = input1;
288 _impl->src_1 = input2;
289 _impl->dst = output;
Michele Di Giorgio237be032021-01-25 15:44:02 +0000290 _impl->op = std::make_unique<opencl::ClElementwiseSquaredDiff>();
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100291 _impl->op->configure(compile_context, input1->info(), input2->info(), output->info(), act_info);
292}
293
294Status CLElementwiseSquaredDiff::validate(const ITensorInfo *input1, const ITensorInfo *input2, const ITensorInfo *output, const ActivationLayerInfo &act_info)
295{
Michele Di Giorgio237be032021-01-25 15:44:02 +0000296 return opencl::ClElementwiseSquaredDiff::validate(input1, input2, output, act_info);
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100297}
298
299void CLElementwiseSquaredDiff::run()
300{
Georgios Pinitas0499dff2020-07-31 22:21:38 +0100301 ITensorPack pack;
302 pack.add_tensor(TensorType::ACL_SRC_0, _impl->src_0);
303 pack.add_tensor(TensorType::ACL_SRC_1, _impl->src_1);
304 pack.add_tensor(TensorType::ACL_DST, _impl->dst);
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100305
Georgios Pinitas0499dff2020-07-31 22:21:38 +0100306 _impl->op->run(pack);
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100307}
308
309struct CLElementwisePower::Impl
310{
Michele Di Giorgio237be032021-01-25 15:44:02 +0000311 const ICLTensor *src_0{ nullptr };
312 const ICLTensor *src_1{ nullptr };
313 ICLTensor *dst{ nullptr };
314 std::unique_ptr<opencl::ClElementwisePower> op{ nullptr };
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100315};
316
317CLElementwisePower::CLElementwisePower()
Georgios Pinitas40f51a62020-11-21 03:04:18 +0000318 : _impl(std::make_unique<Impl>())
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100319{
320}
321CLElementwisePower::CLElementwisePower(CLElementwisePower &&) = default;
322CLElementwisePower &CLElementwisePower::operator=(CLElementwisePower &&) = default;
323CLElementwisePower::~CLElementwisePower() = default;
324
325void CLElementwisePower::configure(ICLTensor *input1, ICLTensor *input2, ICLTensor *output, const ActivationLayerInfo &act_info)
326{
327 configure(CLKernelLibrary::get().get_compile_context(), input1, input2, output, act_info);
328}
329
330void CLElementwisePower::configure(const CLCompileContext &compile_context, ICLTensor *input1, ICLTensor *input2, ICLTensor *output, const ActivationLayerInfo &act_info)
331{
332 _impl->src_0 = input1;
333 _impl->src_1 = input2;
334 _impl->dst = output;
Michele Di Giorgio237be032021-01-25 15:44:02 +0000335 _impl->op = std::make_unique<opencl::ClElementwisePower>();
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100336 _impl->op->configure(compile_context, input1->info(), input2->info(), output->info(), act_info);
337}
338
339Status CLElementwisePower::validate(const ITensorInfo *input1, const ITensorInfo *input2, const ITensorInfo *output, const ActivationLayerInfo &act_info)
340{
Michele Di Giorgio237be032021-01-25 15:44:02 +0000341 return opencl::ClElementwisePower::validate(input1, input2, output, act_info);
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100342}
343
344void CLElementwisePower::run()
345{
Georgios Pinitas0499dff2020-07-31 22:21:38 +0100346 ITensorPack pack;
347 pack.add_tensor(TensorType::ACL_SRC_0, _impl->src_0);
348 pack.add_tensor(TensorType::ACL_SRC_1, _impl->src_1);
349 pack.add_tensor(TensorType::ACL_DST, _impl->dst);
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100350
Georgios Pinitas0499dff2020-07-31 22:21:38 +0100351 _impl->op->run(pack);
Michalis Spyrouad7515d2020-07-24 00:02:23 +0100352}
giuros01164a2722018-11-20 18:34:46 +0000353} // namespace arm_compute