From 25d6dfe5c82ddd4784bc8728fe9c52859321c7a1 Mon Sep 17 00:00:00 2001 From: Swastik Date: Thu, 2 Nov 2023 19:50:18 +0530 Subject: [PATCH 1/3] checker: warn on unused imported functions used via `import math { sin, cos }` --- vlib/v/checker/checker.v | 3 +++ .../checker/tests/import_sym_fn_unused_warning_err.out | 10 ++++++++++ .../checker/tests/import_sym_fn_unused_warning_err.vv | 3 +++ 3 files changed, 16 insertions(+) create mode 100644 vlib/v/checker/tests/import_sym_fn_unused_warning_err.out create mode 100644 vlib/v/checker/tests/import_sym_fn_unused_warning_err.vv diff --git a/vlib/v/checker/checker.v b/vlib/v/checker/checker.v index bf992c0e314d59..a60f030c781ed2 100644 --- a/vlib/v/checker/checker.v +++ b/vlib/v/checker/checker.v @@ -2806,6 +2806,9 @@ fn (mut c Checker) import_stmt(node ast.Import) { if !func.is_pub { c.error('module `${node.mod}` function `${sym.name}()` is private', sym.pos) } + if func.usages != 1 { + c.warn('module `${node.mod}` function `${sym.name}()` is unused', sym.pos) + } continue } if _ := c.file.global_scope.find_const(name) { diff --git a/vlib/v/checker/tests/import_sym_fn_unused_warning_err.out b/vlib/v/checker/tests/import_sym_fn_unused_warning_err.out new file mode 100644 index 00000000000000..d0bb2c363db71a --- /dev/null +++ b/vlib/v/checker/tests/import_sym_fn_unused_warning_err.out @@ -0,0 +1,10 @@ +vlib/v/checker/tests/import_sym_fn_unused_warning_err.vv:1:15: warning: module `math` function `sin()` is unused + 1 | import math { sin, cos } + | ~~~ + 2 | + 3 | fn main() {} +vlib/v/checker/tests/import_sym_fn_unused_warning_err.vv:1:20: warning: module `math` function `cos()` is unused + 1 | import math { sin, cos } + | ~~~ + 2 | + 3 | fn main() {} diff --git a/vlib/v/checker/tests/import_sym_fn_unused_warning_err.vv b/vlib/v/checker/tests/import_sym_fn_unused_warning_err.vv new file mode 100644 index 00000000000000..e5a7d32933c895 --- /dev/null +++ b/vlib/v/checker/tests/import_sym_fn_unused_warning_err.vv @@ -0,0 +1,3 @@ +import math { sin, cos } + +fn main() {} From a25db295fb795bf38d95e4ebbac90feff0bb12fc Mon Sep 17 00:00:00 2001 From: Swastik Date: Thu, 2 Nov 2023 19:50:42 +0530 Subject: [PATCH 2/3] Revert "checker: warn on unused imported functions used via `import math { sin, cos }`" This reverts commit ddf0468f1c4f9af54ada162712c212214e58ca56. --- vlib/v/checker/checker.v | 3 --- .../checker/tests/import_sym_fn_unused_warning_err.out | 10 ---------- .../checker/tests/import_sym_fn_unused_warning_err.vv | 3 --- 3 files changed, 16 deletions(-) delete mode 100644 vlib/v/checker/tests/import_sym_fn_unused_warning_err.out delete mode 100644 vlib/v/checker/tests/import_sym_fn_unused_warning_err.vv diff --git a/vlib/v/checker/checker.v b/vlib/v/checker/checker.v index a60f030c781ed2..bf992c0e314d59 100644 --- a/vlib/v/checker/checker.v +++ b/vlib/v/checker/checker.v @@ -2806,9 +2806,6 @@ fn (mut c Checker) import_stmt(node ast.Import) { if !func.is_pub { c.error('module `${node.mod}` function `${sym.name}()` is private', sym.pos) } - if func.usages != 1 { - c.warn('module `${node.mod}` function `${sym.name}()` is unused', sym.pos) - } continue } if _ := c.file.global_scope.find_const(name) { diff --git a/vlib/v/checker/tests/import_sym_fn_unused_warning_err.out b/vlib/v/checker/tests/import_sym_fn_unused_warning_err.out deleted file mode 100644 index d0bb2c363db71a..00000000000000 --- a/vlib/v/checker/tests/import_sym_fn_unused_warning_err.out +++ /dev/null @@ -1,10 +0,0 @@ -vlib/v/checker/tests/import_sym_fn_unused_warning_err.vv:1:15: warning: module `math` function `sin()` is unused - 1 | import math { sin, cos } - | ~~~ - 2 | - 3 | fn main() {} -vlib/v/checker/tests/import_sym_fn_unused_warning_err.vv:1:20: warning: module `math` function `cos()` is unused - 1 | import math { sin, cos } - | ~~~ - 2 | - 3 | fn main() {} diff --git a/vlib/v/checker/tests/import_sym_fn_unused_warning_err.vv b/vlib/v/checker/tests/import_sym_fn_unused_warning_err.vv deleted file mode 100644 index e5a7d32933c895..00000000000000 --- a/vlib/v/checker/tests/import_sym_fn_unused_warning_err.vv +++ /dev/null @@ -1,3 +0,0 @@ -import math { sin, cos } - -fn main() {} From 010bdc79b37e5090ba0f43f0bbd39e265972fea3 Mon Sep 17 00:00:00 2001 From: Swastik Date: Tue, 18 Mar 2025 00:02:32 +0530 Subject: [PATCH 3/3] checke, cgen: implement alias operator overloading for generic struct parent type --- vlib/v/checker/assign.v | 22 +++++++++++++------ vlib/v/gen/c/assign.v | 13 +++++++++++ ...generic_parent_operator_overloading_test.v | 18 +++++++++++++++ 3 files changed, 46 insertions(+), 7 deletions(-) create mode 100644 vlib/v/tests/aliases/alias_generic_parent_operator_overloading_test.v diff --git a/vlib/v/checker/assign.v b/vlib/v/checker/assign.v index 6a943a62919b6b..5713b79f58cc18 100644 --- a/vlib/v/checker/assign.v +++ b/vlib/v/checker/assign.v @@ -797,20 +797,28 @@ or use an explicit `unsafe{ a[..] }`, if you do not want a copy of the slice.', if left_sym.kind == .struct && (left_sym.info as ast.Struct).generic_types.len > 0 { continue } - if method := left_sym.find_method(extracted_op) { + if method := left_sym.find_method_with_generic_parent(extracted_op) { if method.return_type != left_type_unwrapped { c.error('operator `${extracted_op}` must return `${left_name}` to be used as an assignment operator', node.pos) } } else { - if !parent_sym.is_primitive() { - if left_name == right_name { - c.error('undefined operation `${left_name}` ${extracted_op} `${right_name}`', - node.pos) - } else { - c.error('mismatched types `${left_name}` and `${right_name}`', + if method := parent_sym.find_method_with_generic_parent(extracted_op) { + if parent_sym.kind == .alias + && (parent_sym.info as ast.Alias).parent_type != method.return_type { + c.error('operator `${extracted_op}` must return `${left_name}` to be used as an assignment operator', node.pos) } + } else { + if !parent_sym.is_primitive() { + if left_name == right_name { + c.error('undefined operation `${left_name}` ${extracted_op} `${right_name}`', + node.pos) + } else { + c.error('mismatched types `${left_name}` and `${right_name}`', + node.pos) + } + } } } } diff --git a/vlib/v/gen/c/assign.v b/vlib/v/gen/c/assign.v index f53b5ed93b37c4..b6529c087d30c3 100644 --- a/vlib/v/gen/c/assign.v +++ b/vlib/v/gen/c/assign.v @@ -674,6 +674,19 @@ fn (mut g Gen) assign_stmt(node_ ast.AssignStmt) { g.write(';') } return + } else if left_sym.kind == .alias && g.table.final_sym(var_type).kind == .struct { + struct_info := g.table.final_sym(var_type) + if struct_info.info is ast.Struct && struct_info.info.generic_types.len > 0 { + mut method_name := struct_info.cname + '_' + util.replace_op(extracted_op) + method_name = g.generic_fn_name(struct_info.info.concrete_types, + method_name) + g.write(' = ${method_name}(') + g.expr(left) + g.write(', ') + g.expr(val) + g.writeln(');') + return + } } else { if g.table.final_sym(g.unwrap_generic(var_type)).kind == .array_fixed { g.go_back_to(pos) diff --git a/vlib/v/tests/aliases/alias_generic_parent_operator_overloading_test.v b/vlib/v/tests/aliases/alias_generic_parent_operator_overloading_test.v new file mode 100644 index 00000000000000..14717b3e3da2c1 --- /dev/null +++ b/vlib/v/tests/aliases/alias_generic_parent_operator_overloading_test.v @@ -0,0 +1,18 @@ +import math.vec + +type V2 = vec.Vec2[f32] + +fn test_alias_generic_parent_operator_overloading() { + a := V2{1, 1} + b := V2{10, 20} + + mut c := a + b + assert c.x == 11.0 + assert c.y == 21.0 + dump(c) + + c += a + assert c.x == 12.0 + assert c.y == 22.0 + dump(c) +}