svn commit: samba r11383 - in branches/SAMBA_3_0/source/lib: .

jra at samba.org jra at samba.org
Fri Oct 28 22:22:24 GMT 2005


Author: jra
Date: 2005-10-28 22:22:23 +0000 (Fri, 28 Oct 2005)
New Revision: 11383

WebSVN: http://websvn.samba.org/cgi-bin/viewcvs.cgi?view=rev&root=samba&rev=11383

Log:
Patch from Alex Masterov <alex at infobit.ru> to fix
XATTR calls on *BSD systems (bug #3218).
Jeremy.

Modified:
   branches/SAMBA_3_0/source/lib/system.c


Changeset:
Modified: branches/SAMBA_3_0/source/lib/system.c
===================================================================
--- branches/SAMBA_3_0/source/lib/system.c	2005-10-28 21:13:30 UTC (rev 11382)
+++ branches/SAMBA_3_0/source/lib/system.c	2005-10-28 22:22:23 UTC (rev 11383)
@@ -1367,7 +1367,7 @@
 
 /**************************************************************************
  Wrappers for extented attribute calls. Based on the Linux package with
- support for IRIX also. Expand as other systems have them.
+ support for IRIX and (Net|Free)BSD also. Expand as other systems have them.
 ****************************************************************************/
 
 ssize_t sys_getxattr (const char *path, const char *name, void *value, size_t size)
@@ -1376,10 +1376,22 @@
 	return getxattr(path, name, value, size);
 #elif defined(HAVE_EXTATTR_GET_FILE)
 	char *s;
+	ssize_t retval;
 	int attrnamespace = (strncmp(name, "system", 6) == 0) ? 
 		EXTATTR_NAMESPACE_SYSTEM : EXTATTR_NAMESPACE_USER;
 	const char *attrname = ((s=strchr_m(name, '.')) == NULL) ? name : s + 1;
+	/*
+	 * The BSD implementation has a nasty habit of silently truncating
+	 * the returned value to the size of the buffer, so we have to check
+	 * that the buffer is large enough to fit the returned value.
+	 */
+	retval = extattr_get_file(path, attrnamespace, attrname, NULL, 0);
 
+	if(retval > size) {
+		errno = ERANGE;
+		return -1;
+	}
+
 	return extattr_get_file(path, attrnamespace, attrname, value, size);
 #elif defined(HAVE_ATTR_GET)
 	int retval, flags = 0;
@@ -1403,10 +1415,18 @@
 	return lgetxattr(path, name, value, size);
 #elif defined(HAVE_EXTATTR_GET_LINK)
 	char *s;
+	ssize_t retval;
 	int attrnamespace = (strncmp(name, "system", 6) == 0) ? 
 		EXTATTR_NAMESPACE_SYSTEM : EXTATTR_NAMESPACE_USER;
 	const char *attrname = ((s=strchr_m(name, '.')) == NULL) ? name : s + 1;
 
+	retval = extattr_get_link(path, attrnamespace, attrname, NULL, 0);
+
+	if(retval > size) {
+		errno = ERANGE;
+		return -1;
+	}
+
 	return extattr_get_link(path, attrnamespace, attrname, value, size);
 #elif defined(HAVE_ATTR_GET)
 	int retval, flags = ATTR_DONTFOLLOW;
@@ -1430,10 +1450,18 @@
 	return fgetxattr(filedes, name, value, size);
 #elif defined(HAVE_EXTATTR_GET_FD)
 	char *s;
+	ssize_t retval;
 	int attrnamespace = (strncmp(name, "system", 6) == 0) ? 
 		EXTATTR_NAMESPACE_SYSTEM : EXTATTR_NAMESPACE_USER;
 	const char *attrname = ((s=strchr_m(name, '.')) == NULL) ? name : s + 1;
 
+	retval = extattr_get_fd(filedes, attrnamespace, attrname, NULL, 0);
+
+	if(retval > size) {
+		errno = ERANGE;
+		return -1;
+	}
+
 	return extattr_get_fd(filedes, attrnamespace, attrname, value, size);
 #elif defined(HAVE_ATTR_GETF)
 	int retval, flags = 0;
@@ -1747,7 +1775,24 @@
 	int attrnamespace = (strncmp(name, "system", 6) == 0) ? 
 		EXTATTR_NAMESPACE_SYSTEM : EXTATTR_NAMESPACE_USER;
 	const char *attrname = ((s=strchr_m(name, '.')) == NULL) ? name : s + 1;
-
+	if (flags) {
+		/* Check attribute existence */
+		retval = extattr_get_file(path, attrnamespace, attrname, NULL, 0);
+		if (retval < 0) {
+			/* REPLACE attribute, that doesn't exist */
+			if (flags & XATTR_REPLACE && errno == ENOATTR) {
+				errno = ENOATTR;
+				return -1;
+			}
+		}
+		else {
+			/* CREATE attribute, that already exists */
+			if (flags & XATTR_CREATE) {
+				errno = EEXIST;
+				return -1;
+			}
+		}
+	}
 	retval = extattr_set_file(path, attrnamespace, attrname, value, size);
 	return (retval < 0) ? -1 : 0;
 #elif defined(HAVE_ATTR_SET)
@@ -1775,6 +1820,24 @@
 	int attrnamespace = (strncmp(name, "system", 6) == 0) ? 
 		EXTATTR_NAMESPACE_SYSTEM : EXTATTR_NAMESPACE_USER;
 	const char *attrname = ((s=strchr_m(name, '.')) == NULL) ? name : s + 1;
+	if (flags) {
+		/* Check attribute existence */
+		retval = extattr_get_link(path, attrnamespace, attrname, NULL, 0);
+		if (retval < 0) {
+			/* REPLACE attribute, that doesn't exist */
+			if (flags & XATTR_REPLACE && errno == ENOATTR) {
+				errno = ENOATTR;
+				return -1;
+			}
+		}
+		else {
+			/* CREATE attribute, that already exists */
+			if (flags & XATTR_CREATE) {
+				errno = EEXIST;
+				return -1;
+			}
+		}
+	}
 
 	retval = extattr_set_link(path, attrnamespace, attrname, value, size);
 	return (retval < 0) ? -1 : 0;
@@ -1803,7 +1866,24 @@
 	int attrnamespace = (strncmp(name, "system", 6) == 0) ? 
 		EXTATTR_NAMESPACE_SYSTEM : EXTATTR_NAMESPACE_USER;
 	const char *attrname = ((s=strchr_m(name, '.')) == NULL) ? name : s + 1;
-
+	if (flags) {
+		/* Check attribute existence */
+		retval = extattr_get_fd(filedes, attrnamespace, attrname, NULL, 0);
+		if (retval < 0) {
+			/* REPLACE attribute, that doesn't exist */
+			if (flags & XATTR_REPLACE && errno == ENOATTR) {
+				errno = ENOATTR;
+				return -1;
+			}
+		}
+		else {
+			/* CREATE attribute, that already exists */
+			if (flags & XATTR_CREATE) {
+				errno = EEXIST;
+				return -1;
+			}
+		}
+	}
 	retval = extattr_set_fd(filedes, attrnamespace, attrname, value, size);
 	return (retval < 0) ? -1 : 0;
 #elif defined(HAVE_ATTR_SETF)



More information about the samba-cvs mailing list