--- rsync-2.6.8.acl_xattr/configure.in	2006-10-25 16:29:08.000000000 +0200
+++ rsync-2.6.8.mac/configure.in	2006-10-25 16:21:45.000000000 +0200
@@ -824,6 +824,7 @@
 )
 
 AC_CHECK_HEADERS(attr/xattr.h)
+AC_CHECK_HEADERS(sys/xattr.h)
 AC_MSG_CHECKING(whether to support extended attributes)
 AC_ARG_ENABLE(xattr-support,
 AC_HELP_STRING([--enable-xattr-support], [Include extended attribute support (default=no)]),
@@ -834,8 +835,12 @@
             AC_MSG_RESULT(Using Linux xattrs)
             AC_DEFINE(HAVE_LINUX_XATTRS, 1, [True if you have Linux xattrs])
             ;;
+      darwin*)
+            AC_MSG_RESULT(Using osx xattrs)
+            AC_DEFINE(HAVE_OSX_XATTRS, 1, [True if you have Mac OS X xattrs])
+            ;;
       *)
-            AC_MSG_RESULT(Xattrs requested but not linux.  Good luck)
+            AC_MSG_RESULT(Xattrs requested but not linux or osx.  Good luck)
             ;;
       esac
       ;;
Only in rsync-2.6.8.mac/lib: dummy
diff -ru rsync-2.6.8.acl_xattr/lib/sysxattr.c rsync-2.6.8.mac/lib/sysxattr.c
--- rsync-2.6.8.acl_xattr/lib/sysxattr.c	2006-10-25 16:29:08.000000000 +0200
+++ rsync-2.6.8.mac/lib/sysxattr.c	2006-10-25 16:29:41.000000000 +0200
@@ -36,6 +36,23 @@
 	return llistxattr(path, list, size);
 }
 
+#elif HAVE_OSX_XATTRS
+
+ssize_t sys_lgetxattr(const char *path, const char *name, void *value, size_t size)
+{
+	return getxattr(path, name, value, size, 0, XATTR_NOFOLLOW);
+}
+
+int sys_lsetxattr(const char *path, const char *name, const void *value, size_t size, int flags)
+{
+	return setxattr(path, name, value, size, 0, XATTR_NOFOLLOW | flags);
+}
+
+ssize_t sys_llistxattr(const char *path, char *list, size_t size)
+{
+	return listxattr(path, list, size, XATTR_NOFOLLOW);
+}
+
 #else
 
 #endif /* No xattrs */
diff -ru rsync-2.6.8.acl_xattr/lib/sysxattr.h rsync-2.6.8.mac/lib/sysxattr.h
--- rsync-2.6.8.acl_xattr/lib/sysxattr.h	2006-10-25 16:29:08.000000000 +0200
+++ rsync-2.6.8.mac/lib/sysxattr.h	2006-10-25 16:24:14.000000000 +0200
@@ -4,6 +4,12 @@
 int sys_lsetxattr(const char *path, const char *name, const void *value, size_t size, int flags);
 ssize_t sys_llistxattr(const char *path, char *list, size_t size);
 
+#elif defined HAVE_OSX_XATTRS
+
+ssize_t sys_lgetxattr(const char *path, const char *name, void *value, size_t size);
+int sys_lsetxattr(const char *path, const char *name, const void *value, size_t size, int flags);
+ssize_t sys_llistxattr(const char *path, char *list, size_t size);
+
 #else
 
 #endif /* No xattrs */
Only in rsync-2.6.8.mac/popt: dummy
diff -ru rsync-2.6.8.acl_xattr/rsync.h rsync-2.6.8.mac/rsync.h
--- rsync-2.6.8.acl_xattr/rsync.h	2006-10-25 16:29:09.000000000 +0200
+++ rsync-2.6.8.mac/rsync.h	2006-10-25 16:25:02.000000000 +0200
@@ -674,13 +674,18 @@
 #endif
 #include "smb_acls.h"
 
-#ifdef HAVE_LINUX_XATTRS
+#if defined HAVE_LINUX_XATTRS
+#define SUPPORT_XATTRS 1
+#elif defined HAVE_OSX_XATTRS
 #define SUPPORT_XATTRS 1
 #endif
 
 #if defined SUPPORT_XATTRS && defined HAVE_ATTR_XATTR_H
 #include <attr/xattr.h>
 #endif
+#if defined SUPPORT_XATTRS && defined HAVE_SYS_XATTR_H
+#include <sys/xattr.h>
+#endif
 
 #include "proto.h"
 
diff -ru rsync-2.6.8.acl_xattr/xattr.c rsync-2.6.8.mac/xattr.c
--- rsync-2.6.8.acl_xattr/xattr.c	2006-10-25 16:29:09.000000000 +0200
+++ rsync-2.6.8.mac/xattr.c	2006-10-25 16:21:45.000000000 +0200
@@ -120,7 +120,7 @@
 		namebuf_len = 100;
 		namebuf = new_array(char, namebuf_len);
 		datumbuf_len = 100;
-		datumbuf = new_array(char, datumbuf_len);
+		datumbuf = new_array(char, datumbuf_len+1); /* invariant: datumbuf is always 1 longer */
 		if (!namebuf || !datumbuf)
 			out_of_memory("rsync_xal_get");
 	}
@@ -176,7 +176,7 @@
 			x->rxas = new_rxas;
 		}
 		datum_size = sys_lgetxattr(fname, name, datumbuf, datumbuf_len);
-		if (datum_size > (ssize_t)datumbuf_len) {
+		if (datum_size >= (ssize_t)datumbuf_len) { /* osx allows partial reads; == is this case */
 			datum_size = -1;
 			errno = ERANGE;
 		}
@@ -191,10 +191,13 @@
 					    fname, name, strerror(errno));
 					return -1;
 				}
-				datumbuf = realloc_array(datumbuf, char, datum_size + 1);
+				/* In case the datum_size really did == datumbuf_len, we add a bit to prevent 
+				 * constant resizing in the case where many extended attributes are the same length.
+				 */
+				datumbuf_len = datum_size + 100;
+				datumbuf = realloc_array(datumbuf, char, datumbuf_len + 1); /* preserve +1 invariant */
 				if (!datumbuf)
 					out_of_memory("rsync_xal_get");
-				datumbuf_len = datum_size;
 				datum_size = sys_lgetxattr(fname, name, datumbuf, datumbuf_len);
 				if (datum_size < 0) {
 					rprintf(FERROR,
