Admin logging - suggestions for events to log?

Michael Krax mk-samba at krax.net
Thu Aug 10 11:10:28 GMT 2006


Everybody,

first of all a small status update on my SoC project:
* a user specific format string may now be specified 
  (as of now, this is undocumented and works-for-me; there are some
  small inconsistencies I am working on & it needs testing by me)

I have enclosed a patch to SAMBA_3_0 (bzr branch).  I suppose it is
easier that way for most of you to have a quick look at the code.


I would really appreciate it if some of you could make 1 or 2 suggestions
for more calls to adminlog.

For now, it supports 
* user add and delete
* printer add (couldn't check)
* configuration change (=reload)
* failure to authentify against DC


BTW,
configuration options are:
* admin log = Yes/No

* admin log event types = all -or- auth printing passdb etc.

* admin log levels = all -or- info warn error (+ audit_failure audit_success)
  The last two values correspond to the EventLog documentation.

(* admin log format = please do not specify for now)


I am looking forward to your suggestions ... and any other hints.

Ciao,
Michael

-- 
Michael Krax
Phone +49(0)30.76765923  Mobile +49(0)163.7325923
-------------- next part --------------
diff -Pur -X diff-exclude samba-bzr-vanilla/source/include/admin_log.h SAMBA_3_0.bzr/source/include/admin_log.h
--- samba-bzr-vanilla/source/include/admin_log.h	1970-01-01 01:00:00.000000000 +0100
+++ SAMBA_3_0.bzr/source/include/admin_log.h	2006-08-04 10:05:25.624592184 +0200
@@ -0,0 +1,121 @@
+/* 
+   Unix SMB/CIFS implementation.
+   admin log header file
+   Copyright (C) Michael Krax 2006
+   
+   This program is free software; you can redistribute it and/or modify
+   it under the terms of the GNU General Public License as published by
+   the Free Software Foundation; either version 2 of the License, or
+   (at your option) any later version.
+   
+   This program is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+   GNU General Public License for more details.
+   
+   You should have received a copy of the GNU General Public License
+   along with this program; if not, write to the Free Software
+   Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+*/
+
+#ifndef _ADMIN_LOG_H
+#define _ADMIN_LOG_H
+
+
+/* see also lib/admin_log.c */
+
+
+/*
+  Event Ids 
+*/
+
+/* First part: generic event ids */
+
+#define ADMIN_LOG_EVENTID_CREATE_USER 0x0001
+#define ADMIN_LOG_EVENTID_DELETE_USER 0x0002
+#define ADMIN_LOG_EVENTID_ADD_PRINTER 0x0003
+#define ADMIN_LOG_EVENTID_CONFIGURATION_RELOADED 0x0004
+#define ADMIN_LOG_EVENTID_AUTH_FAILED 0x0005
+
+#define ADMIN_LOG_EVENTID_NTSTATUS 0xfffe  /* use ntstatus code instead */
+
+/* Second part: type specific event ids */
+
+/*
+  Event Type definitions
+  Event types < 0x100 are DBGC debuglevel class ids (see debug.h)
+  Event types > 0x100 are only known to admin_log
+*/
+
+#define ADMIN_LOG_EVENTTYPE_ALL DBGC_ALL
+
+#define ADMIN_LOG_EVENTTYPE_USER 0x0100
+#define ADMIN_LOG_EVENTTYPE_PARAM 0x0101
+
+
+
+
+typedef struct _admin_log_event admin_log_event;
+struct _admin_log_event {
+  char *szUser;  /* local user name, if not available: remote */
+  BOOL bUserVerified; /* the user is authenticated against this server */
+  char *szMachine; /* remote machine name */
+  uint16 iLogLevel; /* provided by calling function */
+  uint16 iEventType; /* provided by calling function */
+  uint16 iEventId; /* unique Id provided by calling function 
+		      can be used to look up error/solution in database */
+  char *szDescription; /* description (freeform), 
+			  provided by calling function */
+  NTSTATUS ntStatus; /* if provided by calling function */
+  
+  time_t tTimestamp; /* event time */
+  char *szSambaVersion; /* local version id */
+  char *szClientOS; /* remote server type and version */
+};
+
+
+/*
+  Log levels
+  All combinations are possible
+*/
+
+#define ADMIN_LOG_LEVEL_INFORMATION      0x0001
+#define ADMIN_LOG_LEVEL_WARNING          0x0002
+#define ADMIN_LOG_LEVEL_ERROR            0x0004
+#define ADMIN_LOG_LEVEL_AUDIT_SUCCESS    0x0008
+#define ADMIN_LOG_LEVEL_AUDIT_FAILURE    0x0010
+
+#define ADMIN_LOG_LEVEL_ALL              0x001f
+
+
+struct _admin_log_level {
+  int iLevel;
+  const char *szName;
+  int syslog_prio;
+};
+
+struct _admin_log_type {
+  int iType;
+  const char *szName;
+};
+
+/* defined to have only one point where we transfer "..." from macro
+   space to c function calls */
+#define ADMINLOG_TYPEID( typeid, priority, ntstatus, user, machine, ... ) \
+  admin_log_typeid( typeid, priority, ntstatus, user, machine, __VA_ARGS__ );
+
+/* basic call using DBGC_CLASS */
+#define ADMINLOG( id, priority, user, machine, ... ) \
+  ADMINLOG_TYPEID( (DBGC_CLASS << 16) | id, priority, NT_STATUS_OK, \
+		   user, machine, __VA_ARGS__ )
+
+/* separate event_type and event_id params */
+#define ADMINLOG_TYPE_ID( type, id, priority, user, machine, ... ) \
+  ADMINLOG_TYPEID( ((type) << 16) | (id), priority, NT_STATUS_OK, \
+		   user, machine, __VA_ARGS__ )
+
+#define ADMINLOG_NTSTATUS( id, ntstatus, priority, user, machine, ... )	\
+  ADMINLOG_TYPEID( (DBGC_CLASS << 16) | (id),				\
+		   priority, ntstatus, user, machine, __VA_ARGS__ )
+
+#endif // _ADMIN_LOG_H
diff -Pur -X diff-exclude samba-bzr-vanilla/source/include/smb.h SAMBA_3_0.bzr/source/include/smb.h
--- samba-bzr-vanilla/source/include/smb.h	2006-08-10 12:09:46.030986750 +0200
+++ SAMBA_3_0.bzr/source/include/smb.h	2006-08-10 10:56:18.967562500 +0200
@@ -72,6 +72,9 @@
 /* Debugging stuff */
 #include "debug.h"
 
+/* administrative logging support */
+#include "admin_log.h"
+
 /* this defines the error codes that receive_smb can put in smb_read_error */
 #define READ_TIMEOUT 1
 #define READ_EOF 2
diff -Pur -X diff-exclude samba-bzr-vanilla/source/lib/admin_log.c SAMBA_3_0.bzr/source/lib/admin_log.c
--- samba-bzr-vanilla/source/lib/admin_log.c	1970-01-01 01:00:00.000000000 +0100
+++ SAMBA_3_0.bzr/source/lib/admin_log.c	2006-08-07 11:40:01.502153750 +0200
@@ -0,0 +1,421 @@
+/* -*-Mode: c; c-basic-offset:8-*-
+   Unix SMB/CIFS implementation.
+   Samba utility functions
+   Admin debug library
+
+   Copyright (C) Michael Krax  2006
+
+   This program is free software; you can redistribute it and/or modify
+   it under the terms of the GNU General Public License as published by
+   the Free Software Foundation; either version 2 of the License, or
+   (at your option) any later version.
+
+   This program is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+   GNU General Public License for more details.
+
+   You should have received a copy of the GNU General Public License
+   along with this program; if not, write to the Free Software
+   Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+*/
+
+#include "includes.h"
+
+
+#define _ADMIN_LOG_SPECIAL_DEBUG 1
+
+
+uint16 _admin_log_levels = ADMIN_LOG_LEVEL_ALL; /* for now */
+
+static int _admin_log_levels_parsed = 0;
+
+static const struct _admin_log_level admin_log_level_strings[] = {
+	{ ADMIN_LOG_LEVEL_INFORMATION, "information", LOG_INFO },
+	{ ADMIN_LOG_LEVEL_WARNING, "warning", LOG_WARNING },
+	{ ADMIN_LOG_LEVEL_ERROR, "error", LOG_ERR },
+	{ ADMIN_LOG_LEVEL_AUDIT_SUCCESS, "audit:success", LOG_INFO },
+	{ ADMIN_LOG_LEVEL_AUDIT_FAILURE, "audit:failure", LOG_ERR },
+	{ ADMIN_LOG_LEVEL_ALL, "all", -1 },
+	{ 0, NULL }
+};
+
+static const struct _admin_log_type admin_log_type_strings[] = {
+	{ ADMIN_LOG_EVENTTYPE_USER, "User specific event" },
+	{ ADMIN_LOG_EVENTTYPE_PARAM, "param" },
+	{ 0, NULL }
+};
+
+/* check if we log this event using the current configuration 
+   function could be converted to a macro
+   but the current form is more readable
+*/
+int admin_log_check_logging(uint32 eventTypeId, uint16 priority)
+{
+	if (! lp_admin_log( ) ) {
+#ifdef _ADMIN_LOG_SPECIAL_DEBUG
+		DEBUG( 100, ( "Admin log disabled in config\n" ) );
+#endif
+		return 0;
+	}
+
+	if (! (priority & admin_log_levels( )) ) {
+#ifdef _ADMIN_LOG_SPECIAL_DEBUG
+		DEBUG( 100, ( "Priority %i not logged\n", priority ) );
+#endif
+		return 0;
+	}
+
+	if (! ( admin_log_event_type( eventTypeId >> 16 ) ) ) {
+#ifdef _ADMIN_LOG_SPECIAL_DEBUG
+		DEBUG( 50, ( "Event Type %i not logged\n", eventTypeId >> 16 ) );
+#endif
+		return 0;
+	}
+
+	/* continue execution of admin_log */
+	return 1;
+}
+
+/* eventTypeId is a combination of (eventType << 16 | eventId)
+   eventType is DBGC_CLASS
+   priority is admin_log-priority */
+void admin_log_typeid(uint32 eventTypeId, uint16 priority,
+		      NTSTATUS ntstatus_code,
+		      const char *user, const char *machine,
+		      const char *format_str, ...)
+{
+	va_list ap;
+	void *mem_ctx = NULL;
+
+	admin_log_event *ale = NULL;
+
+	DEBUG( 100, ( "Admin log started for eventtypeid 0x%x with priority %i\n", 
+		      eventTypeId, priority ) );
+
+	/* check if we log at this level 
+	   we do this before any memory is allocated */
+	if (! admin_log_check_logging( eventTypeId, priority ) ) { 
+		DEBUG( 10, ("Admin log disabled 0x%x %i\n", eventTypeId, priority) );
+		return;
+	} else {
+#ifdef _ADMIN_LOG_SPECIAL_DEBUG
+		DEBUG( 100, ( "Admin logging eventTypeId 0x%x with prio %i\n",
+			      eventTypeId, priority ) );
+#endif
+	}
+			
+
+	mem_ctx = talloc_new( NULL );
+	ale = talloc( mem_ctx, admin_log_event );
+
+	/* fill the ale */
+	init_ale( ale );
+
+	ale->iEventType = eventTypeId >> 16;
+	ale->iEventId = eventTypeId & 0xffff;
+	ale->iLogLevel = priority;
+	ale->ntStatus = ntstatus_code;
+
+	if (user) 
+		ale->szUser = talloc_strdup( ale, user );
+	if (machine)
+		ale->szMachine = talloc_strdup( ale, machine );
+
+	/* process remaining params */
+	va_start( ap, format_str );
+	admin_log_formatstr( ale, format_str, ap );
+	va_end( ap );
+
+	/* do it */
+	admin_log_do_logging( ale );
+
+	/* clean up */
+	talloc_free( mem_ctx );
+  
+}
+
+/* does perform the actual logging */
+void admin_log_do_logging( admin_log_event *ale )
+{
+	char *logentry = NULL;
+
+	if (!ale) return;
+
+	logentry = admin_log_formatentry( ale );
+
+	if (logentry) {
+#if defined(HAVE_SYSLOG)
+		syslog( _admin_log_prio_to_syslog( ale->iLogLevel ), 
+			"%s", logentry );
+#else
+		DEBUG(0,("%s", logentry ));
+#endif
+	}
+	else 
+		{
+			/* error */
+		}
+}
+
+void init_ale( admin_log_event *ale )
+{
+	if (!ale) return;
+
+	ale->szUser = NULL;
+	ale->bUserVerified = 0;
+	ale->szMachine = NULL;
+
+	ale->iLogLevel = 0;
+	ale->iEventType = 0;
+	ale->iEventId = 0;
+	ale->szDescription = NULL;
+	ale->ntStatus = NT_STATUS_OK;
+
+	time( &ale->tTimestamp );
+
+	ale->szSambaVersion = talloc_strdup( ale, SAMBA_VERSION_STRING );
+	ale->szClientOS = NULL;
+}
+
+
+/* replaces %[a-z] etc., writes to ale->szDescription */
+void admin_log_formatstr( admin_log_event *ale, 
+			  const char *format_str, va_list ap )
+{
+	if (!ale) 
+		return;
+
+	if (ale->szDescription) 
+		{
+			talloc_free( ale->szDescription );
+			ale->szDescription = NULL;
+		}
+
+	if (!format_str) return;
+
+	ale->szDescription = talloc_vasprintf( ale, format_str, ap );
+
+}
+
+/* Creates a string based upon info in ale
+   [date-localhost-prefix] 0x03340003 \\MACHINE USER (Event-type-as-text) Description
+   with 0x03340003 being the event type<<16|id; \\MACHINE could be omitted.
+
+   If user specific format is set, use this.
+   In addition to the macros documented in man smb.conf,
+   user may use:
+    %e event type and id (event type<<16|id)
+    %E event type as text
+    %b event description (if available)
+    %n NT status code description
+*/
+
+char *admin_log_formatentry( admin_log_event *ale )
+{
+	char *result = NULL;
+	char *event_type_text = NULL;
+
+	if (!ale) 
+		return NULL;
+
+	event_type_text = _admin_log_event_type_to_text( ale );
+
+	if (!lp_admin_log_format()) {
+		result = talloc_asprintf( ale, "0x%08x \\\\%s \"%s\" (%s) %s", 
+					  (ale->iEventType << 16 | ale->iEventId),
+					  ale->szMachine, 
+					  ale->szUser,
+					  event_type_text,
+					  ale->szDescription);
+
+
+		if (!NT_STATUS_IS_OK(ale->ntStatus)) 
+			result = talloc_asprintf_append( result, ". NT Status: %s", 
+							 get_friendly_nt_error_msg( ale->ntStatus )
+							 );
+	} else {
+		/* use format string */
+		result = talloc_sub_admin_log(
+					      ale,
+					      lp_admin_log_format(),
+					      ale->szUser,
+					      NULL /* domain */,
+					      0, /* uid */
+					      0, /* gid */
+					      ale,
+					      event_type_text);
+	}
+	
+	return( result );
+}
+
+/*  void admin_log_connstruct(uint16 eventType, uint16 priority,
+    struct conn_struct *cs,
+    const char *format_str, ...);
+    / * on the assumption that conn_struct provides user and machine */
+
+
+
+/* private function calls */
+
+const char *_admin_log_type_from_index( int al_class )
+{
+	int i;
+	for( i=0;admin_log_type_strings[i].iType;i++ ) {
+		if (admin_log_type_strings[i].iType == al_class) {
+			return admin_log_type_strings[i].szName;
+		}
+	}
+	return NULL;
+}
+
+char *_admin_log_event_type_to_text( admin_log_event *ale )
+{
+	char *result = NULL;
+
+	if (!ale) 
+		return NULL;
+
+	if (ale->iEventType < ADMIN_LOG_EVENTTYPE_USER) {
+		/* use debugging class information */
+		const char *tmp = debug_classname_from_index( ale->iEventType );
+		if (tmp) 
+			result = talloc_strdup( ale, tmp );
+	} else {
+		/* we should look in our own tables */
+		const char *tmp = _admin_log_type_from_index( ale->iEventType );
+		if (tmp)
+			result = talloc_strdup( ale, tmp );
+	}
+
+	return( result );
+}
+
+
+int _admin_log_prio_to_syslog( int loglevel ) 
+{
+	int j;
+	for (j=0;admin_log_level_strings[j].iLevel;j++) {
+		if (admin_log_level_strings[j].iLevel == loglevel) 
+			return admin_log_level_strings[j].syslog_prio;
+	}
+	return LOG_INFO;
+}
+
+
+int admin_log_levels( void )
+{
+	const char **list;
+	int i, j, tmp, found;
+
+	if (_admin_log_levels_parsed) {
+		return _admin_log_levels;
+	}
+
+	list = lp_admin_log_levels( );
+	if (!list) {
+		DEBUG(10, ("Admin log levels in config is NULL: logging all\n"));
+		return ADMIN_LOG_LEVEL_ALL;
+	}
+
+	tmp = 0;
+	for (i=0;list[i];i++) {
+		found = 0;
+		for (j=0;!found&&admin_log_level_strings[j].iLevel;j++) {
+			if (StrCaseCmp( list[i], admin_log_level_strings[j].szName ) == 0) {
+				DEBUG(100, ( "Admin log level %s (%i) added\n",
+					     admin_log_level_strings[j].szName, 
+					     admin_log_level_strings[j].iLevel ) );
+				tmp |= admin_log_level_strings[j].iLevel;
+				found = 1;
+			}
+		}
+		if ( (list[i]) && (!found) ) {
+			DEBUG(10, ( "Admin log unknown level %s\n", list[i] ) );
+		}
+	}
+
+	_admin_log_levels = tmp;
+	_admin_log_levels_parsed = 1;
+
+	return _admin_log_levels;
+}
+
+int admin_log_lookup_classname( const char *name )
+{
+	return -1;
+}
+
+static int _admin_log_event_types_parsed = 0;
+
+int _admin_log_event_types_count;
+int *_admin_log_event_types = NULL;
+
+/* returns 1 if eventType is to be logged */
+int admin_log_event_type( int eventType )
+{
+	int i, j, tmp, count;
+	const char **list;
+	
+	if (!_admin_log_event_types_parsed) {
+		/* parse list */
+		list = lp_admin_log_event_types( );
+		if (!list)
+			return 1;
+
+		for (count=0; list[count]; count++);
+
+		_admin_log_event_types = talloc_array( NULL, int, count );
+
+		if (!_admin_log_event_types) {
+			DEBUG(0, ( "Admin log event types out of memory (%i)\n", count ) );
+			return 1;
+		}
+
+		j = 0;
+		for (i=0; list[i]; i++) {
+			tmp = debug_lookup_classname( list[i] );
+			if (tmp != -1) {
+				DEBUG( 100, ( "Admin log event type adding %s as %i (from debug class)\n",
+					      list[i], tmp ) );
+				_admin_log_event_types[j] = tmp;
+				j++;
+			} else {
+				tmp = admin_log_lookup_classname( list[i] );
+				if (tmp != -1) {
+					DEBUG( 100, ( "Admin log event type adding %s as %i\n",
+						      list[i], tmp ) );
+					_admin_log_event_types[j] = tmp;
+					j++;
+				} else {
+					/* warning */
+				}
+			}
+		}
+		_admin_log_event_types_count = j;
+		_admin_log_event_types_parsed = 1;
+	}
+
+	if (_admin_log_event_types_parsed) {
+		if (_admin_log_event_types) {
+			for (i=0; i<_admin_log_event_types_count; i++) {
+				if ( (_admin_log_event_types[i] == DBGC_ALL) || 
+				     (_admin_log_event_types[i] == eventType) )
+					return 1;
+			}
+		} else {
+			/* debug all */
+			return 1;
+		}
+		/* we have some event types selected but not the one given 
+		   as a parameter to this call so that we do not log */
+		return 0;
+	} else {
+		/* if we still have no information about what 
+		   event types to log, we do them all */
+		return 1;
+	}
+}
+
+
diff -Pur -X diff-exclude samba-bzr-vanilla/source/lib/substitute.c SAMBA_3_0.bzr/source/lib/substitute.c
--- samba-bzr-vanilla/source/lib/substitute.c	2006-08-07 11:20:41.049630000 +0200
+++ SAMBA_3_0.bzr/source/lib/substitute.c	2006-08-07 10:12:13.588929750 +0200
@@ -754,6 +754,103 @@
 }
 
 
+/****************************************************************************
+ Do some specific substitutions in a string.
+ Also replaces admin log stuff:
+   %e event type and id (event type<<16|id)
+   %E event type as text
+   %b event description (if available)
+   %n NT status code description
+ This function will return an allocated string that have to be freed.
+
+ It is a modified copy of talloc_sub_specified.
+ Modifications by Michael Krax <mk at krax.net>
+****************************************************************************/
+
+char *talloc_sub_admin_log(TALLOC_CTX *mem_ctx,
+			   const char *input_string,
+			   const char *username,
+			   const char *domain,
+			   uid_t uid,
+			   gid_t gid,
+			   const admin_log_event *ale,
+			   const char *event_type_text
+			   )
+{
+	char *a_string;
+	char *ret_string = NULL;
+	char *b, *p, *s;
+	TALLOC_CTX *tmp_ctx;
+
+	if (!(tmp_ctx = talloc_new(mem_ctx))) {
+		DEBUG(0, ("talloc_new failed\n"));
+		return NULL;
+	}
+
+	a_string = talloc_strdup(tmp_ctx, input_string);
+	if (a_string == NULL) {
+		DEBUG(0, ("talloc_sub_specified: Out of memory!\n"));
+		goto done;
+	}
+	
+	for (b = s = a_string; (p = strchr_m(s, '%')); s = a_string + (p - b)) {
+		
+		b = a_string;
+		
+		switch (*(p+1)) {
+		case 'e' : 
+			a_string = talloc_string_sub(
+			        tmp_ctx, a_string, "%e", 
+				talloc_asprintf(tmp_ctx, 
+						"0x%08x", 
+						(ale->iEventType << 16 | ale->iEventId)));
+			break;
+		case 'E' : 
+			a_string = talloc_string_sub(
+				tmp_ctx, a_string, "%E", event_type_text);
+			break;
+		case 'b' :
+		        a_string = talloc_string_sub(
+				tmp_ctx, a_string,
+				"%b", ale->szDescription);
+			break;
+		case 'n' :
+		  if (NT_STATUS_IS_OK(ale->ntStatus)) {
+				a_string = talloc_string_sub(
+					tmp_ctx, a_string, "%n",
+					"");
+				/* replace w/ empty string */
+			} else {
+				a_string = talloc_string_sub(
+					tmp_ctx, a_string, 
+					"%n", 
+					get_friendly_nt_error_msg( 
+								  ale->ntStatus));
+			}
+			break;
+		default: 
+			break;
+		}
+
+		p++;
+		if (a_string == NULL) {
+			goto done;
+		}
+	}
+
+	/* Watch out, using "mem_ctx" here, so all intermediate stuff goes
+	 * away with the TALLOC_FREE(tmp_ctx) further down. */
+
+	ret_string = talloc_sub_specified(mem_ctx, a_string, username, 
+					  domain, uid, gid);
+
+ done:
+	TALLOC_FREE(tmp_ctx);
+	return ret_string;
+}
+
+
+
 void standard_sub_advanced(const char *servicename, const char *user, 
 			   const char *connectpath, gid_t gid, 
 			   const char *smb_name, const char *domain_name,
diff -Pur -X diff-exclude samba-bzr-vanilla/source/param/loadparm.c SAMBA_3_0.bzr/source/param/loadparm.c
--- samba-bzr-vanilla/source/param/loadparm.c	2006-08-07 11:20:42.025691000 +0200
+++ SAMBA_3_0.bzr/source/param/loadparm.c	2006-08-03 09:45:56.528279040 +0200
@@ -309,6 +309,10 @@
 	int client_signing;
 	int server_signing;
 	int iUsershareMaxShares;
+  BOOL bAdminLog;
+  char **szAdminLogEventTypes;
+  char **szAdminLogLevel;
+  char *szAdminLogFormat;
 
 	BOOL bResetOnZeroVC;
 	param_opt_struct *param_opt;
@@ -950,6 +954,10 @@
 	{"debug pid", P_BOOL, P_GLOBAL, &Globals.bDebugPid, NULL, NULL, FLAG_ADVANCED}, 
 	{"debug uid", P_BOOL, P_GLOBAL, &Globals.bDebugUid, NULL, NULL, FLAG_ADVANCED}, 
 	{"enable core files", P_BOOL, P_GLOBAL, &Globals.bEnableCoreFiles, NULL, NULL, FLAG_ADVANCED},
+	{"admin log", P_BOOL, P_GLOBAL, &Globals.bAdminLog, NULL, NULL, FLAG_ADVANCED},
+	{"admin log event types", P_LIST, P_GLOBAL, &Globals.szAdminLogEventTypes, NULL, NULL, FLAG_ADVANCED},
+	{"admin log levels", P_LIST, P_GLOBAL, &Globals.szAdminLogLevel, NULL, NULL, FLAG_ADVANCED},
+	{"admin log format", P_STRING, P_GLOBAL, &Globals.szAdminLogFormat, NULL, NULL, FLAG_ADVANCED},
 
 	{N_("Protocol Options"), P_SEP, P_SEPARATOR}, 
 
@@ -1652,6 +1660,12 @@
 	Globals.bUsershareOwnerOnly = True;
 	/* By default disallow guest access to usershares. */
 	Globals.bUsershareAllowGuests = False;
+
+	/* admin log */
+	Globals.bAdminLog = False; /* off by default */
+	Globals.szAdminLogEventTypes = str_list_make( "all", NULL );
+	Globals.szAdminLogLevel = str_list_make( "error", NULL );
+	string_set( &Globals.szAdminLogFormat, "" );
 }
 
 static TALLOC_CTX *lp_talloc;
@@ -1950,6 +1964,10 @@
 FN_GLOBAL_INTEGER(lp_lock_spin_count, &Globals.iLockSpinCount)
 FN_GLOBAL_INTEGER(lp_lock_spin_time, &Globals.iLockSpinTime)
 FN_GLOBAL_INTEGER(lp_usershare_max_shares, &Globals.iUsershareMaxShares)
+FN_GLOBAL_BOOL(lp_admin_log, &Globals.bAdminLog)
+FN_GLOBAL_LIST(lp_admin_log_event_types, &Globals.szAdminLogEventTypes)
+FN_GLOBAL_LIST(lp_admin_log_levels, &Globals.szAdminLogLevel)
+FN_GLOBAL_STRING(lp_admin_log_format, &Globals.szAdminLogFormat)
 
 FN_LOCAL_STRING(lp_preexec, szPreExec)
 FN_LOCAL_STRING(lp_postexec, szPostExec)
@@ -5006,6 +5024,14 @@
 	set_default_server_announce_type();
 	set_allowed_client_auth();
 
+	if (bLoaded) 
+	  ADMINLOG_TYPE_ID( ADMIN_LOG_EVENTTYPE_PARAM,
+			    ADMIN_LOG_EVENTID_CONFIGURATION_RELOADED,
+			    ADMIN_LOG_LEVEL_INFORMATION,
+			    NULL,
+			    NULL,
+			    "Configuration reloaded." );
+
 	bLoaded = True;
 
 	/* Now we check bWINSsupport and set szWINSserver to 127.0.0.1 */
diff -Pur -X diff-exclude samba-bzr-vanilla/source/passdb/pdb_interface.c SAMBA_3_0.bzr/source/passdb/pdb_interface.c
--- samba-bzr-vanilla/source/passdb/pdb_interface.c	2006-08-10 12:09:44.286877750 +0200
+++ SAMBA_3_0.bzr/source/passdb/pdb_interface.c	2006-08-10 10:56:15.123322250 +0200
@@ -498,8 +498,29 @@
 
 NTSTATUS pdb_add_sam_account(struct samu *sam_acct) 
 {
+        NTSTATUS result;
 	struct pdb_methods *pdb = pdb_get_methods();
-	return pdb->add_sam_account(pdb, sam_acct);
+
+	result = pdb->add_sam_account(pdb, sam_acct);
+
+	if ( !NT_STATUS_IS_OK( result ) ) {
+	  ADMINLOG_NTSTATUS( ADMIN_LOG_EVENTID_CREATE_USER,
+			     result,
+			     ADMIN_LOG_LEVEL_ERROR,
+			     get_current_username(),
+			     get_local_machine_name(),
+			     "Failed to create user %s",
+			     sam_acct->username );
+	} else {
+	  ADMINLOG_NTSTATUS( ADMIN_LOG_EVENTID_CREATE_USER,
+			     result,
+			     ADMIN_LOG_LEVEL_INFORMATION,
+			     get_current_username(), /* is the user executing */
+			     get_local_machine_name(),
+			     "Created user %s",
+			     sam_acct->username );
+	}
+	return result;
 }
 
 NTSTATUS pdb_update_sam_account(struct samu *sam_acct) 
@@ -516,6 +537,7 @@
 
 NTSTATUS pdb_delete_sam_account(struct samu *sam_acct) 
 {
+        NTSTATUS result;
 	struct pdb_methods *pdb = pdb_get_methods();
 
 	if (csamuser != NULL) {
@@ -523,7 +545,26 @@
 		csamuser = NULL;
 	}
 
-	return pdb->delete_sam_account(pdb, sam_acct);
+	result = pdb->delete_sam_account(pdb, sam_acct);
+
+	if ( !NT_STATUS_IS_OK( result ) ) {
+	  ADMINLOG_NTSTATUS( ADMIN_LOG_EVENTID_DELETE_USER,
+			     result,
+			     ADMIN_LOG_LEVEL_ERROR,
+			     get_current_username(),
+			     get_local_machine_name(),
+			     "Failed to delete user %s",
+			     sam_acct->username );
+	} else {
+	  ADMINLOG_NTSTATUS( ADMIN_LOG_EVENTID_DELETE_USER,
+			     result,
+			     ADMIN_LOG_LEVEL_INFORMATION,
+			     get_current_username(),
+			     get_local_machine_name(),
+			     "Deleted user %s",
+			     sam_acct->username );
+	}
+	return result;
 }
 
 NTSTATUS pdb_rename_sam_account(struct samu *oldname, const char *newname)
diff -Pur -X diff-exclude samba-bzr-vanilla/source/rpc_client/cli_netlogon.c SAMBA_3_0.bzr/source/rpc_client/cli_netlogon.c
--- samba-bzr-vanilla/source/rpc_client/cli_netlogon.c	2006-08-07 11:13:34.698984750 +0200
+++ SAMBA_3_0.bzr/source/rpc_client/cli_netlogon.c	2006-06-27 19:51:45.000000000 +0200
@@ -323,7 +323,13 @@
 			&srv_chal_recv); /* output */
 
 	if (!NT_STATUS_IS_OK(result)) {
-		return result;
+	  ADMINLOG_NTSTATUS( ADMIN_LOG_EVENTID_AUTH_FAILED,
+			     result,
+			     ADMIN_LOG_LEVEL_ERROR,
+			     dc->mach_acct,
+			     dc->remote_machine,
+			     "Failed to authentify against DC" );
+	  return result;
 	}
 
 	/*
diff -Pur -X diff-exclude samba-bzr-vanilla/source/rpc_server/srv_spoolss.c SAMBA_3_0.bzr/source/rpc_server/srv_spoolss.c
--- samba-bzr-vanilla/source/rpc_server/srv_spoolss.c	2006-08-07 11:13:39.595290750 +0200
+++ SAMBA_3_0.bzr/source/rpc_server/srv_spoolss.c	2006-08-04 10:25:05.174273376 +0200
@@ -887,6 +887,14 @@
 	}
 	
 	r_u.status = _spoolss_addprinterex(p, &q_u, &r_u);
+
+	ADMINLOG_NTSTATUS( ADMIN_LOG_EVENTID_ADD_PRINTER,
+			   werror_to_ntstatus( r_u.status ), 
+			   W_ERROR_IS_OK( r_u.status )?ADMIN_LOG_LEVEL_INFORMATION:ADMIN_LOG_LEVEL_ERROR,
+			   uidtoname( p->pipe_user.ut.uid ),
+			   p->conn->client_address,
+			   "Printer added" );
+			   
 				
 	if(!spoolss_io_r_addprinterex("", &r_u, rdata, 0)) {
 		DEBUG(0,("spoolss_io_r_addprinterex: unable to marshall SPOOL_R_ADDPRINTEREX.\n"));


More information about the samba-technical mailing list