diff --git a/lib/IR/Verifier.cpp b/lib/IR/Verifier.cpp index 77e005418df..df6b2bdc66c 100644 --- a/lib/IR/Verifier.cpp +++ b/lib/IR/Verifier.cpp @@ -4485,7 +4485,7 @@ void Verifier::visitIntrinsicCall(Intrinsic::ID ID, CallBase &Call) { Assert(UseCall != nullptr, "Uses of llvm.call.preallocated.setup must be calls"); const Function *Fn = UseCall->getCalledFunction(); - if (Fn->getIntrinsicID() == Intrinsic::call_preallocated_arg) { + if (Fn && Fn->getIntrinsicID() == Intrinsic::call_preallocated_arg) { auto *AllocArgIndex = dyn_cast(UseCall->getArgOperand(1)); Assert(AllocArgIndex != nullptr, "llvm.call.preallocated.alloc arg index must be a constant"); @@ -4500,8 +4500,8 @@ void Verifier::visitIntrinsicCall(Intrinsic::ID ID, CallBase &Call) { "llvm.call.preallocated.setup"); FoundCall = true; size_t NumPreallocatedArgs = 0; - for (auto &Arg : Fn->args()) { - if (Arg.hasAttribute(Attribute::Preallocated)) { + for (unsigned i = 0; i < UseCall->getNumArgOperands(); i++) { + if (UseCall->paramHasAttr(i, Attribute::Preallocated)) { ++NumPreallocatedArgs; } } diff --git a/test/Verifier/preallocated-valid.ll b/test/Verifier/preallocated-valid.ll index a296acdef86..07f748ca867 100644 --- a/test/Verifier/preallocated-valid.ll +++ b/test/Verifier/preallocated-valid.ll @@ -14,6 +14,14 @@ define void @preallocated() { ret void } +define void @preallocated_indirect(void (i32*)* %f) { + %cs = call token @llvm.call.preallocated.setup(i32 1) + %x = call i8* @llvm.call.preallocated.arg(token %cs, i32 0) preallocated(i32) + %y = bitcast i8* %x to i32* + call void %f(i32* preallocated(i32) %y) ["preallocated"(token %cs)] + ret void +} + define void @preallocated_setup_without_call() { %cs = call token @llvm.call.preallocated.setup(i32 1) %a0 = call i8* @llvm.call.preallocated.arg(token %cs, i32 0) preallocated(i32)