1616#include < map>
1717#include < memory>
1818#include < ostream>
19+ #include < source_location>
1920#include < sstream>
2021#include < stack>
2122#include < stdexcept>
@@ -95,7 +96,30 @@ class Progress;
9596enum ToolId
9697{
9798 FOREACH_TOOL (GENERATE_ENUM )
98- SIZE // the number of tools, do not put anything after this
99+ SIZE // the number of tools, do not put anything after this
100+ };
101+
102+ // Captures the caller's source location alongside the log message
103+ struct LogMessage
104+ {
105+ std::string message;
106+ std::source_location loc;
107+
108+ LogMessage (const char * msg,
109+ const std::source_location& l = std::source_location::current())
110+ : message(msg), loc(l)
111+ {
112+ }
113+ LogMessage (const std::string& msg,
114+ const std::source_location& l = std::source_location::current())
115+ : message(msg), loc(l)
116+ {
117+ }
118+ LogMessage (std::string_view msg,
119+ const std::source_location& l = std::source_location::current())
120+ : message(msg), loc(l)
121+ {
122+ }
99123};
100124
101125class Logger
@@ -143,43 +167,57 @@ class Logger
143167 }
144168
145169 template <typename ... Args>
146- void info (ToolId tool,
147- int id,
148- const std::string& message,
149- const Args&... args)
170+ void info (ToolId tool, int id, LogMessage log_message, const Args&... args)
150171 {
151- log (tool, spdlog::level::level_enum::info, id, message, args...);
172+ log (tool,
173+ spdlog::level::level_enum::info,
174+ id,
175+ log_message.loc ,
176+ log_message.message ,
177+ args...);
152178 }
153179
154180 template <typename ... Args>
155- void warn (ToolId tool,
156- int id,
157- const std::string& message,
158- const Args&... args)
181+ void warn (ToolId tool, int id, LogMessage log_message, const Args&... args)
159182 {
160183 warning_count_++;
161- log (tool, spdlog::level::level_enum::warn, id, message, args...);
184+ log (tool,
185+ spdlog::level::level_enum::warn,
186+ id,
187+ log_message.loc ,
188+ log_message.message ,
189+ args...);
162190 }
163191
164192 template <typename ... Args>
165193 __attribute__ ((noreturn)) void error (ToolId tool,
166194 int id,
167- const std::string& message ,
195+ LogMessage log_message ,
168196 const Args&... args)
169197 {
170198 error_count_++;
171- log (tool, spdlog::level::err, id, message, args...);
199+ log (tool,
200+ spdlog::level::err,
201+ id,
202+ log_message.loc ,
203+ log_message.message ,
204+ args...);
172205 // Exception should be caught by swig error handler.
173206 throw std::runtime_error (fmt::format (" {}-{:04}" , tool_names_[tool], id));
174207 }
175208
176209 template <typename ... Args>
177210 __attribute__ ((noreturn)) void critical (ToolId tool,
178211 int id,
179- const std::string& message ,
212+ LogMessage log_message ,
180213 const Args&... args)
181214 {
182- log (tool, spdlog::level::level_enum::critical, id, message, args...);
215+ log (tool,
216+ spdlog::level::level_enum::critical,
217+ id,
218+ log_message.loc ,
219+ log_message.message ,
220+ args...);
183221 exit (EXIT_FAILURE );
184222 }
185223
@@ -277,6 +315,7 @@ class Logger
277315 void log (ToolId tool,
278316 spdlog::level::level_enum level,
279317 int id,
318+ std::source_location loc,
280319 const std::string& message,
281320 const Args&... args)
282321 {
@@ -285,13 +324,25 @@ class Logger
285324 auto & counter = message_counters_[tool][id];
286325 auto count = counter++;
287326 if (count < max_message_print) {
288- logger_->log (level,
289- FMT_RUNTIME (" [{} {}-{:04d}] " + message
290- + spdlog::details::os::default_eol),
291- level_names[level],
292- tool_names_[tool],
293- id,
294- args...);
327+ if (source_lines_enabled_ && level >= spdlog::level::warn) {
328+ logger_->log (level,
329+ FMT_RUNTIME (" [{} {}-{:04d}] [{}:{}] " + message
330+ + spdlog::details::os::default_eol),
331+ level_names[level],
332+ tool_names_[tool],
333+ id,
334+ loc.file_name (),
335+ loc.line (),
336+ args...);
337+ } else {
338+ logger_->log (level,
339+ FMT_RUNTIME (" [{} {}-{:04d}] " + message
340+ + spdlog::details::os::default_eol),
341+ level_names[level],
342+ tool_names_[tool],
343+ id,
344+ args...);
345+ }
295346 return ;
296347 }
297348
@@ -372,6 +423,7 @@ class Logger
372423 bool debug_on_{false };
373424 std::atomic_int warning_count_{0 };
374425 std::atomic_int error_count_{0 };
426+ bool source_lines_enabled_{true };
375427 static constexpr const char * level_names[]
376428 = {" TRACE" , " DEBUG" , " INFO" , " WARNING" , " ERROR" , " CRITICAL" , " OFF" };
377429 static constexpr const char * pattern_ = " %v" ;
@@ -400,9 +452,9 @@ struct test_ostream
400452{
401453 public:
402454 template <class T >
403- static auto test (int ) -> decltype(std::declval<std::ostream>()
404- << std::declval<T>(),
405- std::true_type());
455+ static auto test (int )
456+ -> decltype(std::declval<std::ostream>() << std::declval<T>(),
457+ std::true_type());
406458
407459 template <class >
408460 static auto test (...) -> std::false_type;
0 commit comments