cgen: fix var name clash of array/map (fix #1994) (#8765)

pull/8768/head
yuyi 2021-02-15 21:51:57 +08:00 committed by GitHub
parent 629d43caf5
commit a9c2045dbd
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
8 changed files with 96 additions and 17 deletions

View File

@ -5478,7 +5478,7 @@ pub fn (mut c Checker) error(message string, pos token.Position) {
if c.pref.is_verbose {
print_backtrace()
}
msg := message.replace('`array_', '`[]')
msg := message.replace('`Array_', '`[]')
c.warn_or_error(msg, pos, false)
}

View File

@ -437,7 +437,7 @@ fn (mut g Gen) gen_array_contains_method(left_type table.Type) string {
mut elem_type_str := g.typ(left_info.elem_type)
elem_sym := g.table.get_type_symbol(left_info.elem_type)
if elem_sym.kind == .function {
left_type_str = 'array_voidptr'
left_type_str = 'Array_voidptr'
elem_type_str = 'voidptr'
}
g.type_definitions.writeln('static bool ${fn_name}($left_type_str a, $elem_type_str v); // auto')
@ -500,7 +500,7 @@ fn (mut g Gen) gen_array_index_method(left_type table.Type) string {
mut elem_type_str := g.typ(info.elem_type)
elem_sym := g.table.get_type_symbol(info.elem_type)
if elem_sym.kind == .function {
left_type_str = 'array_voidptr'
left_type_str = 'Array_voidptr'
elem_type_str = 'voidptr'
}
g.type_definitions.writeln('static int ${fn_name}($left_type_str a, $elem_type_str v); // auto')

View File

@ -470,7 +470,8 @@ fn (mut g Gen) gen_str_for_struct(info table.Struct, styp string, str_fn_name st
// TODO: this is a bit hacky. styp shouldn't be even parsed with _T_
// use something different than g.typ for styp
clean_struct_v_type_name =
clean_struct_v_type_name.replace('_T_', '<').replace('_', ', ') + '>'
clean_struct_v_type_name.replace('_T_', '<').replace('_', ', ').replace('Array', 'array') +
'>'
}
clean_struct_v_type_name = util.strip_main_name(clean_struct_v_type_name)
// generate ident / indent length = 4 spaces

View File

@ -3795,7 +3795,7 @@ fn (mut g Gen) select_expr(node ast.SelectExpr) {
}
}
chan_array := g.new_tmp_var()
g.write('array_sync__Channel_ptr $chan_array = new_array_from_c_array($n_channels, $n_channels, sizeof(sync__Channel*), _MOV((sync__Channel*[$n_channels]){')
g.write('Array_sync__Channel_ptr $chan_array = new_array_from_c_array($n_channels, $n_channels, sizeof(sync__Channel*), _MOV((sync__Channel*[$n_channels]){')
for i in 0 .. n_channels {
if i > 0 {
g.write(', ')
@ -3806,7 +3806,7 @@ fn (mut g Gen) select_expr(node ast.SelectExpr) {
}
g.writeln('}));')
directions_array := g.new_tmp_var()
g.write('array_sync__Direction $directions_array = new_array_from_c_array($n_channels, $n_channels, sizeof(sync__Direction), _MOV((sync__Direction[$n_channels]){')
g.write('Array_sync__Direction $directions_array = new_array_from_c_array($n_channels, $n_channels, sizeof(sync__Direction), _MOV((sync__Direction[$n_channels]){')
for i in 0 .. n_channels {
if i > 0 {
g.write(', ')
@ -3819,7 +3819,7 @@ fn (mut g Gen) select_expr(node ast.SelectExpr) {
}
g.writeln('}));')
objs_array := g.new_tmp_var()
g.write('array_voidptr $objs_array = new_array_from_c_array($n_channels, $n_channels, sizeof(voidptr), _MOV((voidptr[$n_channels]){')
g.write('Array_voidptr $objs_array = new_array_from_c_array($n_channels, $n_channels, sizeof(voidptr), _MOV((voidptr[$n_channels]){')
for i in 0 .. n_channels {
g.write(if i > 0 { ', &' } else { '&' })
if tmp_objs[i] == '' {
@ -4795,7 +4795,7 @@ fn (mut g Gen) const_decl_init_later(mod string, name string, val string, typ ta
}
}
if g.is_autofree {
if styp.starts_with('array_') {
if styp.starts_with('Array_') {
g.cleanups[mod].writeln('\tarray_free(&$cname);')
}
if styp == 'string' {

View File

@ -218,7 +218,7 @@ fn (mut g Gen) decode_array(value_type table.Type) string {
Option_$styp val2 = $fn_name (jsval);
if(!val2.ok) {
array_free(&res);
return *(Option_array_$styp*)&val2;
return *(Option_Array_$styp*)&val2;
}
$styp val = *($styp*)val2.data;
'
@ -226,7 +226,7 @@ fn (mut g Gen) decode_array(value_type table.Type) string {
return '
if(root && !cJSON_IsArray(root) && !cJSON_IsNull(root)) {
Option err = v_error( string_add(_SLIT("Json element is not an array: "), tos2(cJSON_PrintUnformatted(root))) );
return *(Option_array_$styp *)&err;
return *(Option_Array_$styp *)&err;
}
res = __new_array(0, 0, sizeof($styp));
const cJSON *jsval = NULL;
@ -263,7 +263,7 @@ fn (mut g Gen) decode_map(key_type table.Type, value_type table.Type) string {
Option_$styp_v val2 = $fn_name_v (js_get(root, jsval->string));
if(!val2.ok) {
map_free(&res);
return *(Option_map_${styp}_$styp_v*)&val2;
return *(Option_Map_${styp}_$styp_v*)&val2;
}
$styp_v val = *($styp_v*)val2.data;
'
@ -271,7 +271,7 @@ fn (mut g Gen) decode_map(key_type table.Type, value_type table.Type) string {
return '
if(!cJSON_IsObject(root) && !cJSON_IsNull(root)) {
Option err = v_error( string_add(_SLIT("Json element is not an object: "), tos2(cJSON_PrintUnformatted(root))) );
return *(Option_map_${styp}_$styp_v *)&err;
return *(Option_Map_${styp}_$styp_v *)&err;
}
res = new_map_2(sizeof($styp), sizeof($styp_v), $hash_fn, $key_eq_fn, $clone_fn, $free_fn);
cJSON *jsval = NULL;
@ -299,7 +299,7 @@ fn (mut g Gen) encode_map(key_type table.Type, value_type table.Type) string {
}
return '
o = cJSON_CreateObject();
array_$styp $keys_tmp = map_keys(&val);
Array_$styp $keys_tmp = map_keys(&val);
for (int i = 0; i < ${keys_tmp}.len; ++i) {
$key
cJSON_AddItemToObject(o, (char*) key.str, $fn_name_v ( *($styp_v*) map_get_1(&val, &key, &($styp_v[]) { $zero } ) ) );

View File

@ -87,7 +87,7 @@ fn (mut g Gen) sql_stmt(node ast.SqlStmt) {
g.sql_stmt(expr)
g.sql_stmt_name = tmp_sql_stmt_name
// get last inserted id
g.writeln('array_sqlite__Row rows = sqlite__DB_exec($db_name, _SLIT("SELECT last_insert_rowid()")).arg0;')
g.writeln('Array_sqlite__Row rows = sqlite__DB_exec($db_name, _SLIT("SELECT last_insert_rowid()")).arg0;')
id_name := g.new_tmp_var()
g.writeln('int $id_name = string_int((*(string*)array_get((*(sqlite__Row*)array_get(rows, 0)).vals, 0)));')
g.writeln('sqlite3_bind_int($g.sql_stmt_name, ${i + 0} , $id_name); // id')

View File

@ -417,7 +417,7 @@ pub fn (t &Table) array_cname(elem_type Type) string {
if elem_type.is_ptr() {
res = '_ptr'.repeat(elem_type.nr_muls())
}
return 'array_$elem_type_sym.cname' + res
return 'Array_$elem_type_sym.cname' + res
}
// array_fixed_source_name generates the original name for the v source.
@ -436,7 +436,7 @@ pub fn (t &Table) array_fixed_cname(elem_type Type, size int) string {
if elem_type.is_ptr() {
res = '_ptr'
}
return 'array_fixed_${elem_type_sym.cname}_$size' + res
return 'Array_fixed_${elem_type_sym.cname}_$size' + res
}
[inline]
@ -492,7 +492,7 @@ pub fn (t &Table) map_cname(key_type Type, value_type Type) string {
key_type_sym := t.get_type_symbol(key_type)
value_type_sym := t.get_type_symbol(value_type)
suffix := if value_type.is_ptr() { '_ptr' } else { '' }
return 'map_${key_type_sym.cname}_$value_type_sym.cname' + suffix
return 'Map_${key_type_sym.cname}_$value_type_sym.cname' + suffix
// return 'map_${value_type_sym.name}' + suffix
}

View File

@ -0,0 +1,78 @@
fn test_clash_var_name_of_array() {
array_f32 := 1
array_f64 := 2
array_bool := 3
array_i8 := 4
array_byte := 5
array_i16 := 6
array_u16 := 7
array_int := 8
array_u32 := 9
array_string := 10
array_rune := 11
a_f32 := []f32{}
a_f64 := []f64{}
a_bool := []bool{}
a_i8 := []i8{}
a_byte := []byte{}
a_i16 := []i16{}
a_u16 := []u16{}
a_int := []int{}
a_u32 := []u32{}
a_string := []string{}
a_rune := []rune{}
println(a_f32)
assert '$a_f32' == '[]'
println(a_f64)
assert '$a_f64' == '[]'
println(a_bool)
assert '$a_bool' == '[]'
println(a_i8)
assert '$a_i8' == '[]'
println(a_byte)
assert '$a_byte' == '[]'
println(a_i16)
assert '$a_i16' == '[]'
println(a_u16)
assert '$a_u16' == '[]'
println(a_int)
assert '$a_int' == '[]'
println(a_u32)
assert '$a_u32' == '[]'
println(a_string)
assert '$a_string' == '[]'
println(a_rune)
assert '$a_rune' == '[]'
println(array_f32)
assert array_f32 == 1
println(array_f64)
assert array_f64 == 2
println(array_bool)
assert array_bool == 3
println(array_i8)
assert array_i8 == 4
println(array_byte)
assert array_byte == 5
println(array_i16)
assert array_i16 == 6
println(array_u16)
assert array_u16 == 7
println(array_int)
assert array_int == 8
println(array_u32)
assert array_u32 == 9
println(array_string)
assert array_string == 10
println(array_rune)
assert array_rune == 11
}
fn test_clash_var_name_of_map() {
map_string_int := 1
a := map[string]int{}
assert '$a' == '{}'
assert map_string_int == 1
}