[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
trouble implementing default quotas
I'm implementing a default quota scheme on xfs and have something weird
going on that I don't understand. I am using a recent cvs snapshot and
linux 2.4.17.
I want to use root to store the default user and group quota and only
enforce the default quota if a user doesn't have an explicit quota set.
When I apply this patch, I lock up when a user, with or without a quota,
tries to write to the disk. When I copy some files to the filesystem with
my altered xfs, it appears to lock up returning from the xfs_create call in
xfs_vnodeops.c. It leaves this function via std_return with error 0, but
the console never returns a prompt.
Without my patch, all appears ok, so I know I'm doing something screwy. I
just don't know what.
Any help would be appreciated.
If this is a duplicate post, I'm sorry. I sent one Tuesday night and never
saw it hit the list, so I'm trying again.
Cary
diff -Nur linux.orig/fs/xfs/xfs_trans_dquot.c linux/fs/xfs/xfs_trans_dquot.c
--- linux.orig/fs/xfs/xfs_trans_dquot.c Thu Feb 7 13:02:57 2002
+++ linux/fs/xfs/xfs_trans_dquot.c Fri Feb 8 11:20:09 2002
@@ -573,6 +573,7 @@
xfs_trans_dqresv(
xfs_trans_t *tp,
xfs_dquot_t *dqp,
+ xfs_dquot_t *defaultqp,
long nblks,
long ninos,
uint flags)
@@ -588,14 +589,22 @@
}
ASSERT(XFS_DQ_IS_LOCKED(dqp));
if (flags & XFS_TRANS_DQ_RES_BLKS) {
- hardlimit = INT_GET(dqp->q_core.d_blk_hardlimit,
ARCH_CONVERT);
- softlimit = INT_GET(dqp->q_core.d_blk_softlimit,
ARCH_CONVERT);
+ if ((hardlimit = INT_GET(dqp->q_core.d_blk_hardlimit,
ARCH_CONVERT)) == 0) {
+ hardlimit =
INT_GET(defaultqp->q_core.d_blk_hardlimit, ARCH_CONVERT);
+ }
+ if ((softlimit = INT_GET(dqp->q_core.d_blk_softlimit,
ARCH_CONVERT)) == 0) {
+ softlimit =
INT_GET(defaultqp->q_core.d_blk_hardlimit, ARCH_CONVERT);
+ }
btimer = INT_GET(dqp->q_core.d_btimer, ARCH_CONVERT);
resbcountp = &dqp->q_res_bcount;
} else {
ASSERT(flags & XFS_TRANS_DQ_RES_RTBLKS);
- hardlimit = INT_GET(dqp->q_core.d_rtb_hardlimit,
ARCH_CONVERT);
- softlimit = INT_GET(dqp->q_core.d_rtb_softlimit,
ARCH_CONVERT);
+ if ((hardlimit = INT_GET(dqp->q_core.d_rtb_hardlimit,
ARCH_CONVERT)) == 0) {
+ hardlimit =
INT_GET(defaultqp->q_core.d_rtb_hardlimit, ARCH_CONVERT);
+ }
+ if ((softlimit = INT_GET(dqp->q_core.d_rtb_softlimit,
ARCH_CONVERT)) == 0) {
+ softlimit =
INT_GET(defaultqp->q_core.d_rtb_hardlimit, ARCH_CONVERT);
+ }
btimer = INT_GET(dqp->q_core.d_rtbtimer, ARCH_CONVERT);
resbcountp = &dqp->q_res_rtbcount;
}
@@ -711,6 +720,9 @@
* XFS_TRANS_DQ_RES_RTBLKS reserves realtime disk blocks
* dquots are unlocked on return, if they were not locked by caller.
*/
+
+
+
int
xfs_trans_reserve_quota_bydquots(
xfs_trans_t *tp,
@@ -721,6 +733,8 @@
uint flags)
{
int resvd;
+ int error;
+ xfs_dquot_t *defaultqp;
if (tp && tp->t_dqinfo == NULL)
xfs_trans_alloc_dqinfo(tp);
@@ -729,18 +743,20 @@
resvd = 0;
if (udqp) {
- if (xfs_trans_dqresv(tp, udqp, nblks, ninos, flags))
+ error = xfs_qm_dqget(udqp->q_mount, NULL, 0, XFS_DQ_USER, 0,
&defaultqp);
+ if (xfs_trans_dqresv(tp, udqp, defaultqp, nblks, ninos,
flags))
return (EDQUOT);
resvd = 1;
}
if (gdqp) {
- if (xfs_trans_dqresv(tp, gdqp, nblks, ninos, flags)) {
+ error = xfs_qm_dqget(udqp->q_mount, NULL, 0, XFS_DQ_GROUP,
0, &defaultqp);
+ if (xfs_trans_dqresv(tp, gdqp, defaultqp, nblks, ninos,
flags)) {
/*
* can't do it, so backout previous reservation
*/
if (resvd) {
- xfs_trans_dqresv(tp, udqp, -nblks, -ninos,
+ xfs_trans_dqresv(tp, udqp, defaultqp,
-nblks, -ninos,
flags);
}
return (EDQUOT);