svn commit: r207895 - stable/7/sys/cddl/contrib/opensolaris/uts/common/fs/zfs

Marius Strobl marius at FreeBSD.org
Mon May 10 20:55:25 UTC 2010


Author: marius
Date: Mon May 10 20:55:24 2010
New Revision: 207895
URL: http://svn.freebsd.org/changeset/base/207895

Log:
  MFC: r207683
  
  - Fix broken symlinks on cross platform zfs send/recv. [1]
  - Enable zfs_ace_byteswap() on FreeBSD as it works just fine (tested between
    amd64 and sparc64 in both directions by Michael Moll).
  
  PR:		146272
  Approved by:	mm, pjd
  Obtained from:	OpenSolaris (onnv rev. 8283:1ca59f393041; Bug ID 6764193) [1]

Modified:
  stable/7/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/zfs_byteswap.c
Directory Properties:
  stable/7/sys/   (props changed)
  stable/7/sys/cddl/contrib/opensolaris/   (props changed)
  stable/7/sys/contrib/dev/acpica/   (props changed)
  stable/7/sys/contrib/pf/   (props changed)

Modified: stable/7/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/zfs_byteswap.c
==============================================================================
--- stable/7/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/zfs_byteswap.c	Mon May 10 20:55:24 2010	(r207894)
+++ stable/7/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/zfs_byteswap.c	Mon May 10 20:55:24 2010	(r207895)
@@ -19,12 +19,10 @@
  * CDDL HEADER END
  */
 /*
- * Copyright 2007 Sun Microsystems, Inc.  All rights reserved.
+ * Copyright 2008 Sun Microsystems, Inc.  All rights reserved.
  * Use is subject to license terms.
  */
 
-#pragma ident	"%Z%%M%	%I%	%E% SMI"
-
 #include <sys/zfs_context.h>
 #include <sys/vfs.h>
 #include <sys/fs/zfs.h>
@@ -50,7 +48,6 @@ zfs_oldace_byteswap(ace_t *ace, int ace_
 void
 zfs_ace_byteswap(void *buf, size_t size, boolean_t zfs_layout)
 {
-#ifdef TODO
 	caddr_t end;
 	caddr_t ptr;
 	zfs_ace_t *zacep;
@@ -64,6 +61,20 @@ zfs_ace_byteswap(void *buf, size_t size,
 
 	while (ptr < end) {
 		if (zfs_layout) {
+			/*
+			 * Avoid overrun.  Embedded aces can have one
+			 * of several sizes.  We don't know exactly
+			 * how many our present, only the size of the
+			 * buffer containing them.  That size may be
+			 * larger than needed to hold the aces
+			 * present.  As long as we do not do any
+			 * swapping beyond the end of our block we are
+			 * okay.  It it safe to swap any non-ace data
+			 * within the block since it is just zeros.
+			 */
+			if (ptr + sizeof (zfs_ace_hdr_t) > end) {
+				break;
+			}
 			zacep = (zfs_ace_t *)ptr;
 			zacep->z_hdr.z_access_mask =
 			    BSWAP_32(zacep->z_hdr.z_access_mask);
@@ -72,6 +83,10 @@ zfs_ace_byteswap(void *buf, size_t size,
 			    BSWAP_16(zacep->z_hdr.z_type);
 			entry_type = zacep->z_hdr.z_flags & ACE_TYPE_FLAGS;
 		} else {
+			/* Overrun avoidance */
+			if (ptr + sizeof (ace_t) > end) {
+				break;
+			}
 			acep = (ace_t *)ptr;
 			acep->a_access_mask = BSWAP_32(acep->a_access_mask);
 			acep->a_flags = BSWAP_16(acep->a_flags);
@@ -88,8 +103,14 @@ zfs_ace_byteswap(void *buf, size_t size,
 			break;
 		case ACE_IDENTIFIER_GROUP:
 		default:
+			/* Overrun avoidance */
 			if (zfs_layout) {
-				zacep->z_fuid = BSWAP_64(zacep->z_fuid);
+				if (ptr + sizeof (zfs_ace_t) <= end) {
+					zacep->z_fuid = BSWAP_64(zacep->z_fuid);
+				} else {
+					entry_size = sizeof (zfs_ace_t);
+					break;
+				}
 			}
 			switch (ace_type) {
 			case ACE_ACCESS_ALLOWED_OBJECT_ACE_TYPE:
@@ -108,9 +129,6 @@ zfs_ace_byteswap(void *buf, size_t size,
 		}
 		ptr = ptr + entry_size;
 	}
-#else	/* TODO */
-	panic("%s:%u: TODO", __func__, __LINE__);
-#endif	/* TODO */
 }
 
 /* ARGSUSED */
@@ -173,7 +191,8 @@ zfs_znode_byteswap(void *buf, size_t siz
 	if (zp->zp_acl.z_acl_version == ZFS_ACL_VERSION) {
 		zfs_acl_byteswap((void *)&zp->zp_acl.z_ace_data[0],
 		    ZFS_ACE_SPACE);
-	} else
+	} else {
 		zfs_oldace_byteswap((ace_t *)&zp->zp_acl.z_ace_data[0],
 		    ACE_SLOT_CNT);
+	}
 }


More information about the svn-src-all mailing list