简体   繁体   English

如何使用LLVM C Api / llvm-fs绑定添加元数据节点

[英]How to add metadata nodes using the LLVM C Api/llvm-fs bindings

I'm trying to add metadata nodes to a program, either onto the instructions or as global metadata. 我试图将元数据节点添加到程序中,要么添加到指令中,要么添加为全局元数据。 How do I do this with the LLVM C API? 如何使用LLVM C API做到这一点? It now provides a function LLVMAddNamedMetadataOperand (as found from this question ) but I can't seem to see how to use it. 现在它提供了一个函数LLVMAddNamedMetadataOperand (从这个问题中找到),但是我似乎看不到如何使用它。 This is bound to addNamedMetadataOperand in the llvm-fs bindings. 这绑定到llvm-fs绑定中的addNamedMetadataOperand I tried this: 我尝试了这个:

addNamedMetadataOperand myModule "foobar" (mDString "cat" 3u)

expecting it to make some metadata node called foobar but it doesn't work - complains about cast errors. 期望它生成一些称为foobar元数据节点,但它不起作用-抱怨转换错误。 I thought maybe you were supposed to use addNamedMetadataOperand on an instruction, so I tried: 我认为也许您应该在一条指令上使用addNamedMetadataOperand ,所以我尝试了:

let ret = buildRet bldr (constInt i32 0UL)
addNamedMetadataOperand myModule "foobar" ret

but it didn't like this either. 但它也不喜欢这样。

I added two new "F# friendly functions": mdNode and mdNodeInContext in this commit . 我在此commit中添加了两个新的“ F#友好函数”:mdNode和mdNodeInContext。 With that commit I can modify your example code to: 通过该提交,我可以将示例代码修改为:

open LLVM.Core
open LLVM.Generated.Core
open LLVM.Generated.BitWriter

let i32 = int32Type ()
let i32zero = constInt i32 0UL false

[<EntryPoint>]
let main argv =
    // Set up the module/function
    let module_ = moduleCreateWithName "foobar"
    //let context = getModuleContext module_
    let funcTy = functionType i32 [||]
    let func = addFunction module_ "main" funcTy
    let bldr = createBuilder ()

    let entry = appendBasicBlock func "entry"
    positionBuilderAtEnd bldr entry

    // Make a Metadata node and try and attach it to a ret
    //let mdnode = mDStringInContext context "bazquux" 7u
    let mdstring = mDString "bazquux" 7u
    let ret = buildRet bldr i32zero
    // From http://llvm.org/docs/doxygen/html/classllvm_1_1LLVMContext.html
    // MD_dbg = 0, MD_tbaa = 1, MD_prof = 2, MD_fpmath = 3, MD_range = 4, MD_tbaa_struct = 5
    // Fails here
    //setMetadata ret 0u mdnode
    let myMDName = "my_MD_kind"
    setMetadata ret (getMDKindID myMDName (uint32 myMDName.Length)) (mdNode [|mdstring|])

    // Save bitcode to file
    writeBitcodeToFile module_ "metadatatest.bc"

Which gives the bitcode: 给出位代码:

; ModuleID = 'metadatatest.bc'

define i32 @main() {
entry:
  ret i32 0, !my_MD_kind !0
}

!0 = metadata !{metadata !"bazquux"}

I used getMDKindID rather than one of the pre-defined MD kinds because when I was using 0u I was getting no metadata output. 我使用getMDKindID而不是使用预定义的MD类型之一,因为当我使用0u时,没有任何元数据输出。 I haven't looked deep into why but from looking at http://llvm.org/docs/LangRef.html#metadata it seems that the predefined metadata types have some constraints that the instruction it was applied to wasn't meeting. 我没有深入探讨为什么,但是从查看http://llvm.org/docs/LangRef.html#metadata来看,预定义的元数据类型似乎受到一些限制,即所应用的指令无法满足要求。 Anyhow, let me know if you see more problems with this. 无论如何,请告诉我您是否还有其他问题。 It's not a part of the API that I'm using at the moment but I do want it to work as well as possible. 目前,它不是我正在使用的API的一部分,但我确实希望它尽可能地正常工作。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM