diff --git a/vlib/v/gen/c/cgen.v b/vlib/v/gen/c/cgen.v index 9f22cb465a..2b17153633 100644 --- a/vlib/v/gen/c/cgen.v +++ b/vlib/v/gen/c/cgen.v @@ -2968,7 +2968,7 @@ fn (mut g Gen) gen_assign_stmt(assign_stmt ast.AssignStmt) { scope: 0 } left_sym := g.table.get_type_symbol(g.unwrap_generic(var_type)) - if left is ast.Ident { + if mut left is ast.Ident { ident = left // id_info := ident.var_info() // var_type = id_info.typ @@ -2984,7 +2984,16 @@ fn (mut g Gen) gen_assign_stmt(assign_stmt ast.AssignStmt) { var_type = var_type.set_flag(.atomic_f) } } - if left.obj is ast.Var { + if mut left.obj is ast.Var { + if val is ast.ComptimeSelector { + if val.field_expr is ast.SelectorExpr { + if val.field_expr.expr is ast.Ident { + key_str := '${val.field_expr.expr.name}.typ' + var_type = g.comptime_var_type_map[key_str] or { var_type } + left.obj.typ = var_type + } + } + } is_auto_heap = left.obj.is_auto_heap } } @@ -4098,7 +4107,18 @@ fn (mut g Gen) selector_expr(node ast.SelectorExpr) { .unknown { if node.field_name == 'name' { // typeof(expr).name - g.type_name(node.name_type) + mut name_type := node.name_type + if node.expr is ast.TypeOf { + if node.expr.expr is ast.ComptimeSelector { + if node.expr.expr.field_expr is ast.SelectorExpr { + if node.expr.expr.field_expr.expr is ast.Ident { + key_str := '${node.expr.expr.field_expr.expr.name}.typ' + name_type = g.comptime_var_type_map[key_str] or { name_type } + } + } + } + } + g.type_name(name_type) return } else if node.field_name == 'idx' { // typeof(expr).idx diff --git a/vlib/v/gen/c/fn.v b/vlib/v/gen/c/fn.v index f5b774995e..a31dc37a4e 100644 --- a/vlib/v/gen/c/fn.v +++ b/vlib/v/gen/c/fn.v @@ -819,6 +819,12 @@ fn (mut g Gen) method_call(node ast.CallExpr) { return } } + } else if node.left is ast.Ident && g.comptime_var_type_map.len > 0 { + if node.left.obj is ast.Var { + rec_type = node.left.obj.typ + g.gen_expr_to_string(node.left, rec_type) + return + } } g.get_str_fn(rec_type) } else if node.name == 'free' { @@ -1130,6 +1136,10 @@ fn (mut g Gen) fn_call(node ast.CallExpr) { typ = g.comptime_var_type_map[key_str] or { typ } } } + } else if expr is ast.Ident { + if expr.obj is ast.Var { + typ = expr.obj.typ + } } g.gen_expr_to_string(expr, typ) g.write(')') diff --git a/vlib/v/tests/comptime_for_in_field_selector_test.v b/vlib/v/tests/comptime_for_in_field_selector_test.v index 9c9b4e3014..a9b355e4ef 100644 --- a/vlib/v/tests/comptime_for_in_field_selector_test.v +++ b/vlib/v/tests/comptime_for_in_field_selector_test.v @@ -1,15 +1,36 @@ fn print_field_values(s T) { mut value_list := []string{} + mut value_type_list := []string{} + mut var_value_list := []string{} $for field in T.fields { println(s.$(field.name)) value_list << s.$(field.name).str() + + println(typeof(s.$(field.name)).name) + value_type_list << typeof(s.$(field.name)).name + + val := s.$(field.name) + println(val) + var_value_list << val.str() } assert value_list.len == 4 assert value_list[0] == 'Simon' assert value_list[1] == 'simon1234' assert value_list[2] == 'simon@gmail.com' assert value_list[3] == '15' + + assert value_type_list.len == 4 + assert value_type_list[0] == 'string' + assert value_type_list[1] == 'string' + assert value_type_list[2] == 'string' + assert value_type_list[3] == 'int' + + assert var_value_list.len == 4 + assert var_value_list[0] == 'Simon' + assert var_value_list[1] == 'simon1234' + assert var_value_list[2] == 'simon@gmail.com' + assert var_value_list[3] == '15' } struct Foo {