Fixed so functions can do type conversion between in/out params and arguments. Lossy conversions give a warning now.
This commit is contained in:
parent
b830a41b5f
commit
5f01282df5
2 changed files with 38 additions and 18 deletions
|
|
@ -386,42 +386,60 @@ func (fh *FunctionHandler) processStringArg(arg string, param *FuncParam, funcNa
|
|||
return nil
|
||||
}
|
||||
|
||||
// processVarArg handles variable arguments
|
||||
func (fh *FunctionHandler) processVarArg(sym *Symbol, param *FuncParam, funcName string, line preproc.Line, inAssigns, outAssigns *[]string) error {
|
||||
// Check type compatibility
|
||||
if (sym.IsByte() && param.Symbol.IsWord()) || (sym.IsWord() && param.Symbol.IsByte()) {
|
||||
return fmt.Errorf("%s:%d: CALL %s: type mismatch for parameter %s", line.Filename, line.LineNo, funcName, param.Symbol.Name)
|
||||
}
|
||||
|
||||
if sym.IsConst() {
|
||||
return fmt.Errorf("%s:%d: CALL %s: cannot pass constant to function", line.Filename, line.LineNo, funcName)
|
||||
}
|
||||
|
||||
// Generate IN assignments
|
||||
// Generate IN assignments (sym -> param)
|
||||
if param.Direction.Has(DirIn) {
|
||||
*inAssigns = append(*inAssigns,
|
||||
fmt.Sprintf(" lda %s", sym.FullName()),
|
||||
fmt.Sprintf(" sta %s", param.Symbol.FullName()),
|
||||
)
|
||||
if sym.IsWord() {
|
||||
*inAssigns = append(*inAssigns,
|
||||
fmt.Sprintf(" lda %s+1", sym.FullName()),
|
||||
fmt.Sprintf(" sta %s+1", param.Symbol.FullName()),
|
||||
)
|
||||
if param.Symbol.IsWord() {
|
||||
if sym.IsWord() {
|
||||
*inAssigns = append(*inAssigns,
|
||||
fmt.Sprintf(" lda %s+1", sym.FullName()),
|
||||
fmt.Sprintf(" sta %s+1", param.Symbol.FullName()),
|
||||
)
|
||||
} else {
|
||||
// byte -> word: zero extend
|
||||
*inAssigns = append(*inAssigns,
|
||||
" lda #0",
|
||||
fmt.Sprintf(" sta %s+1", param.Symbol.FullName()),
|
||||
)
|
||||
}
|
||||
} else if sym.IsWord() {
|
||||
// word -> byte: lossy
|
||||
fmt.Printf("%s:%d: warning: CALL %s: truncating word '%s' to byte parameter '%s'\n",
|
||||
line.Filename, line.LineNo, funcName, sym.Name, param.Symbol.Name)
|
||||
}
|
||||
}
|
||||
|
||||
// Generate OUT assignments
|
||||
// Generate OUT assignments (param -> sym)
|
||||
if param.Direction.Has(DirOut) {
|
||||
*outAssigns = append(*outAssigns,
|
||||
fmt.Sprintf(" lda %s", param.Symbol.FullName()),
|
||||
fmt.Sprintf(" sta %s", sym.FullName()),
|
||||
)
|
||||
if sym.IsWord() {
|
||||
*outAssigns = append(*outAssigns,
|
||||
fmt.Sprintf(" lda %s+1", param.Symbol.FullName()),
|
||||
fmt.Sprintf(" sta %s+1", sym.FullName()),
|
||||
)
|
||||
if param.Symbol.IsWord() {
|
||||
*outAssigns = append(*outAssigns,
|
||||
fmt.Sprintf(" lda %s+1", param.Symbol.FullName()),
|
||||
fmt.Sprintf(" sta %s+1", sym.FullName()),
|
||||
)
|
||||
} else {
|
||||
// byte -> word: zero extend
|
||||
*outAssigns = append(*outAssigns,
|
||||
" lda #0",
|
||||
fmt.Sprintf(" sta %s+1", sym.FullName()),
|
||||
)
|
||||
}
|
||||
} else if param.Symbol.IsWord() {
|
||||
// word -> byte: lossy
|
||||
fmt.Printf("%s:%d: warning: CALL %s: truncating word parameter '%s' to byte '%s'\n",
|
||||
line.Filename, line.LineNo, funcName, param.Symbol.Name, sym.Name)
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -587,6 +587,8 @@ func TestHandleFuncCall_Errors(t *testing.T) {
|
|||
line: "CALL test ( 1 2 )",
|
||||
wantErr: "expected 1 arguments, got 2",
|
||||
},
|
||||
//
|
||||
/* This is no error anymore, just a warning.
|
||||
{
|
||||
name: "type mismatch",
|
||||
setup: func(fh *FunctionHandler, st *SymbolTable) {
|
||||
|
|
@ -596,7 +598,7 @@ func TestHandleFuncCall_Errors(t *testing.T) {
|
|||
},
|
||||
line: "CALL test ( wvar )",
|
||||
wantErr: "type mismatch",
|
||||
},
|
||||
}, */
|
||||
{
|
||||
name: "const to out param",
|
||||
setup: func(fh *FunctionHandler, st *SymbolTable) {
|
||||
|
|
|
|||
Loading…
Reference in a new issue