Skip to content

Commit

Permalink
Allow module / function specific debug logging
Browse files Browse the repository at this point in the history
Just setting mce to debug mode generates so much noise it is no
longer useful for debugging. After the changes for example

  mce -T -l'tklock.c:*datapipe_*' -l'tklock.c:*except*'

can be utilized to get debug logging only from datapipe changes
seen by tklock module and the exception state machine activity
resulting from them.
  • Loading branch information
spiiroin committed Jan 16, 2014
1 parent 363d4ea commit 3306556
Show file tree
Hide file tree
Showing 3 changed files with 69 additions and 8 deletions.
64 changes: 59 additions & 5 deletions mce-log.c
Expand Up @@ -18,6 +18,11 @@
* You should have received a copy of the GNU Lesser General Public
* License along with mce. If not, see <http://www.gnu.org/licenses/>.
*/

#include <stdlib.h>
#include <stdbool.h>
#include <fnmatch.h>

#include <glib.h>
#include <glib/gprintf.h>

Expand Down Expand Up @@ -111,7 +116,7 @@ void mce_log_file(loglevel_t loglevel, const char *const file,

loglevel = mce_log_level_normalize(loglevel);

if( mce_log_p(loglevel) ) {
if( mce_log_p_(loglevel, file, function) ) {
gchar *msg = 0;

va_start(args, fmt);
Expand Down Expand Up @@ -181,6 +186,45 @@ void mce_log_close(void)
closelog();
}

static GSList *mce_log_patterns = 0;
static GHashTable *mce_log_functions = 0;

void mce_log_add_pattern(const char *pat)
{
// NB these are never released by desing

mce_log_patterns = g_slist_prepend(mce_log_patterns, strdup(pat));

if( !mce_log_functions )
mce_log_functions = g_hash_table_new_full(g_str_hash, g_str_equal,
free, 0);
}

static bool mce_log_check_pattern(const char *func)
{
gpointer hit = 0;

if( !mce_log_functions )
goto EXIT;

if( (hit = g_hash_table_lookup(mce_log_functions, func)) )
goto EXIT;

hit = GINT_TO_POINTER(1);

for( GSList *item = mce_log_patterns; item; item = item->next ) {
const char *pat = item->data;
if( fnmatch(pat, func, 0) != 0 )
continue;
hit = GINT_TO_POINTER(2);
break;
}
g_hash_table_replace(mce_log_functions, strdup(func), hit);

EXIT:
return GPOINTER_TO_INT(hit) > 1;
}

/**
* Log level testing predicate
*
Expand All @@ -191,11 +235,21 @@ void mce_log_close(void)
*
* @return 1 if logging at givel level is enabled, 0 if not
*/
int mce_log_p(const loglevel_t loglevel)
int mce_log_p_(const loglevel_t loglevel,
const char *const file,
const char *const func)
{
if( loglevel < LL_CRIT )
return logverbosity >= LL_NOTICE;
return logverbosity >= loglevel;
if( mce_log_functions && file && func ) {
char temp[256];
snprintf(temp, sizeof temp, "%s:%s", file, func);
if( mce_log_check_pattern(temp) )
return true;
}

if( loglevel < LL_CRIT )
return logverbosity >= LL_NOTICE;

return logverbosity >= loglevel;
}

#endif /* OSSOLOG_COMPILE */
6 changes: 4 additions & 2 deletions mce-log.h
Expand Up @@ -40,6 +40,8 @@ typedef enum {
LL_DEFAULT = LL_WARN, /**< Default log level */
} loglevel_t;

void mce_log_add_pattern(const char *pat);

#ifdef OSSOLOG_COMPILE
void mce_log_file(loglevel_t loglevel, const char *const file,
const char *const function, const char *const fmt, ...)
Expand All @@ -49,7 +51,8 @@ void mce_log_file(loglevel_t loglevel, const char *const file,
void mce_log_set_verbosity(const int verbosity);
void mce_log_open(const char *const name, const int facility, const int type);
void mce_log_close(void);
int mce_log_p(const loglevel_t loglevel);
int mce_log_p_(const loglevel_t loglevel, const char *const file, const char *const function);
#define mce_log_p(LEV_) mce_log_p_(LEV_,__FILE__,__FUNCTION__)
#else
/** Dummy version used when logging is disabled at compile time */
#define mce_log(_loglevel, _fmt, ...) do {} while (0)
Expand All @@ -62,5 +65,4 @@ int mce_log_p(const loglevel_t loglevel);
/** Dummy version used when logging is disabled at compile time */
#define mce_log_p(_loglevel) 0
#endif /* OSSOLOG_COMPILE */

#endif /* _MCE_LOG_H_ */
7 changes: 6 additions & 1 deletion mce.c
Expand Up @@ -187,6 +187,7 @@ static const char usage_fmt[] =
" -v, --verbose increase debug message verbosity\n"
" -t, --trace=<what> enable domain specific debug logging;\n"
" supported values: \"wakelocks\"\n"
" -l, --log-function=<file:func> add function logging override\n"
" -h, --help display this help and exit\n"
" -V, --version output version information and exit\n"
"\n"
Expand Down Expand Up @@ -764,7 +765,7 @@ int main(int argc, char **argv)
gboolean debugmode = FALSE;
gboolean systemd_notify = FALSE;

const char optline[] = "dsTSMDqvhVt:n";
const char optline[] = "dsTSMDqvhVt:l:n";

struct option const options[] = {
{ "systemd", no_argument, 0, 'n' },
Expand All @@ -779,6 +780,7 @@ int main(int argc, char **argv)
{ "help", no_argument, 0, 'h' },
{ "version", no_argument, 0, 'V' },
{ "trace", required_argument, 0, 't' },
{ "log-function", required_argument, 0, 'l' },
{ 0, 0, 0, 0 }
};

Expand Down Expand Up @@ -839,6 +841,9 @@ int main(int argc, char **argv)
if( !mce_enable_trace(optarg) )
exit(EXIT_FAILURE);
break;
case 'l':
mce_log_add_pattern(optarg);
break;
default:
usage();
exit(EXIT_FAILURE);
Expand Down

0 comments on commit 3306556

Please sign in to comment.