Fix Exception default file/line always reporting Exception.h itself

__FILE__/__LINE__ are preprocessor macros - as default argument values
in the header they expand once, at the header declaration site, not at
each call site. Every throw relying on the defaults (all but File.cpp,
which passed them explicitly) reported Exception.h itself instead of
the real error location.

Switched the defaults to std::source_location::current(), which the
C++20 standard specifically defines to evaluate at the call site when
used as a default argument - unlike macros. Kept the same 4-parameter
signature so every existing call site, including ones that pass
__FILE__/__LINE__ explicitly, is unaffected.

Verified two ways: full-repo compile pass (identical result to before,
13/20 clean, same pre-existing StreamReader.h-blocked failures, nothing
new broken); a real runtime test - a throw relying on defaults from a
known line correctly reported that exact file/line via the caught
exceptions .file/.line members. Test file not included in this commit.
This commit is contained in:
Brad Arant committed 2026-08-22 19:52:44 -07:00
1 parent 29c9a5b855
commit 4082e82466
1 file changed
+15 -1
+15 -1
View File
@@ -4,6 +4,7 @@
#include <string.h> #include <string.h>
#include <string> #include <string>
#include <errno.h> #include <errno.h>
#include <source_location>
namespace coreutils { namespace coreutils {
@@ -15,7 +16,20 @@ namespace coreutils {
class Exception { class Exception {
public: public:
Exception(std::string text, std::string file = __FILE__, int line = __LINE__, int errorNumber = errno); ///
/// file/line default to the caller's actual location. std::source_location::current()
/// is specifically defined by the standard to evaluate at the call site when used as a
/// default argument - unlike __FILE__/__LINE__ (preprocessor macros, which were used
/// here previously and always expanded to this header's own declaration line instead
/// of the real throw site, since macro expansion happens before the compiler even sees
/// "default argument" as a concept). Explicit callers (e.g. throw Exception(msg,
/// __FILE__, __LINE__)) are unaffected - the signature is unchanged.
///
Exception(std::string text,
std::string file = std::source_location::current().file_name(),
int line = std::source_location::current().line(),
int errorNumber = errno);
std::string className; std::string className;
std::string file; std::string file;