Alberto,
The AMDIL backend solves your problem with intrinsic overloading this way:
def int_AMDIL_mad : GCCBuiltin<"__amdil_mad">, TernaryIntFloat;
Where TernaryIntFloat is defined as:
class TernaryIntFloat :
Intrinsic<[llvm_anyfloat_ty], [LLVMMatchType<0>,
LLVMMatchType<0>, LLVMMatchType<0>], []>;
This allows us to write a multi-def for int_AMDIL_mad like so:
defm MAD : TernaryIntrinsicFloat<IL_OP_MAD, int_AMDIL_mad>;
Where TernaryIntrinsicFloat is defined as:
multiclass TernaryIntrinsicFloat<ILOpCode opcode, Intrinsic intr>
{
def _f32 : ThreeInOneOut<opcode, (outs GPRF32:$dst),
(ins GPRF32:$src, GPRF32:$src2, GPRF32:$src3),
!strconcat(opcode.Text, " $dst, $src, $src2, $src3"),
[(set GPRF32:$dst,
(intr GPRF32:$src, GPRF32:$src2, GPRF32:$src3))]>;
def _v2f32 : ThreeInOneOut<opcode, (outs GPRV2F32:$dst),
(ins GPRV2F32:$src, GPRV2F32:$src2, GPRV2F32:$src3),
!strconcat(opcode.Text, " $dst, $src, $src2, $src3"),
[(set GPRV2F32:$dst,
(intr GPRV2F32:$src, GPRV2F32:$src2, GPRV2F32:$src3))]>;
...
}
Now, this doesn't completely work, because LLVM does not allow overloading of intrinsics values, so there needs to be a little coding in *IntrinsicInfo class.
AMD always encodes builtin names as __amdil_mad_f32, __amdil_mad_v2f32, __amdil_mad_v4f32, etc....
So in the function "*IntrinsicInfo::lookup_name", when attempting to find out what intrinsic the function maps to, the AMDIL backend strips off the type, and then looks up for just '__amdil_mad'.
This is how you can do intrinsic overloading in LLVM.
Hope this helps,
Micah