blob: 29a43f769b725586e916f02fed20fe514c1ac4a1 [file] [log] [blame]
Anthony Barbier6ff3b192017-09-04 18:44:23 +01001/*
2 * Copyright (c) 2016, 2017 ARM Limited.
3 *
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 */
24#ifndef ARM_COMPUTE_HELPER_H
25#define ARM_COMPUTE_HELPER_H
26
27#pragma OPENCL EXTENSION cl_khr_fp16 : enable
28
Georgios Pinitase5f8fd62017-06-23 18:03:44 +010029#define EXPAND(x) x
30
Anthony Barbier6ff3b192017-09-04 18:44:23 +010031#define CLAMP(x, min_val, max_val) min(max(x, min_val), max_val)
32
33#define VEC_DATA_TYPE_STR(type, size) type##size
34#define VEC_DATA_TYPE(type, size) VEC_DATA_TYPE_STR(type, size)
35
36#define CONVERT_STR(x, type) (convert_##type((x)))
37#define CONVERT(x, type) CONVERT_STR(x, type)
38
39#define CONVERT_SAT_STR(x, type) (convert_##type##_sat((x)))
40#define CONVERT_SAT(x, type) CONVERT_SAT_STR(x, type)
41
42#define CONVERT_SAT_ROUND_STR(x, type, round) (convert_##type##_sat_##round((x)))
43#define CONVERT_SAT_ROUND(x, type, round) CONVERT_SAT_ROUND_STR(x, type, round)
44
45#define VECTOR_DECLARATION(name) \
46 __global uchar *name##_ptr, \
47 uint name##_stride_x, \
48 uint name##_step_x, \
49 uint name##_offset_first_element_in_bytes
50
51#define IMAGE_DECLARATION(name) \
52 __global uchar *name##_ptr, \
53 uint name##_stride_x, \
54 uint name##_step_x, \
55 uint name##_stride_y, \
56 uint name##_step_y, \
57 uint name##_offset_first_element_in_bytes
58
59#define TENSOR3D_DECLARATION(name) \
60 __global uchar *name##_ptr, \
61 uint name##_stride_x, \
62 uint name##_step_x, \
63 uint name##_stride_y, \
64 uint name##_step_y, \
65 uint name##_stride_z, \
66 uint name##_step_z, \
67 uint name##_offset_first_element_in_bytes
68
69#define CONVERT_TO_VECTOR_STRUCT(name) \
70 update_vector_workitem_ptr(name##_ptr, name##_offset_first_element_in_bytes, name##_stride_x, name##_step_x)
71
72#define CONVERT_TO_VECTOR_STRUCT_NO_STEP(name) \
73 update_vector_workitem_ptr(name##_ptr, name##_offset_first_element_in_bytes, name##_stride_x, 0)
74
75#define CONVERT_TO_IMAGE_STRUCT(name) \
76 update_image_workitem_ptr(name##_ptr, name##_offset_first_element_in_bytes, name##_stride_x, name##_step_x, name##_stride_y, name##_step_y)
77
78#define CONVERT_TO_IMAGE_STRUCT_NO_STEP(name) \
79 update_image_workitem_ptr(name##_ptr, name##_offset_first_element_in_bytes, name##_stride_x, 0, name##_stride_y, 0)
80
Anthony Barbier7ff47a32017-07-11 16:54:04 +010081#define CONVERT_TENSOR3D_TO_IMAGE_STRUCT_NO_STEP(name) \
82 update_image_from_tensor3D_workitem_ptr(name##_ptr, name##_offset_first_element_in_bytes, name##_stride_x, 0, name##_stride_y, 0, name##_stride_z, name##_step_z)
83
Anthony Barbier6ff3b192017-09-04 18:44:23 +010084#define CONVERT_TO_TENSOR3D_STRUCT(name) \
85 update_tensor3D_workitem_ptr(name##_ptr, name##_offset_first_element_in_bytes, name##_stride_x, name##_step_x, name##_stride_y, name##_step_y, \
86 name##_stride_z, name##_step_z)
87
88#define CONVERT_TO_TENSOR3D_STRUCT_NO_STEP(name) \
89 update_tensor3D_workitem_ptr(name##_ptr, name##_offset_first_element_in_bytes, name##_stride_x, 0, name##_stride_y, 0, name##_stride_z, 0)
90
91/** Structure to hold Vector information */
92typedef struct Vector
93{
94 __global uchar *ptr; /**< Pointer to the starting postion of the buffer */
95 int offset_first_element_in_bytes; /**< The offset of the first element in the source image */
96 int stride_x; /**< Stride of the image in X dimension (in bytes) */
97} Vector;
98
99/** Structure to hold Image information */
100typedef struct Image
101{
102 __global uchar *ptr; /**< Pointer to the starting postion of the buffer */
103 int offset_first_element_in_bytes; /**< The offset of the first element in the source image */
104 int stride_x; /**< Stride of the image in X dimension (in bytes) */
105 int stride_y; /**< Stride of the image in Y dimension (in bytes) */
106} Image;
107
108/** Structure to hold 3D tensor information */
109typedef struct Tensor3D
110{
111 __global uchar *ptr; /**< Pointer to the starting postion of the buffer */
112 int offset_first_element_in_bytes; /**< The offset of the first element in the source image */
113 int stride_x; /**< Stride of the image in X dimension (in bytes) */
114 int stride_y; /**< Stride of the image in Y dimension (in bytes) */
115 int stride_z; /**< Stride of the image in Z dimension (in bytes) */
116} Tensor3D;
117
118/** Wrap vector information into an Vector structure, and make the pointer point at this workitem's data.
119 *
120 * @param[in] ptr Pointer to the starting postion of the buffer
121 * @param[in] offset_first_element_in_bytes The offset of the first element in the source vector
122 * @param[in] stride_x Stride of the vector in X dimension (in bytes)
123 * @param[in] step_x stride_x * number of elements along X processed per workitem(in bytes)
124 *
125 * @return An image object
126 */
127Vector inline update_vector_workitem_ptr(__global uchar *ptr, uint offset_first_element_in_bytes, uint stride_x, uint step_x)
128{
129 Vector vector =
130 {
131 .ptr = ptr,
132 .offset_first_element_in_bytes = offset_first_element_in_bytes,
133 .stride_x = stride_x,
134 };
135 vector.ptr += vector.offset_first_element_in_bytes + get_global_id(0) * step_x;
136 return vector;
137}
138
139/** Wrap image information into an Image structure, and make the pointer point at this workitem's data.
140 *
141 * @param[in] ptr Pointer to the starting postion of the buffer
142 * @param[in] offset_first_element_in_bytes The offset of the first element in the source image
143 * @param[in] stride_x Stride of the image in X dimension (in bytes)
144 * @param[in] step_x stride_x * number of elements along X processed per workitem(in bytes)
145 * @param[in] stride_y Stride of the image in Y dimension (in bytes)
146 * @param[in] step_y stride_y * number of elements along Y processed per workitem(in bytes)
147 *
148 * @return An image object
149 */
150Image inline update_image_workitem_ptr(__global uchar *ptr, uint offset_first_element_in_bytes, uint stride_x, uint step_x, uint stride_y, uint step_y)
151{
152 Image img =
153 {
154 .ptr = ptr,
155 .offset_first_element_in_bytes = offset_first_element_in_bytes,
156 .stride_x = stride_x,
157 .stride_y = stride_y
158 };
159 img.ptr += img.offset_first_element_in_bytes + get_global_id(0) * step_x + get_global_id(1) * step_y;
160 return img;
161}
162
Anthony Barbier7ff47a32017-07-11 16:54:04 +0100163/** Wrap 3D tensor information into an image structure, and make the pointer point at this workitem's data.
164 *
165 * @param[in] ptr Pointer to the starting postion of the buffer
166 * @param[in] offset_first_element_in_bytes The offset of the first element in the source image
167 * @param[in] stride_x Stride of the image in X dimension (in bytes)
168 * @param[in] step_x stride_x * number of elements along X processed per workitem(in bytes)
169 * @param[in] stride_y Stride of the image in Y dimension (in bytes)
170 * @param[in] step_y stride_y * number of elements along Y processed per workitem(in bytes)
171 * @param[in] stride_z Stride of the image in Z dimension (in bytes)
172 * @param[in] step_z stride_z * number of elements along Z processed per workitem(in bytes)
173 *
174 * @return A 3D tensor object
175 */
176Image inline update_image_from_tensor3D_workitem_ptr(__global uchar *ptr, uint offset_first_element_in_bytes, uint stride_x, uint step_x, uint stride_y, uint step_y, uint stride_z, uint step_z)
177{
178 Image img =
179 {
180 .ptr = ptr,
181 .offset_first_element_in_bytes = offset_first_element_in_bytes,
182 .stride_x = stride_x,
183 .stride_y = stride_y
184 };
185 img.ptr += img.offset_first_element_in_bytes + get_global_id(0) * step_x + get_global_id(1) * step_y + get_global_id(2) * step_z;
186 return img;
187}
188
Anthony Barbier6ff3b192017-09-04 18:44:23 +0100189/** Wrap 3D tensor information into an tensor structure, and make the pointer point at this workitem's data.
190 *
191 * @param[in] ptr Pointer to the starting postion of the buffer
192 * @param[in] offset_first_element_in_bytes The offset of the first element in the source image
193 * @param[in] stride_x Stride of the image in X dimension (in bytes)
194 * @param[in] step_x stride_x * number of elements along X processed per workitem(in bytes)
195 * @param[in] stride_y Stride of the image in Y dimension (in bytes)
196 * @param[in] step_y stride_y * number of elements along Y processed per workitem(in bytes)
197 * @param[in] stride_z Stride of the image in Z dimension (in bytes)
198 * @param[in] step_z stride_z * number of elements along Z processed per workitem(in bytes)
199 *
200 * @return A 3D tensor object
201 */
202Tensor3D inline update_tensor3D_workitem_ptr(__global uchar *ptr, uint offset_first_element_in_bytes, uint stride_x, uint step_x, uint stride_y, uint step_y, uint stride_z, uint step_z)
203{
204 Tensor3D tensor =
205 {
206 .ptr = ptr,
207 .offset_first_element_in_bytes = offset_first_element_in_bytes,
208 .stride_x = stride_x,
209 .stride_y = stride_y,
210 .stride_z = stride_z
211 };
212 tensor.ptr += tensor.offset_first_element_in_bytes + get_global_id(0) * step_x + get_global_id(1) * step_y + get_global_id(2) * step_z;
213 return tensor;
214}
215
216/** Get the pointer position of a Vector
217 *
218 * @param[in] vec Pointer to the starting position of the buffer
219 * @param[in] x Relative X position
220 */
221__global inline const uchar *vector_offset(const Vector *vec, int x)
222{
223 return vec->ptr + x * vec->stride_x;
224}
225
226/** Get the pointer position of a Image
227 *
228 * @param[in] img Pointer to the starting position of the buffer
229 * @param[in] x Relative X position
230 * @param[in] y Relative Y position
231 */
232__global inline uchar *offset(const Image *img, int x, int y)
233{
234 return img->ptr + x * img->stride_x + y * img->stride_y;
235}
236
237/** Get the pointer position of a Tensor3D
238 *
239 * @param[in] tensor Pointer to the starting postion of the buffer
240 * @param[in] x Relative X position
241 * @param[in] y Relative Y position
242 * @param[in] z Relative Z position
243 */
244__global inline const uchar *tensor3D_offset(const Tensor3D *tensor, int x, int y, int z)
245{
246 return tensor->ptr + x * tensor->stride_x + y * tensor->stride_y + z * tensor->stride_z;
247}
248
249#endif // _HELPER_H