@@ -160,7 +160,7 @@ static void addNamedMetadataStringSet(LLVMContext *Context, Module *M,
160160 NamedMD->addOperand (MDNode::get (*Context, ValueVec));
161161}
162162
163- static void addOCLKernelArgumentMetadata (
163+ static void addKernelArgumentMetadata (
164164 LLVMContext *Context, const std::string &MDName, SPIRVFunction *BF,
165165 llvm::Function *Fn,
166166 std::function<Metadata *(SPIRVFunctionParameter *)> ForeachFnArg) {
@@ -3553,13 +3553,83 @@ void SPIRVToLLVM::transGlobalAnnotations() {
35533553 }
35543554}
35553555
3556+ static llvm::MDNode *
3557+ transDecorationsToMetadataList (llvm::LLVMContext *Context,
3558+ std::vector<SPIRVDecorate const *> Decorates) {
3559+ SmallVector<Metadata *, 4 > MDs;
3560+ MDs.reserve (Decorates.size ());
3561+ for (const auto *Deco : Decorates) {
3562+ std::vector<Metadata *> OPs;
3563+ auto *KindMD = ConstantAsMetadata::get (
3564+ ConstantInt::get (Type::getInt32Ty (*Context), Deco->getDecorateKind ()));
3565+ OPs.push_back (KindMD);
3566+ switch (static_cast <size_t >(Deco->getDecorateKind ())) {
3567+ case DecorationLinkageAttributes: {
3568+ const auto *const LinkAttrDeco =
3569+ static_cast <const SPIRVDecorateLinkageAttr *>(Deco);
3570+ auto *const LinkNameMD =
3571+ MDString::get (*Context, LinkAttrDeco->getLinkageName ());
3572+ auto *const LinkTypeMD = ConstantAsMetadata::get (ConstantInt::get (
3573+ Type::getInt32Ty (*Context), LinkAttrDeco->getLinkageType ()));
3574+ OPs.push_back (LinkNameMD);
3575+ OPs.push_back (LinkTypeMD);
3576+ break ;
3577+ }
3578+ case DecorationMergeINTEL: {
3579+ const auto MergeAttrLits = Deco->getVecLiteral ();
3580+ std::string FirstString = getString (MergeAttrLits);
3581+ std::string SecondString =
3582+ getString (MergeAttrLits.cbegin () + getVec (FirstString).size (),
3583+ MergeAttrLits.cend ());
3584+ OPs.push_back (MDString::get (*Context, FirstString));
3585+ OPs.push_back (MDString::get (*Context, SecondString));
3586+ break ;
3587+ }
3588+ case DecorationMemoryINTEL:
3589+ case DecorationUserSemantic: {
3590+ auto *const StrMD =
3591+ MDString::get (*Context, getString (Deco->getVecLiteral ()));
3592+ OPs.push_back (StrMD);
3593+ break ;
3594+ }
3595+ default : {
3596+ for (const SPIRVWord Lit : Deco->getVecLiteral ()) {
3597+ auto *const LitMD = ConstantAsMetadata::get (
3598+ ConstantInt::get (Type::getInt32Ty (*Context), Lit));
3599+ OPs.push_back (LitMD);
3600+ }
3601+ break ;
3602+ }
3603+ }
3604+ MDs.push_back (MDNode::get (*Context, OPs));
3605+ }
3606+ return MDNode::get (*Context, MDs);
3607+ }
3608+
3609+ void SPIRVToLLVM::transVarDecorationsToMetadata (SPIRVValue *BV, Value *V) {
3610+ if (!BV->isVariable ())
3611+ return ;
3612+
3613+ if (auto *GV = dyn_cast<GlobalVariable>(V)) {
3614+ std::vector<SPIRVDecorate const *> Decorates = BV->getDecorations ();
3615+ if (!Decorates.empty ()) {
3616+ MDNode *MDList = transDecorationsToMetadataList (Context, Decorates);
3617+ GV->setMetadata (SPIRV_MD_DECORATIONS, MDList);
3618+ }
3619+ }
3620+ }
3621+
35563622bool SPIRVToLLVM::transDecoration (SPIRVValue *BV, Value *V) {
35573623 if (!transAlign (BV, V))
35583624 return false ;
35593625
35603626 transIntelFPGADecorations (BV, V);
35613627 transMemAliasingINTELDecorations (BV, V);
35623628
3629+ // Decoration metadata is only enabled in SPIR-V friendly mode
3630+ if (BM->getDesiredBIsRepresentation () == BIsRepresentation::SPIRVFriendlyIR)
3631+ transVarDecorationsToMetadata (BV, V);
3632+
35633633 DbgTran->transDbgInfo (BV, V);
35643634 return true ;
35653635}
@@ -3691,6 +3761,23 @@ static bool transKernelArgTypeMedataFromString(LLVMContext *Ctx,
36913761 return true ;
36923762}
36933763
3764+ void SPIRVToLLVM::transFunctionDecorationsToMetadata (SPIRVFunction *BF,
3765+ Function *F) {
3766+ size_t TotalParameterDecorations = 0 ;
3767+ BF->foreachArgument ([&](SPIRVFunctionParameter *Arg) {
3768+ TotalParameterDecorations += Arg->getNumDecorations ();
3769+ });
3770+ if (TotalParameterDecorations == 0 )
3771+ return ;
3772+
3773+ // Generate metadata for spirv.ParameterDecorations
3774+ addKernelArgumentMetadata (Context, SPIRV_MD_PARAMETER_DECORATIONS, BF, F,
3775+ [=](SPIRVFunctionParameter *Arg) {
3776+ return transDecorationsToMetadataList (
3777+ Context, Arg->getDecorations ());
3778+ });
3779+ }
3780+
36943781bool SPIRVToLLVM::transMetadata () {
36953782 SmallVector<Function *, 2 > CtorKernels;
36963783 for (unsigned I = 0 , E = BM->getNumFunctions (); I != E; ++I) {
@@ -3702,6 +3789,10 @@ bool SPIRVToLLVM::transMetadata() {
37023789 transVectorComputeMetadata (BF);
37033790 transFPGAFunctionMetadata (BF, F);
37043791
3792+ // Decoration metadata is only enabled in SPIR-V friendly mode
3793+ if (BM->getDesiredBIsRepresentation () == BIsRepresentation::SPIRVFriendlyIR)
3794+ transFunctionDecorationsToMetadata (BF, F);
3795+
37053796 if (BF->hasDecorate (internal::DecorationCallableFunctionINTEL))
37063797 F->addFnAttr (kVCMetadata ::VCCallable);
37073798 if (isKernel (BF) &&
@@ -3806,7 +3897,7 @@ bool SPIRVToLLVM::transOCLMetadata(SPIRVFunction *BF) {
38063897 return true ;
38073898
38083899 // Generate metadata for kernel_arg_addr_space
3809- addOCLKernelArgumentMetadata (
3900+ addKernelArgumentMetadata (
38103901 Context, SPIR_MD_KERNEL_ARG_ADDR_SPACE, BF, F,
38113902 [=](SPIRVFunctionParameter *Arg) {
38123903 SPIRVType *ArgTy = Arg->getType ();
@@ -3819,31 +3910,31 @@ bool SPIRVToLLVM::transOCLMetadata(SPIRVFunction *BF) {
38193910 ConstantInt::get (Type::getInt32Ty (*Context), AS));
38203911 });
38213912 // Generate metadata for kernel_arg_access_qual
3822- addOCLKernelArgumentMetadata (Context, SPIR_MD_KERNEL_ARG_ACCESS_QUAL, BF, F,
3823- [=](SPIRVFunctionParameter *Arg) {
3824- std::string Qual;
3825- auto T = Arg->getType ();
3826- if (T->isTypeOCLImage ()) {
3827- auto ST = static_cast <SPIRVTypeImage *>(T);
3828- Qual = transOCLImageTypeAccessQualifier (ST);
3829- } else if (T->isTypePipe ()) {
3830- auto PT = static_cast <SPIRVTypePipe *>(T);
3831- Qual = transOCLPipeTypeAccessQualifier (PT);
3832- } else
3833- Qual = " none" ;
3834- return MDString::get (*Context, Qual);
3835- });
3913+ addKernelArgumentMetadata (Context, SPIR_MD_KERNEL_ARG_ACCESS_QUAL, BF, F,
3914+ [=](SPIRVFunctionParameter *Arg) {
3915+ std::string Qual;
3916+ auto * T = Arg->getType ();
3917+ if (T->isTypeOCLImage ()) {
3918+ auto * ST = static_cast <SPIRVTypeImage *>(T);
3919+ Qual = transOCLImageTypeAccessQualifier (ST);
3920+ } else if (T->isTypePipe ()) {
3921+ auto * PT = static_cast <SPIRVTypePipe *>(T);
3922+ Qual = transOCLPipeTypeAccessQualifier (PT);
3923+ } else
3924+ Qual = " none" ;
3925+ return MDString::get (*Context, Qual);
3926+ });
38363927 // Generate metadata for kernel_arg_type
38373928 if (!transKernelArgTypeMedataFromString (Context, BM, F,
38383929 SPIR_MD_KERNEL_ARG_TYPE))
3839- addOCLKernelArgumentMetadata (Context, SPIR_MD_KERNEL_ARG_TYPE, BF, F,
3840- [=](SPIRVFunctionParameter *Arg) {
3841- return transOCLKernelArgTypeName (Arg);
3842- });
3930+ addKernelArgumentMetadata (Context, SPIR_MD_KERNEL_ARG_TYPE, BF, F,
3931+ [=](SPIRVFunctionParameter *Arg) {
3932+ return transOCLKernelArgTypeName (Arg);
3933+ });
38433934 // Generate metadata for kernel_arg_type_qual
38443935 if (!transKernelArgTypeMedataFromString (Context, BM, F,
38453936 SPIR_MD_KERNEL_ARG_TYPE_QUAL))
3846- addOCLKernelArgumentMetadata (
3937+ addKernelArgumentMetadata (
38473938 Context, SPIR_MD_KERNEL_ARG_TYPE_QUAL, BF, F,
38483939 [=](SPIRVFunctionParameter *Arg) {
38493940 std::string Qual;
@@ -3861,17 +3952,16 @@ bool SPIRVToLLVM::transOCLMetadata(SPIRVFunction *BF) {
38613952 return MDString::get (*Context, Qual);
38623953 });
38633954 // Generate metadata for kernel_arg_base_type
3864- addOCLKernelArgumentMetadata (Context, SPIR_MD_KERNEL_ARG_BASE_TYPE, BF, F,
3865- [=](SPIRVFunctionParameter *Arg) {
3866- return transOCLKernelArgTypeName (Arg);
3867- });
3955+ addKernelArgumentMetadata (Context, SPIR_MD_KERNEL_ARG_BASE_TYPE, BF, F,
3956+ [=](SPIRVFunctionParameter *Arg) {
3957+ return transOCLKernelArgTypeName (Arg);
3958+ });
38683959 // Generate metadata for kernel_arg_name
38693960 if (BM->isGenArgNameMDEnabled ()) {
3870- addOCLKernelArgumentMetadata (Context, SPIR_MD_KERNEL_ARG_NAME, BF, F,
3871- [=](SPIRVFunctionParameter *Arg) {
3872- return MDString::get (*Context,
3873- Arg->getName ());
3874- });
3961+ addKernelArgumentMetadata (Context, SPIR_MD_KERNEL_ARG_NAME, BF, F,
3962+ [=](SPIRVFunctionParameter *Arg) {
3963+ return MDString::get (*Context, Arg->getName ());
3964+ });
38753965 }
38763966 // Generate metadata for kernel_arg_buffer_location
38773967 addBufferLocationMetadata (Context, BF, F, [=](SPIRVFunctionParameter *Arg) {
0 commit comments