From 45a122a8bc25aed60acb42d54f8f01dd87d1ee41 Mon Sep 17 00:00:00 2001 From: Cedric <14017092+douyixuan@users.noreply.github.com> Date: Sat, 7 Sep 2024 21:25:04 +0800 Subject: [PATCH] fix extern func definition with pointer --- compiler/compiler/func.go | 15 ++++++++++++++- compiler/compiler/package.go | 2 +- compiler/compiler/types/type.go | 3 ++- 3 files changed, 17 insertions(+), 3 deletions(-) diff --git a/compiler/compiler/func.go b/compiler/compiler/func.go index d0bad9c..b99c438 100644 --- a/compiler/compiler/func.go +++ b/compiler/compiler/func.go @@ -161,6 +161,7 @@ func (c *Compiler) compileDefineFuncNode(v *parser.DefineFuncNode) value.Value { LlvmReturnType: funcRetType, ReturnTypes: treReturnTypes, IsVariadic: isVariadicFunc, + IsExtern: v.IsExtern, ArgumentTypes: treParams, } @@ -482,6 +483,7 @@ func (c *Compiler) compileCallNode(v *parser.CallNode) value.Value { FuncType: ifaceMethod.LlvmJumpFunction.Type(), ReturnTypes: ifaceMethod.ReturnTypes, LlvmReturnType: returnType, + ArgumentTypes: ifaceMethod.ArgumentTypes, } fn = ifaceMethod.LlvmJumpFunction } else { @@ -538,7 +540,7 @@ func (c *Compiler) compileCallNode(v *parser.CallNode) value.Value { val := internal.LoadIfVariable(c.contextBlock, v) // Convert strings and arrays to i8* when calling external functions - if fnType.IsExternal { + if fnType.IsBuiltin { if v.Type.Name() == "string" { llvmArgs[i] = c.contextBlock.NewExtractValue(val, 1) continue @@ -549,6 +551,17 @@ func (c *Compiler) compileCallNode(v *parser.CallNode) value.Value { continue } } + if fnType.IsExtern { + // Convert pointer to target type as needed + if len(fnType.ArgumentTypes) > 0 { + if _, isPointer := v.Type.(*types.Pointer); isPointer { + if arg := fnType.ArgumentTypes[i]; arg != v.Type { + val = c.contextBlock.NewBitCast(val, arg.LLVM()) + } + } + } + } + llvmArgs[i] = val } diff --git a/compiler/compiler/package.go b/compiler/compiler/package.go index c63866e..97fd120 100644 --- a/compiler/compiler/package.go +++ b/compiler/compiler/package.go @@ -31,7 +31,7 @@ func (p *pkg) setExternal(internalName string, fn *ir.Func, variadic bool) value Type: &types.Function{ LlvmReturnType: types.Void, FuncType: fn.Type(), - IsExternal: true, + IsBuiltin: true, }, Value: fn, } diff --git a/compiler/compiler/types/type.go b/compiler/compiler/types/type.go index face11f..e6eac7a 100644 --- a/compiler/compiler/types/type.go +++ b/compiler/compiler/types/type.go @@ -125,8 +125,9 @@ type Function struct { ReturnTypes []Type IsVariadic bool + IsExtern bool ArgumentTypes []Type - IsExternal bool + IsBuiltin bool // Is used when calling an interface method JumpFunction *ir.Func