From 204fd8be03e45108ba37107b6f61a68334f247c5 Mon Sep 17 00:00:00 2001 From: Delyan Angelov Date: Tue, 3 Nov 2020 10:00:06 +0200 Subject: [PATCH] builder: improve the function redefinition detector --- vlib/v/builder/builder.v | 32 ++++++++++++++++++++++++++++---- 1 file changed, 28 insertions(+), 4 deletions(-) diff --git a/vlib/v/builder/builder.v b/vlib/v/builder/builder.v index bb23519573..06d5db4f39 100644 --- a/vlib/v/builder/builder.v +++ b/vlib/v/builder/builder.v @@ -309,26 +309,50 @@ fn (b &Builder) print_warnings_and_errors() { exit(1) } if b.table.redefined_fns.len > 0 { + mut total_conflicts := 0 for fn_name in b.table.redefined_fns { - eprintln('redefinition of function `$fn_name`') - // eprintln('previous declaration at') // Find where this function was already declared + mut redefines := []FunctionRedefinition{} + mut redefine_conflicts := map[string]int{} for file in b.parsed_files { for stmt in file.stmts { if stmt is ast.FnDecl { if stmt.name == fn_name { - fline := stmt.pos.line_nr - println('$file.path:$fline:') + fheader := stmt.stringify(b.table, 'main') + redefines << FunctionRedefinition{ + fpath: file.path + fline: stmt.pos.line_nr + f: stmt + fheader: fheader + } + redefine_conflicts[fheader]++ } } } } + if redefine_conflicts.len > 1 { + eprintln('redefinition of function `$fn_name`') + for redefine in redefines { + eprintln(util.formatted_error('conflicting declaration:', redefine.fheader, + redefine.fpath, redefine.f.pos)) + } + total_conflicts++ + } + } + if total_conflicts > 0 { b.show_total_warns_and_errors_stats() exit(1) } } } +struct FunctionRedefinition { + fpath string + fline int + fheader string + f ast.FnDecl +} + fn verror(s string) { util.verror('builder error', s) }