1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18#include "xfs.h"
19#include "xfs_fs.h"
20#include "xfs_format.h"
21#include "xfs_log_format.h"
22#include "xfs_trans_resv.h"
23#include "xfs_quota.h"
24#include "xfs_mount.h"
25#include "xfs_inode.h"
26#include "xfs_error.h"
27#include "xfs_trans.h"
28#include "xfs_qm.h"
29
30
31STATIC void
32xfs_fill_statvfs_from_dquot(
33 struct kstatfs *statp,
34 struct xfs_dquot *dqp)
35{
36 __uint64_t limit;
37
38 limit = dqp->q_core.d_blk_softlimit ?
39 be64_to_cpu(dqp->q_core.d_blk_softlimit) :
40 be64_to_cpu(dqp->q_core.d_blk_hardlimit);
41 if (limit && statp->f_blocks > limit) {
42 statp->f_blocks = limit;
43 statp->f_bfree = statp->f_bavail =
44 (statp->f_blocks > dqp->q_res_bcount) ?
45 (statp->f_blocks - dqp->q_res_bcount) : 0;
46 }
47
48 limit = dqp->q_core.d_ino_softlimit ?
49 be64_to_cpu(dqp->q_core.d_ino_softlimit) :
50 be64_to_cpu(dqp->q_core.d_ino_hardlimit);
51 if (limit && statp->f_files > limit) {
52 statp->f_files = limit;
53 statp->f_ffree =
54 (statp->f_files > dqp->q_res_icount) ?
55 (statp->f_ffree - dqp->q_res_icount) : 0;
56 }
57}
58
59
60
61
62
63
64
65
66
67void
68xfs_qm_statvfs(
69 xfs_inode_t *ip,
70 struct kstatfs *statp)
71{
72 xfs_mount_t *mp = ip->i_mount;
73 xfs_dquot_t *dqp;
74
75 if (!xfs_qm_dqget(mp, NULL, xfs_get_projid(ip), XFS_DQ_PROJ, 0, &dqp)) {
76 xfs_fill_statvfs_from_dquot(statp, dqp);
77 xfs_qm_dqput(dqp);
78 }
79}
80
81int
82xfs_qm_newmount(
83 xfs_mount_t *mp,
84 uint *needquotamount,
85 uint *quotaflags)
86{
87 uint quotaondisk;
88 uint uquotaondisk = 0, gquotaondisk = 0, pquotaondisk = 0;
89
90 quotaondisk = xfs_sb_version_hasquota(&mp->m_sb) &&
91 (mp->m_sb.sb_qflags & XFS_ALL_QUOTA_ACCT);
92
93 if (quotaondisk) {
94 uquotaondisk = mp->m_sb.sb_qflags & XFS_UQUOTA_ACCT;
95 pquotaondisk = mp->m_sb.sb_qflags & XFS_PQUOTA_ACCT;
96 gquotaondisk = mp->m_sb.sb_qflags & XFS_GQUOTA_ACCT;
97 }
98
99
100
101
102
103
104
105
106 if (((uquotaondisk && !XFS_IS_UQUOTA_ON(mp)) ||
107 (!uquotaondisk && XFS_IS_UQUOTA_ON(mp)) ||
108 (gquotaondisk && !XFS_IS_GQUOTA_ON(mp)) ||
109 (!gquotaondisk && XFS_IS_GQUOTA_ON(mp)) ||
110 (pquotaondisk && !XFS_IS_PQUOTA_ON(mp)) ||
111 (!pquotaondisk && XFS_IS_PQUOTA_ON(mp))) &&
112 xfs_dev_is_read_only(mp, "changing quota state")) {
113 xfs_warn(mp, "please mount with%s%s%s%s.",
114 (!quotaondisk ? "out quota" : ""),
115 (uquotaondisk ? " usrquota" : ""),
116 (gquotaondisk ? " grpquota" : ""),
117 (pquotaondisk ? " prjquota" : ""));
118 return -EPERM;
119 }
120
121 if (XFS_IS_QUOTA_ON(mp) || quotaondisk) {
122
123
124
125
126 if (quotaondisk && !XFS_QM_NEED_QUOTACHECK(mp)) {
127
128
129
130
131
132
133 xfs_qm_mount_quotas(mp);
134 } else {
135
136
137
138
139
140
141
142 *needquotamount = true;
143 *quotaflags = mp->m_qflags;
144 mp->m_qflags = 0;
145 }
146 }
147
148 return 0;
149}
150