我与LLVM-Haskell绑定的问题是我得到“重复”名称。我认为解释我的问题的最好方法是用一个小的具体例子(注意这个例子是人为设计的,对于这样一个小例子,它有简单的方法......但它确实指出了我的问题)。Haskell LLVM - 创建重复函数
putc :: TFunction (Int32 -> IO Word32)
putc = newNamedFunction ExternalLinkage "putchar"
simple :: TFunction (Int32 -> IO Word32)
simple = do
internalputc <- putc
createNamedFunction ExternalLinkage "simple" $ \x -> do
call internalputc x
call internalputc x
ret (0 :: Word32)
easy :: TFunction (Int32 -> IO Word32)
easy = do
internalputc <- putc
internalsimple <- simple
createNamedFunction ExternalLinkage "easy" $ \x -> do
call internalsimple x
y <- add x (42 :: Int32)
call internalputc y
ret (0 :: Word32)
main :: IO()
main = do
m <- newNamedModule "Main"
defineModule m easy
writeBitcodeToFile "SillyLib" m
如果你现在运行这个程序哈斯克尔(你需要一些像进口Data.Int/Word和LLVM.Core),你会得到下面的输出。
; ModuleID = 'SillyLib'
declare i32 @putchar(i32)
declare i32 @putchar1(i32)
define i32 @simple(i32) {
_L1:
%1 = call i32 @putchar1(i32 %0)
%2 = call i32 @putchar1(i32 %0)
ret i32 0
}
define i32 @easy(i32) {
_L1:
%1 = call i32 @simple(i32 %0)
%2 = add i32 %0, 42
%3 = call i32 @putchar(i32 %2)
ret i32 0
}
的问题是,在IR中,(外部)的putchar被声明两次,但第二次与所述名称putchar1。我有一个很好的理解,为什么这是,但不是一个很好的理解一个很好的普遍的方式。即我不想将所有内容都放在一个巨大的CodeGenModule中。
这给我带来了另一个相关的问题。 LLVM-Haskell绑定是否适合构建编译器的后端。也许有一个合理的解决方案上面 - 我可以找出一种方法来使用它...但似乎更简单,只需手写红外代码...
这是一个不错的解决方案。 – 2013-04-24 22:46:29
如果您要求库声明“putchar”函数两次,则声明两次。这不是一个错误。这里提出的解决方案是正确的。如果你有更多的功能需要维护,你可以使用getModuleValues获取模块的声明功能。请参阅llvm:example/Vector.hs。但要小心这个错误:https://github.com/bos/llvm/issues/78 – Lemming 2016-08-02 08:10:59