181600160SAnastasia Stulova// RUN: %clang_cc1 %s -cl-std=CL1.0 -verify -pedantic -fsyntax-only -triple spir-unknown-unknown 281600160SAnastasia Stulova// RUN: %clang_cc1 %s -cl-std=CL1.0 -verify -pedantic -fsyntax-only -triple spir-unknown-unknown -DFUNCPTREXT 381600160SAnastasia Stulova// RUN: %clang_cc1 %s -cl-std=CL1.0 -verify -pedantic -fsyntax-only -triple spir-unknown-unknown -DVARARGEXT 44fde2b6aSAnastasia Stulova 54fde2b6aSAnastasia Stulova#ifdef FUNCPTREXT 64fde2b6aSAnastasia Stulova#pragma OPENCL EXTENSION __cl_clang_function_pointers : enable 74fde2b6aSAnastasia Stulova#endif 80e874fc0SAnastasia Stulova#ifdef VARARGEXT 90e874fc0SAnastasia Stulova#pragma OPENCL EXTENSION __cl_clang_variadic_functions : enable 100e874fc0SAnastasia Stulova#endif 117c305333SAnastasia Stulova 127c305333SAnastasia Stulova// Variadic functions 130e874fc0SAnastasia Stulovavoid vararg_f(int, ...); 140e874fc0SAnastasia Stulova#ifndef VARARGEXT 150e874fc0SAnastasia Stulova// expected-error@-2 {{invalid prototype, variadic arguments are not allowed in OpenCL}} 164fde2b6aSAnastasia Stulova#endif 170e874fc0SAnastasia Stulovavoid __vararg_f(int, ...); 180e874fc0SAnastasia Stulovatypedef void (*vararg_fptr_t)(int, ...); 190e874fc0SAnastasia Stulova#ifndef VARARGEXT 200e874fc0SAnastasia Stulova// expected-error@-2 {{invalid prototype, variadic arguments are not allowed in OpenCL}} 210e874fc0SAnastasia Stulova#endif 220e874fc0SAnastasia Stulova#ifndef FUNCPTREXT 230e874fc0SAnastasia Stulova// expected-error@-5 {{pointers to functions are not allowed}} 240e874fc0SAnastasia Stulova#endif 250e874fc0SAnastasia Stulovaint printf(__constant const char *st, ...); 260e874fc0SAnastasia Stulova#ifndef VARARGEXT 270e874fc0SAnastasia Stulova// expected-error@-2 {{invalid prototype, variadic arguments are not allowed in OpenCL}} 280e874fc0SAnastasia Stulova#endif 297c305333SAnastasia Stulova 30037dbe95SAlexey Bader// Struct type with function pointer field 31037dbe95SAlexey Badertypedef struct s 32037dbe95SAlexey Bader{ 334fde2b6aSAnastasia Stulova void (*f)(struct s *self, int *i); 344fde2b6aSAnastasia Stulova#ifndef FUNCPTREXT 354fde2b6aSAnastasia Stulova// expected-error@-2 {{pointers to functions are not allowed}} 364fde2b6aSAnastasia Stulova#endif 37037dbe95SAlexey Bader} s_t; 38037dbe95SAlexey Bader 397c305333SAnastasia Stulova//Function pointer 407c305333SAnastasia Stulovavoid foo(void*); 41abbdb563SAnastasia Stulova#ifdef FUNCPTREXT 42abbdb563SAnastasia Stulova//expected-note@-2{{passing argument to parameter here}} 43abbdb563SAnastasia Stulova#endif 447c305333SAnastasia Stulova 451f277940SAlexey Bader// Expect no diagnostics for an empty parameter list. 46*4be105c9SAaron Ballmanvoid bar(); 471f277940SAlexey Bader 48*4be105c9SAaron Ballmanvoid bar() 497c305333SAnastasia Stulova{ 507c305333SAnastasia Stulova // declaring a function pointer is an error 514fde2b6aSAnastasia Stulova void (*fptr)(int); 524fde2b6aSAnastasia Stulova#ifndef FUNCPTREXT 534fde2b6aSAnastasia Stulova // expected-error@-2 {{pointers to functions are not allowed}} 544fde2b6aSAnastasia Stulova#endif 557c305333SAnastasia Stulova 567c305333SAnastasia Stulova // taking the address of a function is an error 57abbdb563SAnastasia Stulova foo((void*)foo); 58abbdb563SAnastasia Stulova#ifndef FUNCPTREXT 59abbdb563SAnastasia Stulova // expected-error@-2{{taking address of function is not allowed}} 60abbdb563SAnastasia Stulova#else 61abbdb563SAnastasia Stulova // FIXME: Functions should probably be in the address space defined by the 62abbdb563SAnastasia Stulova // implementation. It might make sense to put them into the Default address 63abbdb563SAnastasia Stulova // space that is bind to a physical segment by the target rather than fixing 64abbdb563SAnastasia Stulova // it to any of the concrete OpenCL address spaces during parsing. 65abbdb563SAnastasia Stulova // expected-error@-8{{casting 'void (*)(__private void *__private)' to type '__private void *' changes address space}} 66abbdb563SAnastasia Stulova#endif 677c305333SAnastasia Stulova 68abbdb563SAnastasia Stulova foo(&foo); 69abbdb563SAnastasia Stulova#ifndef FUNCPTREXT 70abbdb563SAnastasia Stulova // expected-error@-2{{taking address of function is not allowed}} 71abbdb563SAnastasia Stulova#else 72abbdb563SAnastasia Stulova // expected-error@-4{{passing 'void (*)(__private void *__private)' to parameter of type '__private void *' changes address space of pointer}} 73abbdb563SAnastasia Stulova#endif 74abbdb563SAnastasia Stulova 75abbdb563SAnastasia Stulova // FIXME: If we stop rejecting the line below a bug (PR49315) gets 76abbdb563SAnastasia Stulova // hit due to incorrectly handled pointer conversion. 77abbdb563SAnastasia Stulova#ifndef FUNCPTREXT 787c305333SAnastasia Stulova // initializing an array with the address of functions is an error 797c305333SAnastasia Stulova void* vptrarr[2] = {foo, &foo}; // expected-error{{taking address of function is not allowed}} expected-error{{taking address of function is not allowed}} 80abbdb563SAnastasia Stulova#endif 817c305333SAnastasia Stulova 827c305333SAnastasia Stulova // just calling a function is correct 837c305333SAnastasia Stulova foo(0); 847c305333SAnastasia Stulova} 85