Closed mattkretz closed 7 years ago
Yes.
Off-topic:
Btw, I'm beginning to slightly warm up to the idea to have the "to_fixed" conversion as an implicit one, similar to the situation that the conversion of double
to the more general complex<double>
is implicit. It can produce non-portable code, though:
datapar<T,Abi> intpow(datapar<T,Abi> x, datapar<int, fixed<datapar<T,Abi>::size()>> n)
intpow(datapar<float>(2), datapar<int>(-2))
is fine on SSE2, but gives an error on AVX. And nobody says that float and int are the same size to start with.
You're making an important point. Now that I removed implicit conversions my math function signatures are problematic. E.g.
template <class Abi>
datapar<float, Abi> frexp(datapar<float, Abi> value,
datapar<int, abi_for_size_t<datapar<float, Abi>::size()>>* exp);
So this expects a native ABI for the int
parameter for SSE and AVX2, but with AVX the second argument has to be a fixed_size
ABI. This was easier to use before I restricted conversions between ABIs.
Both directions are conceivable. One user might work with:
using floatv = datapar<float>;
using intv = datapar<int, abi_for_size_t<floatv::size()>>;
The next with:
using floatv = datapar<float>;
using intv = datapar<int, fixed_size<floatv::size()>>;
Both should be supported scenarios. If "to_fixed" is implicit and math functions use fixed_size
instead of abi_for_size
in mixed signatures then we'd be much nicer to our users already. Even if there still is your counterargument.
It is impossible to make every unportable use ill-formed. We just need to optimize for the API that catches the majority of the unportable uses. In any case, the user who actually writes intpow(datapar<float>(2), datapar<int>(-2)
should be punished (best by making the code ill-formed). The user who uses abi_for_size
created a portable combination of datapar
types, but is indistinguishable from the former.
Conclusion? Don't know yet. Keep it conservative until we know better? But I think I need to modify the math signatures to use fixed_size
instead of abi_for_size
.
If we have an implicit conversion from datapar<T, Abi>
to datapar<T, fixed_size<N>>
, I think we support both of your user groups. Math functions should use fixed_size<N>
for secondary parameters, yes. (That was one of the main results of the SG1 discussion asking for fixed_size<N>
some years ago, I believe.) People using abi_for_size
already get different types on SSE vs. AVX and thus are non-portable on the type.
To make explicit conversions easier there could be the following three functions: