xref: /aosp_15_r20/external/OpenCL-CTS/test_conformance/images/kernel_read_write/main.cpp (revision 6467f958c7de8070b317fc65bcb0f6472e388d82)
1 //
2 // Copyright (c) 2017 The Khronos Group Inc.
3 //
4 // Licensed under the Apache License, Version 2.0 (the "License");
5 // you may not use this file except in compliance with the License.
6 // You may obtain a copy of the License at
7 //
8 //    http://www.apache.org/licenses/LICENSE-2.0
9 //
10 // Unless required by applicable law or agreed to in writing, software
11 // distributed under the License is distributed on an "AS IS" BASIS,
12 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 // See the License for the specific language governing permissions and
14 // limitations under the License.
15 //
16 
17 #include <stdio.h>
18 #include <string.h>
19 #include "../testBase.h"
20 #include "../harness/compat.h"
21 #include "../harness/fpcontrol.h"
22 #include "../harness/parseParameters.h"
23 
24 #if defined(__PPC__)
25 // Global varaiable used to hold the FPU control register state. The FPSCR register can not
26 // be used because not all Power implementations retain or observed the NI (non-IEEE
27 // mode) bit.
28 __thread fpu_control_t fpu_control = 0;
29 #endif
30 
31 bool gDebugTrace;
32 bool gExtraValidateInfo;
33 bool gDisableOffsets;
34 bool gTestSmallImages;
35 bool gTestMaxImages;
36 bool gTestImage2DFromBuffer;
37 bool gTestMipmaps;
38 cl_filter_mode    gFilterModeToUse = (cl_filter_mode)-1;
39 // Default is CL_MEM_USE_HOST_PTR for the test
40 cl_mem_flags    gMemFlagsToUse = CL_MEM_USE_HOST_PTR;
41 bool            gUseKernelSamplers = false;
42 int                gTypesToTest = 0;
43 cl_addressing_mode gAddressModeToUse = (cl_addressing_mode)-1;
44 int             gNormalizedModeToUse = 7;
45 cl_channel_type gChannelTypeToUse = (cl_channel_type)-1;
46 cl_channel_order gChannelOrderToUse = (cl_channel_order)-1;
47 bool            gEnablePitch = false;
48 
49 int             gtestTypesToRun = 0;
50 static int testTypesToRun;
51 
52 static void printUsage( const char *execName );
53 
54 extern int test_image_set( cl_device_id device, cl_context context, cl_command_queue queue, test_format_set_fn formatTestFn, cl_mem_object_type imageType );
55 
56 extern int cl_image_requirements_size_ext_negative(cl_device_id device,
57                                                    cl_context context,
58                                                    cl_command_queue queue);
59 extern int cl_image_requirements_size_ext_consistency(cl_device_id device,
60                                                       cl_context context,
61                                                       cl_command_queue queue);
62 extern int clGetImageRequirementsInfoEXT_negative(cl_device_id device,
63                                                   cl_context context,
64                                                   cl_command_queue queue);
65 extern int cl_image_requirements_max_val_ext_negative(cl_device_id device,
66                                                       cl_context context,
67                                                       cl_command_queue queue);
68 extern int cl_image_requirements_max_val_ext_positive(cl_device_id device,
69                                                       cl_context context,
70                                                       cl_command_queue queue);
71 
72 extern int image2d_from_buffer_positive(cl_device_id device, cl_context context,
73                                         cl_command_queue queue);
74 extern int memInfo_image_from_buffer_positive(cl_device_id device,
75                                               cl_context context,
76                                               cl_command_queue queue);
77 extern int imageInfo_image_from_buffer_positive(cl_device_id device,
78                                                 cl_context context,
79                                                 cl_command_queue queue);
80 extern int image_from_buffer_alignment_negative(cl_device_id device,
81                                                 cl_context context,
82                                                 cl_command_queue queue);
83 extern int image_from_small_buffer_negative(cl_device_id device,
84                                             cl_context context,
85                                             cl_command_queue queue);
86 extern int image_from_buffer_fill_positive(cl_device_id device,
87                                            cl_context context,
88                                            cl_command_queue queue);
89 extern int image_from_buffer_read_positive(cl_device_id device,
90                                            cl_context context,
91                                            cl_command_queue queue);
92 
93 /** read_write images only support sampler-less read buildt-ins which require special settings
94   * for some global parameters. This pair of functions temporarily overwrite those global parameters
95   * and then recover them after completing a read_write test.
96   */
overwrite_global_params_for_read_write_test(bool * tTestMipmaps,bool * tDisableOffsets,bool * tNormalizedModeToUse,cl_filter_mode * tFilterModeToUse)97 static void overwrite_global_params_for_read_write_test(  bool            *tTestMipmaps,
98                                                             bool            *tDisableOffsets,
99                                                             bool            *tNormalizedModeToUse,
100                                                             cl_filter_mode  *tFilterModeToUse)
101 {
102     log_info("Overwrite global settings for read_write image tests. The overwritten values:\n");
103     log_info("gTestMipmaps = false, gDisableOffsets = true, gNormalizedModeToUse = false, gFilterModeToUse = CL_FILTER_NEAREST\n" );
104     // mipmap images only support sampler read built-in while read_write images only support
105     // sampler-less read built-in. Hence we cannot test mipmap for read_write image.
106     *tTestMipmaps = gTestMipmaps;
107     gTestMipmaps = false;
108 
109     // Read_write images are read by sampler-less read which does not handle out-of-bound read
110     // It's application responsibility to make sure that the read happens in-bound
111     // Therefore we should not enable offset in testing read_write images because it will cause out-of-bound
112     *tDisableOffsets    = gDisableOffsets;
113     gDisableOffsets     = true;
114 
115     // The sampler-less read image functions behave exactly as the corresponding read image functions
116 
117 
118     *tNormalizedModeToUse   = gNormalizedModeToUse;
119     gNormalizedModeToUse    = false;
120     *tFilterModeToUse       = gFilterModeToUse;
121     gFilterModeToUse        = CL_FILTER_NEAREST;
122 }
123 
124 /** Recover the global settings overwritten for read_write tests. This is necessary because
125   * there may be other tests (i.e. read or write) are called together with read_write test.
126   */
recover_global_params_from_read_write_test(bool tTestMipmaps,bool tDisableOffsets,bool tNormalizedModeToUse,cl_filter_mode tFilterModeToUse)127 static void recover_global_params_from_read_write_test(bool            tTestMipmaps,
128                                                          bool            tDisableOffsets,
129                                                          bool            tNormalizedModeToUse,
130                                                          cl_filter_mode  tFilterModeToUse)
131 {
132     gTestMipmaps            = tTestMipmaps;
133     gDisableOffsets         = tDisableOffsets;
134     gNormalizedModeToUse    = tNormalizedModeToUse;
135     gFilterModeToUse        = tFilterModeToUse;
136 }
137 
doTest(cl_device_id device,cl_context context,cl_command_queue queue,cl_mem_object_type imageType)138 static int doTest( cl_device_id device, cl_context context, cl_command_queue queue, cl_mem_object_type imageType )
139 {
140     int ret = 0;
141     bool is_2d_image = imageType == CL_MEM_OBJECT_IMAGE2D;
142     bool            tTestMipMaps = false;
143     bool            tDisableOffsets = false;
144     bool            tNormalizedModeToUse = false;
145     cl_filter_mode  tFilterModeToUse = (cl_filter_mode)-1;
146 
147     if( testTypesToRun & kReadTests )
148     {
149         gtestTypesToRun = kReadTests;
150         ret += test_image_set( device, context, queue, test_read_image_formats, imageType );
151 
152         if( is_2d_image && is_extension_available( device, "cl_khr_image2d_from_buffer" ) )
153         {
154             log_info( "Testing read_image{f | i | ui} for 2D image from buffer\n" );
155 
156             // NOTE: for 2D image from buffer test, gTestSmallImages, gTestMaxImages, gTestRounding and gTestMipmaps must be false
157             if( gTestSmallImages == false && gTestMaxImages == false && gTestRounding == false && gTestMipmaps == false )
158             {
159                 cl_mem_flags saved_gMemFlagsToUse = gMemFlagsToUse;
160                 gTestImage2DFromBuffer = true;
161 
162                 // disable CL_MEM_USE_HOST_PTR for 1.2 extension but enable this for 2.0
163                 gMemFlagsToUse = CL_MEM_COPY_HOST_PTR;
164 
165                 ret += test_image_set( device, context, queue, test_read_image_formats, imageType );
166 
167                 gTestImage2DFromBuffer = false;
168                 gMemFlagsToUse = saved_gMemFlagsToUse;
169             }
170         }
171     }
172 
173     if( testTypesToRun & kWriteTests )
174     {
175         gtestTypesToRun = kWriteTests;
176         ret += test_image_set( device, context, queue, test_write_image_formats, imageType );
177 
178         if( is_2d_image && is_extension_available( device, "cl_khr_image2d_from_buffer" ) )
179         {
180             log_info( "Testing write_image{f | i | ui} for 2D image from buffer\n" );
181 
182             // NOTE: for 2D image from buffer test, gTestSmallImages, gTestMaxImages,gTestRounding and gTestMipmaps must be false
183             if( gTestSmallImages == false && gTestMaxImages == false && gTestRounding == false && gTestMipmaps == false )
184             {
185                 bool saved_gEnablePitch = gEnablePitch;
186                 cl_mem_flags saved_gMemFlagsToUse = gMemFlagsToUse;
187                 gEnablePitch = true;
188 
189                 // disable CL_MEM_USE_HOST_PTR for 1.2 extension but enable this for 2.0
190                 gMemFlagsToUse = CL_MEM_COPY_HOST_PTR;
191                 gTestImage2DFromBuffer = true;
192 
193                 ret += test_image_set( device, context, queue, test_write_image_formats, imageType );
194 
195                 gTestImage2DFromBuffer = false;
196                 gMemFlagsToUse = saved_gMemFlagsToUse;
197                 gEnablePitch = saved_gEnablePitch;
198             }
199         }
200     }
201 
202     if ((testTypesToRun & kReadWriteTests)
203         && checkForReadWriteImageSupport(device))
204     {
205         return TEST_SKIPPED_ITSELF;
206     }
207 
208     if( ( testTypesToRun & kReadWriteTests ) && !gTestMipmaps )
209     {
210         gtestTypesToRun = kReadWriteTests;
211         overwrite_global_params_for_read_write_test(&tTestMipMaps, &tDisableOffsets, &tNormalizedModeToUse, &tFilterModeToUse);
212         ret += test_image_set( device, context, queue, test_read_image_formats, imageType );
213 
214         if( is_2d_image && is_extension_available( device, "cl_khr_image2d_from_buffer" ) )
215         {
216             log_info("Testing read_image{f | i | ui} for 2D image from buffer\n");
217 
218             // NOTE: for 2D image from buffer test, gTestSmallImages, gTestMaxImages, gTestRounding and gTestMipmaps must be false
219             if( gTestSmallImages == false && gTestMaxImages == false && gTestRounding == false && gTestMipmaps == false )
220             {
221                 cl_mem_flags saved_gMemFlagsToUse = gMemFlagsToUse;
222                 gTestImage2DFromBuffer = true;
223 
224                 // disable CL_MEM_USE_HOST_PTR for 1.2 extension but enable this for 2.0
225                 gMemFlagsToUse = CL_MEM_COPY_HOST_PTR;
226 
227                 ret += test_image_set( device, context, queue, test_read_image_formats, imageType );
228 
229                 gTestImage2DFromBuffer = false;
230                 gMemFlagsToUse = saved_gMemFlagsToUse;
231             }
232         }
233 
234         ret += test_image_set( device, context, queue, test_write_image_formats, imageType );
235 
236         if( is_2d_image && is_extension_available( device, "cl_khr_image2d_from_buffer" ) )
237         {
238             log_info("Testing write_image{f | i | ui} for 2D image from buffer\n");
239 
240             // NOTE: for 2D image from buffer test, gTestSmallImages, gTestMaxImages,gTestRounding and gTestMipmaps must be false
241             if( gTestSmallImages == false && gTestMaxImages == false && gTestRounding == false && gTestMipmaps == false )
242             {
243                 bool saved_gEnablePitch = gEnablePitch;
244                 cl_mem_flags saved_gMemFlagsToUse = gMemFlagsToUse;
245                 gEnablePitch = true;
246 
247                 // disable CL_MEM_USE_HOST_PTR for 1.2 extension but enable this for 2.0
248                 gMemFlagsToUse = CL_MEM_COPY_HOST_PTR;
249                 gTestImage2DFromBuffer = true;
250 
251                 ret += test_image_set( device, context, queue, test_write_image_formats, imageType );
252 
253                 gTestImage2DFromBuffer = false;
254                 gMemFlagsToUse = saved_gMemFlagsToUse;
255                 gEnablePitch = saved_gEnablePitch;
256             }
257         }
258 
259         recover_global_params_from_read_write_test( tTestMipMaps, tDisableOffsets, tNormalizedModeToUse, tFilterModeToUse );
260     }
261 
262     return ret;
263 }
264 
test_1D(cl_device_id device,cl_context context,cl_command_queue queue,int num_elements)265 int test_1D(cl_device_id device, cl_context context, cl_command_queue queue, int num_elements)
266 {
267     return doTest( device, context, queue, CL_MEM_OBJECT_IMAGE1D );
268 }
test_2D(cl_device_id device,cl_context context,cl_command_queue queue,int num_elements)269 int test_2D(cl_device_id device, cl_context context, cl_command_queue queue, int num_elements)
270 {
271     return doTest( device, context, queue, CL_MEM_OBJECT_IMAGE2D );
272 }
test_3D(cl_device_id device,cl_context context,cl_command_queue queue,int num_elements)273 int test_3D(cl_device_id device, cl_context context, cl_command_queue queue, int num_elements)
274 {
275     return doTest( device, context, queue, CL_MEM_OBJECT_IMAGE3D );
276 }
test_1Darray(cl_device_id device,cl_context context,cl_command_queue queue,int num_elements)277 int test_1Darray(cl_device_id device, cl_context context, cl_command_queue queue, int num_elements)
278 {
279     return doTest( device, context, queue, CL_MEM_OBJECT_IMAGE1D_ARRAY );
280 }
test_2Darray(cl_device_id device,cl_context context,cl_command_queue queue,int num_elements)281 int test_2Darray(cl_device_id device, cl_context context, cl_command_queue queue, int num_elements)
282 {
283     return doTest( device, context, queue, CL_MEM_OBJECT_IMAGE2D_ARRAY );
284 }
285 
test_cl_image_requirements_size_ext_negative(cl_device_id device,cl_context context,cl_command_queue queue,int num_elements)286 int test_cl_image_requirements_size_ext_negative(cl_device_id device,
287                                                  cl_context context,
288                                                  cl_command_queue queue,
289                                                  int num_elements)
290 {
291     return cl_image_requirements_size_ext_negative(device, context, queue);
292 }
test_cl_image_requirements_size_ext_consistency(cl_device_id device,cl_context context,cl_command_queue queue,int num_elements)293 int test_cl_image_requirements_size_ext_consistency(cl_device_id device,
294                                                     cl_context context,
295                                                     cl_command_queue queue,
296                                                     int num_elements)
297 {
298     return cl_image_requirements_size_ext_consistency(device, context, queue);
299 }
test_clGetImageRequirementsInfoEXT_negative(cl_device_id device,cl_context context,cl_command_queue queue,int num_elements)300 int test_clGetImageRequirementsInfoEXT_negative(cl_device_id device,
301                                                 cl_context context,
302                                                 cl_command_queue queue,
303                                                 int num_elements)
304 {
305     return clGetImageRequirementsInfoEXT_negative(device, context, queue);
306 }
test_cl_image_requirements_max_val_ext_negative(cl_device_id device,cl_context context,cl_command_queue queue,int num_elements)307 int test_cl_image_requirements_max_val_ext_negative(cl_device_id device,
308                                                     cl_context context,
309                                                     cl_command_queue queue,
310                                                     int num_elements)
311 {
312     return cl_image_requirements_max_val_ext_negative(device, context, queue);
313 }
test_cl_image_requirements_max_val_ext_positive(cl_device_id device,cl_context context,cl_command_queue queue,int num_elements)314 int test_cl_image_requirements_max_val_ext_positive(cl_device_id device,
315                                                     cl_context context,
316                                                     cl_command_queue queue,
317                                                     int num_elements)
318 {
319     return cl_image_requirements_max_val_ext_positive(device, context, queue);
320 }
321 
test_image2d_from_buffer_positive(cl_device_id device,cl_context context,cl_command_queue queue,int num_elements)322 int test_image2d_from_buffer_positive(cl_device_id device, cl_context context,
323                                       cl_command_queue queue, int num_elements)
324 {
325     return image2d_from_buffer_positive(device, context, queue);
326 }
test_memInfo_image_from_buffer_positive(cl_device_id device,cl_context context,cl_command_queue queue,int num_elements)327 int test_memInfo_image_from_buffer_positive(cl_device_id device,
328                                             cl_context context,
329                                             cl_command_queue queue,
330                                             int num_elements)
331 {
332     return memInfo_image_from_buffer_positive(device, context, queue);
333 }
test_imageInfo_image_from_buffer_positive(cl_device_id device,cl_context context,cl_command_queue queue,int num_elements)334 int test_imageInfo_image_from_buffer_positive(cl_device_id device,
335                                               cl_context context,
336                                               cl_command_queue queue,
337                                               int num_elements)
338 {
339     return imageInfo_image_from_buffer_positive(device, context, queue);
340 }
test_image_from_buffer_alignment_negative(cl_device_id device,cl_context context,cl_command_queue queue,int num_elements)341 int test_image_from_buffer_alignment_negative(cl_device_id device,
342                                               cl_context context,
343                                               cl_command_queue queue,
344                                               int num_elements)
345 {
346     return image_from_buffer_alignment_negative(device, context, queue);
347 }
test_image_from_small_buffer_negative(cl_device_id device,cl_context context,cl_command_queue queue,int num_elements)348 int test_image_from_small_buffer_negative(cl_device_id device,
349                                           cl_context context,
350                                           cl_command_queue queue,
351                                           int num_elements)
352 {
353     return image_from_small_buffer_negative(device, context, queue);
354 }
test_image_from_buffer_fill_positive(cl_device_id device,cl_context context,cl_command_queue queue,int num_elements)355 int test_image_from_buffer_fill_positive(cl_device_id device,
356                                          cl_context context,
357                                          cl_command_queue queue,
358                                          int num_elements)
359 {
360     return image_from_buffer_fill_positive(device, context, queue);
361 }
test_image_from_buffer_read_positive(cl_device_id device,cl_context context,cl_command_queue queue,int num_elements)362 int test_image_from_buffer_read_positive(cl_device_id device,
363                                          cl_context context,
364                                          cl_command_queue queue,
365                                          int num_elements)
366 {
367     return image_from_buffer_read_positive(device, context, queue);
368 }
369 
370 test_definition test_list[] = {
371     ADD_TEST(1D),
372     ADD_TEST(2D),
373     ADD_TEST(3D),
374     ADD_TEST(1Darray),
375     ADD_TEST(2Darray),
376     ADD_TEST_VERSION(cl_image_requirements_size_ext_negative, Version(3, 0)),
377     ADD_TEST_VERSION(cl_image_requirements_size_ext_consistency, Version(3, 0)),
378     ADD_TEST_VERSION(clGetImageRequirementsInfoEXT_negative, Version(3, 0)),
379     ADD_TEST_VERSION(cl_image_requirements_max_val_ext_negative, Version(3, 0)),
380     ADD_TEST_VERSION(cl_image_requirements_max_val_ext_positive, Version(3, 0)),
381     ADD_TEST_VERSION(image2d_from_buffer_positive, Version(3, 0)),
382     ADD_TEST_VERSION(memInfo_image_from_buffer_positive, Version(3, 0)),
383     ADD_TEST_VERSION(imageInfo_image_from_buffer_positive, Version(3, 0)),
384     ADD_TEST_VERSION(image_from_buffer_alignment_negative, Version(3, 0)),
385     ADD_TEST_VERSION(image_from_small_buffer_negative, Version(3, 0)),
386     ADD_TEST_VERSION(image_from_buffer_fill_positive, Version(3, 0)),
387     ADD_TEST_VERSION(image_from_buffer_read_positive, Version(3, 0)),
388 };
389 
390 const int test_num = ARRAY_SIZE( test_list );
391 
main(int argc,const char * argv[])392 int main(int argc, const char *argv[])
393 {
394     cl_channel_type chanType;
395     cl_channel_order chanOrder;
396 
397     argc = parseCustomParam(argc, argv);
398     if (argc == -1)
399     {
400         return -1;
401     }
402 
403     const char ** argList = (const char **)calloc( argc, sizeof( char*) );
404 
405     if( NULL == argList )
406     {
407         log_error( "Failed to allocate memory for argList array.\n" );
408         return 1;
409     }
410 
411     argList[0] = argv[0];
412     size_t argCount = 1;
413 
414     // Parse arguments
415     for( int i = 1; i < argc; i++ )
416     {
417         if( strcmp( argv[i], "debug_trace" ) == 0 )
418             gDebugTrace = true;
419 
420         else if( strcmp( argv[i], "CL_FILTER_NEAREST" ) == 0 || strcmp( argv[i], "NEAREST" ) == 0 )
421             gFilterModeToUse = CL_FILTER_NEAREST;
422         else if( strcmp( argv[i], "CL_FILTER_LINEAR" ) == 0 || strcmp( argv[i], "LINEAR" ) == 0 )
423             gFilterModeToUse = CL_FILTER_LINEAR;
424 
425         else if( strcmp( argv[i], "CL_ADDRESS_NONE" ) == 0 )
426             gAddressModeToUse = CL_ADDRESS_NONE;
427         else if( strcmp( argv[i], "CL_ADDRESS_CLAMP" ) == 0 )
428             gAddressModeToUse = CL_ADDRESS_CLAMP;
429         else if( strcmp( argv[i], "CL_ADDRESS_CLAMP_TO_EDGE" ) == 0 )
430             gAddressModeToUse = CL_ADDRESS_CLAMP_TO_EDGE;
431         else if( strcmp( argv[i], "CL_ADDRESS_REPEAT" ) == 0 )
432             gAddressModeToUse = CL_ADDRESS_REPEAT;
433         else if( strcmp( argv[i], "CL_ADDRESS_MIRRORED_REPEAT" ) == 0 )
434             gAddressModeToUse = CL_ADDRESS_MIRRORED_REPEAT;
435 
436         else if( strcmp( argv[i], "NORMALIZED" ) == 0 )
437             gNormalizedModeToUse = true;
438         else if( strcmp( argv[i], "UNNORMALIZED" ) == 0 )
439             gNormalizedModeToUse = false;
440 
441 
442         else if( strcmp( argv[i], "no_offsets" ) == 0 )
443             gDisableOffsets = true;
444         else if( strcmp( argv[i], "small_images" ) == 0 )
445             gTestSmallImages = true;
446         else if( strcmp( argv[i], "max_images" ) == 0 )
447             gTestMaxImages = true;
448         else if( strcmp( argv[i], "use_pitches" ) == 0 )
449             gEnablePitch = true;
450         else if( strcmp( argv[i], "rounding" ) == 0 )
451             gTestRounding = true;
452         else if( strcmp( argv[i], "extra_validate" ) == 0 )
453             gExtraValidateInfo = true;
454         else if( strcmp( argv[i], "test_mipmaps" ) == 0 ) {
455             // 2.0 Spec does not allow using mem flags, unnormalized coordinates with mipmapped images
456             gTestMipmaps = true;
457             gMemFlagsToUse = 0;
458             gNormalizedModeToUse = true;
459         }
460 
461         else if( strcmp( argv[i], "read" ) == 0 )
462             testTypesToRun |= kReadTests;
463         else if( strcmp( argv[i], "write" ) == 0 )
464             testTypesToRun |= kWriteTests;
465         else if( strcmp( argv[i], "read_write" ) == 0 )
466         {
467             testTypesToRun |= kReadWriteTests;
468         }
469 
470         else if( strcmp( argv[i], "local_samplers" ) == 0 )
471             gUseKernelSamplers = true;
472 
473         else if( strcmp( argv[i], "int" ) == 0 )
474             gTypesToTest |= kTestInt;
475         else if( strcmp( argv[i], "uint" ) == 0 )
476             gTypesToTest |= kTestUInt;
477         else if( strcmp( argv[i], "float" ) == 0 )
478             gTypesToTest |= kTestFloat;
479 
480         else if( strcmp( argv[i], "CL_MEM_COPY_HOST_PTR" ) == 0 || strcmp( argv[i], "COPY_HOST_PTR" ) == 0 )
481             gMemFlagsToUse = CL_MEM_COPY_HOST_PTR;
482         else if( strcmp( argv[i], "CL_MEM_USE_HOST_PTR" ) == 0 || strcmp( argv[i], "USE_HOST_PTR" ) == 0 )
483             gMemFlagsToUse = CL_MEM_USE_HOST_PTR;
484         else if( strcmp( argv[i], "CL_MEM_ALLOC_HOST_PTR" ) == 0 || strcmp( argv[i], "ALLOC_HOST_PTR" ) == 0 )
485             gMemFlagsToUse = CL_MEM_ALLOC_HOST_PTR;
486         else if( strcmp( argv[i], "NO_HOST_PTR" ) == 0 )
487             gMemFlagsToUse = 0;
488 
489         else if( strcmp( argv[i], "--help" ) == 0 || strcmp( argv[i], "-h" ) == 0 )
490         {
491             printUsage( argv[ 0 ] );
492             return -1;
493         }
494 
495         else if( ( chanType = get_channel_type_from_name( argv[i] ) ) != (cl_channel_type)-1 )
496             gChannelTypeToUse = chanType;
497 
498         else if( ( chanOrder = get_channel_order_from_name( argv[i] ) ) != (cl_channel_order)-1 )
499             gChannelOrderToUse = chanOrder;
500         else
501         {
502             argList[argCount] = argv[i];
503             argCount++;
504         }
505     }
506 
507     if( testTypesToRun == 0 )
508         testTypesToRun = kAllTests;
509     if( gTypesToTest == 0 )
510         gTypesToTest = kTestAllTypes;
511 
512     if( gTestSmallImages )
513         log_info( "Note: Using small test images\n" );
514 
515     // On most platforms which support denorm, default is FTZ off. However,
516     // on some hardware where the reference is computed, default might be flush denorms to zero e.g. arm.
517     // This creates issues in result verification. Since spec allows the implementation to either flush or
518     // not flush denorms to zero, an implementation may choose not to flush i.e. return denorm result whereas
519     // reference result may be zero (flushed denorm). Hence we need to disable denorm flushing on host side
520     // where reference is being computed to make sure we get non-flushed reference result. If implementation
521     // returns flushed result, we correctly take care of that in verification code.
522 
523     FPU_mode_type oldMode;
524     DisableFTZ(&oldMode);
525 
526     int ret = runTestHarnessWithCheck(argCount, argList, test_num, test_list,
527                                       false, 0, verifyImageSupport);
528 
529     // Restore FP state before leaving
530     RestoreFPState(&oldMode);
531 
532     free(argList);
533     return ret;
534 }
535 
printUsage(const char * execName)536 static void printUsage( const char *execName )
537 {
538     const char *p = strrchr( execName, '/' );
539     if( p != NULL )
540         execName = p + 1;
541 
542     log_info( "Usage: %s [options] [test_names]\n", execName );
543     log_info( "Options:\n" );
544     log_info( "\n" );
545     log_info( "\tThe following flags specify what kinds of operations to test. They can be combined; if none are specified, all are tested:\n" );
546     log_info( "\t\tread - Tests reading from an image\n" );
547     log_info( "\t\twrite - Tests writing to an image (can be specified with read to run both; default is both)\n" );
548     log_info( "\n" );
549     log_info( "\tThe following flags specify the types to test. They can be combined; if none are specified, all are tested:\n" );
550     log_info( "\t\tint - Test integer I/O (read_imagei, write_imagei)\n" );
551     log_info( "\t\tuint - Test unsigned integer I/O (read_imageui, write_imageui)\n" );
552     log_info( "\t\tfloat - Test float I/O (read_imagef, write_imagef)\n" );
553     log_info( "\n" );
554     log_info( "\tCL_FILTER_LINEAR - Only tests formats with CL_FILTER_LINEAR filtering\n" );
555     log_info( "\tCL_FILTER_NEAREST - Only tests formats with CL_FILTER_NEAREST filtering\n" );
556     log_info( "\n" );
557     log_info( "\tNORMALIZED - Only tests formats with NORMALIZED coordinates\n" );
558     log_info( "\tUNNORMALIZED - Only tests formats with UNNORMALIZED coordinates\n" );
559     log_info( "\n" );
560     log_info( "\tCL_ADDRESS_CLAMP - Only tests formats with CL_ADDRESS_CLAMP addressing\n" );
561     log_info( "\tCL_ADDRESS_CLAMP_TO_EDGE - Only tests formats with CL_ADDRESS_CLAMP_TO_EDGE addressing\n" );
562     log_info( "\tCL_ADDRESS_REPEAT - Only tests formats with CL_ADDRESS_REPEAT addressing\n" );
563     log_info( "\tCL_ADDRESS_MIRRORED_REPEAT - Only tests formats with CL_ADDRESS_MIRRORED_REPEAT addressing\n" );
564     log_info( "\n" );
565     log_info( "You may also use appropriate CL_ channel type and ordering constants.\n" );
566     log_info( "\n" );
567     log_info( "\tlocal_samplers - Use samplers declared in the kernel functions instead of passed in as arguments\n" );
568     log_info( "\n" );
569     log_info( "\tThe following specify to use the specific flag to allocate images to use in the tests:\n" );
570     log_info( "\t\tCL_MEM_COPY_HOST_PTR\n" );
571     log_info( "\t\tCL_MEM_USE_HOST_PTR (default)\n" );
572     log_info( "\t\tCL_MEM_ALLOC_HOST_PTR\n" );
573     log_info( "\t\tNO_HOST_PTR - Specifies to use none of the above flags\n" );
574     log_info( "\n" );
575     log_info( "\tThe following modify the types of images tested:\n" );
576     log_info( "\t\tsmall_images - Runs every format through a loop of widths 1-13 and heights 1-9, instead of random sizes\n" );
577     log_info( "\t\tmax_images - Runs every format through a set of size combinations with the max values, max values - 1, and max values / 128\n" );
578     log_info( "\t\trounding - Runs every format through a single image filled with every possible value for that image format, to verify rounding works properly\n" );
579     log_info( "\n" );
580     log_info( "\tno_offsets - Disables offsets when testing reads (can be good for diagnosing address repeating/clamping problems)\n" );
581     log_info( "\tdebug_trace - Enables additional debug info logging\n" );
582     log_info( "\textra_validate - Enables additional validation failure debug information\n" );
583     log_info( "\tuse_pitches - Enables row and slice pitches\n" );
584     log_info( "\ttest_mipmaps - Enables mipmapped images\n");
585     log_info( "\n" );
586     log_info( "Test names:\n" );
587     for( int i = 0; i < test_num; i++ )
588     {
589         log_info( "\t%s\n", test_list[i].name );
590     }
591 }
592