Lines Matching +full:global +full:- +full:regs
1 //===--- SPIRVCallLowering.cpp - Call lowering ------------------*- C++ -*-===//
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
7 //===----------------------------------------------------------------------===//
12 //===----------------------------------------------------------------------===//
60 // Based on the LLVM function attributes, get a SPIR-V FunctionControl.
80 if (MD->getNumOperands() > NumOp) { in getConstInt()
81 auto *CMeta = dyn_cast<ConstantAsMetadata>(MD->getOperand(NumOp)); in getConstInt()
83 return dyn_cast<ConstantInt>(CMeta->getValue()); in getConstInt()
88 // If the function has pointer arguments, we are forced to re-create this
91 // potentially corresponds to different SPIR-V function type, effectively
92 // invalidating logic behind global registry and duplicates tracker.
97 if (F.getParent()->getNamedMetadata("spv.cloned_funcs")) in fixFunctionTypeIfPtrArgs()
102 // check if it's an instance of a non-typed PointerType in fixFunctionTypeIfPtrArgs()
103 if (Arg.getType()->isPointerTy()) { in fixFunctionTypeIfPtrArgs()
109 Type *RetTy = FTy->getReturnType(); in fixFunctionTypeIfPtrArgs()
110 // check if it's an instance of a non-typed PointerType in fixFunctionTypeIfPtrArgs()
111 if (!RetTy->isPointerTy()) in fixFunctionTypeIfPtrArgs()
115 // re-create function type, using TypedPointerType instead of PointerType to in fixFunctionTypeIfPtrArgs()
117 const Type *RetTy = GR->getTypeForSPIRVType(SRetTy); in fixFunctionTypeIfPtrArgs()
120 ArgTys.push_back(const_cast<Type *>(GR->getTypeForSPIRVType(SArgTy))); in fixFunctionTypeIfPtrArgs()
128 auto *NamedMD = F.getParent()->getNamedMetadata("spv.cloned_funcs"); in getOriginalFunctionType()
132 Type *RetTy = F.getFunctionType()->getReturnType(); in getOriginalFunctionType()
138 std::find_if(NamedMD->op_begin(), NamedMD->op_end(), [&F](MDNode *N) { in getOriginalFunctionType()
139 return isa<MDString>(N->getOperand(0)) && in getOriginalFunctionType()
140 cast<MDString>(N->getOperand(0))->getString() == F.getName(); in getOriginalFunctionType()
144 if (ThisFuncMDIt != NamedMD->op_end()) { in getOriginalFunctionType()
146 MDNode *MD = dyn_cast<MDNode>(ThisFuncMD->getOperand(1)); in getOriginalFunctionType()
150 auto *CMeta = dyn_cast<ConstantAsMetadata>(MD->getOperand(1)); in getOriginalFunctionType()
152 assert(Const->getSExtValue() >= -1); in getOriginalFunctionType()
153 // Currently -1 indicates return value, greater values mean in getOriginalFunctionType()
155 if (Const->getSExtValue() == -1) in getOriginalFunctionType()
156 RetTy = CMeta->getType(); in getOriginalFunctionType()
158 ArgTypes[Const->getSExtValue()] = CMeta->getType(); in getOriginalFunctionType()
174 if (ArgAttribute->getString() == "read_only") in getArgAccessQual()
176 if (ArgAttribute->getString() == "write_only") in getArgAccessQual()
184 if (ArgAttribute && ArgAttribute->getString() == "volatile") in getKernelArgTypeQual()
197 Type *OriginalArgType = getOriginalFunctionType(F)->getParamType(ArgIdx); in getArgSPIRVType()
199 // If OriginalArgType is non-pointer, use the OriginalArgType (the type cannot in getArgSPIRVType()
202 return GR->getOrCreateSPIRVType(OriginalArgType, MIRBuilder, ArgAccessQual); in getArgSPIRVType()
205 Type *ArgType = Arg->getType(); in getArgSPIRVType()
207 SPIRVType *ElementType = GR->getOrCreateSPIRVType( in getArgSPIRVType()
208 cast<TypedPointerType>(ArgType)->getElementType(), MIRBuilder); in getArgSPIRVType()
209 return GR->getOrCreateSPIRVPointerType( in getArgSPIRVType()
217 // 2) This is an OpenCL/SPIR-V builtin type if there is spv_assign_type in getArgSPIRVType()
224 GR->getOrCreateSPIRVType(getPointeeTypeByAttr(Arg), MIRBuilder); in getArgSPIRVType()
225 return GR->getOrCreateSPIRVPointerType( in getArgSPIRVType()
230 for (auto User : Arg->users()) { in getArgSPIRVType()
232 // Check if this is spv_assign_type assigning OpenCL/SPIR-V builtin type. in getArgSPIRVType()
233 if (II && II->getIntrinsicID() == Intrinsic::spv_assign_type) { in getArgSPIRVType()
234 MetadataAsValue *VMD = cast<MetadataAsValue>(II->getOperand(1)); in getArgSPIRVType()
236 cast<ConstantAsMetadata>(VMD->getMetadata())->getType(); in getArgSPIRVType()
237 assert(BuiltinType->isTargetExtTy() && "Expected TargetExtType"); in getArgSPIRVType()
238 return GR->getOrCreateSPIRVType(BuiltinType, MIRBuilder, ArgAccessQual); in getArgSPIRVType()
242 if (!II || II->getIntrinsicID() != Intrinsic::spv_assign_ptr_type) in getArgSPIRVType()
245 MetadataAsValue *VMD = cast<MetadataAsValue>(II->getOperand(1)); in getArgSPIRVType()
247 toTypedPointer(cast<ConstantAsMetadata>(VMD->getMetadata())->getType()); in getArgSPIRVType()
248 SPIRVType *ElementType = GR->getOrCreateSPIRVType(ElementTy, MIRBuilder); in getArgSPIRVType()
249 return GR->getOrCreateSPIRVPointerType( in getArgSPIRVType()
252 cast<ConstantInt>(II->getOperand(2))->getZExtValue(), ST)); in getArgSPIRVType()
255 // Replace PointerType with TypedPointerType to be able to map SPIR-V types to in getArgSPIRVType()
257 return GR->getOrCreateSPIRVType(toTypedPointer(OriginalArgType), MIRBuilder, in getArgSPIRVType()
284 GR->setCurrentFunc(MIRBuilder.getMF()); in lowerFormalArguments()
300 GR->assignSPIRVTypeToVReg(SpirvTy, VRegs[i][0], MIRBuilder.getMF()); in lowerFormalArguments()
350 if (Node && i < Node->getNumOperands() && in lowerFormalArguments()
351 isa<MDNode>(Node->getOperand(i))) { in lowerFormalArguments()
352 MDNode *MD = cast<MDNode>(Node->getOperand(i)); in lowerFormalArguments()
353 for (const MDOperand &MDOp : MD->operands()) { in lowerFormalArguments()
359 static_cast<SPIRV::Decoration::Decoration>(Const->getZExtValue()); in lowerFormalArguments()
361 for (unsigned j = 1; j < MD2->getNumOperands(); j++) { in lowerFormalArguments()
364 DecVec.push_back(static_cast<uint32_t>(Const->getZExtValue())); in lowerFormalArguments()
374 Register FuncVReg = MRI->createGenericVirtualRegister(LLT::scalar(32)); in lowerFormalArguments()
375 MRI->setRegClass(FuncVReg, &SPIRV::IDRegClass); in lowerFormalArguments()
377 GR->add(&F, &MIRBuilder.getMF(), FuncVReg); in lowerFormalArguments()
379 Type *FRetTy = FTy->getReturnType(); in lowerFormalArguments()
381 if (Type *FRetElemTy = GR->findDeducedElementType(&F)) { in lowerFormalArguments()
384 GR->addReturnType(&F, DerivedTy); in lowerFormalArguments()
388 SPIRVType *RetTy = GR->getOrCreateSPIRVType(FRetTy, MIRBuilder); in lowerFormalArguments()
390 SPIRVType *FuncTy = GR->getOrCreateOpTypeFunctionWithArgs( in lowerFormalArguments()
397 .addUse(GR->getSPIRVTypeID(RetTy)) in lowerFormalArguments()
399 .addUse(GR->getSPIRVTypeID(FuncTy)); in lowerFormalArguments()
400 GR->recordFunctionDefinition(&F, &MB.getInstr()->getOperand(0)); in lowerFormalArguments()
406 MRI->setRegClass(VRegs[i][0], &SPIRV::IDRegClass); in lowerFormalArguments()
409 .addUse(GR->getSPIRVTypeID(ArgTypeVRegs[i])); in lowerFormalArguments()
411 GR->add(&Arg, &MIRBuilder.getMF(), VRegs[i][0]); in lowerFormalArguments()
432 ST->canUseExtension( in lowerFormalArguments()
442 ST->canUseExtension(SPIRV::Extension::SPV_INTEL_function_pointers); in lowerFormalArguments()
444 if (F.hasFnAttribute("referenced-indirectly")) { in lowerFormalArguments()
446 "Unexpected 'referenced-indirectly' attribute of the kernel " in lowerFormalArguments()
459 // - add a topological sort of IndirectCalls to ensure the best types knowledge
460 // - we may need to fix function formal parameter types if they are opaque
467 SPIRVType *SpirvRetTy = GR->getOrCreateSPIRVType(IC.RetTy, MIRBuilder); in produceIndirectPtrTypes()
470 SPIRVType *SPIRVTy = GR->getOrCreateSPIRVType(IC.ArgTys[i], MIRBuilder); in produceIndirectPtrTypes()
472 if (!GR->getSPIRVTypeForVReg(IC.ArgRegs[i])) in produceIndirectPtrTypes()
473 GR->assignSPIRVTypeToVReg(SPIRVTy, IC.ArgRegs[i], MF); in produceIndirectPtrTypes()
475 // SPIR-V function type: in produceIndirectPtrTypes()
478 SPIRVType *SpirvFuncTy = GR->getOrCreateOpTypeFunctionWithArgs( in produceIndirectPtrTypes()
480 // SPIR-V pointer to function type: in produceIndirectPtrTypes()
481 SPIRVType *IndirectFuncPtrTy = GR->getOrCreateSPIRVPointerType( in produceIndirectPtrTypes()
484 GR->assignSPIRVTypeToVReg(IndirectFuncPtrTy, IC.Callee, MF); in produceIndirectPtrTypes()
492 if (Info.OrigRet.Regs.size() > 1) in lowerCall()
495 GR->setCurrentFunc(MF); in lowerCall()
504 std::string FuncName = Info.Callee.getGlobal()->getName().str(); in lowerCall()
511 OrigRetTy = FTy->getReturnType(); in lowerCall()
513 if (auto *DerivedRetTy = GR->findReturnType(CF)) in lowerCall()
521 Info.OrigRet.Regs.empty() ? Register(0) : Info.OrigRet.Regs[0]; in lowerCall()
524 bool isFunctionDecl = CF && CF->isDeclaration(); in lowerCall()
525 bool canUseOpenCL = ST->canUseExtInstSet(SPIRV::InstructionSet::OpenCL_std); in lowerCall()
526 bool canUseGLSL = ST->canUseExtInstSet(SPIRV::InstructionSet::GLSL_std_450); in lowerCall()
534 assert(Arg.Regs.size() == 1 && "Call arg has multiple VRegs"); in lowerCall()
535 ArgVRegs.push_back(Arg.Regs[0]); in lowerCall()
536 SPIRVType *SPIRVTy = GR->getOrCreateSPIRVType(Arg.Ty, MIRBuilder); in lowerCall()
537 if (!GR->getSPIRVTypeForVReg(Arg.Regs[0])) in lowerCall()
538 GR->assignSPIRVTypeToVReg(SPIRVTy, Arg.Regs[0], MF); in lowerCall()
548 if (isFunctionDecl && !GR->find(CF, &MF).isValid()) { in lowerCall()
557 for (const Argument &Arg : CF->args()) { in lowerCall()
560 Register Reg = MRI->createGenericVirtualRegister(LLT::scalar(32)); in lowerCall()
561 MRI->setRegClass(Reg, &SPIRV::IDRegClass); in lowerCall()
571 if (Info.CB->isIndirectCall()) { in lowerCall()
572 if (!ST->canUseExtension(SPIRV::Extension::SPV_INTEL_function_pointers)) in lowerCall()
573 report_fatal_error("An indirect call is encountered but SPIR-V without " in lowerCall()
586 assert(Arg.Regs.size() == 1 && "Call arg has multiple VRegs"); in lowerCall()
588 IndirectCall.ArgRegs.push_back(Arg.Regs[0]); in lowerCall()
599 ResVReg = MIRBuilder.getMRI()->createVirtualRegister(&SPIRV::IDRegClass); in lowerCall()
600 SPIRVType *RetType = GR->assignTypeToVReg(OrigRetTy, ResVReg, MIRBuilder); in lowerCall()
605 .addUse(GR->getSPIRVTypeID(RetType)) in lowerCall()
610 if (Arg.Regs.size() > 1) in lowerCall()
612 MIB.addUse(Arg.Regs[0]); in lowerCall()
614 return MIB.constrainAllUses(MIRBuilder.getTII(), *ST->getRegisterInfo(), in lowerCall()
615 *ST->getRegBankInfo()); in lowerCall()