Ext_vector_type and C++ overloading

I’m looking for feedback from any interested parties on how the ext_vector_type vectors and their implicit conversions from C and OpenCL C should interact with the implicit conversion mechanisms in C++. Particularly appreciate links to any documentation if it exists.

My background on this problem: I was tracking down an assertion failure when using some ext_vector_type operations in C++ code, and ran into a number of inconsistencies between how C and C++ handle operators involving ext_vector_type types. I started trying to solve these ad-hoc, but realized pretty quickly that I don’t fully understand the complexity of the overload system and implicit conversions, and these tie in deeply enough that they deserve proper handling.

The two related issues I’m working on:

From the OpenCL C spec, 6.4.1. Implicit Conversions:

Implicit conversions from a scalar type to a vector type are allowed. In this case, the scalar may be subject to the usual arithmetic conversion to the element type used by the vector. The scalar type is then widened to the vector.

This widening is handled in the Clang frontend for C by handling it when constructing built-in operators. In C++, for numeric types, operator overloading isn’t involved because neither type is user-defined, so it uses the same built-in operators as C. But as soon as you have an enum involved, there’s an inconsistency between the built-in operators and the overload sets: the built-in does the implicit integral conversion on the enum and then widens it to a vector, but there’s no appropriate operator overload for adding the vector and the enum, which is the cause of the assertion I was tracking down.

Adding in other implicit conversions makes this more complex: user-defined implicit conversions should probably be eligible for the same vector operations, but this also currently doesn’t work at all when these conversions interact with the implicit scalar → vector widening that C can rely on.

I couldn’t find any of these issues documented in the C++ for OpenCL document so I’m not sure what precedent is here. I’m wondering if this scalar → vector widening should be formalized and documented as being a numeric conversion included in the standard conversion sequence? Maybe that’s not appropriate and it should only have these implicit conversions when operators are concerned. How should this interact with user-defined implicit conversions?

I’m actually not sure what the current intention is for this. I can’t find where this extension is documented for Clang. Maybe this actually already works properly for functions outside the built-in operators, and I only need to fix things there. In that case, I still want to know what the intended formal behavior is to ensure consistency with that.

CC @AnastasiaStulova for OpenCL opinions.

I don’t believe such conversions are formalised outside of OpenCL. And in OpenCL so far it only went as far as the quote you provided in the OpenCL C spec i.e. it is some special conversion type.

As for C++ it seems to make sense to make this part of the standard conversion, maybe even numeric (not sure). This can be documented in Clang extension docs: Clang Language Extensions — Clang 17.0.0git documentation. I think there is a great value to clarify this area better for C/C++. The reason why it is inconsistent might be related to the fact that it was organically grown from OpenCL feature and hence it has not been properly documented outside of it.

1 Like