From c8583a46c8d731a2c5d68e4b0521ca8e166645b5 Mon Sep 17 00:00:00 2001 From: Felipe Pena Date: Wed, 25 Dec 2024 08:32:54 -0300 Subject: [PATCH 1/7] fix --- vlib/v/gen/c/cgen.v | 16 +++++++++++--- vlib/v/gen/c/json.v | 54 ++++++++++++++++++++++----------------------- 2 files changed, 40 insertions(+), 30 deletions(-) diff --git a/vlib/v/gen/c/cgen.v b/vlib/v/gen/c/cgen.v index a2f6f8784f1bd7..8ce81ac50eb47a 100644 --- a/vlib/v/gen/c/cgen.v +++ b/vlib/v/gen/c/cgen.v @@ -7116,7 +7116,10 @@ fn (mut g Gen) type_default_sumtype(typ_ ast.Type, sym ast.TypeSymbol) string { fn (mut g Gen) type_default(typ_ ast.Type) string { typ := g.unwrap_generic(typ_) - if typ.has_option_or_result() { + if typ.has_flag(.option) { + return '(${g.styp(typ)}){.state=2}' + } + if typ.has_flag(.result) { return '{0}' } // Always set pointers to 0 @@ -7210,7 +7213,7 @@ fn (mut g Gen) type_default(typ_ ast.Type) string { for field in info.fields { field_sym := g.table.sym(field.typ) if field.has_default_expr - || field_sym.kind in [.array, .map, .string, .bool, .alias, .i8, .i16, .int, .i64, .u8, .u16, .u32, .u64, .f32, .f64, .char, .voidptr, .byteptr, .charptr, .struct, .chan, .sum_type] { + || field_sym.kind in [.enum, .array_fixed, .array, .map, .string, .bool, .alias, .i8, .i16, .int, .i64, .u8, .u16, .u32, .u64, .f32, .f64, .char, .voidptr, .byteptr, .charptr, .struct, .chan, .sum_type] { if sym.language == .c && !field.has_default_expr { continue } @@ -7255,7 +7258,14 @@ fn (mut g Gen) type_default(typ_ ast.Type) string { } } } else { - expr_str = g.expr_string(field.default_expr) + default_str := g.expr_string(field.default_expr) + if default_str.count('\n') > 1 { + println('>>> ${default_str.all_before_last('\n')}') + g.type_default_vars.writeln(default_str.all_before_last('\n')) + expr_str = default_str.all_after_last('\n') + } else { + expr_str = default_str + } } init_str += '.${field_name} = ${expr_str},' } else { diff --git a/vlib/v/gen/c/json.v b/vlib/v/gen/c/json.v index 4faaa578c8f253..0e881cd2ed48f9 100644 --- a/vlib/v/gen/c/json.v +++ b/vlib/v/gen/c/json.v @@ -58,35 +58,35 @@ fn (mut g Gen) gen_jsons() { mut init_styp := '${styp} res' if utyp.has_flag(.option) { - if sym.kind == .struct && !utyp.is_ptr() { - init_styp += ' = ' - g.set_current_pos_as_last_stmt_pos() - pos := g.out.len - g.expr_with_tmp_var(ast.Expr(ast.StructInit{ typ: utyp, typ_str: styp }), - utyp, utyp, 'res') - init_styp = g.out.cut_to(pos).trim_space() - } else { - none_str := g.expr_string(ast.None{}) - init_styp += ' = (${styp}){ .state=2, .err=${none_str}, .data={EMPTY_STRUCT_INITIALIZATION} }' - } + none_str := g.expr_string(ast.None{}) + init_styp += ' = (${styp}){ .state=2, .err=${none_str}, .data={EMPTY_STRUCT_INITIALIZATION} }' } else { - if sym.kind == .struct { + if !utyp.is_ptr() { init_styp += ' = ' g.set_current_pos_as_last_stmt_pos() pos := g.out.len - g.write(init_styp) - if utyp.is_ptr() { - ptr_styp := g.styp(utyp.set_nr_muls(utyp.nr_muls() - 1)) - g.write('HEAP(${ptr_styp}, ') - } - g.expr(ast.Expr(ast.StructInit{ - typ: utyp.set_nr_muls(0) - typ_str: styp - })) - if utyp.is_ptr() { - g.write(')') + g.write(g.type_default(utyp)) + init_generated := g.out.cut_to(pos).trim_space() + if g.type_default_vars.len > 0 { + saved_init := init_styp + init_styp = g.type_default_vars.bytestr() + init_styp += '\n' + init_styp += saved_init + g.type_default_vars.clear() } - init_styp = g.out.cut_to(pos).trim_space() + init_styp += init_generated + // if utyp.is_ptr() { + // ptr_styp := g.styp(utyp.set_nr_muls(utyp.nr_muls() - 1)) + // g.write('HEAP(${ptr_styp}, ') + // } + // g.expr(ast.Expr(ast.StructInit{ + // typ: utyp.set_nr_muls(0) + // typ_str: styp + // })) + // if utyp.is_ptr() { + // g.write(')') + // } + // init_styp = g.out.cut_to(pos).trim_space() } else if utyp.is_ptr() { ptr_styp := g.styp(utyp.set_nr_muls(utyp.nr_muls() - 1)) init_styp += ' = HEAP(${ptr_styp}, {0})' @@ -645,9 +645,9 @@ fn (mut g Gen) gen_prim_type_validation(name string, typ ast.Type, tmp string, i if type_check == '' { return } - dec.writeln('if (!(${type_check})) {') - dec.writeln('\treturn (${ret_styp}){ .is_error = true, .err = _v_error(string__plus(_SLIT("type mismatch for field \'${name}\', expecting `${g.table.type_to_str(typ)}` type, got: "), json__json_print(jsonroot_${tmp}))), .data = {0} };') - dec.writeln('}') + dec.writeln('\t\tif (!(${type_check})) {') + dec.writeln('\t\t\treturn (${ret_styp}){ .is_error = true, .err = _v_error(string__plus(_SLIT("type mismatch for field \'${name}\', expecting `${g.table.type_to_str(typ)}` type, got: "), json__json_print(jsonroot_${tmp}))), .data = {0} };') + dec.writeln('\t\t}') } @[inline] From 26f4ee617fdd22df4e93be0bab8ae9b20dea2a89 Mon Sep 17 00:00:00 2001 From: Felipe Pena Date: Wed, 25 Dec 2024 08:33:06 -0300 Subject: [PATCH 2/7] test --- .../tests/json_decode_option_alias_test.v | 20 +++++++++++++++++++ 1 file changed, 20 insertions(+) create mode 100644 vlib/json/tests/json_decode_option_alias_test.v diff --git a/vlib/json/tests/json_decode_option_alias_test.v b/vlib/json/tests/json_decode_option_alias_test.v new file mode 100644 index 00000000000000..f4c7c51b965e79 --- /dev/null +++ b/vlib/json/tests/json_decode_option_alias_test.v @@ -0,0 +1,20 @@ +import json + +struct Empty {} + +struct SomeStruct { + random_field_a ?string + random_field_b ?string + empty_field ?Empty +} + +type Alias = SomeStruct + +fn test_main() { + data := json.decode(Alias, '{"empty_field":{}}')! + assert data.str() == 'Alias(SomeStruct{ + random_field_a: Option(none) + random_field_b: Option(none) + empty_field: Option(none) +})' +} From 4e62176095305c11bfcf2c13b2066d3ad23a24cc Mon Sep 17 00:00:00 2001 From: Felipe Pena Date: Wed, 25 Dec 2024 08:35:55 -0300 Subject: [PATCH 3/7] cleanup --- vlib/v/gen/c/cgen.v | 1 - 1 file changed, 1 deletion(-) diff --git a/vlib/v/gen/c/cgen.v b/vlib/v/gen/c/cgen.v index 8ce81ac50eb47a..c4be58a43c9343 100644 --- a/vlib/v/gen/c/cgen.v +++ b/vlib/v/gen/c/cgen.v @@ -7260,7 +7260,6 @@ fn (mut g Gen) type_default(typ_ ast.Type) string { } else { default_str := g.expr_string(field.default_expr) if default_str.count('\n') > 1 { - println('>>> ${default_str.all_before_last('\n')}') g.type_default_vars.writeln(default_str.all_before_last('\n')) expr_str = default_str.all_after_last('\n') } else { From 32aa24a618635d7d4c23cc32019bfa379ac9aeed Mon Sep 17 00:00:00 2001 From: Felipe Pena Date: Wed, 25 Dec 2024 08:37:46 -0300 Subject: [PATCH 4/7] cleanup --- vlib/v/gen/c/json.v | 12 ------------ 1 file changed, 12 deletions(-) diff --git a/vlib/v/gen/c/json.v b/vlib/v/gen/c/json.v index 0e881cd2ed48f9..2013abb461dfea 100644 --- a/vlib/v/gen/c/json.v +++ b/vlib/v/gen/c/json.v @@ -75,18 +75,6 @@ fn (mut g Gen) gen_jsons() { g.type_default_vars.clear() } init_styp += init_generated - // if utyp.is_ptr() { - // ptr_styp := g.styp(utyp.set_nr_muls(utyp.nr_muls() - 1)) - // g.write('HEAP(${ptr_styp}, ') - // } - // g.expr(ast.Expr(ast.StructInit{ - // typ: utyp.set_nr_muls(0) - // typ_str: styp - // })) - // if utyp.is_ptr() { - // g.write(')') - // } - // init_styp = g.out.cut_to(pos).trim_space() } else if utyp.is_ptr() { ptr_styp := g.styp(utyp.set_nr_muls(utyp.nr_muls() - 1)) init_styp += ' = HEAP(${ptr_styp}, {0})' From 032f17a064f7d2005c9596425641c25b280545b9 Mon Sep 17 00:00:00 2001 From: Felipe Pena Date: Wed, 25 Dec 2024 10:57:14 -0300 Subject: [PATCH 5/7] fix --- vlib/v/gen/c/cgen.v | 23 ++++++++++++++++++++--- 1 file changed, 20 insertions(+), 3 deletions(-) diff --git a/vlib/v/gen/c/cgen.v b/vlib/v/gen/c/cgen.v index c4be58a43c9343..a9b8053a6ed7fb 100644 --- a/vlib/v/gen/c/cgen.v +++ b/vlib/v/gen/c/cgen.v @@ -7096,14 +7096,19 @@ fn c_fn_name(name_ string) string { } fn (mut g Gen) type_default_sumtype(typ_ ast.Type, sym ast.TypeSymbol) string { + if typ_.has_flag(.option) { + return '(${g.styp(typ_)}){.state=2, .err=_const_none__, .data={EMPTY_STRUCT_INITIALIZATION}}' + } first_typ := g.unwrap_generic((sym.info as ast.SumType).variants[0]) first_sym := g.table.sym(first_typ) first_styp := g.styp(first_typ) first_field := g.get_sumtype_variant_name(first_typ, first_sym) default_str := if first_typ.has_flag(.option) { - '(${first_styp}){ .state=2, .err=_const_none__, .data={EMPTY_STRUCT_INITIALIZATION} }' + '(${first_styp}){.state=2, .err=_const_none__, .data={EMPTY_STRUCT_INITIALIZATION}}' } else if first_sym.info is ast.Struct && first_sym.info.is_empty_struct() { '{EMPTY_STRUCT_INITIALIZATION}' + } else if first_sym.kind == .struct { + '{0}' } else { g.type_default(first_typ) } @@ -7114,10 +7119,20 @@ fn (mut g Gen) type_default_sumtype(typ_ ast.Type, sym ast.TypeSymbol) string { } } +@[inline] +fn (mut g Gen) type_default_no_sumtype(typ_ ast.Type) string { + return g.type_default_impl(typ_, false) +} + +@[inline] fn (mut g Gen) type_default(typ_ ast.Type) string { + return g.type_default_impl(typ_, true) +} + +fn (mut g Gen) type_default_impl(typ_ ast.Type, decode_sumtype bool) string { typ := g.unwrap_generic(typ_) if typ.has_flag(.option) { - return '(${g.styp(typ)}){.state=2}' + return '(${g.styp(typ)}){.state=2, .err=_const_none__, .data={EMPTY_STRUCT_INITIALIZATION}}' } if typ.has_flag(.result) { return '{0}' @@ -7142,7 +7157,7 @@ fn (mut g Gen) type_default(typ_ ast.Type) string { return '{0}' } .sum_type { - return '{0}' // g.type_default_sumtype(typ, sym) + return if decode_sumtype { g.type_default_sumtype(typ, sym) } else { '{0}' } } .interface, .multi_return, .thread { return '{0}' @@ -7271,6 +7286,8 @@ fn (mut g Gen) type_default(typ_ ast.Type) string { zero_str := if field_sym.language == .v && field_sym.info is ast.Struct && field_sym.info.is_empty_struct() { '{EMPTY_STRUCT_INITIALIZATION}' + } else if field_sym.kind == .sum_type { + g.type_default_sumtype(field.typ, field_sym) } else { g.type_default(field.typ) } From 020c8ef192cd287f82690348b3e3458baf77cbd9 Mon Sep 17 00:00:00 2001 From: Felipe Pena Date: Wed, 25 Dec 2024 11:00:02 -0300 Subject: [PATCH 6/7] fix --- vlib/v/gen/c/cgen.v | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/vlib/v/gen/c/cgen.v b/vlib/v/gen/c/cgen.v index a9b8053a6ed7fb..1f9ded74636dc2 100644 --- a/vlib/v/gen/c/cgen.v +++ b/vlib/v/gen/c/cgen.v @@ -7107,10 +7107,8 @@ fn (mut g Gen) type_default_sumtype(typ_ ast.Type, sym ast.TypeSymbol) string { '(${first_styp}){.state=2, .err=_const_none__, .data={EMPTY_STRUCT_INITIALIZATION}}' } else if first_sym.info is ast.Struct && first_sym.info.is_empty_struct() { '{EMPTY_STRUCT_INITIALIZATION}' - } else if first_sym.kind == .struct { - '{0}' } else { - g.type_default(first_typ) + g.type_default_no_sumtype(first_typ) } if default_str[0] == `{` { return '(${g.styp(typ_)}){._${first_field}=HEAP(${first_styp}, ((${first_styp})${default_str})),._typ=${int(first_typ)}}' From ea4435efa2dae5ad6832f454fd0e68e623face8b Mon Sep 17 00:00:00 2001 From: Felipe Pena Date: Wed, 25 Dec 2024 11:03:51 -0300 Subject: [PATCH 7/7] fix --- vlib/v/gen/c/cgen.v | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/vlib/v/gen/c/cgen.v b/vlib/v/gen/c/cgen.v index 1f9ded74636dc2..4dfc2e7b3e6a34 100644 --- a/vlib/v/gen/c/cgen.v +++ b/vlib/v/gen/c/cgen.v @@ -7285,7 +7285,11 @@ fn (mut g Gen) type_default_impl(typ_ ast.Type, decode_sumtype bool) string { && field_sym.info.is_empty_struct() { '{EMPTY_STRUCT_INITIALIZATION}' } else if field_sym.kind == .sum_type { - g.type_default_sumtype(field.typ, field_sym) + if decode_sumtype { + g.type_default_sumtype(field.typ, field_sym) + } else { + '{0}' + } } else { g.type_default(field.typ) }