cl: _testpy/pow (multiargs)

This commit is contained in:
xushiwei
2024-05-15 08:44:00 +08:00
parent 120b507c75
commit 56269bd52b
4 changed files with 182 additions and 9 deletions

12
cl/_testpy/pow/in.go Normal file
View File

@@ -0,0 +1,12 @@
package main
import (
"github.com/goplus/llgo/c"
"github.com/goplus/llgo/py"
"github.com/goplus/llgo/py/math"
)
func main() {
x := math.Pow(py.Float(2), py.Float(3))
c.Printf(c.Str("pow(2, 3) = %f\n"), x.Float64())
}

58
cl/_testpy/pow/out.ll Normal file
View File

@@ -0,0 +1,58 @@
; ModuleID = 'main'
source_filename = "main"
@"main.init$guard" = global ptr null
@__llgo_argc = global ptr null
@__llgo_argv = global ptr null
@__llgo_py.math.pow = linkonce global ptr null
@0 = private unnamed_addr constant [16 x i8] c"pow(2, 3) = %f\0A\00", align 1
@__llgo_py.math = external global ptr
@1 = private unnamed_addr constant [4 x i8] c"pow\00", align 1
define void @main.init() {
_llgo_0:
%0 = load i1, ptr @"main.init$guard", align 1
br i1 %0, label %_llgo_2, label %_llgo_1
_llgo_1: ; preds = %_llgo_0
store i1 true, ptr @"main.init$guard", align 1
call void @"github.com/goplus/llgo/py/math.init"()
%1 = load ptr, ptr @__llgo_py.math, align 8
call void (ptr, ...) @llgoLoadPyModSyms(ptr %1, ptr @1, ptr @__llgo_py.math.pow, ptr null)
br label %_llgo_2
_llgo_2: ; preds = %_llgo_1, %_llgo_0
ret void
}
define void @main(i32 %0, ptr %1) {
_llgo_0:
call void @Py_Initialize()
store i32 %0, ptr @__llgo_argc, align 4
store ptr %1, ptr @__llgo_argv, align 8
call void @"github.com/goplus/llgo/internal/runtime.init"()
call void @main.init()
%2 = call ptr @PyFloat_FromDouble(double 2.000000e+00)
%3 = call ptr @PyFloat_FromDouble(double 3.000000e+00)
%4 = load ptr, ptr @__llgo_py.math.pow, align 8
%5 = call ptr (ptr, ...) @PyObject_CallFunctionObjArgs(ptr %4, ptr %2, ptr %3, ptr null)
%6 = call double @PyFloat_AsDouble(ptr %5)
%7 = call i32 (ptr, ...) @printf(ptr @0, double %6)
ret void
}
declare void @"github.com/goplus/llgo/py/math.init"()
declare void @"github.com/goplus/llgo/internal/runtime.init"()
declare ptr @PyFloat_FromDouble(double)
declare ptr @PyObject_CallFunctionObjArgs(ptr, ...)
declare double @PyFloat_AsDouble(ptr)
declare i32 @printf(ptr, ...)
declare void @llgoLoadPyModSyms(ptr, ...)
declare void @Py_Initialize()

View File

@@ -78,6 +78,11 @@ func (p Program) Null(t Type) Expr {
return Expr{llvm.ConstNull(t.ll), t} return Expr{llvm.ConstNull(t.ll), t}
} }
// PyNull returns a null *PyObject constant expression.
func (p Program) PyNull() Expr {
return p.Null(p.PyObjectPtr())
}
// BoolVal returns a boolean constant expression. // BoolVal returns a boolean constant expression.
func (p Program) BoolVal(v bool) Expr { func (p Program) BoolVal(v bool) Expr {
t := p.Bool() t := p.Bool()

View File

@@ -130,6 +130,7 @@ type aProgram struct {
voidPtr Type voidPtr Type
boolTy Type boolTy Type
cstrTy Type cstrTy Type
cintTy Type
stringTy Type stringTy Type
uintptrTy Type uintptrTy Type
intTy Type intTy Type
@@ -137,11 +138,17 @@ type aProgram struct {
pyObjPtr Type pyObjPtr Type
pyObjPPtr Type pyObjPPtr Type
pyImpTy *types.Signature pyImpTy *types.Signature
//pyNewList *types.Signature
//pyListSetI *types.Signature
//callArgs *types.Signature
callNoArgs *types.Signature callNoArgs *types.Signature
callOneArg *types.Signature callOneArg *types.Signature
callFOArgs *types.Signature
loadPyModS *types.Signature loadPyModS *types.Signature
paramObjPtr_ *types.Var
NeedRuntime bool NeedRuntime bool
NeedPyInit bool NeedPyInit bool
} }
@@ -328,6 +335,13 @@ func (p Program) Any() Type {
return p.anyTy return p.anyTy
} }
func (p Program) CInt() Type {
if p.cintTy == nil { // C.int
p.cintTy = p.rawType(types.Typ[types.Int32]) // TODO(xsw): support 64-bit
}
return p.cintTy
}
// Int returns int type. // Int returns int type.
func (p Program) Int() Type { func (p Program) Int() Type {
if p.intTy == nil { if p.intTy == nil {
@@ -475,12 +489,19 @@ func (p *Package) WriteFile(file string) (err error) {
// ----------------------------------------------------------------------------- // -----------------------------------------------------------------------------
func (p Program) paramObjPtr() *types.Var {
if p.paramObjPtr_ == nil {
objPtr := p.PyObjectPtr().raw.Type
p.paramObjPtr_ = types.NewParam(token.NoPos, nil, "", objPtr)
}
return p.paramObjPtr_
}
func (p Program) tyImportPyModule() *types.Signature { func (p Program) tyImportPyModule() *types.Signature {
if p.pyImpTy == nil { if p.pyImpTy == nil {
charPtr := types.NewPointer(types.Typ[types.Int8]) charPtr := types.NewPointer(types.Typ[types.Int8])
objPtr := p.PyObjectPtr().raw.Type
params := types.NewTuple(types.NewParam(token.NoPos, nil, "", charPtr)) params := types.NewTuple(types.NewParam(token.NoPos, nil, "", charPtr))
results := types.NewTuple(types.NewParam(token.NoPos, nil, "", objPtr)) results := types.NewTuple(p.paramObjPtr())
p.pyImpTy = types.NewSignatureType(nil, nil, nil, params, results, false) p.pyImpTy = types.NewSignatureType(nil, nil, nil, params, results, false)
} }
return p.pyImpTy return p.pyImpTy
@@ -488,9 +509,7 @@ func (p Program) tyImportPyModule() *types.Signature {
func (p Program) tyCallNoArgs() *types.Signature { func (p Program) tyCallNoArgs() *types.Signature {
if p.callNoArgs == nil { if p.callNoArgs == nil {
objPtr := p.PyObjectPtr().raw.Type params := types.NewTuple(p.paramObjPtr())
paramObjPtr := types.NewParam(token.NoPos, nil, "", objPtr)
params := types.NewTuple(paramObjPtr)
p.callNoArgs = types.NewSignatureType(nil, nil, nil, params, params, false) p.callNoArgs = types.NewSignatureType(nil, nil, nil, params, params, false)
} }
return p.callNoArgs return p.callNoArgs
@@ -498,8 +517,7 @@ func (p Program) tyCallNoArgs() *types.Signature {
func (p Program) tyCallOneArg() *types.Signature { func (p Program) tyCallOneArg() *types.Signature {
if p.callOneArg == nil { if p.callOneArg == nil {
objPtr := p.PyObjectPtr().raw.Type paramObjPtr := p.paramObjPtr()
paramObjPtr := types.NewParam(token.NoPos, nil, "", objPtr)
params := types.NewTuple(paramObjPtr, paramObjPtr) params := types.NewTuple(paramObjPtr, paramObjPtr)
results := types.NewTuple(paramObjPtr) results := types.NewTuple(paramObjPtr)
p.callOneArg = types.NewSignatureType(nil, nil, nil, params, results, false) p.callOneArg = types.NewSignatureType(nil, nil, nil, params, results, false)
@@ -507,6 +525,50 @@ func (p Program) tyCallOneArg() *types.Signature {
return p.callOneArg return p.callOneArg
} }
func (p Program) tyCallFunctionObjArgs() *types.Signature {
if p.callFOArgs == nil {
paramObjPtr := p.paramObjPtr()
params := types.NewTuple(paramObjPtr, VArg())
results := types.NewTuple(paramObjPtr)
p.callFOArgs = types.NewSignatureType(nil, nil, nil, params, results, false)
}
return p.callFOArgs
}
/*
func (p Program) tyCall() *types.Signature {
if p.callArgs == nil {
paramObjPtr := p.paramObjPtr()
params := types.NewTuple(paramObjPtr, paramObjPtr, paramObjPtr)
results := types.NewTuple(paramObjPtr)
p.callArgs = types.NewSignatureType(nil, nil, nil, params, results, false)
}
return p.callArgs
}
func (p Program) tyListSetItem() *types.Signature {
if p.pyListSetI == nil {
paramUintptr := types.NewParam(token.NoPos, nil, "", p.Uintptr().raw.Type)
paramCInt := types.NewParam(token.NoPos, nil, "", p.CInt().raw.Type)
paramObjPtr := p.paramObjPtr()
params := types.NewTuple(paramObjPtr, paramUintptr, paramObjPtr)
results := types.NewTuple(paramCInt)
p.pyListSetI = types.NewSignatureType(nil, nil, nil, params, results, false)
}
return p.pyListSetI
}
func (p Program) tyNewList() *types.Signature {
if p.pyNewList == nil {
paramUintptr := types.NewParam(token.NoPos, nil, "", p.Uintptr().raw.Type)
params := types.NewTuple(paramUintptr)
results := types.NewTuple(p.paramObjPtr())
p.pyNewList = types.NewSignatureType(nil, nil, nil, params, results, false)
}
return p.pyNewList
}
*/
func (p Program) tyLoadPyModSyms() *types.Signature { func (p Program) tyLoadPyModSyms() *types.Signature {
if p.loadPyModS == nil { if p.loadPyModS == nil {
objPtr := p.PyObjectPtr().raw.Type objPtr := p.PyObjectPtr().raw.Type
@@ -586,11 +648,47 @@ func (b Builder) pyCall(fn Expr, args []Expr) (ret Expr) {
call := pkg.pyFunc("PyObject_CallOneArg", prog.tyCallOneArg()) call := pkg.pyFunc("PyObject_CallOneArg", prog.tyCallOneArg())
ret = b.Call(call, fn, args[0]) ret = b.Call(call, fn, args[0])
default: default:
panic("todo") call := pkg.pyFunc("PyObject_CallFunctionObjArgs", prog.tyCallFunctionObjArgs())
n = len(args)
callargs := make([]Expr, n+2)
callargs[0] = fn
copy(callargs[1:], args)
callargs[n+1] = prog.PyNull()
ret = b.Call(call, callargs...)
} }
return return
} }
/*
// PyNewList(n uintptr) *Object
func (b Builder) PyNewList(n Expr) (ret Expr) {
prog := b.Prog
pkg := b.Func.Pkg
fn := pkg.pyFunc("PyList_New", prog.tyNewList())
return b.Call(fn, n)
}
// PyListSetItem(list *Object, index uintptr, item *Object) c.Int
func (b Builder) PyListSetItem(list, index, item Expr) (ret Expr) {
prog := b.Prog
pkg := b.Func.Pkg
fn := pkg.pyFunc("PyList_SetItem", prog.tyListSetItem())
return b.Call(fn, list, index, item)
}
// PyList(items ...*Object) *Object
func (b Builder) PyList(args ...Expr) (ret Expr) {
prog := b.Prog
n := len(args)
uintPtr := prog.Uintptr()
list := b.PyNewList(prog.IntVal(uint64(n), uintPtr))
for i, arg := range args {
b.PyListSetItem(list, prog.IntVal(uint64(i), uintPtr), arg)
}
return list
}
*/
// CallPyInit calls Py_Initialize. // CallPyInit calls Py_Initialize.
func (b Builder) CallPyInit() (ret Expr) { func (b Builder) CallPyInit() (ret Expr) {
fn := b.Func.Pkg.pyFunc("Py_Initialize", NoArgsNoRet) fn := b.Func.Pkg.pyFunc("Py_Initialize", NoArgsNoRet)