[SCM] Samba Shared Repository - branch v3-3-stable updated - release-3-3-0pre1-381-gf5b7648

Karolin Seeger kseeger at samba.org
Thu Oct 2 06:47:03 GMT 2008


The branch, v3-3-stable has been updated
       via  f5b7648e6c1bffb9f28d94cbd5b1efffdd3a33f4 (commit)
       via  979a104ce34ca294e41185cfa572c0d89791944e (commit)
       via  5c75c5cc294be58a293073e4bb88733ad8b270d4 (commit)
      from  b311ded4ae326ed7d140d4e8a8a1c81994311e9f (commit)

http://gitweb.samba.org/?p=samba.git;a=shortlog;h=v3-3-stable


- Log -----------------------------------------------------------------
commit f5b7648e6c1bffb9f28d94cbd5b1efffdd3a33f4
Author: Jeremy Allison <jra at samba.org>
Date:   Wed Oct 1 15:00:22 2008 -0700

    Whitespace cleanup.
    Jeremy.
    (cherry picked from commit e782150175ff324b6e0ef1802a9e17f9a5aea560)

commit 979a104ce34ca294e41185cfa572c0d89791944e
Author: Jeremy Allison <jra at samba.org>
Date:   Wed Oct 1 13:23:09 2008 -0700

    Fix use of DLIST_REMOVE as spotted by Constantine Vetoshev <gepardcv at gmail.com>.
    This API is unusual in that if used to remove a non-list head it nulls out
    the next and prev pointers. This is what you want for debugging (don't want
    an entry removed from the list to be still virtually linked into it) but
    means there is no consistent idiom for use as the next and prev pointers
    get trashed on removal from the list, meaning you must save them yourself.
    You can use it one way when deleting everything via the head pointer, as
    this preserves the next pointer, but you *must* use it another way when not
    deleting everything via the head pointer. Fix all known uses of this (the main
    one is in conn_free_internal() and would not free all the private data entries
    for vfs modules. The other changes in web/statuspage.c and winbindd_util.c
    are not strictly neccessary, as the head pointer is being used, but I've done
    them for consistency. Long term we must revisit this as this API is too hard
    to use correctly.
    Jeremy.
    (cherry picked from commit 737825183115732de1f1d6d2bd89ce6402a65b20)

commit 5c75c5cc294be58a293073e4bb88733ad8b270d4
Author: Jeremy Allison <jra at samba.org>
Date:   Wed Oct 1 12:28:45 2008 -0700

    Turn the socket connections into a refcounted list - in the common case there'll now only be one socket per smbd.
    Changed the format of the wire data to (a) include a version number (V1) as the first element. (b) removed the
    ";)" at the end an replaced it with a "\n". Receiver can change back if needed, and now receiver can just log
    "as-is" to a text file (making testing easier). Added my (C). Sorry Holger, but I've changed quite a bit now.
    Jeremy.
    (cherry picked from commit 9a90ceac52f8623dde2bf50e630b10aebbc0e28d)

-----------------------------------------------------------------------

Summary of changes:
 source/modules/vfs_smb_traffic_analyzer.c |  139 ++++++++++++++++++++---------
 source/printing/print_cups.c              |   32 ++++----
 source/smbd/conn.c                        |    2 +-
 source/web/statuspage.c                   |    5 +-
 source/winbindd/winbindd_util.c           |    3 +-
 5 files changed, 116 insertions(+), 65 deletions(-)


Changeset truncated at 500 lines:

diff --git a/source/modules/vfs_smb_traffic_analyzer.c b/source/modules/vfs_smb_traffic_analyzer.c
index 3925424..ff61768 100644
--- a/source/modules/vfs_smb_traffic_analyzer.c
+++ b/source/modules/vfs_smb_traffic_analyzer.c
@@ -3,6 +3,7 @@
  * on the net.
  *
  * Copyright (C) Holger Hetterich, 2008
+ * Copyright (C) Jeremy Allison, 2008
  *
  * 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
@@ -21,12 +22,14 @@
 #include "includes.h"
 
 /* abstraction for the send_over_network function */
-#define UNIX_DOMAIN_SOCKET 1
-#define INTERNET_SOCKET 0
+
+enum sock_type {INTERNET_SOCKET = 0, UNIX_DOMAIN_SOCKET};
+
+#define LOCAL_PATHNAME "/var/tmp/stadsocket"
 
 static int vfs_smb_traffic_analyzer_debug_level = DBGC_VFS;
 
-static int smb_traffic_analyzer_connMode(vfs_handle_struct *handle)
+static enum sock_type smb_traffic_analyzer_connMode(vfs_handle_struct *handle)
 {
 	connection_struct *conn = handle->conn;
         const char *Mode;
@@ -41,28 +44,22 @@ static int smb_traffic_analyzer_connMode(vfs_handle_struct *handle)
 
 /* Connect to an internet socket */
 
-static int smb_traffic_analyzer_connect_inet_socket(vfs_handle_struct *handle)
+static int smb_traffic_analyzer_connect_inet_socket(vfs_handle_struct *handle,
+					const char *name, uint16_t port)
 {
 	/* Create a streaming Socket */
-	const char *Hostname;
 	int sockfd = -1;
-        uint16_t port;
 	struct addrinfo hints;
 	struct addrinfo *ailist = NULL;
 	struct addrinfo *res = NULL;
-	connection_struct *conn = handle->conn;
 	int ret;
 
-	/* get port number, target system from the config parameters */
-	Hostname=lp_parm_const_string(SNUM(conn), "smb_traffic_analyzer",
-				"host", "localhost");
-
 	ZERO_STRUCT(hints);
 	/* By default make sure it supports TCP. */
 	hints.ai_socktype = SOCK_STREAM;
 	hints.ai_flags = AI_ADDRCONFIG;
 
-	ret = getaddrinfo(Hostname,
+	ret = getaddrinfo(name,
 			NULL,
 			&hints,
 			&ailist);
@@ -70,16 +67,13 @@ static int smb_traffic_analyzer_connect_inet_socket(vfs_handle_struct *handle)
         if (ret) {
 		DEBUG(3,("smb_traffic_analyzer_connect_inet_socket: "
 			"getaddrinfo failed for name %s [%s]\n",
-                        Hostname,
+                        name,
                         gai_strerror(ret) ));
 		return -1;
         }
 
-	port = atoi( lp_parm_const_string(SNUM(conn),
-				"smb_traffic_analyzer", "port", "9430"));
-
 	DEBUG(3,("smb_traffic_analyzer: Internet socket mode. Hostname: %s,"
-		"Port: %i\n", Hostname, port));
+		"Port: %i\n", name, port));
 
 	for (res = ailist; res; res = res->ai_next) {
 		struct sockaddr_storage ss;
@@ -113,15 +107,16 @@ static int smb_traffic_analyzer_connect_inet_socket(vfs_handle_struct *handle)
 
 /* Connect to a unix domain socket */
 
-static int smb_traffic_analyzer_connect_unix_socket(vfs_handle_struct *handle)
+static int smb_traffic_analyzer_connect_unix_socket(vfs_handle_struct *handle,
+						const char *name)
 {
 	/* Create the socket to stad */
 	int len, sock;
 	struct sockaddr_un remote;
 
 	DEBUG(7, ("smb_traffic_analyzer_connect_unix_socket: "
-			"Unix domain socket mode. Using "
-			"/var/tmp/stadsocket\n"));
+			"Unix domain socket mode. Using %s\n",
+			name ));
 
 	if ((sock = socket(AF_UNIX, SOCK_STREAM, 0)) == -1) {
 		DEBUG(1, ("smb_traffic_analyzer_connect_unix_socket: "
@@ -129,7 +124,7 @@ static int smb_traffic_analyzer_connect_unix_socket(vfs_handle_struct *handle)
 			"make sure stad is running!\n"));
 	}
 	remote.sun_family = AF_UNIX;
-	strlcpy(remote.sun_path, "/var/tmp/stadsocket",
+	strlcpy(remote.sun_path, name,
 		    sizeof(remote.sun_path));
 	len=strlen(remote.sun_path) + sizeof(remote.sun_family);
 	if (connect(sock, (struct sockaddr *)&remote, len) == -1 ) {
@@ -142,6 +137,16 @@ static int smb_traffic_analyzer_connect_unix_socket(vfs_handle_struct *handle)
 	return sock;
 }
 
+/* Private data allowing shared connection sockets. */
+
+struct refcounted_sock {
+	struct refcounted_sock *next, *prev;
+	char *name;
+	uint16_t port;
+	int sock;
+	unsigned int ref_count;
+};
+
 /* Send data over a socket */
 
 static void smb_traffic_analyzer_send_data(vfs_handle_struct *handle,
@@ -149,16 +154,16 @@ static void smb_traffic_analyzer_send_data(vfs_handle_struct *handle,
 					const char *file_name,
 					bool Write)
 {
-	int *psockfd = NULL;
+	struct refcounted_sock *rf_sock = NULL;
 	struct timeval tv;
 	struct tm *tm = NULL;
 	int seconds;
 	char *str = NULL;
 	size_t len;
 
-	SMB_VFS_HANDLE_GET_DATA(handle, psockfd, int, return);
+	SMB_VFS_HANDLE_GET_DATA(handle, rf_sock, struct refcounted_sock, return);
 
-	if (psockfd == NULL || *psockfd == -1) {
+	if (rf_sock == NULL || rf_sock->sock == -1) {
 		DEBUG(1, ("smb_traffic_analyzer_send_data: socket is "
 			"closed\n"));
 		return;
@@ -172,8 +177,8 @@ static void smb_traffic_analyzer_send_data(vfs_handle_struct *handle,
 	seconds=(float) (tv.tv_usec / 1000);
 
 	str = talloc_asprintf(talloc_tos(),
-			"%u,\"%s\",\"%s\",\"%c\",\"%s\",\"%s\","
-			"\"%04d-%02d-%02d %02d:%02d:%02d.%03d\");",
+			"V1,%u,\"%s\",\"%s\",\"%c\",\"%s\",\"%s\","
+			"\"%04d-%02d-%02d %02d:%02d:%02d.%03d\"\n",
 			(unsigned int)result,
 			handle->conn->server_info->sanitized_username,
 			pdb_get_domain(handle->conn->server_info->sam_account),
@@ -196,48 +201,94 @@ static void smb_traffic_analyzer_send_data(vfs_handle_struct *handle,
 
 	DEBUG(10, ("smb_traffic_analyzer_send_data_socket: sending %s\n",
 			str));
-	if (write_data(*psockfd, str, len) != len) {
+	if (write_data(rf_sock->sock, str, len) != len) {
 		DEBUG(1, ("smb_traffic_analyzer_send_data_socket: "
 			"error sending data to socket!\n"));
 		return ;
 	}
 }
 
+static struct refcounted_sock *sock_list;
+
 static void smb_traffic_analyzer_free_data(void **pptr)
 {
-	int *pfd = *(int **)pptr;
-	if(!pfd) {
+	struct refcounted_sock *rf_sock = *(struct refcounted_sock **)pptr;
+	if (rf_sock == NULL) {
 		return;
 	}
-	if (*pfd != -1) {
-		close(*pfd);
+	rf_sock->ref_count--;
+	if (rf_sock->ref_count != 0) {
+		return;
+	}
+	if (rf_sock->sock != -1) {
+		close(rf_sock->sock);
 	}
-	TALLOC_FREE(pfd);
+	DLIST_REMOVE(sock_list, rf_sock);
+	TALLOC_FREE(rf_sock);
 }
 
 static int smb_traffic_analyzer_connect(struct vfs_handle_struct *handle,
                          const char *service,
                          const char *user)
 {
-	int *pfd = TALLOC_P(handle, int);
+	connection_struct *conn = handle->conn;
+	enum sock_type st = smb_traffic_analyzer_connMode(handle);
+	struct refcounted_sock *rf_sock = NULL;
+	const char *name = (st == UNIX_DOMAIN_SOCKET) ? LOCAL_PATHNAME :
+				lp_parm_const_string(SNUM(conn),
+					"smb_traffic_analyzer",
+				"host", "localhost");
+	uint16_t port = (st == UNIX_DOMAIN_SOCKET) ? 0 :
+				atoi( lp_parm_const_string(SNUM(conn),
+				"smb_traffic_analyzer", "port", "9430"));
 
-	if (!pfd) {
-		errno = ENOMEM;
-		return -1;
+	/* Are we already connected ? */
+	for (rf_sock = sock_list; rf_sock; rf_sock = rf_sock->next) {
+		if (port == rf_sock->port &&
+				(strcmp(name, rf_sock->name) == 0)) {
+			break;
+		}
 	}
 
-	if (smb_traffic_analyzer_connMode(handle) == UNIX_DOMAIN_SOCKET) {
-		*pfd = smb_traffic_analyzer_connect_unix_socket(handle);
+	/* If we're connected already, just increase the
+ 	 * reference count. */
+	if (rf_sock) {
+		rf_sock->ref_count++;
 	} else {
-		*pfd = smb_traffic_analyzer_connect_inet_socket(handle);
-	}
-	if (*pfd == -1) {
-		return -1;
+		/* New connection. */
+		rf_sock = TALLOC_ZERO_P(NULL, struct refcounted_sock);
+		if (rf_sock == NULL) {
+			errno = ENOMEM;
+			return -1;
+		}
+		rf_sock->name = talloc_strdup(rf_sock, name);
+		if (rf_sock->name == NULL) {
+			TALLOC_FREE(rf_sock);
+			errno = ENOMEM;
+			return -1;
+		}
+		rf_sock->port = port;
+		rf_sock->ref_count = 1;
+
+		if (st == UNIX_DOMAIN_SOCKET) {
+			rf_sock->sock = smb_traffic_analyzer_connect_unix_socket(handle,
+							name);
+		} else {
+
+			rf_sock->sock = smb_traffic_analyzer_connect_inet_socket(handle,
+							name,
+							port);
+		}
+		if (rf_sock->sock == -1) {
+			TALLOC_FREE(rf_sock);
+			return -1;
+		}
+		DLIST_ADD(sock_list, rf_sock);
 	}
 
 	/* Store the private data. */
-	SMB_VFS_HANDLE_SET_DATA(handle, pfd, smb_traffic_analyzer_free_data,
-				int, return -1);
+	SMB_VFS_HANDLE_SET_DATA(handle, rf_sock, smb_traffic_analyzer_free_data,
+				struct refcounted_sock, return -1);
 	return SMB_VFS_NEXT_CONNECT(handle, service, user);
 }
 
diff --git a/source/printing/print_cups.c b/source/printing/print_cups.c
index f9568f0..97584cb 100644
--- a/source/printing/print_cups.c
+++ b/source/printing/print_cups.c
@@ -7,12 +7,12 @@
  * it under the terms of the GNU General Public License as published by
  * the Free Software Foundation; either version 3 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, see <http://www.gnu.org/licenses/>.
  */
@@ -109,7 +109,7 @@ bool cups_cache_reload(void)
 			{
 			  "printer-name",
 			  "printer-info"
-			};       
+			};
 	bool ret = False;
 
 	DEBUG(5, ("reloading cups printcap cache\n"));
@@ -657,8 +657,8 @@ static int cups_job_submit(int snum, struct printjob *pjob)
 	ippAddString(request, IPP_TAG_OPERATION, IPP_TAG_NAME, "job-name", NULL,
         	     new_jobname);
 
-	/* 
-	 * add any options defined in smb.conf 
+	/*
+	 * add any options defined in smb.conf
 	 */
 
 	num_options = 0;
@@ -666,7 +666,7 @@ static int cups_job_submit(int snum, struct printjob *pjob)
 	num_options = cupsParseOptions(lp_cups_options(snum), num_options, &options);
 
 	if ( num_options )
-		cupsEncodeOptions(request, num_options, options); 
+		cupsEncodeOptions(request, num_options, options);
 
        /*
 	* Do the request and get back a response...
@@ -712,7 +712,7 @@ static int cups_job_submit(int snum, struct printjob *pjob)
 static int cups_queue_get(const char *sharename,
                enum printing_types printing_type,
                char *lpq_command,
-               print_queue_struct **q, 
+               print_queue_struct **q,
                print_status_struct *status)
 {
 	fstring		printername;
@@ -751,10 +751,10 @@ static int cups_queue_get(const char *sharename,
 
 	*q = NULL;
 
-	/* HACK ALERT!!!  The problem with support the 'printer name' 
-	   option is that we key the tdb off the sharename.  So we will 
-	   overload the lpq_command string to pass in the printername 
-	   (which is basically what we do for non-cups printers ... using 
+	/* HACK ALERT!!!  The problem with support the 'printer name'
+	   option is that we key the tdb off the sharename.  So we will
+	   overload the lpq_command string to pass in the printername
+	   (which is basically what we do for non-cups printers ... using
 	   the lpq_command to get the queue listing). */
 
 	fstrcpy( printername, lpq_command );
@@ -1316,22 +1316,22 @@ bool cups_pull_comment_location(NT_PRINTER_INFO_LEVEL_2 *printer)
 			/* Grab the comment if we don't have one */
         		if ( (strcmp(attr->name, "printer-info") == 0)
 			     && (attr->value_tag == IPP_TAG_TEXT)
-			     && !strlen(printer->comment) ) 
+			     && !strlen(printer->comment) )
 			{
 				DEBUG(5,("cups_pull_comment_location: Using cups comment: %s\n",
-					 attr->values[0].string.text));				
+					 attr->values[0].string.text));
 			    	strlcpy(printer->comment,
 						attr->values[0].string.text,
 						sizeof(printer->comment));
 			}
 
-			/* Grab the location if we don't have one */ 
+			/* Grab the location if we don't have one */
 			if ( (strcmp(attr->name, "printer-location") == 0)
-			     && (attr->value_tag == IPP_TAG_TEXT) 
+			     && (attr->value_tag == IPP_TAG_TEXT)
 			     && !strlen(printer->location) )
 			{
 				DEBUG(5,("cups_pull_comment_location: Using cups location: %s\n",
-					 attr->values[0].string.text));				
+					 attr->values[0].string.text));
 			    	fstrcpy(printer->location,attr->values[0].string.text);
 			}
 
diff --git a/source/smbd/conn.c b/source/smbd/conn.c
index b9433bb..7f34d2b 100644
--- a/source/smbd/conn.c
+++ b/source/smbd/conn.c
@@ -252,8 +252,8 @@ void conn_free_internal(connection_struct *conn)
 	/* Free vfs_connection_struct */
 	handle = conn->vfs_handles;
 	while(handle) {
-		DLIST_REMOVE(conn->vfs_handles, handle);
 		thandle = handle->next;
+		DLIST_REMOVE(conn->vfs_handles, handle);
 		if (handle->free_data)
 			handle->free_data(&handle->data);
 		handle = thandle;
diff --git a/source/web/statuspage.c b/source/web/statuspage.c
index ce24c7c..e684a07 100644
--- a/source/web/statuspage.c
+++ b/source/web/statuspage.c
@@ -43,9 +43,10 @@ static void initPid2Machine (void)
 {
 	/* show machine name rather PID on table "Open Files"? */
 	if (PID_or_Machine) {
-		PIDMAP *p;
+		PIDMAP *p, *next;
 
-		for (p = pidmap; p != NULL; ) {
+		for (p = pidmap; p != NULL; p = next) {
+			next = p->next;
 			DLIST_REMOVE(pidmap, p);
 			SAFE_FREE(p->machine);
 			SAFE_FREE(p);
diff --git a/source/winbindd/winbindd_util.c b/source/winbindd/winbindd_util.c
index 7847d1d..ebcf625 100644
--- a/source/winbindd/winbindd_util.c
+++ b/source/winbindd/winbindd_util.c
@@ -1075,13 +1075,12 @@ void free_getent_state(struct getent_state *state)
 	temp = state;
 
 	while(temp != NULL) {
-		struct getent_state *next;
+		struct getent_state *next = temp->next;
 
 		/* Free sam entries then list entry */
 
 		SAFE_FREE(state->sam_entries);
 		DLIST_REMOVE(state, state);
-		next = temp->next;
 
 		SAFE_FREE(temp);
 		temp = next;


-- 
Samba Shared Repository


More information about the samba-cvs mailing list