diff options
Diffstat (limited to 'lib')
-rw-r--r-- | lib/Bitcode/NaCl/Reader/NaClBitcodeReader.cpp | 31 | ||||
-rw-r--r-- | lib/Bitcode/NaCl/Writer/NaClBitcodeWriter.cpp | 6 |
2 files changed, 20 insertions, 17 deletions
diff --git a/lib/Bitcode/NaCl/Reader/NaClBitcodeReader.cpp b/lib/Bitcode/NaCl/Reader/NaClBitcodeReader.cpp index eaaa85a164..29a842c948 100644 --- a/lib/Bitcode/NaCl/Reader/NaClBitcodeReader.cpp +++ b/lib/Bitcode/NaCl/Reader/NaClBitcodeReader.cpp @@ -1626,16 +1626,11 @@ bool NaClBitcodeReader::ParseFunctionBody(Function *F) { // Build function type for call. FunctionType *FTy = 0; + Type *ReturnType = 0; if (BitCode == naclbitc::FUNC_CODE_INST_CALL_INDIRECT) { // Callee type has been elided, add back in. - Type *Type = getTypeByID(Record[2]); + ReturnType = getTypeByID(Record[2]); ++OpNum; - if (FunctionType *FcnType = dyn_cast<FunctionType>(Type)) { - FTy = FcnType; - Callee = ConvertOpToType(Callee, FcnType->getPointerTo(), CurBBNo); - } else { - return Error("Invalid type for CALL_INDIRECT record"); - } } else { // Get type signature from callee. if (PointerType *OpTy = dyn_cast<PointerType>(Callee->getType())) { @@ -1646,7 +1641,7 @@ bool NaClBitcodeReader::ParseFunctionBody(Function *F) { } unsigned NumParams = Record.size() - OpNum; - if (NumParams != FTy->getNumParams()) + if (FTy && NumParams != FTy->getNumParams()) return Error("Invalid CALL record"); // Process call arguments. @@ -1655,14 +1650,26 @@ bool NaClBitcodeReader::ParseFunctionBody(Function *F) { Value *Arg; if (popValue(Record, &OpNum, NextValueNo, &Arg)) Error("Invalid argument in CALL record"); - if (BitCode == naclbitc::FUNC_CODE_INST_CALL_INDIRECT && - FTy->getParamType(Index)->isPointerTy()) { - return Error("Pointer arguments not allowed for indirect calls"); + if (FTy) { + // Add a cast, to a pointer type if necessary, in case this + // is an intrinsic call that takes a pointer argument. + Arg = ConvertOpToType(Arg, FTy->getParamType(Index), CurBBNo); + } else { + Arg = ConvertOpToScalar(Arg, CurBBNo); } - Arg = ConvertOpToType(Arg, FTy->getParamType(Index), CurBBNo); Args.push_back(Arg); } + if (FTy == 0) { + // Reconstruct the function type and cast the function pointer + // to it. + SmallVector<Type*, 6> ArgTypes; + for (unsigned Index = 0; Index < NumParams; ++Index) + ArgTypes.push_back(Args[Index]->getType()); + FTy = FunctionType::get(ReturnType, ArgTypes, false); + Callee = ConvertOpToType(Callee, FTy->getPointerTo(), CurBBNo); + } + // Construct call. I = CallInst::Create(Callee, Args); cast<CallInst>(I)->setCallingConv(GetDecodedCallingConv(CCInfo>>1)); diff --git a/lib/Bitcode/NaCl/Writer/NaClBitcodeWriter.cpp b/lib/Bitcode/NaCl/Writer/NaClBitcodeWriter.cpp index 166a95bb23..4288aceb06 100644 --- a/lib/Bitcode/NaCl/Writer/NaClBitcodeWriter.cpp +++ b/lib/Bitcode/NaCl/Writer/NaClBitcodeWriter.cpp @@ -893,11 +893,7 @@ static bool WriteInstruction(const Instruction &I, unsigned InstID, // not known. Hence, we must send the type signature to the // reader. Code = naclbitc::FUNC_CODE_INST_CALL_INDIRECT; - PointerType *FcnPtrType = - cast<PointerType>(Callee->getType()); - FunctionType *FcnType = - cast<FunctionType>(FcnPtrType->getElementType()); - Vals.push_back(VE.getTypeID(FcnType)); + Vals.push_back(VE.getTypeID(I.getType())); } } |