Skip to content

Commit

Permalink
fix
Browse files Browse the repository at this point in the history
  • Loading branch information
felipensp committed Sep 22, 2024
1 parent 3307340 commit 387da6e
Show file tree
Hide file tree
Showing 5 changed files with 64 additions and 4 deletions.
12 changes: 12 additions & 0 deletions vlib/v/checker/checker.v
Original file line number Diff line number Diff line change
Expand Up @@ -1197,6 +1197,18 @@ fn (mut c Checker) check_expr_option_or_result_call(expr ast.Expr, ret_type ast.
expr_ret_type = unaliased_ret_type
}
}
// var with option function
if expr.is_fn_var && expr.fn_var_type.has_option_or_result()
&& expr.or_block.kind == .absent {
ret_sym := c.table.sym(expr.fn_var_type)
if expr.fn_var_type.has_flag(.option) {
c.error('type `?${ret_sym.name}` is an Option, it must be unwrapped first',
expr.pos)
} else {
c.error('type `?${ret_sym.name}` is an Result, it must be unwrapped first',
expr.pos)
}
}
if expr_ret_type.has_option_or_result() {
if expr.or_block.kind == .absent {
ret_sym := c.table.sym(expr_ret_type)
Expand Down
7 changes: 7 additions & 0 deletions vlib/v/checker/tests/option_fn_var_err.out
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
vlib/v/checker/tests/option_fn_var_err.vv:18:9: error: type `?DataFn` is an Option, it must be unwrapped first
16 | fn main() {
17 | req := find_func('vlang')
18 | fun := req('options')
| ~~~~~~~~~~~~~~
19 | println(fun)
20 | }
20 changes: 20 additions & 0 deletions vlib/v/checker/tests/option_fn_var_err.vv
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
module main

type DataFn = fn (name string) string

fn which_lang(name string) string {
return name
}

fn find_func(name string) ?DataFn {
return match name {
'vlang' { which_lang }
else { none }
}
}

fn main() {
req := find_func('vlang')
fun := req('options')
println(fun)
}
8 changes: 4 additions & 4 deletions vlib/v/gen/c/match.v
Original file line number Diff line number Diff line change
Expand Up @@ -92,10 +92,10 @@ fn (mut g Gen) match_expr(node ast.MatchExpr) {
cur_line = g.go_before_last_stmt().trim_left(' \t')
tmp_var = g.new_tmp_var()
mut func_decl := ''
if g.table.final_sym(node.return_type).kind == .function {
func_sym := g.table.final_sym(node.return_type)
if func_sym.info is ast.FnType {
def := g.fn_var_signature(func_sym.info.func.return_type, func_sym.info.func.params.map(it.typ),
ret_final_sym := g.table.final_sym(node.return_type)
if !node.return_type.has_option_or_result() && ret_final_sym.kind == .function {
if ret_final_sym.info is ast.FnType {
def := g.fn_var_signature(ret_final_sym.info.func.return_type, ret_final_sym.info.func.params.map(it.typ),
tmp_var)
func_decl = '${def} = &${g.typ(node.return_type)};'
}
Expand Down
21 changes: 21 additions & 0 deletions vlib/v/tests/options/option_fn_var_test.v
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
module main

type DataFn = fn (name string) string

fn which_lang(name string) string {
return name
}

fn find_func(name string) ?DataFn {
return match name {
'vlang' { which_lang }
else { none }
}
}

fn test_main() {
req := find_func('vlang')?
fun := req('options')
println(fun)
assert fun == 'options'
}

0 comments on commit 387da6e

Please sign in to comment.