@@ -160,7 +160,7 @@ static void addNamedMetadataStringSet(LLVMContext *Context, Module *M,
160
160
NamedMD->addOperand (MDNode::get (*Context, ValueVec));
161
161
}
162
162
163
- static void addOCLKernelArgumentMetadata (
163
+ static void addKernelArgumentMetadata (
164
164
LLVMContext *Context, const std::string &MDName, SPIRVFunction *BF,
165
165
llvm::Function *Fn,
166
166
std::function<Metadata *(SPIRVFunctionParameter *)> ForeachFnArg) {
@@ -3570,13 +3570,83 @@ void SPIRVToLLVM::transGlobalAnnotations() {
3570
3570
}
3571
3571
}
3572
3572
3573
+ static llvm::MDNode *
3574
+ transDecorationsToMetadataList (llvm::LLVMContext *Context,
3575
+ std::vector<SPIRVDecorate const *> Decorates) {
3576
+ SmallVector<Metadata *, 4 > MDs;
3577
+ MDs.reserve (Decorates.size ());
3578
+ for (const auto *Deco : Decorates) {
3579
+ std::vector<Metadata *> OPs;
3580
+ auto *KindMD = ConstantAsMetadata::get (
3581
+ ConstantInt::get (Type::getInt32Ty (*Context), Deco->getDecorateKind ()));
3582
+ OPs.push_back (KindMD);
3583
+ switch (static_cast <size_t >(Deco->getDecorateKind ())) {
3584
+ case DecorationLinkageAttributes: {
3585
+ const auto *const LinkAttrDeco =
3586
+ static_cast <const SPIRVDecorateLinkageAttr *>(Deco);
3587
+ auto *const LinkNameMD =
3588
+ MDString::get (*Context, LinkAttrDeco->getLinkageName ());
3589
+ auto *const LinkTypeMD = ConstantAsMetadata::get (ConstantInt::get (
3590
+ Type::getInt32Ty (*Context), LinkAttrDeco->getLinkageType ()));
3591
+ OPs.push_back (LinkNameMD);
3592
+ OPs.push_back (LinkTypeMD);
3593
+ break ;
3594
+ }
3595
+ case DecorationMergeINTEL: {
3596
+ const auto MergeAttrLits = Deco->getVecLiteral ();
3597
+ std::string FirstString = getString (MergeAttrLits);
3598
+ std::string SecondString =
3599
+ getString (MergeAttrLits.cbegin () + getVec (FirstString).size (),
3600
+ MergeAttrLits.cend ());
3601
+ OPs.push_back (MDString::get (*Context, FirstString));
3602
+ OPs.push_back (MDString::get (*Context, SecondString));
3603
+ break ;
3604
+ }
3605
+ case DecorationMemoryINTEL:
3606
+ case DecorationUserSemantic: {
3607
+ auto *const StrMD =
3608
+ MDString::get (*Context, getString (Deco->getVecLiteral ()));
3609
+ OPs.push_back (StrMD);
3610
+ break ;
3611
+ }
3612
+ default : {
3613
+ for (const SPIRVWord Lit : Deco->getVecLiteral ()) {
3614
+ auto *const LitMD = ConstantAsMetadata::get (
3615
+ ConstantInt::get (Type::getInt32Ty (*Context), Lit));
3616
+ OPs.push_back (LitMD);
3617
+ }
3618
+ break ;
3619
+ }
3620
+ }
3621
+ MDs.push_back (MDNode::get (*Context, OPs));
3622
+ }
3623
+ return MDNode::get (*Context, MDs);
3624
+ }
3625
+
3626
+ void SPIRVToLLVM::transVarDecorationsToMetadata (SPIRVValue *BV, Value *V) {
3627
+ if (!BV->isVariable ())
3628
+ return ;
3629
+
3630
+ if (auto *GV = dyn_cast<GlobalVariable>(V)) {
3631
+ std::vector<SPIRVDecorate const *> Decorates = BV->getDecorations ();
3632
+ if (!Decorates.empty ()) {
3633
+ MDNode *MDList = transDecorationsToMetadataList (Context, Decorates);
3634
+ GV->setMetadata (SPIRV_MD_DECORATIONS, MDList);
3635
+ }
3636
+ }
3637
+ }
3638
+
3573
3639
bool SPIRVToLLVM::transDecoration (SPIRVValue *BV, Value *V) {
3574
3640
if (!transAlign (BV, V))
3575
3641
return false ;
3576
3642
3577
3643
transIntelFPGADecorations (BV, V);
3578
3644
transMemAliasingINTELDecorations (BV, V);
3579
3645
3646
+ // Decoration metadata is only enabled in SPIR-V friendly mode
3647
+ if (BM->getDesiredBIsRepresentation () == BIsRepresentation::SPIRVFriendlyIR)
3648
+ transVarDecorationsToMetadata (BV, V);
3649
+
3580
3650
DbgTran->transDbgInfo (BV, V);
3581
3651
return true ;
3582
3652
}
@@ -3708,6 +3778,23 @@ static bool transKernelArgTypeMedataFromString(LLVMContext *Ctx,
3708
3778
return true ;
3709
3779
}
3710
3780
3781
+ void SPIRVToLLVM::transFunctionDecorationsToMetadata (SPIRVFunction *BF,
3782
+ Function *F) {
3783
+ size_t TotalParameterDecorations = 0 ;
3784
+ BF->foreachArgument ([&](SPIRVFunctionParameter *Arg) {
3785
+ TotalParameterDecorations += Arg->getNumDecorations ();
3786
+ });
3787
+ if (TotalParameterDecorations == 0 )
3788
+ return ;
3789
+
3790
+ // Generate metadata for spirv.ParameterDecorations
3791
+ addKernelArgumentMetadata (Context, SPIRV_MD_PARAMETER_DECORATIONS, BF, F,
3792
+ [=](SPIRVFunctionParameter *Arg) {
3793
+ return transDecorationsToMetadataList (
3794
+ Context, Arg->getDecorations ());
3795
+ });
3796
+ }
3797
+
3711
3798
bool SPIRVToLLVM::transMetadata () {
3712
3799
SmallVector<Function *, 2 > CtorKernels;
3713
3800
for (unsigned I = 0 , E = BM->getNumFunctions (); I != E; ++I) {
@@ -3719,6 +3806,10 @@ bool SPIRVToLLVM::transMetadata() {
3719
3806
transVectorComputeMetadata (BF);
3720
3807
transFPGAFunctionMetadata (BF, F);
3721
3808
3809
+ // Decoration metadata is only enabled in SPIR-V friendly mode
3810
+ if (BM->getDesiredBIsRepresentation () == BIsRepresentation::SPIRVFriendlyIR)
3811
+ transFunctionDecorationsToMetadata (BF, F);
3812
+
3722
3813
if (BF->hasDecorate (internal::DecorationCallableFunctionINTEL))
3723
3814
F->addFnAttr (kVCMetadata ::VCCallable);
3724
3815
if (isKernel (BF) &&
@@ -3823,7 +3914,7 @@ bool SPIRVToLLVM::transOCLMetadata(SPIRVFunction *BF) {
3823
3914
return true ;
3824
3915
3825
3916
// Generate metadata for kernel_arg_addr_space
3826
- addOCLKernelArgumentMetadata (
3917
+ addKernelArgumentMetadata (
3827
3918
Context, SPIR_MD_KERNEL_ARG_ADDR_SPACE, BF, F,
3828
3919
[=](SPIRVFunctionParameter *Arg) {
3829
3920
SPIRVType *ArgTy = Arg->getType ();
@@ -3836,31 +3927,31 @@ bool SPIRVToLLVM::transOCLMetadata(SPIRVFunction *BF) {
3836
3927
ConstantInt::get (Type::getInt32Ty (*Context), AS));
3837
3928
});
3838
3929
// Generate metadata for kernel_arg_access_qual
3839
- addOCLKernelArgumentMetadata (Context, SPIR_MD_KERNEL_ARG_ACCESS_QUAL, BF, F,
3840
- [=](SPIRVFunctionParameter *Arg) {
3841
- std::string Qual;
3842
- auto T = Arg->getType ();
3843
- if (T->isTypeOCLImage ()) {
3844
- auto ST = static_cast <SPIRVTypeImage *>(T);
3845
- Qual = transOCLImageTypeAccessQualifier (ST);
3846
- } else if (T->isTypePipe ()) {
3847
- auto PT = static_cast <SPIRVTypePipe *>(T);
3848
- Qual = transOCLPipeTypeAccessQualifier (PT);
3849
- } else
3850
- Qual = " none" ;
3851
- return MDString::get (*Context, Qual);
3852
- });
3930
+ addKernelArgumentMetadata (Context, SPIR_MD_KERNEL_ARG_ACCESS_QUAL, BF, F,
3931
+ [=](SPIRVFunctionParameter *Arg) {
3932
+ std::string Qual;
3933
+ auto * T = Arg->getType ();
3934
+ if (T->isTypeOCLImage ()) {
3935
+ auto * ST = static_cast <SPIRVTypeImage *>(T);
3936
+ Qual = transOCLImageTypeAccessQualifier (ST);
3937
+ } else if (T->isTypePipe ()) {
3938
+ auto * PT = static_cast <SPIRVTypePipe *>(T);
3939
+ Qual = transOCLPipeTypeAccessQualifier (PT);
3940
+ } else
3941
+ Qual = " none" ;
3942
+ return MDString::get (*Context, Qual);
3943
+ });
3853
3944
// Generate metadata for kernel_arg_type
3854
3945
if (!transKernelArgTypeMedataFromString (Context, BM, F,
3855
3946
SPIR_MD_KERNEL_ARG_TYPE))
3856
- addOCLKernelArgumentMetadata (Context, SPIR_MD_KERNEL_ARG_TYPE, BF, F,
3857
- [=](SPIRVFunctionParameter *Arg) {
3858
- return transOCLKernelArgTypeName (Arg);
3859
- });
3947
+ addKernelArgumentMetadata (Context, SPIR_MD_KERNEL_ARG_TYPE, BF, F,
3948
+ [=](SPIRVFunctionParameter *Arg) {
3949
+ return transOCLKernelArgTypeName (Arg);
3950
+ });
3860
3951
// Generate metadata for kernel_arg_type_qual
3861
3952
if (!transKernelArgTypeMedataFromString (Context, BM, F,
3862
3953
SPIR_MD_KERNEL_ARG_TYPE_QUAL))
3863
- addOCLKernelArgumentMetadata (
3954
+ addKernelArgumentMetadata (
3864
3955
Context, SPIR_MD_KERNEL_ARG_TYPE_QUAL, BF, F,
3865
3956
[=](SPIRVFunctionParameter *Arg) {
3866
3957
std::string Qual;
@@ -3878,17 +3969,16 @@ bool SPIRVToLLVM::transOCLMetadata(SPIRVFunction *BF) {
3878
3969
return MDString::get (*Context, Qual);
3879
3970
});
3880
3971
// Generate metadata for kernel_arg_base_type
3881
- addOCLKernelArgumentMetadata (Context, SPIR_MD_KERNEL_ARG_BASE_TYPE, BF, F,
3882
- [=](SPIRVFunctionParameter *Arg) {
3883
- return transOCLKernelArgTypeName (Arg);
3884
- });
3972
+ addKernelArgumentMetadata (Context, SPIR_MD_KERNEL_ARG_BASE_TYPE, BF, F,
3973
+ [=](SPIRVFunctionParameter *Arg) {
3974
+ return transOCLKernelArgTypeName (Arg);
3975
+ });
3885
3976
// Generate metadata for kernel_arg_name
3886
3977
if (BM->isGenArgNameMDEnabled ()) {
3887
- addOCLKernelArgumentMetadata (Context, SPIR_MD_KERNEL_ARG_NAME, BF, F,
3888
- [=](SPIRVFunctionParameter *Arg) {
3889
- return MDString::get (*Context,
3890
- Arg->getName ());
3891
- });
3978
+ addKernelArgumentMetadata (Context, SPIR_MD_KERNEL_ARG_NAME, BF, F,
3979
+ [=](SPIRVFunctionParameter *Arg) {
3980
+ return MDString::get (*Context, Arg->getName ());
3981
+ });
3892
3982
}
3893
3983
// Generate metadata for kernel_arg_buffer_location
3894
3984
addBufferLocationMetadata (Context, BF, F, [=](SPIRVFunctionParameter *Arg) {
0 commit comments