https://gcc.gnu.org/bugzilla/show_bug.cgi?id=89582
--- Comment #4 from Richard Biener <rguenth at gcc dot gnu.org> ---
Looks like LLVM has all the ABI details exposed very early but also in a very
awkward way(?). The vfloat one shows
define { <2 x float>, <2 x float> } @f(<2 x float> %x.coerce0, <2 x float>
%x.coerce1, <2 x float> %y.coerce0, <2 x float> %y.coerce1) #0 {
%1 = alloca %struct.vfloat, align 16
%x = alloca %struct.vfloat, align 16
%y = alloca %struct.vfloat, align 16
%2 = bitcast %struct.vfloat* %x to { <2 x float>, <2 x float> }*
%3 = getelementptr inbounds { <2 x float>, <2 x float> }, { <2 x float>, <2 x
float> }* %2, i32 0, i32 0
store <2 x float> %x.coerce0, <2 x float>* %3, align 16
%4 = getelementptr inbounds { <2 x float>, <2 x float> }, { <2 x float>, <2 x
float> }* %2, i32 0, i32 1
store <2 x float> %x.coerce1, <2 x float>* %4, align 8
%5 = bitcast %struct.vfloat* %y to { <2 x float>, <2 x float> }*
%6 = getelementptr inbounds { <2 x float>, <2 x float> }, { <2 x float>, <2 x
float> }* %5, i32 0, i32 0
store <2 x float> %y.coerce0, <2 x float>* %6, align 16
%7 = getelementptr inbounds { <2 x float>, <2 x float> }, { <2 x float>, <2 x
float> }* %5, i32 0, i32 1
store <2 x float> %y.coerce1, <2 x float>* %7, align 8
for the parameter setup (if I deciper the IL correctly) and
%32 = bitcast %struct.vfloat* %1 to { <2 x float>, <2 x float> }*
%33 = load { <2 x float>, <2 x float> }, { <2 x float>, <2 x float> }* %32,
align 16
ret { <2 x float>, <2 x float> } %33
for the return value.
I was thinking of a way to expose the ABI details to GIMPLE recently
but feared this would look a bit like a mess (also considering
prologue/epilogue expansion target constraints).