Logo AND Algorithmique Numérique Distribuée

Public GIT Repository
Further cleanups
[simgrid.git] / src / xbt / log.c
index 123ad9d..2183371 100644 (file)
@@ -239,7 +239,7 @@ XBT_LOG_NEW_DEFAULT_SUBCATEGORY(SA, VSS);
 
 int main() {
        / * Now set the parent's priority.  (the string would typcially be a runtime option) * /
-       xbt_log_control_set("SA.thresh=3");
+       xbt_log_control_set("SA.thresh:3");
 
        / * This request is enabled, because WARNING >= INFO. * /
        CWARN2(VSS, "Low fuel level.");
@@ -270,13 +270,13 @@ Any SimGrid program can furthermore be configured at run time by passing a
 are synonyms provided by aestheticism). You can provide several of those
 arguments to change the setting of several categories, they will be applied
 from left to right. So, 
-\verbatim --xbt-log="root.thres=debug root.thres=critical"\endverbatim 
+\verbatim --xbt-log="root.thres:debug root.thres:critical"\endverbatim 
 should disable any logging.
 
 Note that the quotes on above line are mandatory because there is a space in
 the argument, so we are protecting ourselves from the shell, not from SimGrid.
 We could also reach the same effect with this:
-\verbatim --xbt-log=root.thres=debug --xbt-log=root.thres=critical\endverbatim 
+\verbatim --xbt-log=root.thres:debug --xbt-log=root.thres:critical\endverbatim 
 
 \section log_use_misc 3.2 Misc and Caveats
 
@@ -339,7 +339,7 @@ welcome here, too.
 
 */
 
-
+\f
 typedef struct {
   char *catname;
   e_xbt_log_priority_t thresh;
@@ -351,7 +351,7 @@ static void _free_setting(void *s) {
   xbt_log_setting_t set=(xbt_log_setting_t)s;
   if (set) {
     free(set->catname);
-/*    free(set); FIXME: uncommenting this leads to segfault when more than one chunk is passed as gras-log */
+    //free(set); /*FIXME: uncommenting this leads to segfault when more than one chunk is passed as gras-log */
   }
 }
 
@@ -378,6 +378,10 @@ XBT_LOG_NEW_CATEGORY(msg,"All MSG categories");
 XBT_LOG_NEW_CATEGORY(simix,"All SIMIX categories");
 XBT_LOG_NEW_DEFAULT_SUBCATEGORY(log,xbt,"Loggings from the logging mechanism itself");
 
+/** @brief Get all logging settings from the command line
+ * 
+ * xbt_log_control_set() is called on each string we got from cmd line
+ */
 void xbt_log_init(int *argc,char **argv) {
        int i,j;
        char *opt;
@@ -413,135 +417,102 @@ void xbt_log_exit(void) {
   VERB0("Exited log");
 }
 
-static void _apply_control(xbt_log_category_t cat) {
+void _xbt_log_event_log( xbt_log_event_t ev, const char *fmt, ...) {
+  
+  xbt_log_category_t cat = ev->cat;
+  
+  va_start(ev->ap, fmt);
+  while(1) {
+    xbt_log_appender_t appender = cat->appender;
+    if (appender != NULL) {
+       
+      appender->do_append(appender, ev, fmt);
+    }
+    if (!cat->willLogToParent)
+      break;
+
+    cat = cat->parent;
+  } 
+  va_end(ev->ap);
+}
+
+/*
+ * This gets called the first time a category is referenced and performs the
+ * initialization. 
+ * Also resets threshold to inherited!
+ */
+int _xbt_log_cat_init(xbt_log_category_t category,
+                     e_xbt_log_priority_t priority) {
   int cursor;
   xbt_log_setting_t setting=NULL;
   int found = 0;
   s_xbt_log_event_t _log_ev;
-  
-  
+       
+  if(category == &_XBT_LOGV(XBT_LOG_ROOT_CAT)){
+    category->threshold = xbt_log_priority_info;/* xbt_log_priority_debug*/;
+    category->appender = xbt_log_default_appender;
+  } else {
+
+    if (!category->parent)
+      category->parent = &_XBT_LOGV(XBT_LOG_ROOT_CAT);
+    
+    xbt_log_parent_set(category, category->parent);
+  }
+
+  /* Apply the control */  
   if (!xbt_log_settings)
-    return;
+    return priority >= category->threshold;
+  
+  xbt_assert0(category,"NULL category");
+  xbt_assert(category->name);
   
-  xbt_assert0(cat,"NULL category");
-  xbt_assert(cat->name);
-
   xbt_dynar_foreach(xbt_log_settings,cursor,setting) {
     xbt_assert0(setting,"Damnit, NULL cat in the list");
     xbt_assert1(setting->catname,"NULL setting(=%p)->catname",(void*)setting);
-
-    if (!strcmp(setting->catname,cat->name)) {
-       
     
+    if (!strcmp(setting->catname,category->name)) {
+      
       found = 1;
-
-      xbt_log_threshold_set(cat, setting->thresh);
+      
+      xbt_log_threshold_set(category, setting->thresh);
       xbt_dynar_cursor_rm(xbt_log_settings,&cursor);
+      free(setting);
 
-
-      if (cat->threshold <= xbt_log_priority_debug) {
-        _log_ev.cat = cat;
+      if (category->threshold <= xbt_log_priority_debug) {
+        _log_ev.cat = category;
         _log_ev.priority = xbt_log_priority_debug;
         _log_ev.fileName = __FILE__ ;
         _log_ev.functionName = _XBT_FUNCTION ;
         _log_ev.lineNum = __LINE__ ;
-
+       
        _xbt_log_event_log(&_log_ev,
-                "Apply settings for category '%s': set threshold to %s (=%d)",
-                cat->name,
-                xbt_log_priority_names[cat->threshold], cat->threshold);
+                          "Apply settings for category '%s': set threshold to %s (=%d)",
+                          category->name,
+                          xbt_log_priority_names[category->threshold], category->threshold);
       }
     }
-   
   }
   
-  if (!found && cat->threshold <= xbt_log_priority_verbose) {
-       
-    _log_ev.cat = cat;
+  if (!found && category->threshold <= xbt_log_priority_verbose) {
+    
+    _log_ev.cat = category;
     _log_ev.priority = xbt_log_priority_verbose;
     _log_ev.fileName = __FILE__ ;
     _log_ev.functionName = _XBT_FUNCTION ;
     _log_ev.lineNum = __LINE__ ;
-
+    
     _xbt_log_event_log(&_log_ev,
-                       "Category '%s': inherited threshold = %s (=%d)",
-                       cat->name,
-                       xbt_log_priority_names[cat->threshold], cat->threshold);
+                      "Category '%s': inherited threshold = %s (=%d)",
+                      category->name,
+                      xbt_log_priority_names[category->threshold], category->threshold);
   }
-  
-
-}
-
-void _xbt_log_event_log( xbt_log_event_t ev, const char *fmt, ...) {
-  
-
-  xbt_log_category_t cat = ev->cat;
-  
-  
-
-
-  va_start(ev->ap, fmt);
-  while(1) {
-    xbt_log_appender_t appender = cat->appender;
-    if (appender != NULL) {
-       
-      appender->do_append(appender, ev, fmt);
-    }
-    if (!cat->willLogToParent)
-      break;
-
-    cat = cat->parent;
-  } 
-  va_end(ev->ap);
-}
-
-static void _cat_init(xbt_log_category_t category) 
-{
-       
-       
-       if(category == &_XBT_LOGV(XBT_LOG_ROOT_CAT)){
-       category->threshold = xbt_log_priority_info;/* xbt_log_priority_debug*/;
-       category->appender = xbt_log_default_appender;
-       } 
-       else 
-       {
-
-               #if (defined(_WIN32) && !defined(DLL_STATIC))
-               if(!category->parent){
-                       category->parent = &_XBT_LOGV(XBT_LOG_ROOT_CAT);
-               }
-               #endif
-       
-       xbt_log_parent_set(category, category->parent);
-       }
-  
-  _apply_control(category);
-  
-}
-
-/*
- * This gets called the first time a category is referenced and performs the
- * initialization. 
- * Also resets threshold to inherited!
- */
-int _xbt_log_cat_init(e_xbt_log_priority_t priority,xbt_log_category_t category) 
-{
     
-       _cat_init(category);
-       
-       
-       
-               
-       return priority >= category->threshold;
+  return priority >= category->threshold;
 }
 
 void xbt_log_parent_set(xbt_log_category_t cat,xbt_log_category_t parent) 
 {
        
-       
        xbt_assert0(cat,"NULL category to be given a parent");
        xbt_assert1(parent,"The parent category of %s is NULL",cat->name);
        
@@ -568,16 +539,15 @@ void xbt_log_parent_set(xbt_log_category_t cat,xbt_log_category_t parent)
        
        if (parent->threshold == xbt_log_priority_uninitialized){
                
-               _cat_init(parent);
+         _xbt_log_cat_init(parent,
+                           xbt_log_priority_uninitialized/* ignored*/);
        }
        
        cat->threshold = parent->threshold;
        
        cat->isThreshInherited = 1;
        
-       
-       
-} /* log_setParent */
+}
 
 static void _set_inherited_thresholds(xbt_log_category_t cat) {
        
@@ -606,29 +576,28 @@ void xbt_log_threshold_set(xbt_log_category_t   cat,
  
 }
 
-static void _xbt_log_parse_setting(const char*        control_string,
-                                   xbt_log_setting_t set) {
+static xbt_log_setting_t _xbt_log_parse_setting(const char* control_string) {
+
+  xbt_log_setting_t set = xbt_new(s_xbt_log_setting_t,1);
   const char *name, *dot, *eq;
   
-  
-  
   set->catname=NULL;
   if (!*control_string) 
-    return;
+    return set;
   DEBUG1("Parse log setting '%s'",control_string);
 
   control_string += strspn(control_string, " ");
   name = control_string;
   control_string += strcspn(control_string, ".= ");
   dot = control_string;
-  control_string += strcspn(control_string, "= ");
+  control_string += strcspn(control_string, ":= ");
   eq = control_string;
   control_string += strcspn(control_string, " ");
 
-  xbt_assert1(*dot == '.' && *eq == '=',
+  xbt_assert1(*dot == '.' && (*eq == '=' || *eq == ':'),
               "Invalid control string '%s'",control_string);
 
-  if (!strncmp(dot + 1, "thresh", min((size_t)(eq - dot - 1),strlen("thresh")))) {
+  if (!strncmp(dot + 1, "thresh", (size_t)(eq - dot - 1))) {
     int i;
     char *neweq=xbt_strdup(eq+1);
     char *p=neweq-1;
@@ -649,13 +618,14 @@ static void _xbt_log_parse_setting(const char*        control_string,
     if (i<xbt_log_priority_infinite) {
       set->thresh= (e_xbt_log_priority_t) i;
     } else {
-      xbt_assert1(FALSE,"Unknown priority name: %s",eq+1);
+      THROW1(arg_error,0,
+            "Unknown priority name: %s (must be one of: trace,debug,verbose,info,warning,error,critical)",eq+1);
     }
     free(neweq);
   } else {
     char buff[512];
     snprintf(buff,min(512,eq - dot - 1),"%s",dot+1);
-    xbt_assert1(FALSE,"Unknown setting of the log category: %s",buff);
+    THROW1(arg_error,0,"Unknown setting of the log category: %s",buff);
   }
   set->catname=(char*)xbt_malloc(dot - name+1);
     
@@ -663,52 +633,19 @@ static void _xbt_log_parse_setting(const char*        control_string,
   set->catname[dot-name]='\0'; /* Just in case */
   DEBUG1("This is for cat '%s'", set->catname);
   
+  return set;
 }
 
 static xbt_log_category_t _xbt_log_cat_searchsub(xbt_log_category_t cat,char *name) {
   xbt_log_category_t child;
   
-  
-  if (!strcmp(cat->name,name)) {
+  if (!strcmp(cat->name,name)) 
     return cat;
-  }
-  for(child=cat->firstChild ; child != NULL; child = child->nextSibling) {
-    return _xbt_log_cat_searchsub(child,name);
-  }
-  
-  THROW0(not_found_error,0,"No such category");
-}
 
-static void _cleanup_double_spaces(char *s) {
-  char *p = s;
-  int   e = 0;
-  
-  while (1) {
-    if (!*p)
-      goto end;
-    
-    if (!isspace(*p))
-      break;
-    
-    p++;
-  }
-  
-  e = 1;
+  for(child=cat->firstChild ; child != NULL; child = child->nextSibling) 
+    return _xbt_log_cat_searchsub(child,name);
   
-  do {
-    if (e)
-      *s++ = *p;
-    
-    if (!*++p)
-      goto end;
-    
-    if (e ^ !isspace(*p))
-      if ((e = !e))
-       *s++ = ' ';
-  } while (1);
-
- end:
-  *s = '\0';
+  THROW1(not_found_error,0,"No such category: %s", name);
 }
 
 /**
@@ -717,7 +654,7 @@ static void _cleanup_double_spaces(char *s) {
  *
  * Typically passed a command-line argument. The string has the syntax:
  *
- *      ( [category] "." [keyword] "=" value (" ")... )...
+ *      ( [category] "." [keyword] ":" value (" ")... )...
  *
  * where [category] is one the category names (see \ref XBT_log_cats for a complete list) 
  * and keyword is one of the following:
@@ -725,20 +662,15 @@ static void _cleanup_double_spaces(char *s) {
  *    - thres: category's threshold priority. Possible values:
  *             TRACE,DEBUG,VERBOSE,INFO,WARNING,ERROR,CRITICAL
  *             
- *
- * \warning
- * This routine may only be called once and that must be before any other
- * logging command! Typically, this is done from main().
- * \todo the previous warning seems a bit old and need double checking
  */
 void xbt_log_control_set(const char* control_string) {
   xbt_log_setting_t set;
   char *cs;
   char *p;
   int done = 0;
-  
-  
-  
+
+  if (!control_string || control_string[0] == '\0')
+    return;
   DEBUG1("Parse log settings '%s'",control_string);
   if (control_string == NULL)
     return;
@@ -746,10 +678,9 @@ void xbt_log_control_set(const char* control_string) {
     xbt_log_settings = xbt_dynar_new(sizeof(xbt_log_setting_t),
                                       _free_setting);
 
-  set = xbt_new(s_xbt_log_setting_t,1);
   cs=xbt_strdup(control_string);
 
-  _cleanup_double_spaces(cs);
+  xbt_str_strip_spaces(cs);
 
   while (!done) {
     xbt_log_category_t cat=NULL;
@@ -764,7 +695,7 @@ void xbt_log_control_set(const char* control_string) {
       p=cs;
       done = 1;
     }
-    _xbt_log_parse_setting(p,set);
+    set = _xbt_log_parse_setting(p);
 
     TRY {
       cat = _xbt_log_cat_searchsub(&_XBT_LOGV(root),set->catname);
@@ -778,20 +709,16 @@ void xbt_log_control_set(const char* control_string) {
       DEBUG0("Store for further application");
       DEBUG1("push %p to the settings",(void*)set);
       xbt_dynar_push(xbt_log_settings,&set);
-      /* malloc in advance the next slot */
-      set = xbt_new(s_xbt_log_setting_t,1);
     } 
 
     if (found) {
       DEBUG0("Apply directly");
-      free(set->catname);
       xbt_log_threshold_set(cat,set->thresh);
+      _free_setting((void*)set);
+      free(set);
     }
   }
-  free(set);
   free(cs);
-  
-  
 } 
 
 void xbt_log_appender_set(xbt_log_category_t cat, xbt_log_appender_t app) {