diff options
author | Andrew Lenharth <andrewl@lenharth.org> | 2005-06-22 21:04:42 +0000 |
---|---|---|
committer | Andrew Lenharth <andrewl@lenharth.org> | 2005-06-22 21:04:42 +0000 |
commit | 213e557cef3e653e2d3a00b07b137c143128430a (patch) | |
tree | 2b864d830fba118c8d2fa07144629603caf85214 | |
parent | d0a4c62a031ea9f0e2be2fe1f16af2209602ed94 (diff) |
If we support structs as va_list, we must pass pointers to them to va_copy
See last commit for LangRef, this implements it on all targets.
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@22273 91177308-0d34-0410-b5e6-96231b3b80d8
-rw-r--r-- | lib/AsmParser/llvmAsmParser.y | 27 | ||||
-rw-r--r-- | lib/Bytecode/Reader/ReaderWrappers.cpp | 12 | ||||
-rw-r--r-- | lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp | 9 | ||||
-rw-r--r-- | lib/Target/CBackend/CBackend.cpp | 2 | ||||
-rw-r--r-- | lib/Target/CBackend/Writer.cpp | 2 | ||||
-rw-r--r-- | lib/Target/IA64/IA64ISelPattern.cpp | 13 | ||||
-rw-r--r-- | lib/Target/PowerPC/PPC64ISelPattern.cpp | 14 | ||||
-rw-r--r-- | lib/Target/SparcV9/SparcV9BurgISel.cpp | 17 | ||||
-rw-r--r-- | lib/Target/X86/X86ISelPattern.cpp | 13 |
9 files changed, 43 insertions, 66 deletions
diff --git a/lib/AsmParser/llvmAsmParser.y b/lib/AsmParser/llvmAsmParser.y index b71f618779..178c533093 100644 --- a/lib/AsmParser/llvmAsmParser.y +++ b/lib/AsmParser/llvmAsmParser.y @@ -749,14 +749,12 @@ static PATypeHolder HandleUpRefs(const Type *ty) { } if (ObsoleteVarArgs && NewVarArgs) - { - std::cerr << "This file is corrupt in that it uses both new and old style varargs\n"; - abort(); - } + ThrowException("This file is corrupt in that it uses both new and old style varargs"); if(ObsoleteVarArgs) { if(Function* F = Result->getNamedFunction("llvm.va_start")) { - assert(F->arg_size() == 0 && "Obsolete va_start takes 0 argument!"); + if (F->arg_size() != 0) + ThrowException("Obsolete va_start takes 0 argument!"); //foo = va_start() // -> @@ -782,7 +780,9 @@ static PATypeHolder HandleUpRefs(const Type *ty) { } if(Function* F = Result->getNamedFunction("llvm.va_end")) { - assert(F->arg_size() == 1 && "Obsolete va_end takes 1 argument!"); + if(F->arg_size() != 1) + ThrowException("Obsolete va_end takes 1 argument!"); + //vaend foo // -> //bar = alloca 1 of typeof(foo) @@ -804,24 +804,29 @@ static PATypeHolder HandleUpRefs(const Type *ty) { } if(Function* F = Result->getNamedFunction("llvm.va_copy")) { - assert(F->arg_size() == 1 && "Obsolete va_copy takes 1 argument!"); + if(F->arg_size() != 1) + ThrowException("Obsolete va_copy takes 1 argument!"); //foo = vacopy(bar) // -> //a = alloca 1 of typeof(foo) - //vacopy(a, bar) + //b = alloca 1 of typeof(foo) + //store bar -> b + //vacopy(a, b) //foo = load a const Type* RetTy = Type::getPrimitiveType(Type::VoidTyID); const Type* ArgTy = F->getFunctionType()->getReturnType(); const Type* ArgTyPtr = PointerType::get(ArgTy); Function* NF = Result->getOrInsertFunction("llvm.va_copy", - RetTy, ArgTyPtr, ArgTy, 0); + RetTy, ArgTyPtr, ArgTyPtr, 0); while (!F->use_empty()) { CallInst* CI = cast<CallInst>(F->use_back()); AllocaInst* a = new AllocaInst(ArgTy, 0, "vacopy.fix.1", CI); - new CallInst(NF, a, CI->getOperand(1), "", CI); - Value* foo = new LoadInst(a, "vacopy.fix.2", CI); + AllocaInst* b = new AllocaInst(ArgTy, 0, "vacopy.fix.2", CI); + new StoreInst(CI->getOperand(1), b, CI); + new CallInst(NF, a, b, "", CI); + Value* foo = new LoadInst(a, "vacopy.fix.3", CI); CI->replaceAllUsesWith(foo); CI->getParent()->getInstList().erase(CI); } diff --git a/lib/Bytecode/Reader/ReaderWrappers.cpp b/lib/Bytecode/Reader/ReaderWrappers.cpp index c000c9a3f5..a198447d72 100644 --- a/lib/Bytecode/Reader/ReaderWrappers.cpp +++ b/lib/Bytecode/Reader/ReaderWrappers.cpp @@ -221,20 +221,24 @@ static ModuleProvider* CheckVarargs(ModuleProvider* MP) { //foo = vacopy(bar) // -> //a = alloca 1 of typeof(foo) - //vacopy(a, bar) + //b = alloca 1 of typeof(foo) + //store bar -> b + //vacopy(a, b) //foo = load a const Type* RetTy = Type::getPrimitiveType(Type::VoidTyID); const Type* ArgTy = F->getFunctionType()->getReturnType(); const Type* ArgTyPtr = PointerType::get(ArgTy); Function* NF = M->getOrInsertFunction("llvm.va_copy", - RetTy, ArgTyPtr, ArgTy, 0); + RetTy, ArgTyPtr, ArgTyPtr, 0); for(Value::use_iterator I = F->use_begin(), E = F->use_end(); I != E;) if (CallInst* CI = dyn_cast<CallInst>(*I++)) { AllocaInst* a = new AllocaInst(ArgTy, 0, "vacopy.fix.1", CI); - new CallInst(NF, a, CI->getOperand(1), "", CI); - Value* foo = new LoadInst(a, "vacopy.fix.2", CI); + AllocaInst* b = new AllocaInst(ArgTy, 0, "vacopy.fix.2", CI); + new StoreInst(CI->getOperand(1), b, CI); + new CallInst(NF, a, b, "", CI); + Value* foo = new LoadInst(a, "vacopy.fix.3", CI); CI->replaceAllUsesWith(foo); CI->getParent()->getInstList().erase(CI); } diff --git a/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp b/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp index 0c94ea74cd..fa6d6d4d14 100644 --- a/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp +++ b/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp @@ -855,10 +855,11 @@ SDOperand TargetLowering::LowerVAEnd(SDOperand Chain, SDOperand L, std::pair<SDOperand,SDOperand> TargetLowering::LowerVACopy(SDOperand Chain, SDOperand Src, SDOperand Dest, SelectionDAG &DAG) { - // We have no sane default behavior, just emit a useful error message and bail - // out. - std::cerr << "Variable arguments handling not implemented on this target!\n"; - abort(); + //Default to returning the input list + SDOperand Val = DAG.getLoad(getPointerTy(), Chain, Src, DAG.getSrcValue(NULL)); + SDOperand Result = DAG.getNode(ISD::STORE, MVT::Other, Val.getValue(1), + Val, Dest, DAG.getSrcValue(NULL)); + return std::make_pair(Result, Result); } std::pair<SDOperand,SDOperand> diff --git a/lib/Target/CBackend/CBackend.cpp b/lib/Target/CBackend/CBackend.cpp index 65979933db..c30b306483 100644 --- a/lib/Target/CBackend/CBackend.cpp +++ b/lib/Target/CBackend/CBackend.cpp @@ -1495,7 +1495,7 @@ void CWriter::visitCallInst(CallInst &I) { Out << "0; "; Out << "va_copy(*(va_list*)"; writeOperand(I.getOperand(1)); - Out << ", *(va_list*)&"; + Out << ", *(va_list*)"; writeOperand(I.getOperand(2)); Out << ')'; return; diff --git a/lib/Target/CBackend/Writer.cpp b/lib/Target/CBackend/Writer.cpp index 65979933db..c30b306483 100644 --- a/lib/Target/CBackend/Writer.cpp +++ b/lib/Target/CBackend/Writer.cpp @@ -1495,7 +1495,7 @@ void CWriter::visitCallInst(CallInst &I) { Out << "0; "; Out << "va_copy(*(va_list*)"; writeOperand(I.getOperand(1)); - Out << ", *(va_list*)&"; + Out << ", *(va_list*)"; writeOperand(I.getOperand(2)); Out << ')'; return; diff --git a/lib/Target/IA64/IA64ISelPattern.cpp b/lib/Target/IA64/IA64ISelPattern.cpp index 0830468a95..804ad9937e 100644 --- a/lib/Target/IA64/IA64ISelPattern.cpp +++ b/lib/Target/IA64/IA64ISelPattern.cpp @@ -120,10 +120,6 @@ namespace { LowerVAArgNext(SDOperand Chain, SDOperand VAList, const Type *ArgTy, SelectionDAG &DAG); - virtual std::pair<SDOperand,SDOperand> - LowerVACopy(SDOperand Chain, SDOperand Src, SDOperand Dest, - SelectionDAG &DAG); - virtual std::pair<SDOperand, SDOperand> LowerFrameReturnAddress(bool isFrameAddr, SDOperand Chain, unsigned Depth, SelectionDAG &DAG); @@ -413,15 +409,6 @@ LowerVAArgNext(SDOperand Chain, SDOperand VAList, return std::make_pair(Result, Chain); } -std::pair<SDOperand,SDOperand> -IA64TargetLowering::LowerVACopy(SDOperand Chain, SDOperand Src, - SDOperand Dest, SelectionDAG &DAG) -{ - SDOperand Result = DAG.getNode(ISD::STORE, MVT::Other, Chain, - Src, Dest, DAG.getSrcValue(NULL)); - return std::make_pair(Result, Result); -} - std::pair<SDOperand, SDOperand> IA64TargetLowering:: LowerFrameReturnAddress(bool isFrameAddress, SDOperand Chain, unsigned Depth, SelectionDAG &DAG) { diff --git a/lib/Target/PowerPC/PPC64ISelPattern.cpp b/lib/Target/PowerPC/PPC64ISelPattern.cpp index 20fd724444..6761ab1115 100644 --- a/lib/Target/PowerPC/PPC64ISelPattern.cpp +++ b/lib/Target/PowerPC/PPC64ISelPattern.cpp @@ -104,10 +104,6 @@ namespace { LowerVAArgNext(SDOperand Chain, SDOperand VAList, const Type *ArgTy, SelectionDAG &DAG); - virtual std::pair<SDOperand,SDOperand> - LowerVACopy(SDOperand Chain, SDOperand Src, SDOperand Dest, - SelectionDAG &DAG); - virtual std::pair<SDOperand, SDOperand> LowerFrameReturnAddress(bool isFrameAddr, SDOperand Chain, unsigned Depth, SelectionDAG &DAG); @@ -390,16 +386,6 @@ LowerVAArgNext(SDOperand Chain, SDOperand VAList, return std::make_pair(Result, Chain); } -std::pair<SDOperand,SDOperand> -PPC64TargetLowering::LowerVACopy(SDOperand Chain, SDOperand Src, - SDOperand Dest, SelectionDAG &DAG) -{ - SDOperand Result = DAG.getNode(ISD::STORE, MVT::Other, Chain, - Src, Dest, DAG.getSrcValue(NULL)); - return std::make_pair(Result, Result); -} - - std::pair<SDOperand, SDOperand> PPC64TargetLowering:: LowerFrameReturnAddress(bool isFrameAddress, SDOperand Chain, unsigned Depth, SelectionDAG &DAG) { diff --git a/lib/Target/SparcV9/SparcV9BurgISel.cpp b/lib/Target/SparcV9/SparcV9BurgISel.cpp index cc2c81f3bb..a6722b1862 100644 --- a/lib/Target/SparcV9/SparcV9BurgISel.cpp +++ b/lib/Target/SparcV9/SparcV9BurgISel.cpp @@ -2881,11 +2881,18 @@ static bool CodeGenIntrinsic(Intrinsic::ID iid, CallInst &callInstr, return true; // no-op on SparcV9 case Intrinsic::vacopy: - // Simple store of current va_list (arg2) to new va_list (arg1) - mvec.push_back(BuildMI(V9::STXi, 3). - addReg(callInstr.getOperand(2)). - addReg(callInstr.getOperand(1)).addSImm(0)); - return true; + { + MachineCodeForInstruction& m1 = MachineCodeForInstruction::get(&callInstr); + TmpInstruction* VReg = + new TmpInstruction(m1, callInstr.getOperand(1)->getType()); + + // Simple store of current va_list (arg2) to new va_list (arg1) + mvec.push_back(BuildMI(V9::LDXi, 3). + addReg(callInstr.getOperand(2)).addSImm(0).addRegDef(VReg)); + mvec.push_back(BuildMI(V9::STXi, 3). + addReg(VReg).addReg(callInstr.getOperand(1)).addSImm(0)); + return true; + } } } diff --git a/lib/Target/X86/X86ISelPattern.cpp b/lib/Target/X86/X86ISelPattern.cpp index d28de2828d..e858c4c821 100644 --- a/lib/Target/X86/X86ISelPattern.cpp +++ b/lib/Target/X86/X86ISelPattern.cpp @@ -182,10 +182,6 @@ namespace { LowerVAArgNext(SDOperand Chain, SDOperand VAList, const Type *ArgTy, SelectionDAG &DAG); - virtual std::pair<SDOperand,SDOperand> - LowerVACopy(SDOperand Chain, SDOperand Src, SDOperand Dest, - SelectionDAG &DAG); - virtual std::pair<SDOperand, SDOperand> LowerFrameReturnAddress(bool isFrameAddr, SDOperand Chain, unsigned Depth, SelectionDAG &DAG); @@ -475,15 +471,6 @@ X86TargetLowering::LowerVAArgNext(SDOperand Chain, SDOperand VAList, return std::make_pair(Result, Chain); } -std::pair<SDOperand,SDOperand> -X86TargetLowering::LowerVACopy(SDOperand Chain, SDOperand Src, - SDOperand Dest, SelectionDAG &DAG) -{ - SDOperand Result = DAG.getNode(ISD::STORE, MVT::Other, Chain, - Src, Dest, DAG.getSrcValue(NULL)); - return std::make_pair(Result, Result); -} - //===----------------------------------------------------------------------===// // Fast Calling Convention implementation //===----------------------------------------------------------------------===// |