Closed ghost closed 8 months ago
I modified my code. It compiles but the result is not what is expected:
func TestIntGEN(*testing.T) {
// Create a new LLVM IR module.
m := ir.NewModule()
hello := constant.NewCharArrayFromString("Hello, %d!\n\x00")
ten := constant.NewInt(types.I32, 10)
numb := m.NewGlobalDef("ten", ten)
str := m.NewGlobalDef("str", hello)
// Add external function declaration of printf.
printf := m.NewFunc("printf", types.I32, ir.NewParam("", types.NewPointer(types.I8)))
printf.Sig.Variadic = true
main := m.NewFunc("main", types.I32)
entry := main.NewBlock("")
// Cast *[15]i8 to *i8.
zero := constant.NewInt(types.I64, 0)
// allocate memory for ten
tenPtr := entry.NewAlloca(numb.Typ)
// store the pointer to ten in tenPtr
entry.NewStore(numb, tenPtr)
gep := constant.NewGetElementPtr(hello.Typ, str, zero, zero)
entry.NewCall(printf, gep, tenPtr)
entry.NewRet(constant.NewInt(types.I32, 0))
fmt.Println(m)
}
It looks like the pointer is accessing a random value instead. Someone could help?
The resulting LLVM-IR is:
@ten = global i32 10
@str = global [12 x i8] c"Hello, %d!\0A\00"
declare i32 @printf(i8* %0, ...)
define i32 @main() {
0:
%1 = alloca i32*
store i32* @ten, i32** %1
%2 = call i32 (i8*, ...) @printf(i8* getelementptr ([12 x i8], [12 x i8]* @str, i64 0, i64 0), i32** %1)
ret i32 0
}
Hi @dequeb,
I updated the example code you posted to make it print "Hello, 10!". The random value that was printed was the pointer address, rather than the value stored within the local variable. Hope this helps!
Contents of foo.go
:
package main
import (
"fmt"
"github.com/llir/llvm/ir"
"github.com/llir/llvm/ir/constant"
"github.com/llir/llvm/ir/types"
)
func main() {
// Create a new LLVM IR module.
m := ir.NewModule()
hello := constant.NewCharArrayFromString("Hello, %d!\n\x00")
ten := constant.NewInt(types.I32, 10)
numb := m.NewGlobalDef("ten", ten)
str := m.NewGlobalDef("str", hello)
// Add external function declaration of printf.
printf := m.NewFunc("printf", types.I32, ir.NewParam("", types.NewPointer(types.I8)))
printf.Sig.Variadic = true
main := m.NewFunc("main", types.I32)
entry := main.NewBlock("")
// Cast *[15]i8 to *i8.
zero := constant.NewInt(types.I64, 0)
// load value of global variable to local variable.
tenVal := entry.NewLoad(types.I32, numb)
gep := constant.NewGetElementPtr(hello.Typ, str, zero, zero)
entry.NewCall(printf, gep, tenVal)
entry.NewRet(constant.NewInt(types.I32, 0))
fmt.Println(m)
}
Output LLVM IR (foo.ll
):
@ten = global i32 10
@str = global [12 x i8] c"Hello, %d!\0A\00"
declare i32 @printf(i8* %0, ...)
define i32 @main() {
0:
%1 = load i32, i32* @ten
%2 = call i32 (i8*, ...) @printf(i8* getelementptr ([12 x i8], [12 x i8]* @str, i64 0, i64 0), i32 %1)
ret i32 0
}
Output from lli
:
$ go run foo.go > foo.ll
$ lli foo.ll
Hello, 10!
Thank you.
De : Robin @.> Envoyé : Sunday, March 10, 2024 8:38:13 PM À : llir/llvm @.> Cc : dequeb @.>; Mention @.> Objet : Re: [llir/llvm] Hello 10 instead of Hello world. Passing a IntPtr to printf (go - LLIR/LLVM) (Issue #234)
Hi @dequebhttps://github.com/dequeb,
I updated the example code you posted to make it print "Hello, 10!". The random value that was printed was the pointer address, rather than the value stored within the local variable. Hope this helps!
Contents of foo.go:
package main
import ( "fmt"
"github.com/llir/llvm/ir"
"github.com/llir/llvm/ir/constant"
"github.com/llir/llvm/ir/types"
)
func main() { // Create a new LLVM IR module. m := ir.NewModule() hello := constant.NewCharArrayFromString("Hello, %d!\n\x00") ten := constant.NewInt(types.I32, 10) numb := m.NewGlobalDef("ten", ten) str := m.NewGlobalDef("str", hello) // Add external function declaration of printf. printf := m.NewFunc("printf", types.I32, ir.NewParam("", types.NewPointer(types.I8))) printf.Sig.Variadic = true main := m.NewFunc("main", types.I32) entry := main.NewBlock("") // Cast [15]i8 to i8. zero := constant.NewInt(types.I64, 0) // allocate memory for ten tenVal := entry.NewLoad(types.I32, numb) gep := constant.NewGetElementPtr(hello.Typ, str, zero, zero) entry.NewCall(printf, gep, tenVal) entry.NewRet(constant.NewInt(types.I32, 0)) fmt.Println(m) }
Output LLVM IR (foo.ll):
@ten = global i32 10 @str = global [12 x i8] c"Hello, %d!\0A\00"
declare i32 @printf(i8* %0, ...)
define i32 @main() { 0: %1 = load i32, i32 @ten %2 = call i32 (i8, ...) @printf(i8 getelementptr ([12 x i8], [12 x i8] @str, i64 0, i64 0), i32 %1) ret i32 0 }
Output from lli:
$ go run foo.go > foo.ll $ lli foo.ll Hello, 10!
— Reply to this email directly, view it on GitHubhttps://github.com/llir/llvm/issues/234#issuecomment-1987439311, or unsubscribehttps://github.com/notifications/unsubscribe-auth/AUS3HCKCTOUX6WEXWVAMXFDYXT4HLAVCNFSM6AAAAABEOEBDY6VHI2DSMVQWIX3LMV43OSLTON2WKQ3PNVWWK3TUHMYTSOBXGQZTSMZRGE. You are receiving this because you were mentioned.Message ID: @.***>
I, I'm new to LLIR/LLVM Based on the example Hello Word, I'd like to pass other types of variables (like int here). The following program crashes at line 25 with the error
invalid gep source type; expected pointer or vector of pointers type, got *types.IntType
. Could someone help me?