From b18d0e3702a7bcb97734d3d77f33166dd42e8146 Mon Sep 17 00:00:00 2001 From: abul Date: Fri, 18 Apr 2025 19:01:02 +0530 Subject: [PATCH 1/2] added --- compiler/src/dmd/expressionsem.d | 16 ++++++++++++---- compiler/src/dmd/funcsem.d | 12 ++++++++---- compiler/src/dmd/templatesem.d | 2 +- compiler/src/dmd/typesem.d | 7 ++++++- compiler/test/fail_compilation/fix21167.d | 11 +++++++++++ 5 files changed, 38 insertions(+), 10 deletions(-) create mode 100644 compiler/test/fail_compilation/fix21167.d diff --git a/compiler/src/dmd/expressionsem.d b/compiler/src/dmd/expressionsem.d index 8ea9262998af..a63ffe34aab9 100644 --- a/compiler/src/dmd/expressionsem.d +++ b/compiler/src/dmd/expressionsem.d @@ -6723,7 +6723,7 @@ private extern (C++) final class ExpressionSemanticVisitor : Visitor return setError(); } - void errorHelper(const(char)* failMessage) scope + void errorHelper(const(char)* failMessage, Loc argLoc = Loc.initial) scope { OutBuffer buf; buf.writeByte('('); @@ -6736,7 +6736,11 @@ private extern (C++) final class ExpressionSemanticVisitor : Visitor .error(exp.loc, "%s `%s` is not callable using argument types `%s`", p, exp.e1.toErrMsg(), buf.peekChars()); if (failMessage) - errorSupplemental(exp.loc, "%s", failMessage); + { + // Use the argument's location if provided, otherwise use the function call location + Loc errorLoc = argLoc != Loc.initial ? argLoc : exp.loc; + errorSupplemental(errorLoc, "%s", failMessage); + } } if (callMatch(exp.f, tf, null, exp.argumentList, 0, &errorHelper, sc) == MATCH.nomatch) @@ -6799,7 +6803,7 @@ private extern (C++) final class ExpressionSemanticVisitor : Visitor exp.f = exp.f.toAliasFunc(); TypeFunction tf = cast(TypeFunction)exp.f.type; - void errorHelper2(const(char)* failMessage) scope + void errorHelper2(const(char)* failMessage, Loc argLoc = Loc.initial) scope { OutBuffer buf; buf.writeByte('('); @@ -6817,7 +6821,11 @@ private extern (C++) final class ExpressionSemanticVisitor : Visitor .error(exp.loc, "%s `%s` is not callable using argument types `%s`", exp.f.kind(), exp.f.toErrMsg(), buf.peekChars()); if (failMessage) - errorSupplemental(exp.loc, "%s", failMessage); + { + // Use the argument's location if provided, otherwise use the function call location + Loc errorLoc = argLoc != Loc.initial ? argLoc : exp.loc; + errorSupplemental(errorLoc, "%s", failMessage); + } .errorSupplemental(exp.f.loc, "`%s%s` declared here", exp.f.toPrettyChars(), parametersTypeToChars(tf.parameterList)); exp.f = null; } diff --git a/compiler/src/dmd/funcsem.d b/compiler/src/dmd/funcsem.d index a02d9b778100..c994c4d5b65e 100644 --- a/compiler/src/dmd/funcsem.d +++ b/compiler/src/dmd/funcsem.d @@ -1837,12 +1837,14 @@ FuncDeclaration resolveFuncCall(Loc loc, Scope* sc, Dsymbol s, } bool calledHelper; - void errorHelper(const(char)* failMessage) scope + void errorHelper(const(char)* failMessage, Loc argLoc = Loc.initial) scope { .error(loc, "%s `%s%s%s` is not callable using argument types `%s`", fd.kind(), fd.toPrettyChars(), parametersTypeToChars(tf.parameterList), tf.modToChars(), fargsBuf.peekChars()); - errorSupplemental(loc, failMessage); + // Use the argument's location if provided, otherwise use the function call location + Loc errorLoc = argLoc != Loc.initial ? argLoc : loc; + errorSupplemental(errorLoc, failMessage); calledHelper = true; } @@ -1910,9 +1912,11 @@ FuncDeclaration resolveFuncCall(Loc loc, Scope* sc, Dsymbol s, } } - void errorHelper2(const(char)* failMessage) scope + void errorHelper2(const(char)* failMessage, Loc argLoc = Loc.initial) scope { - errorSupplemental(loc, failMessage); + // Use the argument's location if provided, otherwise use the function call location + Loc errorLoc = argLoc != Loc.initial ? argLoc : loc; + errorSupplemental(errorLoc, failMessage); } functionResolve(m, orig_s, loc, sc, tiargs, tthis, argumentList, &errorHelper2); diff --git a/compiler/src/dmd/templatesem.d b/compiler/src/dmd/templatesem.d index a2ef8459742d..c280bb175506 100644 --- a/compiler/src/dmd/templatesem.d +++ b/compiler/src/dmd/templatesem.d @@ -1886,7 +1886,7 @@ extern (D) RootObject declareParameter(TemplateDeclaration td, Scope* sc, Templa * errorHelper = delegate to send error message to if not null */ void functionResolve(ref MatchAccumulator m, Dsymbol dstart, Loc loc, Scope* sc, Objects* tiargs, - Type tthis, ArgumentList argumentList, void delegate(const(char)*) scope errorHelper = null) + Type tthis, ArgumentList argumentList, void delegate(const(char)*, Loc = Loc.initial) scope errorHelper = null) { version (none) { diff --git a/compiler/src/dmd/typesem.d b/compiler/src/dmd/typesem.d index 05fc8f8cb3ab..d587d7e0f29a 100644 --- a/compiler/src/dmd/typesem.d +++ b/compiler/src/dmd/typesem.d @@ -703,7 +703,7 @@ extern (D) bool checkComplexTransition(Type type, Loc loc, Scope* sc) * MATCHxxxx */ extern (D) MATCH callMatch(FuncDeclaration fd, TypeFunction tf, Type tthis, ArgumentList argumentList, - int flag = 0, void delegate(const(char)*) scope errorHelper = null, Scope* sc = null) + int flag = 0, void delegate(const(char)*, Loc = Loc.initial) scope errorHelper = null, Scope* sc = null) { //printf("callMatch() fd: %s, tf: %s\n", fd ? fd.ident.toChars() : "null", toChars(tf)); MATCH match = MATCH.exact; // assume exact match @@ -872,7 +872,12 @@ extern (D) MATCH callMatch(FuncDeclaration fd, TypeFunction tf, Type tthis, Argu u + 1, parameterToChars(p, tf, false)); // If an error happened previously, `pMessage` was already filled else if (buf.length == 0) + { buf.writestring(tf.getParamError(args[u], p)); + // Use the argument's location for the error message instead of the function call location + errorHelper(buf.peekChars(), args[u].loc); + return MATCH.nomatch; + } errorHelper(buf.peekChars()); } diff --git a/compiler/test/fail_compilation/fix21167.d b/compiler/test/fail_compilation/fix21167.d new file mode 100644 index 000000000000..68fcdc756aaa --- /dev/null +++ b/compiler/test/fail_compilation/fix21167.d @@ -0,0 +1,11 @@ +void f(int, int, int){} + +void main() +{ + f( + 1, + "foo", + 3 + ); + +} From 188faac420c8d50ddd7a3932435fd9f11f57bf49 Mon Sep 17 00:00:00 2001 From: abul Date: Fri, 18 Apr 2025 19:11:03 +0530 Subject: [PATCH 2/2] error --- compiler/test/fail_compilation/fix21167.d | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/compiler/test/fail_compilation/fix21167.d b/compiler/test/fail_compilation/fix21167.d index 68fcdc756aaa..197526d4d142 100644 --- a/compiler/test/fail_compilation/fix21167.d +++ b/compiler/test/fail_compilation/fix21167.d @@ -1,3 +1,11 @@ +/* +TEST_OUTPUT: +--- +fail_compilation/fix21167.d(13): Error: function `f` is not callable using argument types `(int, string, int)` +fail_compilation/fix21167.d(15): cannot pass argument `"foo"` of type `string` to parameter `int __param_1` +fail_compilation/fix21167.d(9): `fix21167.f(int __param_0, int __param_1, int __param_2)` declared here +--- +*/ void f(int, int, int){} void main()