forked from OSchip/llvm-project
Fix handling of vaargs on PPC32 when going from regsave to overflow.
It can happen that when we only have 1 more register left in the regsave area we need to store a value bigger than 1 register and therefore we go to the overflow area. In this case we have to leave the last slot in the regsave area unused and keep using overflow area. Do this by storing a limit value to the used register counter in the overflow block. Issue diagnosed by and solution tested by Mark Millard! llvm-svn: 261422
This commit is contained in:
parent
43b121df05
commit
039b970c97
|
@ -3505,6 +3505,7 @@ public:
|
||||||
|
|
||||||
Address PPC32_SVR4_ABIInfo::EmitVAArg(CodeGenFunction &CGF, Address VAList,
|
Address PPC32_SVR4_ABIInfo::EmitVAArg(CodeGenFunction &CGF, Address VAList,
|
||||||
QualType Ty) const {
|
QualType Ty) const {
|
||||||
|
const unsigned OverflowLimit = 8;
|
||||||
if (const ComplexType *CTy = Ty->getAs<ComplexType>()) {
|
if (const ComplexType *CTy = Ty->getAs<ComplexType>()) {
|
||||||
// TODO: Implement this. For now ignore.
|
// TODO: Implement this. For now ignore.
|
||||||
(void)CTy;
|
(void)CTy;
|
||||||
|
@ -3547,7 +3548,7 @@ Address PPC32_SVR4_ABIInfo::EmitVAArg(CodeGenFunction &CGF, Address VAList,
|
||||||
}
|
}
|
||||||
|
|
||||||
llvm::Value *CC =
|
llvm::Value *CC =
|
||||||
Builder.CreateICmpULT(NumRegs, Builder.getInt8(8), "cond");
|
Builder.CreateICmpULT(NumRegs, Builder.getInt8(OverflowLimit), "cond");
|
||||||
|
|
||||||
llvm::BasicBlock *UsingRegs = CGF.createBasicBlock("using_regs");
|
llvm::BasicBlock *UsingRegs = CGF.createBasicBlock("using_regs");
|
||||||
llvm::BasicBlock *UsingOverflow = CGF.createBasicBlock("using_overflow");
|
llvm::BasicBlock *UsingOverflow = CGF.createBasicBlock("using_overflow");
|
||||||
|
@ -3599,6 +3600,8 @@ Address PPC32_SVR4_ABIInfo::EmitVAArg(CodeGenFunction &CGF, Address VAList,
|
||||||
{
|
{
|
||||||
CGF.EmitBlock(UsingOverflow);
|
CGF.EmitBlock(UsingOverflow);
|
||||||
|
|
||||||
|
Builder.CreateStore(Builder.getInt8(OverflowLimit), NumRegsAddr);
|
||||||
|
|
||||||
// Everything in the overflow area is rounded up to a size of at least 4.
|
// Everything in the overflow area is rounded up to a size of at least 4.
|
||||||
CharUnits OverflowAreaAlign = CharUnits::fromQuantity(4);
|
CharUnits OverflowAreaAlign = CharUnits::fromQuantity(4);
|
||||||
|
|
||||||
|
|
|
@ -37,6 +37,7 @@ void testva (int n, ...)
|
||||||
// CHECK-PPC-NEXT: br label %[[CONT:[a-z0-9]+]]
|
// CHECK-PPC-NEXT: br label %[[CONT:[a-z0-9]+]]
|
||||||
//
|
//
|
||||||
// CHECK-PPC:[[USING_OVERFLOW]]
|
// CHECK-PPC:[[USING_OVERFLOW]]
|
||||||
|
// CHECK-PPC-NEXT: store i8 8, i8* [[GPRPTR]], align 4
|
||||||
// CHECK-PPC-NEXT: [[OVERFLOW_AREA_P:%[0-9]+]] = getelementptr inbounds %struct.__va_list_tag, %struct.__va_list_tag* [[ARRAYDECAY]], i32 0, i32 3
|
// CHECK-PPC-NEXT: [[OVERFLOW_AREA_P:%[0-9]+]] = getelementptr inbounds %struct.__va_list_tag, %struct.__va_list_tag* [[ARRAYDECAY]], i32 0, i32 3
|
||||||
// CHECK-PPC-NEXT: [[OVERFLOW_AREA:%.+]] = load i8*, i8** [[OVERFLOW_AREA_P]], align 4
|
// CHECK-PPC-NEXT: [[OVERFLOW_AREA:%.+]] = load i8*, i8** [[OVERFLOW_AREA_P]], align 4
|
||||||
// CHECK-PPC-NEXT: %{{[0-9]+}} = ptrtoint i8* %argp.cur to i32
|
// CHECK-PPC-NEXT: %{{[0-9]+}} = ptrtoint i8* %argp.cur to i32
|
||||||
|
@ -76,6 +77,7 @@ void testva (int n, ...)
|
||||||
// CHECK-PPC-NEXT: br label %[[CONT:[a-z0-9]+]]
|
// CHECK-PPC-NEXT: br label %[[CONT:[a-z0-9]+]]
|
||||||
//
|
//
|
||||||
// CHECK-PPC:[[USING_OVERFLOW]]
|
// CHECK-PPC:[[USING_OVERFLOW]]
|
||||||
|
// CHECK-PPC-NEXT: store i8 8, i8* [[GPRPTR]], align 4
|
||||||
// CHECK-PPC-NEXT: [[OVERFLOW_AREA_P:%[0-9]+]] = getelementptr inbounds %struct.__va_list_tag, %struct.__va_list_tag* [[ARRAYDECAY]], i32 0, i32 3
|
// CHECK-PPC-NEXT: [[OVERFLOW_AREA_P:%[0-9]+]] = getelementptr inbounds %struct.__va_list_tag, %struct.__va_list_tag* [[ARRAYDECAY]], i32 0, i32 3
|
||||||
// CHECK-PPC-NEXT: [[OVERFLOW_AREA:%.+]] = load i8*, i8** [[OVERFLOW_AREA_P]], align 4
|
// CHECK-PPC-NEXT: [[OVERFLOW_AREA:%.+]] = load i8*, i8** [[OVERFLOW_AREA_P]], align 4
|
||||||
// CHECK-PPC-NEXT: [[MEMADDR:%.+]] = bitcast i8* [[OVERFLOW_AREA]] to i32*
|
// CHECK-PPC-NEXT: [[MEMADDR:%.+]] = bitcast i8* [[OVERFLOW_AREA]] to i32*
|
||||||
|
|
Loading…
Reference in New Issue