Skip to content

Commit f0904a6

Browse files
committed
[PowePC][AIX] Handle variadic vector call operands.
Patch adds support for passing vector call operands to variadic functions. Arguments which are fixed shadow GPRs and stack space even when they are passed in vector registers, while arguments passed through ellipses are passed in properly aligned GPRs if available and on the stack once all GPR arguments registers are consumed. Differential Revision: https://reviews.llvm.org/D97956
1 parent 8a00386 commit f0904a6

File tree

4 files changed

+306
-3
lines changed

4 files changed

+306
-3
lines changed

llvm/lib/Target/PowerPC/PPCISelLowering.cpp

Lines changed: 46 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7079,6 +7079,52 @@ SDValue PPCTargetLowering::LowerCall_AIX(
70797079
continue;
70807080
}
70817081

7082+
// Vector arguments passed to VarArg functions need custom handling when
7083+
// they are passed (at least partially) in GPRs.
7084+
if (VA.isMemLoc() && VA.needsCustom() && ValVT.isVector()) {
7085+
assert(CFlags.IsVarArg && "Custom MemLocs only used for Vector args.");
7086+
// Store value to its stack slot.
7087+
SDValue PtrOff =
7088+
DAG.getConstant(VA.getLocMemOffset(), dl, StackPtr.getValueType());
7089+
PtrOff = DAG.getNode(ISD::ADD, dl, PtrVT, StackPtr, PtrOff);
7090+
SDValue Store =
7091+
DAG.getStore(Chain, dl, Arg, PtrOff, MachinePointerInfo());
7092+
MemOpChains.push_back(Store);
7093+
const unsigned OriginalValNo = VA.getValNo();
7094+
// Then load the GPRs from the stack
7095+
unsigned LoadOffset = 0;
7096+
auto HandleCustomVecRegLoc = [&]() {
7097+
assert(I != E && "Unexpected end of CCvalAssigns.");
7098+
assert(ArgLocs[I].isRegLoc() && ArgLocs[I].needsCustom() &&
7099+
"Expected custom RegLoc.");
7100+
CCValAssign RegVA = ArgLocs[I++];
7101+
assert(RegVA.getValNo() == OriginalValNo &&
7102+
"Custom MemLoc ValNo and custom RegLoc ValNo must match.");
7103+
SDValue Add = DAG.getNode(ISD::ADD, dl, PtrVT, PtrOff,
7104+
DAG.getConstant(LoadOffset, dl, PtrVT));
7105+
SDValue Load = DAG.getLoad(PtrVT, dl, Store, Add, MachinePointerInfo());
7106+
MemOpChains.push_back(Load.getValue(1));
7107+
RegsToPass.push_back(std::make_pair(RegVA.getLocReg(), Load));
7108+
LoadOffset += PtrByteSize;
7109+
};
7110+
7111+
// In 64-bit there will be exactly 2 custom RegLocs that follow, and in
7112+
// in 32-bit there will be 2 custom RegLocs if we are passing in R9 and
7113+
// R10.
7114+
HandleCustomVecRegLoc();
7115+
HandleCustomVecRegLoc();
7116+
7117+
if (I != E && ArgLocs[I].isRegLoc() && ArgLocs[I].needsCustom() &&
7118+
ArgLocs[I].getValNo() == OriginalValNo) {
7119+
assert(!IsPPC64 &&
7120+
"Only 2 custom RegLocs expected for 64-bit codegen.");
7121+
HandleCustomVecRegLoc();
7122+
HandleCustomVecRegLoc();
7123+
}
7124+
7125+
continue;
7126+
}
7127+
70827128
if (VA.isMemLoc()) {
70837129
SDValue PtrOff =
70847130
DAG.getConstant(VA.getLocMemOffset(), dl, StackPtr.getValueType());
Lines changed: 133 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,133 @@
1+
; NOTE: Assertions have been autogenerated by utils/update_mir_test_checks.py
2+
; RUN: llc -verify-machineinstrs -stop-before=ppc-vsx-copy -vec-extabi \
3+
; RUN: -mcpu=pwr7 -mtriple powerpc-ibm-aix-xcoff < %s | \
4+
; RUN: FileCheck --check-prefix=32BIT %s
5+
6+
; RUN: llc -verify-machineinstrs -stop-before=ppc-vsx-copy -vec-extabi \
7+
; RUN: -mcpu=pwr7 -mtriple powerpc64-ibm-aix-xcoff < %s | \
8+
; RUN: FileCheck --check-prefix=64BIT %s
9+
10+
define <4 x i32> @caller() {
11+
; 32BIT-LABEL: name: caller
12+
; 32BIT: bb.0.entry:
13+
; 32BIT: ADJCALLSTACKDOWN 176, 0, implicit-def dead $r1, implicit $r1
14+
; 32BIT: [[LWZtoc:%[0-9]+]]:gprc = LWZtoc %const.0, $r2 :: (load 4 from got)
15+
; 32BIT: [[LXVW4X:%[0-9]+]]:vsrc = LXVW4X $zero, killed [[LWZtoc]] :: (load 16 from constant-pool)
16+
; 32BIT: [[LI:%[0-9]+]]:gprc = LI 48
17+
; 32BIT: STXVW4X killed [[LXVW4X]], $r1, killed [[LI]] :: (store 16)
18+
; 32BIT: [[LWZtoc1:%[0-9]+]]:gprc = LWZtoc %const.1, $r2 :: (load 4 from got)
19+
; 32BIT: [[LXVW4X1:%[0-9]+]]:vsrc = LXVW4X $zero, killed [[LWZtoc1]] :: (load 16 from constant-pool)
20+
; 32BIT: [[LI1:%[0-9]+]]:gprc = LI 32
21+
; 32BIT: STXVW4X killed [[LXVW4X1]], $r1, killed [[LI1]] :: (store 16)
22+
; 32BIT: [[LWZtoc2:%[0-9]+]]:gprc = LWZtoc %const.2, $r2 :: (load 4 from got)
23+
; 32BIT: [[LXVW4X2:%[0-9]+]]:vsrc = LXVW4X $zero, killed [[LWZtoc2]] :: (load 16 from constant-pool)
24+
; 32BIT: [[LI2:%[0-9]+]]:gprc = LI 160
25+
; 32BIT: STXVW4X killed [[LXVW4X2]], $r1, killed [[LI2]] :: (store 16)
26+
; 32BIT: [[LWZtoc3:%[0-9]+]]:gprc = LWZtoc %const.3, $r2 :: (load 4 from got)
27+
; 32BIT: [[LXVW4X3:%[0-9]+]]:vsrc = LXVW4X $zero, killed [[LWZtoc3]] :: (load 16 from constant-pool)
28+
; 32BIT: [[LI3:%[0-9]+]]:gprc = LI 144
29+
; 32BIT: STXVW4X killed [[LXVW4X3]], $r1, killed [[LI3]] :: (store 16)
30+
; 32BIT: [[LWZtoc4:%[0-9]+]]:gprc = LWZtoc %const.4, $r2 :: (load 4 from got)
31+
; 32BIT: [[LXVW4X4:%[0-9]+]]:vsrc = LXVW4X $zero, killed [[LWZtoc4]] :: (load 16 from constant-pool)
32+
; 32BIT: [[LI4:%[0-9]+]]:gprc = LI 128
33+
; 32BIT: STXVW4X killed [[LXVW4X4]], $r1, killed [[LI4]] :: (store 16)
34+
; 32BIT: [[LWZtoc5:%[0-9]+]]:gprc = LWZtoc %const.5, $r2 :: (load 4 from got)
35+
; 32BIT: [[LXVW4X5:%[0-9]+]]:vsrc = LXVW4X $zero, killed [[LWZtoc5]] :: (load 16 from constant-pool)
36+
; 32BIT: [[LI5:%[0-9]+]]:gprc = LI 112
37+
; 32BIT: STXVW4X killed [[LXVW4X5]], $r1, killed [[LI5]] :: (store 16)
38+
; 32BIT: [[LWZtoc6:%[0-9]+]]:gprc = LWZtoc %const.6, $r2 :: (load 4 from got)
39+
; 32BIT: [[LXVW4X6:%[0-9]+]]:vsrc = LXVW4X $zero, killed [[LWZtoc6]] :: (load 16 from constant-pool)
40+
; 32BIT: [[LI6:%[0-9]+]]:gprc = LI 96
41+
; 32BIT: STXVW4X killed [[LXVW4X6]], $r1, killed [[LI6]] :: (store 16)
42+
; 32BIT: [[LWZtoc7:%[0-9]+]]:gprc = LWZtoc %const.7, $r2 :: (load 4 from got)
43+
; 32BIT: [[LXVW4X7:%[0-9]+]]:vsrc = LXVW4X $zero, killed [[LWZtoc7]] :: (load 16 from constant-pool)
44+
; 32BIT: [[LI7:%[0-9]+]]:gprc = LI 80
45+
; 32BIT: STXVW4X killed [[LXVW4X7]], $r1, killed [[LI7]] :: (store 16)
46+
; 32BIT: [[LWZtoc8:%[0-9]+]]:gprc = LWZtoc %const.8, $r2 :: (load 4 from got)
47+
; 32BIT: [[LXVW4X8:%[0-9]+]]:vsrc = LXVW4X $zero, killed [[LWZtoc8]] :: (load 16 from constant-pool)
48+
; 32BIT: [[LI8:%[0-9]+]]:gprc = LI 64
49+
; 32BIT: STXVW4X killed [[LXVW4X8]], $r1, killed [[LI8]] :: (store 16)
50+
; 32BIT: [[LWZ:%[0-9]+]]:gprc = LWZ 52, $r1 :: (load 4)
51+
; 32BIT: [[LWZ1:%[0-9]+]]:gprc = LWZ 48, $r1 :: (load 4)
52+
; 32BIT: [[LWZ2:%[0-9]+]]:gprc = LWZ 44, $r1 :: (load 4)
53+
; 32BIT: [[LWZ3:%[0-9]+]]:gprc = LWZ 40, $r1 :: (load 4)
54+
; 32BIT: [[LWZ4:%[0-9]+]]:gprc = LWZ 36, $r1 :: (load 4)
55+
; 32BIT: [[LWZ5:%[0-9]+]]:gprc = LWZ 32, $r1 :: (load 4)
56+
; 32BIT: [[LI9:%[0-9]+]]:gprc = LI 9
57+
; 32BIT: $r3 = COPY [[LI9]]
58+
; 32BIT: $r5 = COPY [[LWZ5]]
59+
; 32BIT: $r6 = COPY [[LWZ4]]
60+
; 32BIT: $r7 = COPY [[LWZ3]]
61+
; 32BIT: $r8 = COPY [[LWZ2]]
62+
; 32BIT: $r9 = COPY [[LWZ1]]
63+
; 32BIT: $r10 = COPY [[LWZ]]
64+
; 32BIT: BL_NOP <mcsymbol .callee[PR]>, csr_aix32_altivec, implicit-def dead $lr, implicit $rm, implicit $r3, implicit $r5, implicit $r6, implicit $r7, implicit $r8, implicit $r9, implicit $r10, implicit $r2, implicit-def $r1, implicit-def $v2
65+
; 32BIT: ADJCALLSTACKUP 176, 0, implicit-def dead $r1, implicit $r1
66+
; 32BIT: [[COPY:%[0-9]+]]:vsrc = COPY $v2
67+
; 32BIT: $v2 = COPY [[COPY]]
68+
; 32BIT: BLR implicit $lr, implicit $rm, implicit $v2
69+
70+
; 64BIT-LABEL: name: caller
71+
; 64BIT: bb.0.entry:
72+
; 64BIT: ADJCALLSTACKDOWN 208, 0, implicit-def dead $r1, implicit $r1
73+
; 64BIT: [[LDtocCPT:%[0-9]+]]:g8rc = LDtocCPT %const.0, $x2 :: (load 8 from got)
74+
; 64BIT: [[LXVW4X:%[0-9]+]]:vsrc = LXVW4X $zero8, killed [[LDtocCPT]] :: (load 16 from constant-pool)
75+
; 64BIT: [[LI8_:%[0-9]+]]:g8rc = LI8 96
76+
; 64BIT: STXVW4X killed [[LXVW4X]], $x1, killed [[LI8_]] :: (store 16)
77+
; 64BIT: [[LDtocCPT1:%[0-9]+]]:g8rc = LDtocCPT %const.1, $x2 :: (load 8 from got)
78+
; 64BIT: [[LXVW4X1:%[0-9]+]]:vsrc = LXVW4X $zero8, killed [[LDtocCPT1]] :: (load 16 from constant-pool)
79+
; 64BIT: [[LI8_1:%[0-9]+]]:g8rc = LI8 80
80+
; 64BIT: STXVW4X killed [[LXVW4X1]], $x1, killed [[LI8_1]] :: (store 16)
81+
; 64BIT: [[LDtocCPT2:%[0-9]+]]:g8rc = LDtocCPT %const.2, $x2 :: (load 8 from got)
82+
; 64BIT: [[LXVW4X2:%[0-9]+]]:vsrc = LXVW4X $zero8, killed [[LDtocCPT2]] :: (load 16 from constant-pool)
83+
; 64BIT: [[LI8_2:%[0-9]+]]:g8rc = LI8 64
84+
; 64BIT: STXVW4X killed [[LXVW4X2]], $x1, killed [[LI8_2]] :: (store 16)
85+
; 64BIT: [[LDtocCPT3:%[0-9]+]]:g8rc = LDtocCPT %const.3, $x2 :: (load 8 from got)
86+
; 64BIT: [[LXVW4X3:%[0-9]+]]:vsrc = LXVW4X $zero8, killed [[LDtocCPT3]] :: (load 16 from constant-pool)
87+
; 64BIT: [[LI8_3:%[0-9]+]]:g8rc = LI8 192
88+
; 64BIT: STXVW4X killed [[LXVW4X3]], $x1, killed [[LI8_3]] :: (store 16)
89+
; 64BIT: [[LDtocCPT4:%[0-9]+]]:g8rc = LDtocCPT %const.4, $x2 :: (load 8 from got)
90+
; 64BIT: [[LXVW4X4:%[0-9]+]]:vsrc = LXVW4X $zero8, killed [[LDtocCPT4]] :: (load 16 from constant-pool)
91+
; 64BIT: [[LI8_4:%[0-9]+]]:g8rc = LI8 176
92+
; 64BIT: STXVW4X killed [[LXVW4X4]], $x1, killed [[LI8_4]] :: (store 16)
93+
; 64BIT: [[LDtocCPT5:%[0-9]+]]:g8rc = LDtocCPT %const.5, $x2 :: (load 8 from got)
94+
; 64BIT: [[LXVW4X5:%[0-9]+]]:vsrc = LXVW4X $zero8, killed [[LDtocCPT5]] :: (load 16 from constant-pool)
95+
; 64BIT: [[LI8_5:%[0-9]+]]:g8rc = LI8 160
96+
; 64BIT: STXVW4X killed [[LXVW4X5]], $x1, killed [[LI8_5]] :: (store 16)
97+
; 64BIT: [[LDtocCPT6:%[0-9]+]]:g8rc = LDtocCPT %const.6, $x2 :: (load 8 from got)
98+
; 64BIT: [[LXVW4X6:%[0-9]+]]:vsrc = LXVW4X $zero8, killed [[LDtocCPT6]] :: (load 16 from constant-pool)
99+
; 64BIT: [[LI8_6:%[0-9]+]]:g8rc = LI8 144
100+
; 64BIT: STXVW4X killed [[LXVW4X6]], $x1, killed [[LI8_6]] :: (store 16)
101+
; 64BIT: [[LDtocCPT7:%[0-9]+]]:g8rc = LDtocCPT %const.7, $x2 :: (load 8 from got)
102+
; 64BIT: [[LXVW4X7:%[0-9]+]]:vsrc = LXVW4X $zero8, killed [[LDtocCPT7]] :: (load 16 from constant-pool)
103+
; 64BIT: [[LI8_7:%[0-9]+]]:g8rc = LI8 128
104+
; 64BIT: STXVW4X killed [[LXVW4X7]], $x1, killed [[LI8_7]] :: (store 16)
105+
; 64BIT: [[LDtocCPT8:%[0-9]+]]:g8rc = LDtocCPT %const.8, $x2 :: (load 8 from got)
106+
; 64BIT: [[LXVW4X8:%[0-9]+]]:vsrc = LXVW4X $zero8, killed [[LDtocCPT8]] :: (load 16 from constant-pool)
107+
; 64BIT: [[LI8_8:%[0-9]+]]:g8rc = LI8 112
108+
; 64BIT: STXVW4X killed [[LXVW4X8]], $x1, killed [[LI8_8]] :: (store 16)
109+
; 64BIT: [[LD:%[0-9]+]]:g8rc = LD 104, $x1 :: (load 8)
110+
; 64BIT: [[LD1:%[0-9]+]]:g8rc = LD 96, $x1 :: (load 8)
111+
; 64BIT: [[LD2:%[0-9]+]]:g8rc = LD 88, $x1 :: (load 8)
112+
; 64BIT: [[LD3:%[0-9]+]]:g8rc = LD 80, $x1 :: (load 8)
113+
; 64BIT: [[LD4:%[0-9]+]]:g8rc = LD 72, $x1 :: (load 8)
114+
; 64BIT: [[LD5:%[0-9]+]]:g8rc = LD 64, $x1 :: (load 8)
115+
; 64BIT: [[LI8_9:%[0-9]+]]:g8rc = LI8 9
116+
; 64BIT: $x3 = COPY [[LI8_9]]
117+
; 64BIT: $x5 = COPY [[LD5]]
118+
; 64BIT: $x6 = COPY [[LD4]]
119+
; 64BIT: $x7 = COPY [[LD3]]
120+
; 64BIT: $x8 = COPY [[LD2]]
121+
; 64BIT: $x9 = COPY [[LD1]]
122+
; 64BIT: $x10 = COPY [[LD]]
123+
; 64BIT: BL8_NOP <mcsymbol .callee[PR]>, csr_ppc64_altivec, implicit-def dead $lr8, implicit $rm, implicit $x3, implicit $x5, implicit $x6, implicit $x7, implicit $x8, implicit $x9, implicit $x10, implicit $x2, implicit-def $r1, implicit-def $v2
124+
; 64BIT: ADJCALLSTACKUP 208, 0, implicit-def dead $r1, implicit $r1
125+
; 64BIT: [[COPY:%[0-9]+]]:vsrc = COPY $v2
126+
; 64BIT: $v2 = COPY [[COPY]]
127+
; 64BIT: BLR8 implicit $lr8, implicit $rm, implicit $v2
128+
entry:
129+
%call = tail call <4 x i32> (i32, ...) @callee(i32 9, <4 x i32> <i32 0, i32 1, i32 2, i32 3>, <4 x i32> <i32 4, i32 5, i32 6, i32 7>, <4 x i32> <i32 8, i32 9, i32 10, i32 11>, <4 x i32> <i32 12, i32 13, i32 14, i32 15>, <4 x i32> <i32 16, i32 17, i32 18, i32 19>, <4 x i32> <i32 20, i32 21, i32 22, i32 23>, <4 x i32> <i32 24, i32 25, i32 26, i32 27>, <4 x i32> <i32 28, i32 29, i32 30, i32 31>, <4 x i32> <i32 32, i32 33, i32 34, i32 35>)
130+
ret <4 x i32> %call
131+
}
132+
133+
declare <4 x i32> @callee(i32, ...)
Lines changed: 90 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,90 @@
1+
; NOTE: Assertions have been autogenerated by utils/update_mir_test_checks.py
2+
; RUN: llc -verify-machineinstrs -stop-before=ppc-vsx-copy -vec-extabi \
3+
; RUN: -mcpu=pwr7 -mtriple powerpc-ibm-aix-xcoff < %s | \
4+
; RUN: FileCheck --check-prefix=32BIT %s
5+
6+
; RUN: llc -verify-machineinstrs -stop-before=ppc-vsx-copy -vec-extabi \
7+
; RUN: -mcpu=pwr7 -mtriple powerpc64-ibm-aix-xcoff < %s | \
8+
; RUN: FileCheck --check-prefix=64BIT %s
9+
10+
define void @caller() {
11+
; 32BIT-LABEL: name: caller
12+
; 32BIT: bb.0.entry:
13+
; 32BIT: ADJCALLSTACKDOWN 88, 0, implicit-def dead $r1, implicit $r1
14+
; 32BIT: [[LWZtoc:%[0-9]+]]:gprc = LWZtoc %const.0, $r2 :: (load 4 from got)
15+
; 32BIT: [[LXVW4X:%[0-9]+]]:vsrc = LXVW4X $zero, killed [[LWZtoc]] :: (load 16 from constant-pool)
16+
; 32BIT: [[LI:%[0-9]+]]:gprc = LI 64
17+
; 32BIT: STXVW4X killed [[LXVW4X]], $r1, killed [[LI]] :: (store 16)
18+
; 32BIT: [[LIS:%[0-9]+]]:gprc = LIS 38314
19+
; 32BIT: [[ORI:%[0-9]+]]:gprc = ORI killed [[LIS]], 63376
20+
; 32BIT: STW killed [[ORI]], 84, $r1 :: (store 4 into undef + 4, basealign 8)
21+
; 32BIT: [[LIS1:%[0-9]+]]:gprc = LIS 16389
22+
; 32BIT: [[ORI1:%[0-9]+]]:gprc = ORI killed [[LIS1]], 48905
23+
; 32BIT: STW killed [[ORI1]], 80, $r1 :: (store 4, align 8)
24+
; 32BIT: [[LWZtoc1:%[0-9]+]]:gprc = LWZtoc %const.1, $r2 :: (load 4 from got)
25+
; 32BIT: [[LXVW4X1:%[0-9]+]]:vsrc = LXVW4X $zero, killed [[LWZtoc1]] :: (load 16 from constant-pool)
26+
; 32BIT: [[LWZtoc2:%[0-9]+]]:gprc = LWZtoc %const.2, $r2 :: (load 4 from got)
27+
; 32BIT: [[XFLOADf64_:%[0-9]+]]:vsfrc = XFLOADf64 $zero, killed [[LWZtoc2]] :: (load 8 from constant-pool)
28+
; 32BIT: [[LIS2:%[0-9]+]]:gprc = LIS 16393
29+
; 32BIT: [[ORI2:%[0-9]+]]:gprc = ORI killed [[LIS2]], 8697
30+
; 32BIT: [[LIS3:%[0-9]+]]:gprc = LIS 61467
31+
; 32BIT: [[ORI3:%[0-9]+]]:gprc = ORI killed [[LIS3]], 34414
32+
; 32BIT: [[LWZtoc3:%[0-9]+]]:gprc = LWZtoc %const.3, $r2 :: (load 4 from got)
33+
; 32BIT: [[XFLOADf64_1:%[0-9]+]]:vsfrc = XFLOADf64 $zero, killed [[LWZtoc3]] :: (load 8 from constant-pool)
34+
; 32BIT: [[LI1:%[0-9]+]]:gprc = LI 55
35+
; 32BIT: $r3 = COPY [[LI1]]
36+
; 32BIT: $v2 = COPY [[LXVW4X1]]
37+
; 32BIT: $f1 = COPY [[XFLOADf64_]]
38+
; 32BIT: $r9 = COPY [[ORI2]]
39+
; 32BIT: $r10 = COPY [[ORI3]]
40+
; 32BIT: $f2 = COPY [[XFLOADf64_1]]
41+
; 32BIT: BL_NOP <mcsymbol .callee[PR]>, csr_aix32_altivec, implicit-def dead $lr, implicit $rm, implicit $r3, implicit $v2, implicit $f1, implicit $r9, implicit $r10, implicit $f2, implicit $r2, implicit-def $r1, implicit-def $v2
42+
; 32BIT: ADJCALLSTACKUP 88, 0, implicit-def dead $r1, implicit $r1
43+
; 32BIT: [[COPY:%[0-9]+]]:vsrc = COPY $v2
44+
; 32BIT: BLR implicit $lr, implicit $rm
45+
46+
; 64BIT-LABEL: name: caller
47+
; 64BIT: bb.0.entry:
48+
; 64BIT: ADJCALLSTACKDOWN 120, 0, implicit-def dead $r1, implicit $r1
49+
; 64BIT: [[LDtocCPT:%[0-9]+]]:g8rc = LDtocCPT %const.0, $x2 :: (load 8 from got)
50+
; 64BIT: [[LXVW4X:%[0-9]+]]:vsrc = LXVW4X $zero8, killed [[LDtocCPT]] :: (load 16 from constant-pool)
51+
; 64BIT: [[LI8_:%[0-9]+]]:g8rc = LI8 96
52+
; 64BIT: STXVW4X killed [[LXVW4X]], $x1, killed [[LI8_]] :: (store 16)
53+
; 64BIT: [[LIS8_:%[0-9]+]]:g8rc = LIS8 16389
54+
; 64BIT: [[ORI8_:%[0-9]+]]:g8rc = ORI8 killed [[LIS8_]], 48905
55+
; 64BIT: [[RLDIC:%[0-9]+]]:g8rc = RLDIC killed [[ORI8_]], 32, 1
56+
; 64BIT: [[ORIS8_:%[0-9]+]]:g8rc = ORIS8 killed [[RLDIC]], 38314
57+
; 64BIT: [[ORI8_1:%[0-9]+]]:g8rc = ORI8 killed [[ORIS8_]], 63376
58+
; 64BIT: STD killed [[ORI8_1]], 112, $x1 :: (store 8)
59+
; 64BIT: [[LDtocCPT1:%[0-9]+]]:g8rc = LDtocCPT %const.1, $x2 :: (load 8 from got)
60+
; 64BIT: [[LXVW4X1:%[0-9]+]]:vsrc = LXVW4X $zero8, killed [[LDtocCPT1]] :: (load 16 from constant-pool)
61+
; 64BIT: [[LD:%[0-9]+]]:g8rc = LD 104, $x1 :: (load 8)
62+
; 64BIT: [[LD1:%[0-9]+]]:g8rc = LD 96, $x1 :: (load 8)
63+
; 64BIT: [[LDtocCPT2:%[0-9]+]]:g8rc = LDtocCPT %const.2, $x2 :: (load 8 from got)
64+
; 64BIT: [[XFLOADf64_:%[0-9]+]]:vsfrc = XFLOADf64 $zero8, killed [[LDtocCPT2]] :: (load 8 from constant-pool)
65+
; 64BIT: [[LDtocCPT3:%[0-9]+]]:g8rc = LDtocCPT %const.3, $x2 :: (load 8 from got)
66+
; 64BIT: [[XFLOADf64_1:%[0-9]+]]:vsfrc = XFLOADf64 $zero8, killed [[LDtocCPT3]] :: (load 8 from constant-pool)
67+
; 64BIT: [[LIS8_1:%[0-9]+]]:g8rc = LIS8 16393
68+
; 64BIT: [[ORI8_2:%[0-9]+]]:g8rc = ORI8 killed [[LIS8_1]], 8697
69+
; 64BIT: [[RLDIC1:%[0-9]+]]:g8rc = RLDIC killed [[ORI8_2]], 32, 1
70+
; 64BIT: [[ORIS8_1:%[0-9]+]]:g8rc = ORIS8 killed [[RLDIC1]], 61467
71+
; 64BIT: [[ORI8_3:%[0-9]+]]:g8rc = ORI8 killed [[ORIS8_1]], 34414
72+
; 64BIT: [[LI8_1:%[0-9]+]]:g8rc = LI8 55
73+
; 64BIT: $x3 = COPY [[LI8_1]]
74+
; 64BIT: $v2 = COPY [[LXVW4X1]]
75+
; 64BIT: $f1 = COPY [[XFLOADf64_]]
76+
; 64BIT: $x7 = COPY [[ORI8_3]]
77+
; 64BIT: $x9 = COPY [[LD1]]
78+
; 64BIT: $x10 = COPY [[LD]]
79+
; 64BIT: $f2 = COPY [[XFLOADf64_1]]
80+
; 64BIT: BL8_NOP <mcsymbol .callee[PR]>, csr_ppc64_altivec, implicit-def dead $lr8, implicit $rm, implicit $x3, implicit $v2, implicit $f1, implicit $x7, implicit $x9, implicit $x10, implicit $f2, implicit $x2, implicit-def $r1, implicit-def $v2
81+
; 64BIT: ADJCALLSTACKUP 120, 0, implicit-def dead $r1, implicit $r1
82+
; 64BIT: [[COPY:%[0-9]+]]:vsrc = COPY $v2
83+
; 64BIT: BLR8 implicit $lr8, implicit $rm
84+
entry:
85+
%call = tail call <4 x i32> (i32, <4 x i32>, double, ...) @callee(i32 signext 55, <4 x i32> <i32 170, i32 187, i32 204, i32 221>, double 3.141590e+00, <4 x i32> <i32 10, i32 20, i32 30, i32 40>, double 2.718280e+00)
86+
ret void
87+
}
88+
89+
declare <4 x i32> @callee(i32 signext, <4 x i32>, double, ...)
90+
Lines changed: 37 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,47 @@
1-
; RUN: not --crash llc -verify-machineinstrs -stop-before=ppc-vsx-copy -vec-extabi \
1+
; RUN: llc -verify-machineinstrs -stop-before=ppc-vsx-copy -vec-extabi \
22
; RUN: -mcpu=pwr7 -mtriple powerpc-ibm-aix-xcoff < %s 2>&1 | \
33
; RUN: FileCheck %s
44

55
define void @caller() {
66
entry:
7-
%call = tail call <4 x i32> (double, double, double, ...) @split_spill(double 0.000000e+00, double 0.000000e+00, double 0.000000e+00, <4 x i32> <i32 1, i32 2, i32 3, i32 4>)
7+
%call = tail call <4 x i32> (double, double, double, ...) @split_spill(double 0.000000e+00, double 1.000000e+00, double 2.000000e+00, <4 x i32> <i32 1, i32 2, i32 3, i32 4>)
88
ret void
99
}
1010

1111
declare <4 x i32> @split_spill(double, double, double, ...)
1212

13-
; CHECK: ERROR: Unexpected register handling for calling convention.
13+
; CHECK: ADJCALLSTACKDOWN 64, 0, implicit-def dead $r1, implicit $r1
14+
; CHECK: [[VECCONSTADDR:%[0-9]+]]:gprc = LWZtoc %const.0, $r2 :: (load 4 from got)
15+
; CHECK: [[VECCONST:%[0-9]+]]:vsrc = LXVW4X $zero, killed [[VECCONSTADDR]] :: (load 16 from constant-pool)
16+
; CHECK: [[STACKOFFSET:%[0-9]+]]:gprc = LI 48
17+
; CHECK: STXVW4X killed [[VECCONST]], $r1, killed [[STACKOFFSET]] :: (store 16)
18+
; CHECK-DAG: [[ELEMENT1:%[0-9]+]]:gprc = LWZ 48, $r1 :: (load 4)
19+
; CHECK-DAG: [[ELEMENT2:%[0-9]+]]:gprc = LWZ 52, $r1 :: (load 4)
20+
; CHECK: [[FLOAT1ADDR:%[0-9]+]]:gprc_and_gprc_nor0 = LWZtoc %const.1, $r2 :: (load 4 from got)
21+
; CHECK: [[FLOAT1:%[0-9]+]]:f4rc = LFS 0, killed [[FLOAT1ADDR]] :: (load 4 from constant-pool)
22+
; CHECK: [[DOUBLE1:%[0-9]+]]:f8rc = COPY [[FLOAT1]]
23+
; CHECK: [[FLOAT2ADDR:%[0-9]+]]:gprc_and_gprc_nor0 = LWZtoc %const.2, $r2 :: (load 4 from got)
24+
; CHECK: [[FLOAT2:%[0-9]+]]:f4rc = LFS 0, killed [[FLOAT2ADDR]] :: (load 4 from constant-pool)
25+
; CHECK: [[DOUBLE2:%[0-9]+]]:f8rc = COPY [[FLOAT2]]
26+
27+
; CHECK: [[DZERO:%[0-9]+]]:vsfrc = XXLXORdpz
28+
; CHECK: [[DTOI1:%[0-9]+]]:gprc = LIS 16368
29+
; CHECK: [[DTOI2:%[0-9]+]]:gprc = LIS 16384
30+
; CHECK: [[IZERO:%[0-9]+]]:gprc = LI 0
31+
32+
; CHECK-DAG: $f1 = COPY [[DZERO]]
33+
; CHECK-DAG: $r3 = COPY [[IZERO]]
34+
; CHECK-DAG: $r4 = COPY [[IZERO]]
35+
36+
; CHECK-DAG: $f2 = COPY [[DOUBLE1]]
37+
; CHECK-DAG: $r5 = COPY [[DTOI1]]
38+
; CHECK-DAG: $r6 = COPY [[IZERO]]
39+
40+
; CHECK-DAG: $f3 = COPY [[DOUBLE2]]
41+
; CHECK-DAG: $r7 = COPY [[DTOI2]]
42+
; CHECK-DAG: $r8 = COPY [[IZERO]]
43+
44+
; CHECK-DAG: $r9 = COPY [[ELEMENT1]]
45+
; CHECK-DAG: $r10 = COPY [[ELEMENT2]]
46+
47+
; CHECK: BL_NOP <mcsymbol .split_spill[PR]>, csr_aix32_altivec, implicit-def dead $lr, implicit $rm, implicit $f1, implicit $r3, implicit $r4, implicit $f2, implicit $r5, implicit $r6, implicit $f3, implicit $r7, implicit $r8, implicit $r9, implicit $r10, implicit $r2, implicit-def $r1, implicit-def $v2

0 commit comments

Comments
 (0)