From 8a504f8eee88accb56f89d1e778e1825ba986f74 Mon Sep 17 00:00:00 2001 From: Irmen de Jong Date: Tue, 8 Dec 2020 21:17:31 +0100 Subject: [PATCH] fixed compiler crash: when passing the name of a subroutine instead of an array or string to an UWORD parameter now allows taking the address of a subroutine &routine --- compiler/src/prog8/ast/processing/AstChecker.kt | 13 +++++-------- .../prog8/ast/processing/VerifyFunctionArgTypes.kt | 5 +++-- examples/test.p8 | 13 ++++++------- 3 files changed, 14 insertions(+), 17 deletions(-) diff --git a/compiler/src/prog8/ast/processing/AstChecker.kt b/compiler/src/prog8/ast/processing/AstChecker.kt index be9a7f947..db1d6af90 100644 --- a/compiler/src/prog8/ast/processing/AstChecker.kt +++ b/compiler/src/prog8/ast/processing/AstChecker.kt @@ -455,15 +455,12 @@ internal class AstChecker(private val program: Program, override fun visit(addressOf: AddressOf) { val variable=addressOf.identifier.targetVarDecl(program.namespace) - if(variable==null) - errors.err("pointer-of operand must be the name of a heap variable", addressOf.position) - else { - if(variable.datatype !in ArrayDatatypes - && variable.type!=VarDeclType.MEMORY - && variable.struct == null - && variable.datatype != DataType.STR && variable.datatype!=DataType.STRUCT) + if(variable!=null + && variable.datatype !in ArrayDatatypes + && variable.type!=VarDeclType.MEMORY + && variable.struct == null + && variable.datatype != DataType.STR && variable.datatype!=DataType.STRUCT) errors.err("invalid pointer-of operand type", addressOf.position) - } super.visit(addressOf) } diff --git a/compiler/src/prog8/ast/processing/VerifyFunctionArgTypes.kt b/compiler/src/prog8/ast/processing/VerifyFunctionArgTypes.kt index 1fd3d272e..6726c23de 100644 --- a/compiler/src/prog8/ast/processing/VerifyFunctionArgTypes.kt +++ b/compiler/src/prog8/ast/processing/VerifyFunctionArgTypes.kt @@ -41,8 +41,9 @@ class VerifyFunctionArgTypes(val program: Program) : IAstVisitor { fun checkTypes(call: IFunctionCall, scope: INameScope, program: Program): String? { val argITypes = call.args.map { it.inferType(program) } - if(argITypes.any { !it.isKnown }) - throw FatalAstException("unknown dt") + val firstUnknownDt = argITypes.indexOfFirst { it.isUnknown } + if(firstUnknownDt>=0) + return "argument ${firstUnknownDt+1} invalid argument type" val argtypes = argITypes.map { it.typeOrElse(DataType.STRUCT) } val target = call.target.targetStatement(scope) if (target is Subroutine) { diff --git a/examples/test.p8 b/examples/test.p8 index f599bb8f7..85102c4df 100644 --- a/examples/test.p8 +++ b/examples/test.p8 @@ -8,12 +8,6 @@ errors { sub tofix() { - ; TODO fix compiler crash: when passing the name of a subroutine instead of an array or string to an UWORD parameter - - ; TODO allow taking the address of a subroutine &routine - - - while c64.CHRIN() { ; TODO: the loop condition isn't properly tested because a ldx is in the way before the beq } @@ -46,7 +40,12 @@ errors { main { sub start() { - + function(&start) test_stack.test() } + + sub function(uword param) { + txt.print_uwhex(param, 1) + param++ + } }