All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH VER 6] Extend project quotas to support 32bit project identifiers.
@ 2010-09-26  6:10 Arkadiusz Miśkiewicz
  2010-09-26  6:10 ` [PATCH VER 6] xfsprogs: projid32bit handling Arkadiusz Miśkiewicz
                   ` (2 more replies)
  0 siblings, 3 replies; 9+ messages in thread
From: Arkadiusz Miśkiewicz @ 2010-09-26  6:10 UTC (permalink / raw)
  To: xfs

This patch adds support for 32bit project quota identifiers.

On disk format is backward compatible with 16bit projid numbers. projid
on disk is now keept in two 16bit values - di_projid_lo (which holds the
same position as old 16bit projid value) and new di_projid_hi (takes
existing padding) and convertes from/to 32bit value on the fly.

xfs_admin (for existing fs), mkfs.xfs (for new fs) needs to be used
to enable PROJID32BIT support.

Signed-off-by: Arkadiusz Miśkiewicz <arekm@maven.pl>
Reviewed-by: Christoph Hellwig <hch@lst.de>
---

News:
- use 0x80 instead of 0x20 for PROJID32BIT superblock bit (as 0x20
  and 0x40 are reserved)
- style fix

 fs/xfs/linux-2.6/xfs_ioctl.c   |   14 +++++++-------
 fs/xfs/linux-2.6/xfs_ioctl32.c |    2 ++
 fs/xfs/linux-2.6/xfs_ioctl32.h |    5 +++--
 fs/xfs/linux-2.6/xfs_linux.h   |    2 +-
 fs/xfs/quota/xfs_qm.c          |   12 ++++++------
 fs/xfs/quota/xfs_qm_bhv.c      |    2 +-
 fs/xfs/quota/xfs_qm_syscalls.c |    2 +-
 fs/xfs/xfs_dinode.h            |    5 +++--
 fs/xfs/xfs_fs.h                |    5 +++--
 fs/xfs/xfs_inode.c             |   14 ++++++++------
 fs/xfs/xfs_inode.h             |   26 +++++++++++++++++++++++---
 fs/xfs/xfs_itable.c            |    3 ++-
 fs/xfs/xfs_rename.c            |    2 +-
 fs/xfs/xfs_sb.h                |   10 +++++++++-
 fs/xfs/xfs_types.h             |    2 --
 fs/xfs/xfs_vnodeops.c          |   16 ++++++++--------
 16 files changed, 78 insertions(+), 44 deletions(-)

diff --git a/fs/xfs/linux-2.6/xfs_ioctl.c b/fs/xfs/linux-2.6/xfs_ioctl.c
index 4fec427..30dd78f 100644
--- a/fs/xfs/linux-2.6/xfs_ioctl.c
+++ b/fs/xfs/linux-2.6/xfs_ioctl.c
@@ -788,7 +788,7 @@ xfs_ioc_fsgetxattr(
 	xfs_ilock(ip, XFS_ILOCK_SHARED);
 	fa.fsx_xflags = xfs_ip2xflags(ip);
 	fa.fsx_extsize = ip->i_d.di_extsize << ip->i_mount->m_sb.sb_blocklog;
-	fa.fsx_projid = ip->i_d.di_projid;
+	fa.fsx_projid = xfs_get_projid(ip);
 
 	if (attr) {
 		if (ip->i_afp) {
@@ -907,10 +907,10 @@ xfs_ioctl_setattr(
 		return XFS_ERROR(EIO);
 
 	/*
-	 * Disallow 32bit project ids because on-disk structure
-	 * is 16bit only.
+	 * Disallow 32bit project ids when projid32bit feature is not enabled.
 	 */
-	if ((mask & FSX_PROJID) && (fa->fsx_projid > (__uint16_t)-1))
+	if ((mask & FSX_PROJID) && (fa->fsx_projid > (__uint16_t)-1) &&
+			!xfs_sb_version_hasprojid32bit(&ip->i_mount->m_sb))
 		return XFS_ERROR(EINVAL);
 
 	/*
@@ -959,7 +959,7 @@ xfs_ioctl_setattr(
 	if (mask & FSX_PROJID) {
 		if (XFS_IS_QUOTA_RUNNING(mp) &&
 		    XFS_IS_PQUOTA_ON(mp) &&
-		    ip->i_d.di_projid != fa->fsx_projid) {
+		    xfs_get_projid(ip) != fa->fsx_projid) {
 			ASSERT(tp);
 			code = xfs_qm_vop_chown_reserve(tp, ip, udqp, gdqp,
 						capable(CAP_FOWNER) ?
@@ -1061,12 +1061,12 @@ xfs_ioctl_setattr(
 		 * Change the ownerships and register quota modifications
 		 * in the transaction.
 		 */
-		if (ip->i_d.di_projid != fa->fsx_projid) {
+		if (xfs_get_projid(ip) != fa->fsx_projid) {
 			if (XFS_IS_QUOTA_RUNNING(mp) && XFS_IS_PQUOTA_ON(mp)) {
 				olddquot = xfs_qm_vop_chown(tp, ip,
 							&ip->i_gdquot, gdqp);
 			}
-			ip->i_d.di_projid = fa->fsx_projid;
+			xfs_set_projid(ip, fa->fsx_projid);
 
 			/*
 			 * We may have to rev the inode as well as
diff --git a/fs/xfs/linux-2.6/xfs_ioctl32.c b/fs/xfs/linux-2.6/xfs_ioctl32.c
index 6c83f7f..1124157 100644
--- a/fs/xfs/linux-2.6/xfs_ioctl32.c
+++ b/fs/xfs/linux-2.6/xfs_ioctl32.c
@@ -165,6 +165,7 @@ xfs_ioctl32_bstat_copyin(
 	    get_user(bstat->bs_extents,	&bstat32->bs_extents)	||
 	    get_user(bstat->bs_gen,	&bstat32->bs_gen)	||
 	    get_user(bstat->bs_projid,	&bstat32->bs_projid)	||
+	    get_user(bstat->bs_projid_hi,	&bstat32->bs_projid_hi)	||
 	    get_user(bstat->bs_dmevmask, &bstat32->bs_dmevmask)	||
 	    get_user(bstat->bs_dmstate,	&bstat32->bs_dmstate)	||
 	    get_user(bstat->bs_aextents, &bstat32->bs_aextents))
@@ -218,6 +219,7 @@ xfs_bulkstat_one_fmt_compat(
 	    put_user(buffer->bs_extents,  &p32->bs_extents)	||
 	    put_user(buffer->bs_gen,	  &p32->bs_gen)		||
 	    put_user(buffer->bs_projid,	  &p32->bs_projid)	||
+	    put_user(buffer->bs_projid_hi,	&p32->bs_projid_hi)	||
 	    put_user(buffer->bs_dmevmask, &p32->bs_dmevmask)	||
 	    put_user(buffer->bs_dmstate,  &p32->bs_dmstate)	||
 	    put_user(buffer->bs_aextents, &p32->bs_aextents))
diff --git a/fs/xfs/linux-2.6/xfs_ioctl32.h b/fs/xfs/linux-2.6/xfs_ioctl32.h
index 1024c4f..f92d662 100644
--- a/fs/xfs/linux-2.6/xfs_ioctl32.h
+++ b/fs/xfs/linux-2.6/xfs_ioctl32.h
@@ -65,8 +65,9 @@ typedef struct compat_xfs_bstat {
 	__s32		bs_extsize;	/* extent size			*/
 	__s32		bs_extents;	/* number of extents		*/
 	__u32		bs_gen;		/* generation count		*/
-	__u16		bs_projid;	/* project id			*/
-	unsigned char	bs_pad[14];	/* pad space, unused		*/
+	__u16		bs_projid;	/* lower part of project id	*/
+	__u16		bs_projid_hi;	/* high part of project id	*/
+	unsigned char	bs_pad[12];	/* pad space, unused		*/
 	__u32		bs_dmevmask;	/* DMIG event mask		*/
 	__u16		bs_dmstate;	/* DMIG state info		*/
 	__u16		bs_aextents;	/* attribute number of extents	*/
diff --git a/fs/xfs/linux-2.6/xfs_linux.h b/fs/xfs/linux-2.6/xfs_linux.h
index 2fa0bd9..844b9a9 100644
--- a/fs/xfs/linux-2.6/xfs_linux.h
+++ b/fs/xfs/linux-2.6/xfs_linux.h
@@ -144,7 +144,7 @@
 #define SYNCHRONIZE()	barrier()
 #define __return_address __builtin_return_address(0)
 
-#define dfltprid	0
+#define XFS_PROJID_DEFAULT	0
 #define MAXPATHLEN	1024
 
 #define MIN(a,b)	(min(a,b))
diff --git a/fs/xfs/quota/xfs_qm.c b/fs/xfs/quota/xfs_qm.c
index 9a92407..9a8885e 100644
--- a/fs/xfs/quota/xfs_qm.c
+++ b/fs/xfs/quota/xfs_qm.c
@@ -837,7 +837,7 @@ xfs_qm_dqattach_locked(
 			xfs_qm_dqattach_one(ip, ip->i_d.di_gid, XFS_DQ_GROUP,
 						flags & XFS_QMOPT_DQALLOC,
 						ip->i_udquot, &ip->i_gdquot) :
-			xfs_qm_dqattach_one(ip, ip->i_d.di_projid, XFS_DQ_PROJ,
+			xfs_qm_dqattach_one(ip, xfs_get_projid(ip), XFS_DQ_PROJ,
 						flags & XFS_QMOPT_DQALLOC,
 						ip->i_udquot, &ip->i_gdquot);
 		/*
@@ -1248,7 +1248,7 @@ xfs_qm_dqget_noattach(
 					     XFS_QMOPT_DQALLOC|XFS_QMOPT_DOWARN,
 					     &gdqp) :
 				xfs_qm_dqget(mp, ip,
-					     ip->i_d.di_projid, XFS_DQ_PROJ,
+					     xfs_get_projid(ip), XFS_DQ_PROJ,
 					     XFS_QMOPT_DQALLOC|XFS_QMOPT_DOWARN,
 					     &gdqp);
 		if (error) {
@@ -2332,9 +2332,9 @@ xfs_qm_vop_dqalloc(
 			xfs_dqunlock(gq);
 		}
 	} else if ((flags & XFS_QMOPT_PQUOTA) && XFS_IS_PQUOTA_ON(mp)) {
-		if (ip->i_d.di_projid != prid) {
+		if (xfs_get_projid(ip) != prid) {
 			xfs_iunlock(ip, lockflags);
-			if ((error = xfs_qm_dqget(mp, NULL, (xfs_dqid_t)prid,
+			if ((error = xfs_qm_dqget(mp, NULL, prid,
 						 XFS_DQ_PROJ,
 						 XFS_QMOPT_DQALLOC |
 						 XFS_QMOPT_DOWARN,
@@ -2454,7 +2454,7 @@ xfs_qm_vop_chown_reserve(
 	}
 	if (XFS_IS_OQUOTA_ON(ip->i_mount) && gdqp) {
 		if (XFS_IS_PQUOTA_ON(ip->i_mount) &&
-		     ip->i_d.di_projid != be32_to_cpu(gdqp->q_core.d_id))
+		     xfs_get_projid(ip) != be32_to_cpu(gdqp->q_core.d_id))
 			prjflags = XFS_QMOPT_ENOSPC;
 
 		if (prjflags ||
@@ -2558,7 +2558,7 @@ xfs_qm_vop_create_dqattach(
 		ip->i_gdquot = gdqp;
 		ASSERT(XFS_IS_OQUOTA_ON(mp));
 		ASSERT((XFS_IS_GQUOTA_ON(mp) ?
-			ip->i_d.di_gid : ip->i_d.di_projid) ==
+			ip->i_d.di_gid : xfs_get_projid(ip)) ==
 				be32_to_cpu(gdqp->q_core.d_id));
 		xfs_trans_mod_dquot(tp, gdqp, XFS_TRANS_DQ_ICOUNT, 1);
 	}
diff --git a/fs/xfs/quota/xfs_qm_bhv.c b/fs/xfs/quota/xfs_qm_bhv.c
index bea02d7..45b5cb1 100644
--- a/fs/xfs/quota/xfs_qm_bhv.c
+++ b/fs/xfs/quota/xfs_qm_bhv.c
@@ -81,7 +81,7 @@ xfs_qm_statvfs(
 	xfs_mount_t		*mp = ip->i_mount;
 	xfs_dquot_t		*dqp;
 
-	if (!xfs_qm_dqget(mp, NULL, ip->i_d.di_projid, XFS_DQ_PROJ, 0, &dqp)) {
+	if (!xfs_qm_dqget(mp, NULL, xfs_get_projid(ip), XFS_DQ_PROJ, 0, &dqp)) {
 		xfs_fill_statvfs_from_dquot(statp, &dqp->q_core);
 		xfs_qm_dqput(dqp);
 	}
diff --git a/fs/xfs/quota/xfs_qm_syscalls.c b/fs/xfs/quota/xfs_qm_syscalls.c
index 45e5849..a89065b 100644
--- a/fs/xfs/quota/xfs_qm_syscalls.c
+++ b/fs/xfs/quota/xfs_qm_syscalls.c
@@ -1175,7 +1175,7 @@ xfs_qm_internalqcheck_adjust(
 	}
 	xfs_qm_internalqcheck_get_dquots(mp,
 					(xfs_dqid_t) ip->i_d.di_uid,
-					(xfs_dqid_t) ip->i_d.di_projid,
+					(xfs_dqid_t) xfs_get_projid(ip),
 					(xfs_dqid_t) ip->i_d.di_gid,
 					&ud, &gd);
 	if (XFS_IS_UQUOTA_ON(mp)) {
diff --git a/fs/xfs/xfs_dinode.h b/fs/xfs/xfs_dinode.h
index e5b153b..dffba9b 100644
--- a/fs/xfs/xfs_dinode.h
+++ b/fs/xfs/xfs_dinode.h
@@ -49,8 +49,9 @@ typedef struct xfs_dinode {
 	__be32		di_uid;		/* owner's user id */
 	__be32		di_gid;		/* owner's group id */
 	__be32		di_nlink;	/* number of links to file */
-	__be16		di_projid;	/* owner's project id */
-	__u8		di_pad[8];	/* unused, zeroed space */
+	__be16		di_projid_lo;	/* lower part of owner's project id */
+	__be16		di_projid_hi;	/* higher part owner's project id */
+	__u8		di_pad[6];	/* unused, zeroed space */
 	__be16		di_flushiter;	/* incremented on flush */
 	xfs_timestamp_t	di_atime;	/* time last accessed */
 	xfs_timestamp_t	di_mtime;	/* time last modified */
diff --git a/fs/xfs/xfs_fs.h b/fs/xfs/xfs_fs.h
index 87c2e9d..ae1c500 100644
--- a/fs/xfs/xfs_fs.h
+++ b/fs/xfs/xfs_fs.h
@@ -293,9 +293,10 @@ typedef struct xfs_bstat {
 	__s32		bs_extsize;	/* extent size			*/
 	__s32		bs_extents;	/* number of extents		*/
 	__u32		bs_gen;		/* generation count		*/
-	__u16		bs_projid;	/* project id			*/
+	__u16		bs_projid;	/* lower part of project id	*/
 	__u16		bs_forkoff;	/* inode fork offset in bytes	*/
-	unsigned char	bs_pad[12];	/* pad space, unused		*/
+	__u16		bs_projid_hi;	/* higher part of project id	*/
+	unsigned char	bs_pad[10];	/* pad space, unused		*/
 	__u32		bs_dmevmask;	/* DMIG event mask		*/
 	__u16		bs_dmstate;	/* DMIG state info		*/
 	__u16		bs_aextents;	/* attribute number of extents	*/
diff --git a/fs/xfs/xfs_inode.c b/fs/xfs/xfs_inode.c
index 34798f3..2ab5959 100644
--- a/fs/xfs/xfs_inode.c
+++ b/fs/xfs/xfs_inode.c
@@ -660,7 +660,8 @@ xfs_dinode_from_disk(
 	to->di_uid = be32_to_cpu(from->di_uid);
 	to->di_gid = be32_to_cpu(from->di_gid);
 	to->di_nlink = be32_to_cpu(from->di_nlink);
-	to->di_projid = be16_to_cpu(from->di_projid);
+	to->di_projid_lo = be16_to_cpu(from->di_projid_lo);
+	to->di_projid_hi = be16_to_cpu(from->di_projid_hi);
 	memcpy(to->di_pad, from->di_pad, sizeof(to->di_pad));
 	to->di_flushiter = be16_to_cpu(from->di_flushiter);
 	to->di_atime.t_sec = be32_to_cpu(from->di_atime.t_sec);
@@ -695,7 +696,8 @@ xfs_dinode_to_disk(
 	to->di_uid = cpu_to_be32(from->di_uid);
 	to->di_gid = cpu_to_be32(from->di_gid);
 	to->di_nlink = cpu_to_be32(from->di_nlink);
-	to->di_projid = cpu_to_be16(from->di_projid);
+	to->di_projid_lo = cpu_to_be16(from->di_projid_lo);
+	to->di_projid_hi = cpu_to_be16(from->di_projid_hi);
 	memcpy(to->di_pad, from->di_pad, sizeof(to->di_pad));
 	to->di_flushiter = cpu_to_be16(from->di_flushiter);
 	to->di_atime.t_sec = cpu_to_be32(from->di_atime.t_sec);
@@ -874,7 +876,7 @@ xfs_iread(
 	if (ip->i_d.di_version == 1) {
 		ip->i_d.di_nlink = ip->i_d.di_onlink;
 		ip->i_d.di_onlink = 0;
-		ip->i_d.di_projid = 0;
+		xfs_set_projid(ip, 0);
 	}
 
 	ip->i_delayed_blks = 0;
@@ -983,7 +985,7 @@ xfs_ialloc(
 	xfs_nlink_t	nlink,
 	xfs_dev_t	rdev,
 	cred_t		*cr,
-	xfs_prid_t	prid,
+	prid_t		prid,
 	int		okalloc,
 	xfs_buf_t	**ialloc_context,
 	boolean_t	*call_again,
@@ -1027,7 +1029,7 @@ xfs_ialloc(
 	ASSERT(ip->i_d.di_nlink == nlink);
 	ip->i_d.di_uid = current_fsuid();
 	ip->i_d.di_gid = current_fsgid();
-	ip->i_d.di_projid = prid;
+	xfs_set_projid(ip, prid);
 	memset(&(ip->i_d.di_pad[0]), 0, sizeof(ip->i_d.di_pad));
 
 	/*
@@ -3008,7 +3010,7 @@ xfs_iflush_int(
 			memset(&(ip->i_d.di_pad[0]), 0, sizeof(ip->i_d.di_pad));
 			memset(&(dip->di_pad[0]), 0,
 			      sizeof(dip->di_pad));
-			ASSERT(ip->i_d.di_projid == 0);
+			ASSERT(xfs_get_projid(ip) == 0);
 		}
 	}
 
diff --git a/fs/xfs/xfs_inode.h b/fs/xfs/xfs_inode.h
index 0898c54..2a7343a 100644
--- a/fs/xfs/xfs_inode.h
+++ b/fs/xfs/xfs_inode.h
@@ -134,8 +134,9 @@ typedef struct xfs_icdinode {
 	__uint32_t	di_uid;		/* owner's user id */
 	__uint32_t	di_gid;		/* owner's group id */
 	__uint32_t	di_nlink;	/* number of links to file */
-	__uint16_t	di_projid;	/* owner's project id */
-	__uint8_t	di_pad[8];	/* unused, zeroed space */
+	__uint16_t	di_projid_lo;	/* lower part of owner's project id */
+	__uint16_t	di_projid_hi;	/* higher part of owner's project id */
+	__uint8_t	di_pad[6];	/* unused, zeroed space */
 	__uint16_t	di_flushiter;	/* incremented on flush */
 	xfs_ictimestamp_t di_atime;	/* time last accessed */
 	xfs_ictimestamp_t di_mtime;	/* time last modified */
@@ -335,6 +336,25 @@ xfs_iflags_test_and_clear(xfs_inode_t *ip, unsigned short flags)
 }
 
 /*
+ * Project quota id helpers (previously projid was 16bit only
+ * and using two 16bit values to hold new 32bit projid was choosen
+ * to retain compatibility with "old" filesystems).
+ */
+static inline prid_t
+xfs_get_projid(struct xfs_inode *ip)
+{
+	return (prid_t)ip->i_d.di_projid_hi << 16 | ip->i_d.di_projid_lo;
+}
+
+static inline void
+xfs_set_projid(struct xfs_inode *ip,
+		prid_t projid)
+{
+	ip->i_d.di_projid_hi = (__uint16_t) (projid >> 16);
+	ip->i_d.di_projid_lo = (__uint16_t) (projid & 0xffff);
+}
+
+/*
  * Manage the i_flush queue embedded in the inode.  This completion
  * queue synchronizes processes attempting to flush the in-core
  * inode back to disk.
@@ -456,7 +476,7 @@ void		xfs_inode_free(struct xfs_inode *ip);
  * xfs_inode.c prototypes.
  */
 int		xfs_ialloc(struct xfs_trans *, xfs_inode_t *, mode_t,
-			   xfs_nlink_t, xfs_dev_t, cred_t *, xfs_prid_t,
+			   xfs_nlink_t, xfs_dev_t, cred_t *, prid_t,
 			   int, struct xfs_buf **, boolean_t *, xfs_inode_t **);
 
 uint		xfs_ip2xflags(struct xfs_inode *);
diff --git a/fs/xfs/xfs_itable.c b/fs/xfs/xfs_itable.c
index 7e3626e..178b54b 100644
--- a/fs/xfs/xfs_itable.c
+++ b/fs/xfs/xfs_itable.c
@@ -92,7 +92,8 @@ xfs_bulkstat_one_int(
 	 * further change.
 	 */
 	buf->bs_nlink = dic->di_nlink;
-	buf->bs_projid = dic->di_projid;
+	buf->bs_projid = dic->di_projid_lo;
+	buf->bs_projid_hi = dic->di_projid_hi;
 	buf->bs_ino = ino;
 	buf->bs_mode = dic->di_mode;
 	buf->bs_uid = dic->di_uid;
diff --git a/fs/xfs/xfs_rename.c b/fs/xfs/xfs_rename.c
index 8fca957..494b5cd 100644
--- a/fs/xfs/xfs_rename.c
+++ b/fs/xfs/xfs_rename.c
@@ -183,7 +183,7 @@ xfs_rename(
 	 * tree quota mechanism would be circumvented.
 	 */
 	if (unlikely((target_dp->i_d.di_flags & XFS_DIFLAG_PROJINHERIT) &&
-		     (target_dp->i_d.di_projid != src_ip->i_d.di_projid))) {
+		     (xfs_get_projid(target_dp) != xfs_get_projid(src_ip)))) {
 		error = XFS_ERROR(EXDEV);
 		goto error_return;
 	}
diff --git a/fs/xfs/xfs_sb.h b/fs/xfs/xfs_sb.h
index 1b017c6..1eb2ba5 100644
--- a/fs/xfs/xfs_sb.h
+++ b/fs/xfs/xfs_sb.h
@@ -80,10 +80,12 @@ struct xfs_mount;
 #define XFS_SB_VERSION2_RESERVED4BIT	0x00000004
 #define XFS_SB_VERSION2_ATTR2BIT	0x00000008	/* Inline attr rework */
 #define XFS_SB_VERSION2_PARENTBIT	0x00000010	/* parent pointers */
+#define XFS_SB_VERSION2_PROJID32BIT	0x00000080	/* 32 bit project id */
 
 #define	XFS_SB_VERSION2_OKREALFBITS	\
 	(XFS_SB_VERSION2_LAZYSBCOUNTBIT	| \
-	 XFS_SB_VERSION2_ATTR2BIT)
+	 XFS_SB_VERSION2_ATTR2BIT	| \
+	 XFS_SB_VERSION2_PROJID32BIT)
 #define	XFS_SB_VERSION2_OKSASHFBITS	\
 	(0)
 #define XFS_SB_VERSION2_OKREALBITS	\
@@ -495,6 +497,12 @@ static inline void xfs_sb_version_removeattr2(xfs_sb_t *sbp)
 		sbp->sb_versionnum &= ~XFS_SB_VERSION_MOREBITSBIT;
 }
 
+static inline int xfs_sb_version_hasprojid32bit(xfs_sb_t *sbp)
+{
+	return xfs_sb_version_hasmorebits(sbp) &&
+		(sbp->sb_features2 & XFS_SB_VERSION2_PROJID32BIT);
+}
+
 /*
  * end of superblock version macros
  */
diff --git a/fs/xfs/xfs_types.h b/fs/xfs/xfs_types.h
index 3207752..26d1867 100644
--- a/fs/xfs/xfs_types.h
+++ b/fs/xfs/xfs_types.h
@@ -73,8 +73,6 @@ typedef	__int32_t	xfs_tid_t;	/* transaction identifier */
 typedef	__uint32_t	xfs_dablk_t;	/* dir/attr block number (in file) */
 typedef	__uint32_t	xfs_dahash_t;	/* dir/attr hash value */
 
-typedef __uint16_t	xfs_prid_t;	/* prid_t truncated to 16bits in XFS */
-
 typedef __uint32_t	xlog_tid_t;	/* transaction ID type */
 
 /*
diff --git a/fs/xfs/xfs_vnodeops.c b/fs/xfs/xfs_vnodeops.c
index 4c7c7bf..e4166ec 100644
--- a/fs/xfs/xfs_vnodeops.c
+++ b/fs/xfs/xfs_vnodeops.c
@@ -114,7 +114,7 @@ xfs_setattr(
 		 */
 		ASSERT(udqp == NULL);
 		ASSERT(gdqp == NULL);
-		code = xfs_qm_vop_dqalloc(ip, uid, gid, ip->i_d.di_projid,
+		code = xfs_qm_vop_dqalloc(ip, uid, gid, xfs_get_projid(ip),
 					 qflags, &udqp, &gdqp);
 		if (code)
 			return code;
@@ -1266,7 +1266,7 @@ xfs_create(
 	boolean_t		unlock_dp_on_error = B_FALSE;
 	uint			cancel_flags;
 	int			committed;
-	xfs_prid_t		prid;
+	prid_t			prid;
 	struct xfs_dquot	*udqp = NULL;
 	struct xfs_dquot	*gdqp = NULL;
 	uint			resblks;
@@ -1279,9 +1279,9 @@ xfs_create(
 		return XFS_ERROR(EIO);
 
 	if (dp->i_d.di_flags & XFS_DIFLAG_PROJINHERIT)
-		prid = dp->i_d.di_projid;
+		prid = xfs_get_projid(dp);
 	else
-		prid = dfltprid;
+		prid = XFS_PROJID_DEFAULT;
 
 	/*
 	 * Make sure that we have allocated dquot(s) on disk.
@@ -1880,7 +1880,7 @@ xfs_link(
 	 * the tree quota mechanism could be circumvented.
 	 */
 	if (unlikely((tdp->i_d.di_flags & XFS_DIFLAG_PROJINHERIT) &&
-		     (tdp->i_d.di_projid != sip->i_d.di_projid))) {
+		     (xfs_get_projid(tdp) != xfs_get_projid(sip)))) {
 		error = XFS_ERROR(EXDEV);
 		goto error_return;
 	}
@@ -1955,7 +1955,7 @@ xfs_symlink(
 	int			byte_cnt;
 	int			n;
 	xfs_buf_t		*bp;
-	xfs_prid_t		prid;
+	prid_t			prid;
 	struct xfs_dquot	*udqp, *gdqp;
 	uint			resblks;
 
@@ -1978,9 +1978,9 @@ xfs_symlink(
 
 	udqp = gdqp = NULL;
 	if (dp->i_d.di_flags & XFS_DIFLAG_PROJINHERIT)
-		prid = dp->i_d.di_projid;
+		prid = xfs_get_projid(dp);
 	else
-		prid = (xfs_prid_t)dfltprid;
+		prid = XFS_PROJID_DEFAULT;
 
 	/*
 	 * Make sure that we have allocated dquot(s) on disk.
-- 
1.7.3

_______________________________________________
xfs mailing list
xfs@oss.sgi.com
http://oss.sgi.com/mailman/listinfo/xfs

^ permalink raw reply related	[flat|nested] 9+ messages in thread

* [PATCH VER 6] xfsprogs: projid32bit handling
  2010-09-26  6:10 [PATCH VER 6] Extend project quotas to support 32bit project identifiers Arkadiusz Miśkiewicz
@ 2010-09-26  6:10 ` Arkadiusz Miśkiewicz
  2010-09-26  6:10   ` [PATCH VER 6] xfstests: Quota project id setting overflow Arkadiusz Miśkiewicz
                     ` (2 more replies)
  2010-09-28  1:43 ` [PATCH VER 6] Extend project quotas to support 32bit project identifiers Christoph Hellwig
  2010-10-01 13:57 ` Alex Elder
  2 siblings, 3 replies; 9+ messages in thread
From: Arkadiusz Miśkiewicz @ 2010-09-26  6:10 UTC (permalink / raw)
  To: xfs

Add projid32bit handling to userspace. mkfs.xfs is able to enable this
feature for new filesystems. xfs_db knows what projid_lo/hi are.

Signed-off-by: Arkadiusz Miśkiewicz <arekm@maven.pl>
Reviewed-by: Christoph Hellwig <hch@lst.de>
---

News:
- use 0x80 instead of 0x20 for PROJID32BIT superblock bit (as 0x20
  and 0x40 are reserved)                                                                                                                                     

 db/check.c               |    2 +-
 db/inode.c               |    6 ++++--
 db/sb.c                  |    6 ++++++
 include/xfs_dinode.h     |    5 +++--
 include/xfs_fs.h         |   16 ++++++++++++++--
 include/xfs_inode.h      |   25 ++++++++++++++++++++++---
 include/xfs_sb.h         |   17 ++++++++++++++++-
 include/xfs_types.h      |    2 --
 libxfs/util.c            |   13 ++++++++-----
 libxfs/xfs_ialloc.c      |    3 ++-
 libxfs/xfs_inode.c       |    6 ++++--
 logprint/log_print_all.c |    6 ++++--
 man/man3/xfsctl.3        |    4 +++-
 man/man8/mkfs.xfs.8      |    7 +++++++
 man/man8/xfs_db.8        |    6 ++++--
 mkfs/xfs_mkfs.c          |   21 +++++++++++++++++----
 mkfs/xfs_mkfs.h          |    3 ++-
 quota/quot.c             |    2 +-
 repair/README            |    2 +-
 19 files changed, 119 insertions(+), 33 deletions(-)

diff --git a/db/check.c b/db/check.c
index 4f8a62a..a8939a4 100644
--- a/db/check.c
+++ b/db/check.c
@@ -2840,7 +2840,7 @@ process_inode(
 			break;
 		}
 		if (ic) {
-			dqprid = idic.di_projid;	/* dquot ID is u32 */
+			dqprid = xfs_get_projid(idic);	/* dquot ID is u32 */
 			quota_add(&dqprid, &idic.di_gid, &idic.di_uid,
 				  0, bc, ic, rc);
 		}
diff --git a/db/inode.c b/db/inode.c
index 4aa4e1a..6f8592a 100644
--- a/db/inode.c
+++ b/db/inode.c
@@ -81,8 +81,10 @@ const field_t	inode_core_flds[] = {
 	  FLD_COUNT, TYP_NONE },
 	{ "onlink", FLDT_UINT16D, OI(COFF(onlink)), inode_core_onlink_count,
 	  FLD_COUNT, TYP_NONE },
-	{ "projid", FLDT_UINT16D, OI(COFF(projid)), inode_core_projid_count,
-	  FLD_COUNT, TYP_NONE },
+	{ "projid_lo", FLDT_UINT16D, OI(COFF(projid_lo)),
+	  inode_core_projid_count, FLD_COUNT, TYP_NONE },
+	{ "projid_hi", FLDT_UINT16D, OI(COFF(projid_hi)),
+	  inode_core_projid_count, FLD_COUNT, TYP_NONE },
 	{ "uid", FLDT_UINT32D, OI(COFF(uid)), C1, 0, TYP_NONE },
 	{ "gid", FLDT_UINT32D, OI(COFF(gid)), C1, 0, TYP_NONE },
 	{ "flushiter", FLDT_UINT16D, OI(COFF(flushiter)), C1, 0, TYP_NONE },
diff --git a/db/sb.c b/db/sb.c
index 961a939..21f38c5 100644
--- a/db/sb.c
+++ b/db/sb.c
@@ -620,6 +620,8 @@ version_string(
 		strcat(s, ",ATTR2");
 	if (xfs_sb_version_haslazysbcount(sbp))
 		strcat(s, ",LAZYSBCOUNT");
+	if (xfs_sb_version_hasprojid32bit(sbp))
+		strcat(s, ",PROJID32BIT");
 	return s;
 }
 
@@ -696,6 +698,10 @@ version_f(
 			xfs_sb_version_addattr2(&mp->m_sb);
 			version = mp->m_sb.sb_versionnum;
 			features = mp->m_sb.sb_features2;
+		} else if (!strcasecmp(argv[1], "projid32bit")) {
+			xfs_sb_version_addprojid32bit(&mp->m_sb);
+			version = mp->m_sb.sb_versionnum;
+			features = mp->m_sb.sb_features2;
 		} else {
 			dbprintf(_("%s: invalid version change command \"%s\"\n"),
 				progname, argv[1]);
diff --git a/include/xfs_dinode.h b/include/xfs_dinode.h
index d7cf392..f28c088 100644
--- a/include/xfs_dinode.h
+++ b/include/xfs_dinode.h
@@ -52,8 +52,9 @@ typedef struct xfs_dinode_core {
 	__be32		di_uid;		/* owner's user id */
 	__be32		di_gid;		/* owner's group id */
 	__be32		di_nlink;	/* number of links to file */
-	__be16		di_projid;	/* owner's project id */
-	__u8		di_pad[8];	/* unused, zeroed space */
+	__be16		di_projid_lo;	/* lower part of owner's project id */
+	__be16		di_projid_hi;	/* higher part owner's project id */
+	__u8		di_pad[6];	/* unused, zeroed space */
 	__be16		di_flushiter;	/* incremented on flush */
 	xfs_timestamp_t	di_atime;	/* time last accessed */
 	xfs_timestamp_t	di_mtime;	/* time last modified */
diff --git a/include/xfs_fs.h b/include/xfs_fs.h
index 74e7274..9a51c64 100644
--- a/include/xfs_fs.h
+++ b/include/xfs_fs.h
@@ -299,9 +299,10 @@ typedef struct xfs_bstat {
 	__s32		bs_extsize;	/* extent size			*/
 	__s32		bs_extents;	/* number of extents		*/
 	__u32		bs_gen;		/* generation count		*/
-	__u16		bs_projid;	/* project id			*/
+	__u16		bs_projid;	/* lower part of project id	*/
 	__u16		bs_forkoff;	/* inode fork offset in bytes	*/
-	unsigned char	bs_pad[12];	/* pad space, unused		*/
+	__u16		bs_projid_hi;	/* higher part of project id	*/
+	unsigned char	bs_pad[10];	/* pad space, unused		*/
 	__u32		bs_dmevmask;	/* DMIG event mask		*/
 	__u16		bs_dmstate;	/* DMIG state info		*/
 	__u16		bs_aextents;	/* attribute number of extents	*/
@@ -506,4 +507,15 @@ typedef struct xfs_handle {
 #define BBTOB(bbs)	((bbs) << BBSHIFT)
 #endif
 
+/*
+ * Project quota id helpers (previously projid was 16bit only
+ * and using two 16bit values to hold new 32bit projid was choosen
+ * to retain compatibility with "old" filesystems).
+ */
+static inline __uint32_t
+bstat_get_projid(struct xfs_bstat *bs)
+{
+	return (__uint32_t)bs->bs_projid_hi << 16 | bs->bs_projid;
+}
+
 #endif	/* __XFS_FS_H__ */
diff --git a/include/xfs_inode.h b/include/xfs_inode.h
index b19b467..7e6fc91 100644
--- a/include/xfs_inode.h
+++ b/include/xfs_inode.h
@@ -124,8 +124,9 @@ typedef struct xfs_icdinode {
 	__uint32_t	di_uid;		/* owner's user id */
 	__uint32_t	di_gid;		/* owner's group id */
 	__uint32_t	di_nlink;	/* number of links to file */
-	__uint16_t	di_projid;	/* owner's project id */
-	__uint8_t	di_pad[8];	/* unused, zeroed space */
+	__uint16_t	di_projid_lo;	/* lower part of owner's project id */
+	__uint16_t	di_projid_hi;	/* higher part of owner's project id */
+	__uint8_t	di_pad[6];	/* unused, zeroed space */
 	__uint16_t	di_flushiter;	/* incremented on flush */
 	xfs_ictimestamp_t di_atime;	/* time last accessed */
 	xfs_ictimestamp_t di_mtime;	/* time last modified */
@@ -204,6 +205,24 @@ typedef struct xfs_icdinode {
 		((ip)->i_d.di_anextents = (n)))
 
 
+/*
+ * Project quota id helpers (previously projid was 16bit only
+ * and using two 16bit values to hold new 32bit projid was choosen
+ * to retain compatibility with "old" filesystems).
+ */
+static inline __uint32_t
+xfs_get_projid(struct xfs_icdinode i_d)
+{
+	return (__uint32_t)i_d.di_projid_hi << 16 | i_d.di_projid_lo;
+}
+
+static inline void
+xfs_set_projid(struct xfs_icdinode *i_d,
+		__uint32_t projid)
+{
+	i_d->di_projid_hi = (__uint16_t) (projid >> 16);
+	i_d->di_projid_lo = (__uint16_t) (projid & 0xffff);
+}
 
 #ifdef __KERNEL__
 
@@ -510,7 +529,7 @@ int		xfs_finish_reclaim_all(struct xfs_mount *, int);
 int		xfs_iread(struct xfs_mount *, struct xfs_trans *, xfs_ino_t,
 			  xfs_inode_t **, xfs_daddr_t, uint);
 int		xfs_ialloc(struct xfs_trans *, xfs_inode_t *, mode_t,
-			   xfs_nlink_t, xfs_dev_t, struct cred *, xfs_prid_t,
+			   xfs_nlink_t, xfs_dev_t, struct cred *, prid_t,
 			   int, struct xfs_buf **, boolean_t *, xfs_inode_t **);
 
 uint		xfs_ip2xflags(struct xfs_inode *);
diff --git a/include/xfs_sb.h b/include/xfs_sb.h
index 1e86489..f88dc32 100644
--- a/include/xfs_sb.h
+++ b/include/xfs_sb.h
@@ -80,10 +80,12 @@ struct xfs_mount;
 #define XFS_SB_VERSION2_RESERVED4BIT	0x00000004
 #define XFS_SB_VERSION2_ATTR2BIT	0x00000008	/* Inline attr rework */
 #define XFS_SB_VERSION2_PARENTBIT	0x00000010	/* parent pointers */
+#define XFS_SB_VERSION2_PROJID32BIT	0x00000080	/* 32 bit project id */
 
 #define	XFS_SB_VERSION2_OKREALFBITS	\
 	(XFS_SB_VERSION2_LAZYSBCOUNTBIT	| \
-	 XFS_SB_VERSION2_ATTR2BIT)
+	 XFS_SB_VERSION2_ATTR2BIT	| \
+	 XFS_SB_VERSION2_PROJID32BIT)
 #define	XFS_SB_VERSION2_OKSASHFBITS	\
 	(0)
 #define XFS_SB_VERSION2_OKREALBITS	\
@@ -489,6 +491,19 @@ static inline void xfs_sb_version_removeattr2(xfs_sb_t *sbp)
 		sbp->sb_versionnum &= ~XFS_SB_VERSION_MOREBITSBIT;
 }
 
+static inline int xfs_sb_version_hasprojid32bit(xfs_sb_t *sbp)
+{
+	return xfs_sb_version_hasmorebits(sbp) &&
+		(sbp->sb_features2 & XFS_SB_VERSION2_PROJID32BIT);
+}
+
+static inline void xfs_sb_version_addprojid32bit(xfs_sb_t *sbp)
+{
+	sbp->sb_versionnum |= XFS_SB_VERSION_MOREBITSBIT;
+	sbp->sb_features2 |= XFS_SB_VERSION2_PROJID32BIT;
+	sbp->sb_bad_features2 |= XFS_SB_VERSION2_PROJID32BIT;
+}
+
 /*
  * end of superblock version macros
  */
diff --git a/include/xfs_types.h b/include/xfs_types.h
index 0f51916..228b948 100644
--- a/include/xfs_types.h
+++ b/include/xfs_types.h
@@ -81,8 +81,6 @@ typedef	__int32_t	xfs_tid_t;	/* transaction identifier */
 typedef	__uint32_t	xfs_dablk_t;	/* dir/attr block number (in file) */
 typedef	__uint32_t	xfs_dahash_t;	/* dir/attr hash value */
 
-typedef __uint16_t	xfs_prid_t;	/* prid_t truncated to 16bits in XFS */
-
 /*
  * These types are 64 bits on disk but are either 32 or 64 bits in memory.
  * Disk based types:
diff --git a/libxfs/util.c b/libxfs/util.c
index 409fb92..077d2a2 100644
--- a/libxfs/util.c
+++ b/libxfs/util.c
@@ -134,7 +134,7 @@ libxfs_iread(
 	 * made it 32 bits long.  If this is an old format inode,
 	 * convert it in memory to look like a new one.  If it gets
 	 * flushed to disk we will convert back before flushing or
-	 * logging it.  We zero out the new projid field and the old link
+	 * logging it.  We zero out the new projid_lo/hi field and the old link
 	 * count field.  We'll handle clearing the pad field (the remains
 	 * of the old uuid field) when we actually convert the inode to
 	 * the new format. We don't change the version number so that we
@@ -143,7 +143,7 @@ libxfs_iread(
 	if (ip->i_d.di_version == XFS_DINODE_VERSION_1) {
 		ip->i_d.di_nlink = ip->i_d.di_onlink;
 		ip->i_d.di_onlink = 0;
-		ip->i_d.di_projid = 0;
+		xfs_set_projid(&ip->i_d, 0);
 	}
 
 	ip->i_delayed_blks = 0;
@@ -219,7 +219,7 @@ libxfs_ialloc(
 	ASSERT(ip->i_d.di_nlink == nlink);
 	ip->i_d.di_uid = cr->cr_uid;
 	ip->i_d.di_gid = cr->cr_gid;
-	ip->i_d.di_projid = pip ? 0 : fsx->fsx_projid;
+	xfs_set_projid(&ip->i_d, pip ? 0 : fsx->fsx_projid);
 	memset(&(ip->i_d.di_pad[0]), 0, sizeof(ip->i_d.di_pad));
 
 	/*
@@ -231,7 +231,10 @@ libxfs_ialloc(
 	if (xfs_sb_version_hasnlink(&tp->t_mountp->m_sb) &&
 	    ip->i_d.di_version == XFS_DINODE_VERSION_1) {
 		ip->i_d.di_version = XFS_DINODE_VERSION_2;
-		/* old link count, projid field, pad field already zeroed */
+		/*
+		 * old link count, projid_lo/hi field, pad field
+		 * already zeroed
+		 */
 	}
 
 	if (pip && (pip->i_d.di_mode & S_ISGID)) {
@@ -446,7 +449,7 @@ libxfs_iflush_int(xfs_inode_t *ip, xfs_buf_t *bp)
 			memset(&(ip->i_d.di_pad[0]), 0, sizeof(ip->i_d.di_pad));
 			memset(&(dip->di_core.di_pad[0]), 0,
 			      sizeof(dip->di_core.di_pad));
-			ASSERT(ip->i_d.di_projid == 0);
+			ASSERT(xfs_get_projid(ip->i_d) == 0);
 		}
 	}
 
diff --git a/libxfs/xfs_ialloc.c b/libxfs/xfs_ialloc.c
index 39fdf96..32ae4b0 100644
--- a/libxfs/xfs_ialloc.c
+++ b/libxfs/xfs_ialloc.c
@@ -46,7 +46,8 @@ xfs_ialloc_log_di(
 		offsetof(xfs_dinode_core_t, di_uid),
 		offsetof(xfs_dinode_core_t, di_gid),
 		offsetof(xfs_dinode_core_t, di_nlink),
-		offsetof(xfs_dinode_core_t, di_projid),
+		offsetof(xfs_dinode_core_t, di_projid_lo),
+		offsetof(xfs_dinode_core_t, di_projid_hi),
 		offsetof(xfs_dinode_core_t, di_pad),
 		offsetof(xfs_dinode_core_t, di_atime),
 		offsetof(xfs_dinode_core_t, di_mtime),
diff --git a/libxfs/xfs_inode.c b/libxfs/xfs_inode.c
index b0adabc..1c9ea3b 100644
--- a/libxfs/xfs_inode.c
+++ b/libxfs/xfs_inode.c
@@ -589,7 +589,8 @@ xfs_dinode_from_disk(
 	to->di_uid = be32_to_cpu(from->di_uid);
 	to->di_gid = be32_to_cpu(from->di_gid);
 	to->di_nlink = be32_to_cpu(from->di_nlink);
-	to->di_projid = be16_to_cpu(from->di_projid);
+	to->di_projid_lo = be16_to_cpu(from->di_projid_lo);
+	to->di_projid_hi = be16_to_cpu(from->di_projid_hi);
 	memcpy(to->di_pad, from->di_pad, sizeof(to->di_pad));
 	to->di_flushiter = be16_to_cpu(from->di_flushiter);
 	to->di_atime.t_sec = be32_to_cpu(from->di_atime.t_sec);
@@ -624,7 +625,8 @@ xfs_dinode_to_disk(
 	to->di_uid = cpu_to_be32(from->di_uid);
 	to->di_gid = cpu_to_be32(from->di_gid);
 	to->di_nlink = cpu_to_be32(from->di_nlink);
-	to->di_projid = cpu_to_be16(from->di_projid);
+	to->di_projid_lo = cpu_to_be16(from->di_projid_lo);
+	to->di_projid_hi = cpu_to_be16(from->di_projid_hi);
 	memcpy(to->di_pad, from->di_pad, sizeof(to->di_pad));
 	to->di_flushiter = cpu_to_be16(from->di_flushiter);
 	to->di_atime.t_sec = cpu_to_be32(from->di_atime.t_sec);
diff --git a/logprint/log_print_all.c b/logprint/log_print_all.c
index c21e05c..572dac8 100644
--- a/logprint/log_print_all.c
+++ b/logprint/log_print_all.c
@@ -238,8 +238,10 @@ xlog_recover_print_inode_core(
 	     "onlink:%d\n"),
 	       (di->di_magic>>8) & 0xff, di->di_magic & 0xff,
 	       di->di_mode, di->di_version, di->di_format, di->di_onlink);
-	printf(_("		uid:%d  gid:%d  nlink:%d projid:%d\n"),
-	       di->di_uid, di->di_gid, di->di_nlink, (uint)di->di_projid);
+	printf(_("		uid:%d  gid:%d  nlink:%d\n"),
+	       di->di_uid, di->di_gid, di->di_nlink);
+	printf(_("		projid_lo:%d projid_hi:%d\n"),
+	       (uint)di->di_projid_lo, (uint)di->di_projid_hi);
 	printf(_("		atime:%d  mtime:%d  ctime:%d\n"),
 	       di->di_atime.t_sec, di->di_mtime.t_sec, di->di_ctime.t_sec);
 	printf(_("		flushiter:%d\n"), di->di_flushiter);
diff --git a/man/man3/xfsctl.3 b/man/man3/xfsctl.3
index 784b3e0..4239a62 100644
--- a/man/man3/xfsctl.3
+++ b/man/man3/xfsctl.3
@@ -565,7 +565,9 @@ The structure has the following elements:
 .B bs_gen
 (generation count),
 .B bs_projid
-(project id),
+(project id - low word),
+.B bs_projid_hi
+(project id - high word, used when projid32bit feature is enabled),
 .B bs_dmevmask
 (DMIG event mask),
 .B bs_dmstate
diff --git a/man/man8/mkfs.xfs.8 b/man/man8/mkfs.xfs.8
index fdd38d4..a59bc89 100644
--- a/man/man8/mkfs.xfs.8
+++ b/man/man8/mkfs.xfs.8
@@ -350,6 +350,13 @@ between attribute and extent data.
 The previous version 1, which has fixed regions for attribute and
 extent data, is kept for backwards compatibility with kernels older
 than version 2.6.16.
+.TP
+.BI projid32bit[= value]
+This is used to enable 32bit quota project identifiers. The
+.I value
+is either 0 or 1, with 1 signifying that 32bit projid are to be enabled.
+If the
+is omitted, 0 is assumed.
 .RE
 .TP
 .BI \-l " log_section_options"
diff --git a/man/man8/xfs_db.8 b/man/man8/xfs_db.8
index 629ae58..17ac601 100644
--- a/man/man8/xfs_db.8
+++ b/man/man8/xfs_db.8
@@ -1474,8 +1474,10 @@ number of links to the file in a version 1 inode.
 .B nlinkv2
 number of links to the file in a version 2 inode.
 .TP
-.B projid
-owner's project id (version 2 inode only).
+.B projid_lo
+owner's project id (low word; version 2 inode only).
+.B projid_hi
+owner's project id (high word; version 2 inode only).
 .TP
 .B uid
 owner's user id.
diff --git a/mkfs/xfs_mkfs.c b/mkfs/xfs_mkfs.c
index 2d09e36..155a0b5 100644
--- a/mkfs/xfs_mkfs.c
+++ b/mkfs/xfs_mkfs.c
@@ -106,6 +106,8 @@ char	*iopts[] = {
 	"size",
 #define	I_ATTR		5
 	"attr",
+#define	I_PROJID32BIT	6
+	"projid32bit",
 	NULL
 };
 
@@ -829,6 +831,7 @@ main(
 	__uint64_t		agsize;
 	xfs_alloc_rec_t		*arec;
 	int			attrversion;
+	int			projid32bit;
 	struct xfs_btree_block	*block;
 	int			blflag;
 	int			blocklog;
@@ -923,6 +926,7 @@ main(
 	textdomain(PACKAGE);
 
 	attrversion = 2;
+	projid32bit = 0;
 	blflag = bsflag = slflag = ssflag = lslflag = lssflag = 0;
 	blocklog = blocksize = 0;
 	sectorlog = lsectorlog = XFS_MIN_SECTORSIZE_LOG;
@@ -1259,6 +1263,14 @@ main(
 						illegal(value, "i attr");
 					attrversion = c;
 					break;
+				case I_PROJID32BIT:
+					if (!value)
+						value = "0";
+					c = atoi(value);
+					if (c < 0 || c > 1)
+						illegal(value, "i projid32bit");
+					projid32bit = c;
+					break;
 				default:
 					unknown('i', value);
 				}
@@ -2261,7 +2273,7 @@ an AG size that is one stripe unit smaller, for example %llu.\n"),
 	if (!qflag || Nflag) {
 		printf(_(
 		   "meta-data=%-22s isize=%-6d agcount=%lld, agsize=%lld blks\n"
-		   "         =%-22s sectsz=%-5u attr=%u\n"
+		   "         =%-22s sectsz=%-5u attr=%u projid32bit=%u\n"
 		   "data     =%-22s bsize=%-6u blocks=%llu, imaxpct=%u\n"
 		   "         =%-22s sunit=%-6u swidth=%u blks\n"
 		   "naming   =version %-14u bsize=%-6u ascii-ci=%d\n"
@@ -2269,7 +2281,7 @@ an AG size that is one stripe unit smaller, for example %llu.\n"),
 		   "         =%-22s sectsz=%-5u sunit=%d blks, lazy-count=%d\n"
 		   "realtime =%-22s extsz=%-6d blocks=%lld, rtextents=%lld\n"),
 			dfile, isize, (long long)agcount, (long long)agsize,
-			"", sectorsize, attrversion,
+			"", sectorsize, attrversion, projid32bit,
 			"", blocksize, (long long)dblocks, imaxpct,
 			"", dsunit, dswidth,
 			dirversion, dirblocksize, nci,
@@ -2336,7 +2348,7 @@ an AG size that is one stripe unit smaller, for example %llu.\n"),
 		sbp->sb_logsectsize = 0;
 	}
 	sbp->sb_features2 = XFS_SB_VERSION2_MKFS(lazy_sb_counters,
-					attrversion == 2, 0);
+					attrversion == 2, projid32bit == 1, 0);
 	sbp->sb_versionnum = XFS_SB_VERSION_MKFS(iaflag, dsunit != 0,
 					logversion == 2, attrversion == 1,
 					(sectorsize != BBSIZE ||
@@ -2804,7 +2816,8 @@ usage( void )
 /* data subvol */	[-d agcount=n,agsize=n,file,name=xxx,size=num,\n\
 			    (sunit=value,swidth=value|su=num,sw=num),\n\
 			    sectlog=n|sectsize=num\n\
-/* inode size */	[-i log=n|perblock=n|size=num,maxpct=n,attr=0|1|2]\n\
+/* inode size */	[-i log=n|perblock=n|size=num,maxpct=n,attr=0|1|2,\n\
+			    projid32bit=0|1]\n\
 /* log subvol */	[-l agnum=n,internal,size=num,logdev=xxx,version=n\n\
 			    sunit=value|su=num,sectlog=n|sectsize=num,\n\
 			    lazy-count=0|1]\n\
diff --git a/mkfs/xfs_mkfs.h b/mkfs/xfs_mkfs.h
index 49401d6..f25a7f3 100644
--- a/mkfs/xfs_mkfs.h
+++ b/mkfs/xfs_mkfs.h
@@ -36,9 +36,10 @@
 	        XFS_DFL_SB_VERSION_BITS |                               \
 	0 ) : XFS_SB_VERSION_1 )
 
-#define XFS_SB_VERSION2_MKFS(lazycount, attr2, parent) (\
+#define XFS_SB_VERSION2_MKFS(lazycount, attr2, projid32bit, parent) (\
 	((lazycount) ? XFS_SB_VERSION2_LAZYSBCOUNTBIT : 0) |		\
 	((attr2) ? XFS_SB_VERSION2_ATTR2BIT : 0) |			\
+	((projid32bit) ? XFS_SB_VERSION2_PROJID32BIT : 0) |		\
 	((parent) ? XFS_SB_VERSION2_PARENTBIT : 0) |			\
 	0 )
 
diff --git a/quota/quot.c b/quota/quot.c
index 09d349f..54387ea 100644
--- a/quota/quot.c
+++ b/quota/quot.c
@@ -102,7 +102,7 @@ quot_bulkstat_add(
 	}
 	for (i = 0; i < 3; i++) {
 		id = (i == 0) ? p->bs_uid : ((i == 1) ?
-				p->bs_gid : p->bs_projid);
+			p->bs_gid : bstat_get_projid(p));
 		hp = &duhash[i][id % DUHASH];
 		for (dp = *hp; dp; dp = dp->next)
 			if (dp->id == id)
diff --git a/repair/README b/repair/README
index 69cb0c5..7f168e6 100644
--- a/repair/README
+++ b/repair/README
@@ -130,7 +130,7 @@ D - 0)	rewrite directory leaf block holemap comparison code.
 	it does describe doesn't conflict with reality.
 
 D - 0)	rewrite setting nlinks handling -- for version 1
-	inodes, set both nlinks and onlinks (zero projid
+	inodes, set both nlinks and onlinks (zero projid_lo/hi
 	and pad) if we have to change anything.  For
 	version 2, I think we're ok.
 
-- 
1.7.3

_______________________________________________
xfs mailing list
xfs@oss.sgi.com
http://oss.sgi.com/mailman/listinfo/xfs

^ permalink raw reply related	[flat|nested] 9+ messages in thread

* [PATCH VER 6] xfstests: Quota project id setting overflow
  2010-09-26  6:10 ` [PATCH VER 6] xfsprogs: projid32bit handling Arkadiusz Miśkiewicz
@ 2010-09-26  6:10   ` Arkadiusz Miśkiewicz
  2010-10-01 13:57     ` Alex Elder
  2010-09-26  6:13   ` [PATCH VER 6] xfsprogs: projid32bit handling Arkadiusz Miskiewicz
  2010-10-01 13:57   ` Alex Elder
  2 siblings, 1 reply; 9+ messages in thread
From: Arkadiusz Miśkiewicz @ 2010-09-26  6:10 UTC (permalink / raw)
  To: xfs

From: Arkadiusz Miskiewicz <arekm@maven.pl>

Test 3 quota project setting id conditions:
- set 16bit project quota id -> should succeed
- set 32bit project quota id -> should succeed (with projid32bit
  patch applied; fail otherwise)
- over 32bit project quota id -> should always fail

Signed-off-by: Arkadiusz Miśkiewicz <arekm@maven.pl>
Reviewed-by: Christoph Hellwig <hch@lst.de>
---

News:
- one error message corrected

 244     |  125 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 244.out |    2 +
 group   |    1 +
 3 files changed, 128 insertions(+), 0 deletions(-)
 create mode 100644 244
 create mode 100644 244.out

diff --git a/244 b/244
new file mode 100644
index 0000000..4b460cf
--- /dev/null
+++ b/244
@@ -0,0 +1,125 @@
+#! /bin/bash
+# FS QA Test No. 244
+#
+# test to verify that proper project quota id is correctly set
+#
+#-----------------------------------------------------------------------
+# Copyright (c) 2010 Arkadiusz Miśkiewicz.  All Rights Reserved.
+#
+# 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.
+#
+# This program is distributed in the hope that it would 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 the Free Software Foundation,
+# Inc.,  51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+#
+#-----------------------------------------------------------------------
+#
+# creator
+owner=arekm@maven.pl
+
+seq=`basename $0`
+echo "QA output created by $seq"
+
+here=`pwd`
+tmp=/tmp/$$
+status=1	# failure is the default!
+trap "_cleanup; exit \$status" 0 1 2 3 15
+
+# get standard environment, filters and checks
+. ./common.rc
+. ./common.filter
+. ./common.quota
+
+_cleanup()
+{
+	cd /
+	umount $SCRATCH_MNT 2>/dev/null
+	rm -f $tmp.*
+}
+
+# real QA test starts here
+_supported_fs xfs
+_require_xfs_quota
+_require_scratch
+
+export MOUNT_OPTIONS="-opquota"
+
+# make fs with no projid32bit
+_scratch_mkfs_xfs -i projid32bit=0 >> $seq.full || _fail "mkfs failed"
+_qmount
+# make sure project quota is supported
+_require_prjquota ${SCRATCH_DEV}
+
+dir=$SCRATCH_MNT/project
+
+status=0
+
+echo "Silence is golden"
+
+# Do testing on filesystem with projid32bit feature disabled
+mkdir $dir
+
+touch $dir/below16bit
+# below 16bit value
+$XFS_QUOTA_PROG -x -c "project -s -p $dir/below16bit 3422" $SCRATCH_DEV >> $seq.full
+projid=$($XFS_IO_PROG -r -c "lsproj" $dir/below16bit)
+if [ "projid = 3422" != "$projid" ]; then
+	echo "FAIL: projid32bit disabled: returned projid value ($projid) doesn't match set one (projid = 3422)"
+	status=1
+fi
+
+# 32bit value, should fail
+touch $dir/over16bit
+if $XFS_QUOTA_PROG -x -c "project -s -p $dir/over16bit 108545" $SCRATCH_DEV >> $seq.full 2>&1; then
+	echo "FAIL: projid32bit disabled: setting 32bit projid succeeded while it should fail"
+	status=1
+fi
+
+# over 32bit value, should fail
+touch $dir/over32bit
+if $XFS_QUOTA_PROG -x -c "project -s -p $dir/over32bit 5344967296" $SCRATCH_DEV >> $seq.full 2>&1; then
+	echo "FAIL: projid32bit disabled: setting over 32bit projid succeeded while it should fail"
+	status=1
+fi
+
+#  Do testing on filesystem with projid32bit feature enabled
+umount $SCRATCH_DEV 2>/dev/null
+_scratch_mkfs_xfs -i projid32bit=1 >> $seq.full || _fail "mkfs failed"
+_qmount
+mkdir $dir
+
+touch $dir/below16bit
+# below 16bit value, should succeed
+$XFS_QUOTA_PROG -x -c "project -s -p $dir/below16bit 3422" $SCRATCH_DEV >> $seq.full
+projid=$($XFS_IO_PROG -r -c "lsproj" $dir/below16bit)
+if [ "projid = 3422" != "$projid" ]; then
+	echo "FAIL: projid32bit enabled: returned projid value ($projid) doesn't match set one (projid = 3422)"
+	status=1
+fi
+
+# 32bit value, should succeed
+touch $dir/over16bit
+if $XFS_QUOTA_PROG -x -c "project -s -p $dir/over16bit 108545" $SCRATCH_DEV >> $seq.full 2>&1; then
+	projid=$($XFS_IO_PROG -r -c "lsproj" $dir/over16bit)
+	if [ "projid = 108545" != "$projid" ]; then
+		echo "FAIL: projid32bit enabled: returned projid value ($projid) doesn't match set one (projid = 108545)"
+		status=1
+	fi
+else
+	echo "FAIL: projid32bit enabled: setting 32bit projid failed while it should succeed"
+	status=1
+fi
+
+# over 32bit value, should fail
+touch $dir/over32bit
+if $XFS_QUOTA_PROG -x -c "project -s -p $dir/over32bit 5344967296" $SCRATCH_DEV >> $seq.full 2>&1; then
+	echo "FAIL: projid32bit enabled: setting over 32bit projid succeeded while it should fail"
+	status=1
+fi
diff --git a/244.out b/244.out
new file mode 100644
index 0000000..440da1f
--- /dev/null
+++ b/244.out
@@ -0,0 +1,2 @@
+QA output created by 244
+Silence is golden
diff --git a/group b/group
index e6dab13..0cd158b 100644
--- a/group
+++ b/group
@@ -357,3 +357,4 @@ deprecated
 241 auto
 242 auto quick prealloc
 243 auto quick prealloc
+244 auto quota quick
-- 
1.7.3

_______________________________________________
xfs mailing list
xfs@oss.sgi.com
http://oss.sgi.com/mailman/listinfo/xfs

^ permalink raw reply related	[flat|nested] 9+ messages in thread

* Re: [PATCH VER 6] xfsprogs: projid32bit handling
  2010-09-26  6:10 ` [PATCH VER 6] xfsprogs: projid32bit handling Arkadiusz Miśkiewicz
  2010-09-26  6:10   ` [PATCH VER 6] xfstests: Quota project id setting overflow Arkadiusz Miśkiewicz
@ 2010-09-26  6:13   ` Arkadiusz Miskiewicz
  2010-10-01 13:57     ` Alex Elder
  2010-10-01 13:57   ` Alex Elder
  2 siblings, 1 reply; 9+ messages in thread
From: Arkadiusz Miskiewicz @ 2010-09-26  6:13 UTC (permalink / raw)
  To: xfs

On Sunday 26 of September 2010, Arkadiusz Miśkiewicz wrote:
> Add projid32bit handling to userspace. mkfs.xfs is able to enable this
> feature for new filesystems. xfs_db knows what projid_lo/hi are.

... and xfs_admin if someone needs it anyway.

News:
- use 0x80 instead of 0x20 for PROJID32BIT superblock bit (as 0x20
  and 0x40 are reserved)

diff --git a/db/xfs_admin.sh b/db/xfs_admin.sh
index a7a3fdb..ec8424d 100755
--- a/db/xfs_admin.sh
+++ b/db/xfs_admin.sh
@@ -6,9 +6,43 @@
 status=0
 DB_OPTS=""
 REPAIR_OPTS=""
-USAGE="Usage: xfs_admin [-efjluV] [-c 0|1] [-L label] [-U uuid] device"
+USAGE="Usage: xfs_admin [-efjlpuV] [-c 0|1] [-L label] [-U uuid] device"
 
-while getopts "efjluc:L:U:V" c
+set_features2_bit() {
+	device="$1"
+	bit="$2"
+
+	if [ -z "$device" ]; then
+		echo "$0: device name is missing" >&2
+		return 1
+	fi
+
+	if [ -z "$bit" ]; then
+		echo "$0: bits to set are missing" >&2
+		return 1
+	fi
+
+	# read current bits
+	features2=$(xfs_db -p xfs_admin -x -r -c 'sb' -c 'print features2' "$device" | awk ' { print $3 } ')
+	if [ -z "$features2" ]; then
+		echo "$0: can't read features2 from superblock!" >&2
+		return 1
+	fi
+	bad_features2=$(xfs_db -p xfs_admin -x -r -c 'sb' -c 'print bad_features2' "$device" | awk ' { print $3 } ')
+	if [ -z "$bad_features2" ]; then
+		echo "$0: can't read bad_features2 from superblock!" >&2
+		return 1
+	fi
+
+	# set new bits
+	features2=$((features2 | bit))
+	bad_features2=$((bad_features2 | bit))
+	xfs_db -p xfs_admin -x -c 'sb' -c "write features2 $features2" "$device" && \
+		xfs_db -p xfs_admin -x -c 'sb' -c "write bad_features2 $bad_features2" "$device"
+	return $?
+}
+
+while getopts "efjlu3c:L:U:V" c
 do
 	case $c in
 	c)	REPAIR_OPTS=$REPAIR_OPTS" -c lazycount="$OPTARG;;
@@ -17,6 +51,7 @@ do
 	j)	DB_OPTS=$DB_OPTS" -c 'version log2'";;
 	l)	DB_OPTS=$DB_OPTS" -r -c label";;
 	L)	DB_OPTS=$DB_OPTS" -c 'label "$OPTARG"'";;
+	3)	FEATURES_BIT="0x80";;
 	u)	DB_OPTS=$DB_OPTS" -r -c uuid";;
 	U)	DB_OPTS=$DB_OPTS" -c 'uuid "$OPTARG"'";;
 	V)	xfs_db -p xfs_admin -V
@@ -31,7 +66,12 @@ done
 set -- extra $@
 shift $OPTIND
 case $# in
-	1)	if [ -n "$DB_OPTS" ]
+	1)	if [ -n "$FEATURES_BIT" ]
+		then
+			set_features2_bit "$1" "$FEATURES_BIT"
+			status=$?
+		fi
+		if [ -n "$DB_OPTS" ]
 		then
 			eval xfs_db -x -p xfs_admin $DB_OPTS $1
 			status=$?
diff --git a/man/man8/xfs_admin.8 b/man/man8/xfs_admin.8
index 8e3155b..6b727f3 100644
--- a/man/man8/xfs_admin.8
+++ b/man/man8/xfs_admin.8
@@ -4,7 +4,7 @@ xfs_admin \- change parameters of an XFS filesystem
 .SH SYNOPSIS
 .B xfs_admin
 [
-.B \-eflu
+.B \-eflu3
 ] [
 .BR "\-c 0" | 1
 ] [
@@ -55,6 +55,9 @@ Print the current filesystem label.
 .B \-u
 Print the current filesystem UUID (Universally Unique IDentifier).
 .TP
+.B \-3
+Enable 32bit project identifier support (PROJID32BIT feature).
+.TP
 .BR "\-c 0" | 1
 Enable (1) or disable (0) lazy-counters in the filesystem.
 This operation may take quite a bit of time on large filesystems as the


-- 
Arkadiusz Miśkiewicz        PLD/Linux Team
arekm / maven.pl            http://ftp.pld-linux.org/

_______________________________________________
xfs mailing list
xfs@oss.sgi.com
http://oss.sgi.com/mailman/listinfo/xfs

^ permalink raw reply related	[flat|nested] 9+ messages in thread

* Re: [PATCH VER 6] Extend project quotas to support 32bit project identifiers.
  2010-09-26  6:10 [PATCH VER 6] Extend project quotas to support 32bit project identifiers Arkadiusz Miśkiewicz
  2010-09-26  6:10 ` [PATCH VER 6] xfsprogs: projid32bit handling Arkadiusz Miśkiewicz
@ 2010-09-28  1:43 ` Christoph Hellwig
  2010-10-01 13:57 ` Alex Elder
  2 siblings, 0 replies; 9+ messages in thread
From: Christoph Hellwig @ 2010-09-28  1:43 UTC (permalink / raw)
  To: Arkadiusz Mi??kiewicz; +Cc: xfs

All three patches looks good to me.

Thanks a lot Arkadiusz!

_______________________________________________
xfs mailing list
xfs@oss.sgi.com
http://oss.sgi.com/mailman/listinfo/xfs

^ permalink raw reply	[flat|nested] 9+ messages in thread

* Re: [PATCH VER 6] Extend project quotas to support 32bit project identifiers.
  2010-09-26  6:10 [PATCH VER 6] Extend project quotas to support 32bit project identifiers Arkadiusz Miśkiewicz
  2010-09-26  6:10 ` [PATCH VER 6] xfsprogs: projid32bit handling Arkadiusz Miśkiewicz
  2010-09-28  1:43 ` [PATCH VER 6] Extend project quotas to support 32bit project identifiers Christoph Hellwig
@ 2010-10-01 13:57 ` Alex Elder
  2 siblings, 0 replies; 9+ messages in thread
From: Alex Elder @ 2010-10-01 13:57 UTC (permalink / raw)
  To: Arkadiusz Miśkiewicz; +Cc: xfs

On Sun, 2010-09-26 at 08:10 +0200, Arkadiusz Miśkiewicz wrote:
> This patch adds support for 32bit project quota identifiers.
> 
> On disk format is backward compatible with 16bit projid numbers. projid
> on disk is now keept in two 16bit values - di_projid_lo (which holds the
> same position as old 16bit projid value) and new di_projid_hi (takes
> existing padding) and convertes from/to 32bit value on the fly.
> 
> xfs_admin (for existing fs), mkfs.xfs (for new fs) needs to be used
> to enable PROJID32BIT support.
> 
> Signed-off-by: Arkadiusz Miśkiewicz <arekm@maven.pl>
> Reviewed-by: Christoph Hellwig <hch@lst.de>
> ---

Minor suggestion, below (which I can implement), otherwise this
looks good.

I didn't review it as carefully this time.  But the model now
is that 32-bit project id's are only supported if the filesystem
has that feature bit set.  And the feature bit is only set at
mkfs time or by xfs_db (not automatically as you had it before).
This sounds good to me.

Reviewed-by: Alex Elder <aelder@sgi.com>

> News:
> - use 0x80 instead of 0x20 for PROJID32BIT superblock bit (as 0x20
>   and 0x40 are reserved)
> - style fix

. . .

> diff --git a/fs/xfs/linux-2.6/xfs_ioctl32.h b/fs/xfs/linux-2.6/xfs_ioctl32.h
> index 1024c4f..f92d662 100644
> --- a/fs/xfs/linux-2.6/xfs_ioctl32.h
> +++ b/fs/xfs/linux-2.6/xfs_ioctl32.h
> @@ -65,8 +65,9 @@ typedef struct compat_xfs_bstat {
>  	__s32		bs_extsize;	/* extent size			*/
>  	__s32		bs_extents;	/* number of extents		*/
>  	__u32		bs_gen;		/* generation count		*/
> -	__u16		bs_projid;	/* project id			*/
> -	unsigned char	bs_pad[14];	/* pad space, unused		*/
> +	__u16		bs_projid;	/* lower part of project id	*/

This could be:
          __u16           bs_projid_lo;   /* ... */
#define bs_projid bs_projid_lo

...to make it work with old code but be more consistent with new.

> +	__u16		bs_projid_hi;	/* high part of project id	*/
> +	unsigned char	bs_pad[12];	/* pad space, unused		*/
>  	__u32		bs_dmevmask;	/* DMIG event mask		*/
>  	__u16		bs_dmstate;	/* DMIG state info		*/
>  	__u16		bs_aextents;	/* attribute number of extents	*/

. . .

> diff --git a/fs/xfs/xfs_fs.h b/fs/xfs/xfs_fs.h
> index 87c2e9d..ae1c500 100644
> --- a/fs/xfs/xfs_fs.h
> +++ b/fs/xfs/xfs_fs.h
> @@ -293,9 +293,10 @@ typedef struct xfs_bstat {
>  	__s32		bs_extsize;	/* extent size			*/
>  	__s32		bs_extents;	/* number of extents		*/
>  	__u32		bs_gen;		/* generation count		*/
> -	__u16		bs_projid;	/* project id			*/
> +	__u16		bs_projid;	/* lower part of project id	*/

Same thing here.

>  	__u16		bs_forkoff;	/* inode fork offset in bytes	*/
> -	unsigned char	bs_pad[12];	/* pad space, unused		*/
> +	__u16		bs_projid_hi;	/* higher part of project id	*/
> +	unsigned char	bs_pad[10];	/* pad space, unused		*/
>  	__u32		bs_dmevmask;	/* DMIG event mask		*/
>  	__u16		bs_dmstate;	/* DMIG state info		*/
>  	__u16		bs_aextents;	/* attribute number of extents	*/

. . .

_______________________________________________
xfs mailing list
xfs@oss.sgi.com
http://oss.sgi.com/mailman/listinfo/xfs

^ permalink raw reply	[flat|nested] 9+ messages in thread

* Re: [PATCH VER 6] xfsprogs: projid32bit handling
  2010-09-26  6:10 ` [PATCH VER 6] xfsprogs: projid32bit handling Arkadiusz Miśkiewicz
  2010-09-26  6:10   ` [PATCH VER 6] xfstests: Quota project id setting overflow Arkadiusz Miśkiewicz
  2010-09-26  6:13   ` [PATCH VER 6] xfsprogs: projid32bit handling Arkadiusz Miskiewicz
@ 2010-10-01 13:57   ` Alex Elder
  2 siblings, 0 replies; 9+ messages in thread
From: Alex Elder @ 2010-10-01 13:57 UTC (permalink / raw)
  To: Arkadiusz Miśkiewicz; +Cc: xfs

On Sun, 2010-09-26 at 08:10 +0200, Arkadiusz Miśkiewicz wrote:
> Add projid32bit handling to userspace. mkfs.xfs is able to enable this
> feature for new filesystems. xfs_db knows what projid_lo/hi are.
> 
> Signed-off-by: Arkadiusz Miśkiewicz <arekm@maven.pl>
> Reviewed-by: Christoph Hellwig <hch@lst.de>

This looks good (although I've only done a quick review).
I have found a few nits, below, which could be pretty
easily fixed before it's committed (by me unless some
else is going to do it).

I think it would be nice to have xfs_repair (and check)
report the existence of non-zero bs_projid_hi on a
filesystem without the PROJID32BIT superblock bit set.
But that wait.

Reviewed-by: Alex Elder <aelder@sgi.com>

> ---
> 
> News:
> - use 0x80 instead of 0x20 for PROJID32BIT superblock bit (as 0x20
>   and 0x40 are reserved)                                                                                                                                     

. . .

> diff --git a/include/xfs_fs.h b/include/xfs_fs.h
> index 74e7274..9a51c64 100644
> --- a/include/xfs_fs.h
> +++ b/include/xfs_fs.h
> @@ -299,9 +299,10 @@ typedef struct xfs_bstat {
>  	__s32		bs_extsize;	/* extent size			*/
>  	__s32		bs_extents;	/* number of extents		*/
>  	__u32		bs_gen;		/* generation count		*/
> -	__u16		bs_projid;	/* project id			*/
> +	__u16		bs_projid;	/* lower part of project id	*/

This:
          __u16           bs_projid_lo;   /* lower part... */
#define bs_projid bs_projid_lo

...would make the old code compile but would make the
struct definition more consistent with the others.


>  	__u16		bs_forkoff;	/* inode fork offset in bytes	*/
> -	unsigned char	bs_pad[12];	/* pad space, unused		*/
> +	__u16		bs_projid_hi;	/* higher part of project id	*/
> +	unsigned char	bs_pad[10];	/* pad space, unused		*/
>  	__u32		bs_dmevmask;	/* DMIG event mask		*/
>  	__u16		bs_dmstate;	/* DMIG state info		*/
>  	__u16		bs_aextents;	/* attribute number of extents	*/

. . .

> diff --git a/man/man8/mkfs.xfs.8 b/man/man8/mkfs.xfs.8
> index fdd38d4..a59bc89 100644
> --- a/man/man8/mkfs.xfs.8
> +++ b/man/man8/mkfs.xfs.8
> @@ -350,6 +350,13 @@ between attribute and extent data.
>  The previous version 1, which has fixed regions for attribute and
>  extent data, is kept for backwards compatibility with kernels older
>  than version 2.6.16.
> +.TP
> +.BI projid32bit[= value]

       projid32bit[=value]

> +This is used to enable 32bit quota project identifiers. The
> +.I value
> +is either 0 or 1, with 1 signifying that 32bit projid are to be enabled.
> +If the

   If the value

> +is omitted, 0 is assumed.
>  .RE
>  .TP
>  .BI \-l " log_section_options"

. . .

_______________________________________________
xfs mailing list
xfs@oss.sgi.com
http://oss.sgi.com/mailman/listinfo/xfs

^ permalink raw reply	[flat|nested] 9+ messages in thread

* Re: [PATCH VER 6] xfstests: Quota project id setting overflow
  2010-09-26  6:10   ` [PATCH VER 6] xfstests: Quota project id setting overflow Arkadiusz Miśkiewicz
@ 2010-10-01 13:57     ` Alex Elder
  0 siblings, 0 replies; 9+ messages in thread
From: Alex Elder @ 2010-10-01 13:57 UTC (permalink / raw)
  To: Arkadiusz Miśkiewicz; +Cc: xfs

On Sun, 2010-09-26 at 08:10 +0200, Arkadiusz Miśkiewicz wrote:
> From: Arkadiusz Miskiewicz <arekm@maven.pl>
> 
> Test 3 quota project setting id conditions:
> - set 16bit project quota id -> should succeed
> - set 32bit project quota id -> should succeed (with projid32bit
>   patch applied; fail otherwise)
> - over 32bit project quota id -> should always fail
> 
> Signed-off-by: Arkadiusz Miśkiewicz <arekm@maven.pl>
> Reviewed-by: Christoph Hellwig <hch@lst.de>

Looks good.

Reviewed-by: Alex Elder <aelder@sgi.com>



_______________________________________________
xfs mailing list
xfs@oss.sgi.com
http://oss.sgi.com/mailman/listinfo/xfs

^ permalink raw reply	[flat|nested] 9+ messages in thread

* Re: [PATCH VER 6] xfsprogs: projid32bit handling
  2010-09-26  6:13   ` [PATCH VER 6] xfsprogs: projid32bit handling Arkadiusz Miskiewicz
@ 2010-10-01 13:57     ` Alex Elder
  0 siblings, 0 replies; 9+ messages in thread
From: Alex Elder @ 2010-10-01 13:57 UTC (permalink / raw)
  To: Arkadiusz Miskiewicz; +Cc: xfs

On Sun, 2010-09-26 at 08:13 +0200, Arkadiusz Miskiewicz wrote:
> On Sunday 26 of September 2010, Arkadiusz Miśkiewicz wrote:
> > Add projid32bit handling to userspace. mkfs.xfs is able to enable this
> > feature for new filesystems. xfs_db knows what projid_lo/hi are.
> 
> ... and xfs_admin if someone needs it anyway.

Do you intend for this to be included or not?

I also have a question, below.

> 
> News:
> - use 0x80 instead of 0x20 for PROJID32BIT superblock bit (as 0x20
>   and 0x40 are reserved)
> 
> diff --git a/db/xfs_admin.sh b/db/xfs_admin.sh
> index a7a3fdb..ec8424d 100755
> --- a/db/xfs_admin.sh
> +++ b/db/xfs_admin.sh
> @@ -6,9 +6,43 @@
>  status=0
>  DB_OPTS=""
>  REPAIR_OPTS=""
> -USAGE="Usage: xfs_admin [-efjluV] [-c 0|1] [-L label] [-U uuid] device"
> +USAGE="Usage: xfs_admin [-efjlpuV] [-c 0|1] [-L label] [-U uuid] device"

Here you are describing a "p" flag, but below you are
actually adding a "3" flag (and documented as such in
the man page).  I prefer "p" (but maybe there's a reason
you used "3" below).  Which is it?
 
> -while getopts "efjluc:L:U:V" c
> +set_features2_bit() {
> +	device="$1"
> +	bit="$2"
> +
> +	if [ -z "$device" ]; then
> +		echo "$0: device name is missing" >&2
> +		return 1
> +	fi
> +
> +	if [ -z "$bit" ]; then
> +		echo "$0: bits to set are missing" >&2
> +		return 1
> +	fi
> +
> +	# read current bits
> +	features2=$(xfs_db -p xfs_admin -x -r -c 'sb' -c 'print features2' "$device" | awk ' { print $3 } ')
> +	if [ -z "$features2" ]; then
> +		echo "$0: can't read features2 from superblock!" >&2
> +		return 1
> +	fi
> +	bad_features2=$(xfs_db -p xfs_admin -x -r -c 'sb' -c 'print bad_features2' "$device" | awk ' { print $3 } ')
> +	if [ -z "$bad_features2" ]; then
> +		echo "$0: can't read bad_features2 from superblock!" >&2
> +		return 1
> +	fi
> +
> +	# set new bits
> +	features2=$((features2 | bit))
> +	bad_features2=$((bad_features2 | bit))
> +	xfs_db -p xfs_admin -x -c 'sb' -c "write features2 $features2" "$device" && \
> +		xfs_db -p xfs_admin -x -c 'sb' -c "write bad_features2 $bad_features2" "$device"
> +	return $?
> +}
> +
> +while getopts "efjlu3c:L:U:V"
>  do
>  	case $c in
>  	c)	REPAIR_OPTS=$REPAIR_OPTS" -c lazycount="$OPTARG;;
> @@ -17,6 +51,7 @@ do
>  	j)	DB_OPTS=$DB_OPTS" -c 'version log2'";;
>  	l)	DB_OPTS=$DB_OPTS" -r -c label";;
>  	L)	DB_OPTS=$DB_OPTS" -c 'label "$OPTARG"'";;
> +	3)	FEATURES_BIT="0x80";;

>  	u)	DB_OPTS=$DB_OPTS" -r -c uuid";;
>  	U)	DB_OPTS=$DB_OPTS" -c 'uuid "$OPTARG"'";;
>  	V)	xfs_db -p xfs_admin -V
> @@ -31,7 +66,12 @@ done
>  set -- extra $@
>  shift $OPTIND
>  case $# in
> -	1)	if [ -n "$DB_OPTS" ]
> +	1)	if [ -n "$FEATURES_BIT" ]
> +		then
> +			set_features2_bit "$1" "$FEATURES_BIT"
> +			status=$?
> +		fi
> +		if [ -n "$DB_OPTS" ]
>  		then
>  			eval xfs_db -x -p xfs_admin $DB_OPTS $1
>  			status=$?
> diff --git a/man/man8/xfs_admin.8 b/man/man8/xfs_admin.8
> index 8e3155b..6b727f3 100644
> --- a/man/man8/xfs_admin.8
> +++ b/man/man8/xfs_admin.8
> @@ -4,7 +4,7 @@ xfs_admin \- change parameters of an XFS filesystem
>  .SH SYNOPSIS
>  .B xfs_admin
>  [
> -.B \-eflu
> +.B \-eflu3
>  ] [
>  .BR "\-c 0" | 1
>  ] [
> @@ -55,6 +55,9 @@ Print the current filesystem label.
>  .B \-u
>  Print the current filesystem UUID (Universally Unique IDentifier).
>  .TP
> +.B \-3
> +Enable 32bit project identifier support (PROJID32BIT feature).
> +.TP
>  .BR "\-c 0" | 1
>  Enable (1) or disable (0) lazy-counters in the filesystem.
>  This operation may take quite a bit of time on large filesystems as the
> 
> 



_______________________________________________
xfs mailing list
xfs@oss.sgi.com
http://oss.sgi.com/mailman/listinfo/xfs

^ permalink raw reply	[flat|nested] 9+ messages in thread

end of thread, other threads:[~2010-10-01 13:57 UTC | newest]

Thread overview: 9+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2010-09-26  6:10 [PATCH VER 6] Extend project quotas to support 32bit project identifiers Arkadiusz Miśkiewicz
2010-09-26  6:10 ` [PATCH VER 6] xfsprogs: projid32bit handling Arkadiusz Miśkiewicz
2010-09-26  6:10   ` [PATCH VER 6] xfstests: Quota project id setting overflow Arkadiusz Miśkiewicz
2010-10-01 13:57     ` Alex Elder
2010-09-26  6:13   ` [PATCH VER 6] xfsprogs: projid32bit handling Arkadiusz Miskiewicz
2010-10-01 13:57     ` Alex Elder
2010-10-01 13:57   ` Alex Elder
2010-09-28  1:43 ` [PATCH VER 6] Extend project quotas to support 32bit project identifiers Christoph Hellwig
2010-10-01 13:57 ` Alex Elder

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.