summaryrefslogtreecommitdiff
path: root/fs/xfs
diff options
context:
space:
mode:
authorDarrick J. Wong <djwong@kernel.org>2021-09-01 11:11:00 -0700
committerDarrick J. Wong <djwong@kernel.org>2021-12-15 17:29:06 -0800
commit3bb48abd08490f924bea58c49dd8327a5e2b5325 (patch)
tree0959a9316d9596f4339cad76c190f815350568e8 /fs/xfs
parentcaf2bf9198a6e1fc6a9fd628a090759543d18283 (diff)
xfs: convert all users to xfs_imeta_log
Convert all open-coded sb metadata inode pointer logging to use xfs_imeta_log. Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Diffstat (limited to 'fs/xfs')
-rw-r--r--fs/xfs/xfs_qm.c71
1 files changed, 43 insertions, 28 deletions
diff --git a/fs/xfs/xfs_qm.c b/fs/xfs/xfs_qm.c
index 91fe235a3135..cf371199f366 100644
--- a/fs/xfs/xfs_qm.c
+++ b/fs/xfs/xfs_qm.c
@@ -26,6 +26,7 @@
#include "xfs_ag.h"
#include "xfs_ialloc.h"
#include "xfs_health.h"
+#include "xfs_imeta.h"
/*
* The global quota manager. There is only one of these for the entire
@@ -731,6 +732,18 @@ xfs_qm_destroy_quotainfo(
mp->m_quotainfo = NULL;
}
+static inline const struct xfs_imeta_path *
+xfs_qflags_to_imeta(
+ unsigned int qflags)
+{
+ if (qflags & XFS_QMOPT_UQUOTA)
+ return &XFS_IMETA_USRQUOTA;
+ else if (qflags & XFS_QMOPT_GQUOTA)
+ return &XFS_IMETA_GRPQUOTA;
+ else
+ return &XFS_IMETA_PRJQUOTA;
+}
+
/*
* Switch the group and project quota in-core inode pointers if needed.
*
@@ -738,6 +751,12 @@ xfs_qm_destroy_quotainfo(
* between gquota and pquota. If the on-disk superblock has GQUOTA and the
* filesystem is now mounted with PQUOTA, just use sb_gquotino for sb_pquotino
* and vice-versa.
+ *
+ * We tolerate the direct manipulation of the in-core sb quota inode pointers
+ * here because calling xfs_imeta_log is only really required for filesystems
+ * with the metadata directory feature. That feature requires a v5 superblock,
+ * which always supports simultaneous group and project quotas, so we'll never
+ * get here.
*/
STATIC int
xfs_qm_qino_switch(
@@ -776,8 +795,13 @@ xfs_qm_qino_switch(
if (error)
return error;
- mp->m_sb.sb_gquotino = NULLFSINO;
- mp->m_sb.sb_pquotino = NULLFSINO;
+ if (flags & XFS_QMOPT_PQUOTA) {
+ mp->m_sb.sb_gquotino = NULLFSINO;
+ mp->m_sb.sb_pquotino = ino;
+ } else if (flags & XFS_QMOPT_GQUOTA) {
+ mp->m_sb.sb_gquotino = ino;
+ mp->m_sb.sb_pquotino = NULLFSINO;
+ }
*need_alloc = false;
return 0;
}
@@ -792,7 +816,9 @@ xfs_qm_qino_alloc(
struct xfs_inode **ipp,
unsigned int flags)
{
+ struct xfs_imeta_end ic;
struct xfs_trans *tp;
+ const struct xfs_imeta_path *path = xfs_qflags_to_imeta(flags);
int error;
bool need_alloc = true;
@@ -802,29 +828,12 @@ xfs_qm_qino_alloc(
if (error)
return error;
- error = xfs_trans_alloc(mp, &M_RES(mp)->tr_create,
- need_alloc ? XFS_QM_QINOCREATE_SPACE_RES(mp) : 0,
+ error = xfs_trans_alloc(mp, &M_RES(mp)->tr_imeta_create,
+ need_alloc ? xfs_imeta_create_space_res(mp) : 0,
0, 0, &tp);
if (error)
return error;
- if (need_alloc) {
- struct xfs_icreate_args args = {
- .nlink = 1,
- };
- xfs_ino_t ino;
-
- xfs_icreate_args_rootfile(&args, S_IFREG);
-
- error = xfs_dialloc(&tp, 0, S_IFREG, &ino);
- if (!error)
- error = xfs_icreate(tp, ino, &args, ipp);
- if (error) {
- xfs_trans_cancel(tp);
- return error;
- }
- }
-
/*
* Make the changes in the superblock, and log those too.
* sbfields arg may contain fields other than *QUOTINO;
@@ -842,22 +851,28 @@ xfs_qm_qino_alloc(
/* qflags will get updated fully _after_ quotacheck */
mp->m_sb.sb_qflags = mp->m_qflags & XFS_ALL_QUOTA_ACCT;
}
- if (flags & XFS_QMOPT_UQUOTA)
- mp->m_sb.sb_uquotino = (*ipp)->i_ino;
- else if (flags & XFS_QMOPT_GQUOTA)
- mp->m_sb.sb_gquotino = (*ipp)->i_ino;
- else
- mp->m_sb.sb_pquotino = (*ipp)->i_ino;
spin_unlock(&mp->m_sb_lock);
xfs_log_sb(tp);
+ if (need_alloc) {
+ error = xfs_imeta_create(&tp, path, S_IFREG,
+ XFS_IMETA_CREATE_NOQUOTA, ipp, &ic);
+ if (error) {
+ xfs_trans_cancel(tp);
+ xfs_imeta_end_update(mp, &ic, error);
+ return error;
+ }
+ }
+
error = xfs_trans_commit(tp);
if (error) {
ASSERT(xfs_is_shutdown(mp));
xfs_alert(mp, "%s failed (error %d)!", __func__, error);
}
- if (need_alloc)
+ if (need_alloc) {
+ xfs_imeta_end_update(mp, &ic, error);
xfs_finish_inode_setup(*ipp);
+ }
return error;
}