Use sec_initial_uid() in the places where being root doesn't matter,
[samba.git] / source3 / lib / debug.c
index 6c1bfea04f74fa2a7ba421218b7cf648ae5f6161..83211dd5e6e2e7ef46f9f6a55198c9f35907ab4c 100644 (file)
@@ -90,11 +90,9 @@ bool    AllowDebugChange = True;
 */
 bool    override_logfile;
 
-static TALLOC_CTX *tmp_debug_ctx;
-
 /*
  * This is to allow assignment to DEBUGLEVEL before the debug
- * system has been initialised.
+ * system has been initialized.
  */
 static int debug_all_class_hack = 1;
 static bool debug_all_class_isset_hack = True;
@@ -183,6 +181,8 @@ static char **classname_table = NULL;
  Free memory pointed to by global pointers.
 ****************************************************************************/
 
+static bool initialized;
+
 void gfree_debugsyms(void)
 {
        int i;
@@ -194,13 +194,23 @@ void gfree_debugsyms(void)
                SAFE_FREE( classname_table );
        }
 
-       if ( DEBUGLEVEL_CLASS != &debug_all_class_hack )
+       if ( DEBUGLEVEL_CLASS != &debug_all_class_hack ) {
                SAFE_FREE( DEBUGLEVEL_CLASS );
+               DEBUGLEVEL_CLASS = &debug_all_class_hack;
+       }
 
-       if ( DEBUGLEVEL_CLASS_ISSET != &debug_all_class_isset_hack )
+       if ( DEBUGLEVEL_CLASS_ISSET != &debug_all_class_isset_hack ) {
                SAFE_FREE( DEBUGLEVEL_CLASS_ISSET );
+               DEBUGLEVEL_CLASS_ISSET = &debug_all_class_isset_hack;
+       }
 
        SAFE_FREE(format_bufr);
+
+       debug_num_classes = 0;
+
+       debug_level = DEBUGLEVEL_CLASS;
+
+       initialized = false;
 }
 
 /****************************************************************************
@@ -429,8 +439,9 @@ static bool debug_parse_params(char **params)
 
        /* Fill in new debug class levels */
        for (; i < debug_num_classes && params[i]; i++) {
-               if ((class_name=strtok(params[i],":")) &&
-                       (class_level=strtok(NULL, "\0")) &&
+               char *saveptr;
+               if ((class_name = strtok_r(params[i],":", &saveptr)) &&
+                       (class_level = strtok_r(NULL, "\0", &saveptr)) &&
             ((ndx = debug_lookup_classname(class_name)) != -1)) {
                                DEBUGLEVEL_CLASS[ndx] = atoi(class_level);
                                DEBUGLEVEL_CLASS_ISSET[ndx] = True;
@@ -459,14 +470,14 @@ bool debug_parse_levels(const char *params_str)
        if (AllowDebugChange == False)
                return True;
 
-       params = str_list_make(params_str, NULL);
+       params = str_list_make_v3(talloc_tos(), params_str, NULL);
 
        if (debug_parse_params(params)) {
                debug_dump_status(5);
-               str_list_free(&params);
+               TALLOC_FREE(params);
                return True;
        } else {
-               str_list_free(&params);
+               TALLOC_FREE(params);
                return False;
        }
 }
@@ -475,7 +486,7 @@ bool debug_parse_levels(const char *params_str)
  Receive a "set debug level" message.
 ****************************************************************************/
 
-static void debug_message(struct messaging_context *msg_ctx,
+void debug_message(struct messaging_context *msg_ctx,
                          void *private_data, 
                          uint32_t msg_type, 
                          struct server_id src,
@@ -529,13 +540,12 @@ Init debugging (one time stuff)
 
 void debug_init(void)
 {
-       static bool initialised = False;
        const char **p;
 
-       if (initialised)
+       if (initialized)
                return;
 
-       initialised = True;
+       initialized = true;
 
        for(p = default_classname_table; *p; p++) {
                debug_add_class(*p);
@@ -566,7 +576,9 @@ void setup_logging(const char *pname, bool interactive)
        stdout_logging = False;
        if (dbf) {
                x_fflush(dbf);
-               (void) x_fclose(dbf);
+                if (dbf != x_stdout) {
+                        (void) x_fclose(dbf);
+                }
        }
 
        dbf = NULL;
@@ -591,6 +603,15 @@ void setup_logging(const char *pname, bool interactive)
 #endif
 }
 
+/**
+   Just run logging to stdout for this program 
+*/
+_PUBLIC_ void setup_logging_stdout(void)
+{
+       setup_logging(NULL, True);
+}
+
+
 /***************************************************************************
  Set the logfile name.
 **************************************************************************/
@@ -666,8 +687,8 @@ bool reopen_logs( void )
        force_check_log_size();
        (void)umask(oldumask);
 
-       /* Take over stderr to catch ouput into logs */
-       if (dbf && sys_dup2(x_fileno(dbf), 2) == -1) {
+       /* Take over stderr to catch output into logs */
+       if (dbf && dup2(x_fileno(dbf), 2) == -1) {
                close_low_fds(True); /* Close stderr too, if dup2 can't point it
                                        at the logfile */
        }
@@ -717,7 +738,7 @@ void check_log_size( void )
         *  loop check do a new check as root.
         */
 
-       if( geteuid() != 0 )
+       if( geteuid() != sec_initial_uid() )
                return;
 
        if(log_overflow || !need_to_check_log_size() )
@@ -725,7 +746,8 @@ void check_log_size( void )
 
        maxlog = lp_max_log_size() * 1024;
 
-       if( sys_fstat( x_fileno( dbf ), &st ) == 0 && st.st_size > maxlog ) {
+       if(sys_fstat(x_fileno(dbf), &st, false) == 0
+          && st.st_ex_size > maxlog ) {
                (void)reopen_logs();
                if( dbf && get_file_size( debugf ) > maxlog ) {
                        char *name = NULL;
@@ -818,7 +840,7 @@ void check_log_size( void )
                /* map debug levels to syslog() priorities
                 * note that not all DEBUG(0, ...) calls are
                 * necessarily errors */
-               static int priority_map[] = {
+               static const int priority_map[4] = {
                        LOG_ERR,     /* 0 */
                        LOG_WARNING, /* 1 */
                        LOG_NOTICE,  /* 2 */
@@ -826,17 +848,24 @@ void check_log_size( void )
                };
                int     priority;
                char *msgbuf = NULL;
+               int ret;
 
-               if( syslog_level >= ( sizeof(priority_map) / sizeof(priority_map[0]) ) || syslog_level < 0)
+               if( syslog_level >= ARRAY_SIZE(priority_map) || syslog_level < 0)
                        priority = LOG_DEBUG;
                else
                        priority = priority_map[syslog_level];
 
+               /*
+                * Specify the facility to interoperate with other syslog
+                * callers (vfs_full_audit for example).
+                */
+               priority |= SYSLOG_FACILITY;
+
                va_start(ap, format_str);
-               vasprintf(&msgbuf, format_str, ap);
+               ret = vasprintf(&msgbuf, format_str, ap);
                va_end(ap);
 
-               if (msgbuf) {
+               if (ret != -1) {
                        syslog(priority, "%s", msgbuf);
                }
                SAFE_FREE(msgbuf);
@@ -858,8 +887,6 @@ void check_log_size( void )
        }
 
  done:
-       TALLOC_FREE(tmp_debug_ctx);
-
        errno = old_errno;
 
        return( 0 );
@@ -969,7 +996,7 @@ void dbgflush( void )
 
 ****************************************************************************/
 
-bool dbghdr(int level, int cls, const char *file, const char *func, int line)
+bool dbghdrclass(int level, int cls, const char *location, const char *func)
 {
        /* Ensure we don't lose any real errno value. */
        int old_errno = errno;
@@ -1027,12 +1054,14 @@ bool dbghdr(int level, int cls, const char *file, const char *func, int line)
                /* Print it all out at once to prevent split syslog output. */
                if( lp_debug_prefix_timestamp() ) {
                    (void)Debug1( "[%s, %2d%s] ",
-                       current_timestring(lp_debug_hires_timestamp()), level,
-                       header_str);
+                       current_timestring(talloc_tos(),
+                                          lp_debug_hires_timestamp()),
+                       level, header_str);
                } else {
-                   (void)Debug1( "[%s, %2d%s] %s:%s(%d)\n",
-                       current_timestring(lp_debug_hires_timestamp()), level,
-                       header_str, file, func, line );
+                   (void)Debug1( "[%s, %2d%s] %s(%s)\n",
+                       current_timestring(talloc_tos(),
+                                          lp_debug_hires_timestamp()),
+                       level, header_str, location, func );
                }
        }
 
@@ -1040,6 +1069,12 @@ bool dbghdr(int level, int cls, const char *file, const char *func, int line)
        return( True );
 }
 
+bool dbghdr(int level, const char *location, const char *func)
+{
+       /* For compatibility with Samba 4, which doesn't have debug classes */
+       return dbghdrclass(level, 0, location, func);
+}
+
 /***************************************************************************
  Add text to the body of the "current" debug message via the format buffer.
 
@@ -1058,12 +1093,13 @@ bool dbghdr(int level, int cls, const char *file, const char *func, int line)
        va_list ap;
        char *msgbuf = NULL;
        bool ret = true;
+       int res;
 
        va_start(ap, format_str);
-       vasprintf(&msgbuf, format_str, ap);
+       res = vasprintf(&msgbuf, format_str, ap);
        va_end(ap);
 
-       if (msgbuf) {
+       if (res != -1) {
                format_debug_text(msgbuf);
        } else {
                ret = false;
@@ -1071,14 +1107,3 @@ bool dbghdr(int level, int cls, const char *file, const char *func, int line)
        SAFE_FREE(msgbuf);
        return ret;
 }
-
-/*
- * Get us a temporary talloc context usable just for DEBUG arguments
- */
-TALLOC_CTX *debug_ctx(void)
-{
-        if (tmp_debug_ctx == NULL) {
-                tmp_debug_ctx = talloc_named_const(NULL, 0, "debug_ctx");
-        }
-        return tmp_debug_ctx;
-}