Mandatory feature macros in OpenCL C 3.0?

In opencl-c-bash.h a number of feature macros are always defined when using SPIRV i.e.

// Define header-only feature macros for OpenCL C 3.0.
#if (__OPENCL_CPP_VERSION__ == 202100 || __OPENCL_C_VERSION__ == 300)
// For the SPIR and SPIR-V target all features are supported.
#if defined(__SPIR__) || defined(__SPIRV__)
#define __opencl_c_work_group_collective_functions 1
#define __opencl_c_atomic_order_seq_cst 1
#define __opencl_c_atomic_scope_device 1
#define __opencl_c_atomic_scope_all_devices 1
#define __opencl_c_read_write_images 1
#endif // defined(__SPIR__)
#endif // (__OPENCL_CPP_VERSION__ == 202100 || __OPENCL_C_VERSION__ == 300)

If these are optional feature macros, why are they always defined here?

For context I’m working on CLVK and CLSPV with the goal of running OpenCL C on Vulkan, the Vulkan Spec says that

Sequentially consistent atomics and barriers are not supported and SequentiallyConsistent is treated as AcquireRelease. SequentiallyConsistent should not be used.

So we won’t be able to report support for __opencl_c_atomic_order_sequentially consistent. There are also other feature macros we can’t support at this time.


@AnastasiaStulova, I believe you reviewed this code previously and you are acting as a code owner also so your opinion would be greatly value.

The SPIR/SPIR-V targets are sort of special as they don’t represent a concrete device, hence they are supposed to support all extensions and features.

It should be possible to disable optional features using the -cl-ext option; see the User Manual; but I’m actually not sure if that interacts well with the defines in opencl-c-base.h.

Correct, clang is still missing optionality for header based features/extensions. The main ideas are discussed in Support header based extensions in -cl-ext · Issue #55674 · llvm/llvm-project · GitHub but it hasn’t been worked on by anyone as far as I am aware.

PS if there are any better approaches we can also consider the alternatives…

Thanks for the reply, I will check out that flag and try to get it working with the project I’m working on.

I’m a little confused by the SPIR-V target supporting all extensions and features. I’m pretty sure there are a number of cases in the SPIR-V spec of features that should not be used in certain circumstances. For example, in the definition of SequentiallyConsistent from the SPIR-V spec it says:

All observers see this memory access in the same order with respect to other sequentially-consistent memory accesses from this invocation.
If the declared memory model is Vulkan, SequentiallyConsistent must not be used.

So how can the SPIR-V target support always support __opencl_c_atomic_order_seq_cst when it is forbidden in some cases?

If the declared memory model is Vulkan, SequentiallyConsistent must not be used.

When compiling OpenCL using mainline Clang, it will target the OpenCL memory model, not the Vulkan memory model. As far as I’m aware, all OpenCL features/extensions will have a counterpart in the OpenCL/kernel flavour of SPIR-V, hence the SPIR-V target supporting all features/extensions (of OpenCL).

I’m not involved in clspv development, but it’s possible you need to restrict the allowable OpenCL features there if there’s no suitable mapping to the Vulkan/shader flavour of SPIR-V. In fact, if there is a SPIR-V target in clspv, it’s probably not the same as clang’s SPIR-V target because they are targeting different SPIR-V flavours.

Thanks for all your help, I have figured out my issue and found a temporary solution.

I think you’re right that -cl-ext isn’t interacting well with opencl-c-base.h. The BaseSPIRTargetInfo enables all the options, and this is then overridden with the -cl-ext information here by setCommandLineOpenCLOpts in TargetInfo.h. opencl-c-base.h needs to be included after all this since it conditionally defines some values depending on the existence of feature macros, like here, so that is where my problem is coming from. Another problem is that OpenCLExtensions.def is missing some of the feature macros so they can’t be enabled by -cl-ext here.

I put up a PR - ⚙ D137652 Remove mandatory define of optional features macros for OpenCL C 3.0 - which should fix this. I would really appreciate a review; this could be my first contribution to the LLVM!