1 //===-- Log.cpp -------------------------------------------------*- C++ -*-===//
3 // The LLVM Compiler Infrastructure
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
8 //===----------------------------------------------------------------------===//
10 #include "lldb/lldb-python.h"
21 // Other libraries and framework includes
23 #include "lldb/Core/Debugger.h"
24 #include "lldb/Core/Log.h"
25 #include "lldb/Core/PluginManager.h"
26 #include "lldb/Core/StreamFile.h"
27 #include "lldb/Core/StreamString.h"
28 #include "lldb/Host/Host.h"
29 #include "lldb/Host/TimeValue.h"
30 #include "lldb/Host/Mutex.h"
31 #include "lldb/Interpreter/Args.h"
33 using namespace lldb_private;
42 Log::Log (const StreamSP &stream_sp) :
43 m_stream_sp(stream_sp),
60 Log::GetOptions() const
78 //----------------------------------------------------------------------
79 // All logging eventually boils down to this function call. If we have
80 // a callback registered, then we call the logging callback. If we have
81 // a valid file handle, we also log to the file.
82 //----------------------------------------------------------------------
84 Log::PrintfWithFlagsVarArg (uint32_t flags, const char *format, va_list args)
88 static uint32_t g_sequence_id = 0;
90 // Enabling the thread safe logging actually deadlocks right now.
91 // Need to fix this at some point.
92 // static Mutex g_LogThreadedMutex(Mutex::eMutexTypeRecursive);
93 // Mutex::Locker locker (g_LogThreadedMutex);
95 // Add a sequence ID if requested
96 if (m_options.Test (LLDB_LOG_OPTION_PREPEND_SEQUENCE))
97 header.Printf ("%u ", ++g_sequence_id);
99 // Timestamp if requested
100 if (m_options.Test (LLDB_LOG_OPTION_PREPEND_TIMESTAMP))
102 TimeValue now = TimeValue::Now();
103 header.Printf ("%9d.%6.6d ", now.seconds(), now.nanoseconds());
106 // Add the process and thread if requested
107 if (m_options.Test (LLDB_LOG_OPTION_PREPEND_PROC_AND_THREAD))
108 header.Printf ("[%4.4x/%4.4" PRIx64 "]: ", getpid(), Host::GetCurrentThreadID());
110 // Add the process and thread if requested
111 if (m_options.Test (LLDB_LOG_OPTION_PREPEND_THREAD_NAME))
113 std::string thread_name (Host::GetThreadName (getpid(), Host::GetCurrentThreadID()));
114 if (!thread_name.empty())
115 header.Printf ("%s ", thread_name.c_str());
118 header.PrintfVarArg (format, args);
119 m_stream_sp->Printf("%s\n", header.GetData());
121 if (m_options.Test (LLDB_LOG_OPTION_BACKTRACE))
122 Host::Backtrace (*m_stream_sp, 1024);
123 m_stream_sp->Flush();
129 Log::PutCString (const char *cstr)
135 //----------------------------------------------------------------------
136 // Simple variable argument logging with flags.
137 //----------------------------------------------------------------------
139 Log::Printf(const char *format, ...)
142 va_start (args, format);
143 PrintfWithFlagsVarArg (0, format, args);
148 Log::VAPrintf (const char *format, va_list args)
150 PrintfWithFlagsVarArg (0, format, args);
154 //----------------------------------------------------------------------
155 // Simple variable argument logging with flags.
156 //----------------------------------------------------------------------
158 Log::PrintfWithFlags (uint32_t flags, const char *format, ...)
161 va_start (args, format);
162 PrintfWithFlagsVarArg (flags, format, args);
166 //----------------------------------------------------------------------
167 // Print debug strings if and only if the global debug option is set to
169 //----------------------------------------------------------------------
171 Log::Debug (const char *format, ...)
173 if (GetOptions().Test(LLDB_LOG_OPTION_DEBUG))
176 va_start (args, format);
177 PrintfWithFlagsVarArg (LLDB_LOG_FLAG_DEBUG, format, args);
183 //----------------------------------------------------------------------
184 // Print debug strings if and only if the global debug option is set to
186 //----------------------------------------------------------------------
188 Log::DebugVerbose (const char *format, ...)
190 if (GetOptions().AllSet (LLDB_LOG_OPTION_DEBUG | LLDB_LOG_OPTION_VERBOSE))
193 va_start (args, format);
194 PrintfWithFlagsVarArg (LLDB_LOG_FLAG_DEBUG | LLDB_LOG_FLAG_VERBOSE, format, args);
200 //----------------------------------------------------------------------
201 // Log only if all of the bits are set
202 //----------------------------------------------------------------------
204 Log::LogIf (uint32_t bits, const char *format, ...)
206 if (m_options.AllSet (bits))
209 va_start (args, format);
210 PrintfWithFlagsVarArg (0, format, args);
216 //----------------------------------------------------------------------
217 // Printing of errors that are not fatal.
218 //----------------------------------------------------------------------
220 Log::Error (const char *format, ...)
222 char *arg_msg = NULL;
224 va_start (args, format);
225 ::vasprintf (&arg_msg, format, args);
230 PrintfWithFlags (LLDB_LOG_FLAG_ERROR, "error: %s", arg_msg);
235 //----------------------------------------------------------------------
236 // Printing of errors that ARE fatal. Exit with ERR exit code
238 //----------------------------------------------------------------------
240 Log::FatalError (int err, const char *format, ...)
242 char *arg_msg = NULL;
244 va_start (args, format);
245 ::vasprintf (&arg_msg, format, args);
250 PrintfWithFlags (LLDB_LOG_FLAG_ERROR | LLDB_LOG_FLAG_FATAL, "error: %s", arg_msg);
257 //----------------------------------------------------------------------
258 // Printing of warnings that are not fatal only if verbose mode is
260 //----------------------------------------------------------------------
262 Log::Verbose (const char *format, ...)
264 if (m_options.Test(LLDB_LOG_OPTION_VERBOSE))
267 va_start (args, format);
268 PrintfWithFlagsVarArg (LLDB_LOG_FLAG_VERBOSE, format, args);
273 //----------------------------------------------------------------------
274 // Printing of warnings that are not fatal only if verbose mode is
276 //----------------------------------------------------------------------
278 Log::WarningVerbose (const char *format, ...)
280 if (m_options.Test(LLDB_LOG_OPTION_VERBOSE))
282 char *arg_msg = NULL;
284 va_start (args, format);
285 ::vasprintf (&arg_msg, format, args);
290 PrintfWithFlags (LLDB_LOG_FLAG_WARNING | LLDB_LOG_FLAG_VERBOSE, "warning: %s", arg_msg);
295 //----------------------------------------------------------------------
296 // Printing of warnings that are not fatal.
297 //----------------------------------------------------------------------
299 Log::Warning (const char *format, ...)
301 char *arg_msg = NULL;
303 va_start (args, format);
304 ::vasprintf (&arg_msg, format, args);
309 PrintfWithFlags (LLDB_LOG_FLAG_WARNING, "warning: %s", arg_msg);
314 typedef std::map <ConstString, Log::Callbacks> CallbackMap;
315 typedef CallbackMap::iterator CallbackMapIter;
317 typedef std::map <ConstString, LogChannelSP> LogChannelMap;
318 typedef LogChannelMap::iterator LogChannelMapIter;
321 // Surround our callback map with a singleton function so we don't have any
322 // global initializers.
326 static CallbackMap g_callback_map;
327 return g_callback_map;
330 static LogChannelMap &
333 static LogChannelMap g_channel_map;
334 return g_channel_map;
338 Log::RegisterLogChannel (const ConstString &channel, const Log::Callbacks &log_callbacks)
340 GetCallbackMap().insert(std::make_pair(channel, log_callbacks));
344 Log::UnregisterLogChannel (const ConstString &channel)
346 return GetCallbackMap().erase(channel) != 0;
350 Log::GetLogChannelCallbacks (const ConstString &channel, Log::Callbacks &log_callbacks)
352 CallbackMap &callback_map = GetCallbackMap ();
353 CallbackMapIter pos = callback_map.find(channel);
354 if (pos != callback_map.end())
356 log_callbacks = pos->second;
359 ::memset (&log_callbacks, 0, sizeof(log_callbacks));
364 Log::EnableAllLogChannels
366 StreamSP &log_stream_sp,
367 uint32_t log_options,
368 const char **categories,
369 Stream *feedback_strm
372 CallbackMap &callback_map = GetCallbackMap ();
373 CallbackMapIter pos, end = callback_map.end();
375 for (pos = callback_map.begin(); pos != end; ++pos)
376 pos->second.enable (log_stream_sp, log_options, categories, feedback_strm);
378 LogChannelMap &channel_map = GetChannelMap ();
379 LogChannelMapIter channel_pos, channel_end = channel_map.end();
380 for (channel_pos = channel_map.begin(); channel_pos != channel_end; ++channel_pos)
382 channel_pos->second->Enable (log_stream_sp, log_options, feedback_strm, categories);
388 Log::AutoCompleteChannelName (const char *channel_name, StringList &matches)
390 LogChannelMap &map = GetChannelMap ();
391 LogChannelMapIter pos, end = map.end();
392 for (pos = map.begin(); pos != end; ++pos)
394 const char *pos_channel_name = pos->first.GetCString();
395 if (channel_name && channel_name[0])
397 if (NameMatches (channel_name, eNameMatchStartsWith, pos_channel_name))
399 matches.AppendString(pos_channel_name);
403 matches.AppendString(pos_channel_name);
409 Log::DisableAllLogChannels (Stream *feedback_strm)
411 CallbackMap &callback_map = GetCallbackMap ();
412 CallbackMapIter pos, end = callback_map.end();
413 const char *categories[1] = {NULL};
415 for (pos = callback_map.begin(); pos != end; ++pos)
416 pos->second.disable (categories, feedback_strm);
418 LogChannelMap &channel_map = GetChannelMap ();
419 LogChannelMapIter channel_pos, channel_end = channel_map.end();
420 for (channel_pos = channel_map.begin(); channel_pos != channel_end; ++channel_pos)
421 channel_pos->second->Disable (categories, feedback_strm);
427 Log::Callbacks log_callbacks = { DisableLog, EnableLog, ListLogCategories };
428 Log::RegisterLogChannel (ConstString("lldb"), log_callbacks);
434 DisableAllLogChannels (NULL);
438 Log::ListAllLogChannels (Stream *strm)
440 CallbackMap &callback_map = GetCallbackMap ();
441 LogChannelMap &channel_map = GetChannelMap ();
443 if (callback_map.empty() && channel_map.empty())
445 strm->PutCString ("No logging channels are currently registered.\n");
449 CallbackMapIter pos, end = callback_map.end();
450 for (pos = callback_map.begin(); pos != end; ++pos)
451 pos->second.list_categories (strm);
455 for (idx = 0; (name = PluginManager::GetLogChannelCreateNameAtIndex (idx)) != NULL; ++idx)
457 LogChannelSP log_channel_sp(LogChannel::FindPlugin (name));
459 log_channel_sp->ListCategories (strm);
464 Log::GetVerbose() const
466 // FIXME: This has to be centralized between the stream and the log...
467 if (m_options.Test(LLDB_LOG_OPTION_VERBOSE))
471 return m_stream_sp->GetVerbose();
475 //------------------------------------------------------------------
476 // Returns true if the debug flag bit is set in this stream.
477 //------------------------------------------------------------------
479 Log::GetDebug() const
482 return m_stream_sp->GetDebug();
488 LogChannel::FindPlugin (const char *plugin_name)
490 LogChannelSP log_channel_sp;
491 LogChannelMap &channel_map = GetChannelMap ();
492 ConstString log_channel_name (plugin_name);
493 LogChannelMapIter pos = channel_map.find (log_channel_name);
494 if (pos == channel_map.end())
496 ConstString const_plugin_name (plugin_name);
497 LogChannelCreateInstance create_callback = PluginManager::GetLogChannelCreateCallbackForPluginName (const_plugin_name);
500 log_channel_sp.reset(create_callback());
503 // Cache the one and only loaded instance of each log channel
504 // plug-in after it has been loaded once.
505 channel_map[log_channel_name] = log_channel_sp;
511 // We have already loaded an instance of this log channel class,
512 // so just return the cached instance.
513 log_channel_sp = pos->second;
515 return log_channel_sp;
518 LogChannel::LogChannel () :
523 LogChannel::~LogChannel ()