109467b48Spatrick//===-- VECallingConv.td - Calling Conventions VE ----------*- tablegen -*-===// 209467b48Spatrick// 309467b48Spatrick// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 409467b48Spatrick// See https://llvm.org/LICENSE.txt for license information. 509467b48Spatrick// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 609467b48Spatrick// 709467b48Spatrick//===----------------------------------------------------------------------===// 809467b48Spatrick// 909467b48Spatrick// This describes the calling conventions for the VE architectures. 1009467b48Spatrick// 1109467b48Spatrick//===----------------------------------------------------------------------===// 1209467b48Spatrick 1309467b48Spatrick//===----------------------------------------------------------------------===// 1409467b48Spatrick// Aurora VE 1509467b48Spatrick//===----------------------------------------------------------------------===// 16097a140dSpatrickdef CC_VE_C_Stack: CallingConv<[ 17*73471bf0Spatrick // F128 are assigned to the stack in 16-byte aligned units 18*73471bf0Spatrick CCIfType<[f128], CCAssignToStackWithShadow<16, 16, [SX7]>>, 19097a140dSpatrick 20097a140dSpatrick // All of the rest are assigned to the stack in 8-byte aligned units. 21097a140dSpatrick CCAssignToStack<0, 8> 22097a140dSpatrick]>; 23097a140dSpatrick 24*73471bf0Spatrick///// C Calling Convention (VE ABI v2.1) ///// 25*73471bf0Spatrick// 26*73471bf0Spatrick// Reference: https://www.nec.com/en/global/prod/hpc/aurora/document/VE-ABI_v2.1.pdf 27*73471bf0Spatrick// 28*73471bf0Spatrickdef CC_VE_C : CallingConv<[ 29097a140dSpatrick // All arguments get passed in generic registers if there is space. 30097a140dSpatrick 31*73471bf0Spatrick // Promote i1/i8/i16/i32 arguments to i64. 32*73471bf0Spatrick CCIfType<[i1, i8, i16, i32], CCPromoteToType<i64>>, 33097a140dSpatrick 34*73471bf0Spatrick // Convert float arguments to i64 with padding. 35*73471bf0Spatrick // 63 31 0 36*73471bf0Spatrick // +------+------+ 37*73471bf0Spatrick // | float| 0 | 38*73471bf0Spatrick // +------+------+ 39*73471bf0Spatrick CCIfType<[f32], CCBitConvertToType<i64>>, 40097a140dSpatrick 41*73471bf0Spatrick // bool, char, int, enum, long, long long, float, double 42*73471bf0Spatrick // --> generic 64 bit registers 43097a140dSpatrick CCIfType<[i64, f64], 44097a140dSpatrick CCAssignToReg<[SX0, SX1, SX2, SX3, SX4, SX5, SX6, SX7]>>, 45097a140dSpatrick 46*73471bf0Spatrick // long double --> pair of generic 64 bit registers 47*73471bf0Spatrick // 48*73471bf0Spatrick // NOTE: If Q1 is allocated while SX1 is free, llvm tries to allocate SX1 for 49*73471bf0Spatrick // following operands, this masks SX1 to avoid such behavior. 50*73471bf0Spatrick CCIfType<[f128], 51*73471bf0Spatrick CCAssignToRegWithShadow<[Q0, Q1, Q2, Q3], 52*73471bf0Spatrick [SX0, SX1, SX3, SX5]>>, 53*73471bf0Spatrick 54097a140dSpatrick // Alternatively, they are assigned to the stack in 8-byte aligned units. 55097a140dSpatrick CCDelegateTo<CC_VE_C_Stack> 56097a140dSpatrick]>; 57097a140dSpatrick 58*73471bf0Spatrick///// Standard vararg C Calling Convention (VE ABI v2.1) ///// 59097a140dSpatrick// All arguments get passed in stack for varargs function or non-prototyped 60097a140dSpatrick// function. 61097a140dSpatrickdef CC_VE2 : CallingConv<[ 62*73471bf0Spatrick // Promote i1/i8/i16/i32 arguments to i64. 63*73471bf0Spatrick CCIfType<[i1, i8, i16, i32], CCPromoteToType<i64>>, 64*73471bf0Spatrick 65*73471bf0Spatrick // Convert float arguments to i64 with padding. 66*73471bf0Spatrick // 63 31 0 67097a140dSpatrick // +------+------+ 68*73471bf0Spatrick // | float| 0 | 69097a140dSpatrick // +------+------+ 70*73471bf0Spatrick CCIfType<[f32], CCBitConvertToType<i64>>, 71*73471bf0Spatrick 72*73471bf0Spatrick // F128 are assigned to the stack in 16-byte aligned units 73*73471bf0Spatrick CCIfType<[f128], CCAssignToStack<16, 16>>, 74097a140dSpatrick 75097a140dSpatrick CCAssignToStack<0, 8> 76097a140dSpatrick]>; 77097a140dSpatrick 78*73471bf0Spatrickdef RetCC_VE_C : CallingConv<[ 79*73471bf0Spatrick // Promote i1/i8/i16/i32 return values to i64. 80*73471bf0Spatrick CCIfType<[i1, i8, i16, i32], CCPromoteToType<i64>>, 81097a140dSpatrick 82*73471bf0Spatrick // Convert float return values to i64 with padding. 83*73471bf0Spatrick // 63 31 0 84*73471bf0Spatrick // +------+------+ 85*73471bf0Spatrick // | float| 0 | 86*73471bf0Spatrick // +------+------+ 87*73471bf0Spatrick CCIfType<[f32], CCBitConvertToType<i64>>, 88097a140dSpatrick 89*73471bf0Spatrick // bool, char, int, enum, long, long long, float, double 90*73471bf0Spatrick // --> generic 64 bit registers 91097a140dSpatrick CCIfType<[i64, f64], 92097a140dSpatrick CCAssignToReg<[SX0, SX1, SX2, SX3, SX4, SX5, SX6, SX7]>>, 93*73471bf0Spatrick 94*73471bf0Spatrick // long double --> pair of generic 64 bit registers 95*73471bf0Spatrick CCIfType<[f128], 96*73471bf0Spatrick CCAssignToRegWithShadow<[Q0, Q1, Q2, Q3], 97*73471bf0Spatrick [SX0, SX1, SX3, SX5]>>, 98*73471bf0Spatrick]>; 99*73471bf0Spatrick 100*73471bf0Spatrick///// Custom fastcc ///// 101*73471bf0Spatrick// 102*73471bf0Spatrick// This passes vector params and return values in registers. Scalar values are 103*73471bf0Spatrick// handled conforming to the standard cc. 104*73471bf0Spatrickdef CC_VE_Fast : CallingConv<[ 105*73471bf0Spatrick // vector --> generic vector registers 106*73471bf0Spatrick CCIfType<[v256i32, v256f32, v256i64, v256f64], 107*73471bf0Spatrick CCAssignToReg<[V0, V1, V2, V3, V4, V5, V6, V7]>>, 108*73471bf0Spatrick // TODO: make this conditional on packed mode 109*73471bf0Spatrick CCIfType<[v512i32, v512f32], 110*73471bf0Spatrick CCAssignToReg<[V0, V1, V2, V3, V4, V5, V6, V7]>>, 111*73471bf0Spatrick 112*73471bf0Spatrick // vector mask --> generic vector mask registers 113*73471bf0Spatrick CCIfType<[v256i1], 114*73471bf0Spatrick CCAssignToReg<[VM1, VM2, VM3, VM4, VM5, VM6, VM7]>>, 115*73471bf0Spatrick 116*73471bf0Spatrick // pair of vector mask --> generic vector mask registers 117*73471bf0Spatrick CCIfType<[v512i1], 118*73471bf0Spatrick CCAssignToRegWithShadow<[VMP1, VMP2, VMP3], 119*73471bf0Spatrick [VM1, VM3, VM5]>>, 120*73471bf0Spatrick 121*73471bf0Spatrick // Follow the standard C CC for scalars. 122*73471bf0Spatrick CCDelegateTo<CC_VE_C> 123*73471bf0Spatrick]>; 124*73471bf0Spatrick 125*73471bf0Spatrickdef RetCC_VE_Fast : CallingConv<[ 126*73471bf0Spatrick // vector --> generic vector registers 127*73471bf0Spatrick CCIfType<[v256i32, v256f32, v256i64, v256f64], 128*73471bf0Spatrick CCAssignToReg<[V0, V1, V2, V3, V4, V5, V6, V7]>>, 129*73471bf0Spatrick // TODO: make this conditional on packed mode 130*73471bf0Spatrick CCIfType<[v512i32, v512f32], 131*73471bf0Spatrick CCAssignToReg<[V0, V1, V2, V3, V4, V5, V6, V7]>>, 132*73471bf0Spatrick 133*73471bf0Spatrick // vector mask --> generic vector mask registers 134*73471bf0Spatrick CCIfType<[v256i1], 135*73471bf0Spatrick CCAssignToReg<[VM1, VM2, VM3, VM4, VM5, VM6, VM7]>>, 136*73471bf0Spatrick 137*73471bf0Spatrick // pair of vector mask --> generic vector mask registers 138*73471bf0Spatrick CCIfType<[v512i1], 139*73471bf0Spatrick CCAssignToRegWithShadow<[VMP1, VMP2, VMP3], 140*73471bf0Spatrick [VM1, VM3, VM5]>>, 141*73471bf0Spatrick 142*73471bf0Spatrick // Follow the standard C CC for scalars. 143*73471bf0Spatrick CCDelegateTo<RetCC_VE_C> 144097a140dSpatrick]>; 14509467b48Spatrick 14609467b48Spatrick// Callee-saved registers 14709467b48Spatrickdef CSR : CalleeSavedRegs<(add (sequence "SX%u", 18, 33))>; 14809467b48Spatrickdef CSR_NoRegs : CalleeSavedRegs<(add)>; 149097a140dSpatrick 150097a140dSpatrick// PreserveAll (clobbers s62,s63) - used for ve_grow_stack 151*73471bf0Spatrickdef CSR_preserve_all : CalleeSavedRegs<(add (sequence "SX%u", 0, 61), 152*73471bf0Spatrick (sequence "V%u", 0, 63), 153*73471bf0Spatrick (sequence "VM%u", 1, 15))>; 154