From: "Darrick J. Wong" <darrick.wong@oracle.com>
To: darrick.wong@oracle.com
Cc: linux-xfs@vger.kernel.org
Subject: [PATCH 13/21] xfs: wire up rmap map and unmap to the realtime rmapbt
Date: Tue, 31 Dec 2019 17:17:41 -0800 [thread overview]
Message-ID: <157784146157.1368137.15012539914173796507.stgit@magnolia> (raw)
In-Reply-To: <157784137939.1368137.1149711841610071256.stgit@magnolia>
From: Darrick J. Wong <darrick.wong@oracle.com>
Connect the map and unmap reverse-mapping operations to the realtime
rmapbt via the deferred operation callbacks. This enables us to
perform rmap operations against the correct btree.
Signed-off-by: Darrick J. Wong <darrick.wong@oracle.com>
---
fs/xfs/libxfs/xfs_rmap.c | 62 ++++++++++++++++++++++++++++++----------------
fs/xfs/libxfs/xfs_rmap.h | 2 +
fs/xfs/xfs_log_recover.c | 6 ++--
fs/xfs/xfs_rmap_item.c | 13 ++++++++--
fs/xfs/xfs_rmap_item.h | 2 +
5 files changed, 56 insertions(+), 29 deletions(-)
diff --git a/fs/xfs/libxfs/xfs_rmap.c b/fs/xfs/libxfs/xfs_rmap.c
index 3e625ba057e6..2bb1d0cea443 100644
--- a/fs/xfs/libxfs/xfs_rmap.c
+++ b/fs/xfs/libxfs/xfs_rmap.c
@@ -22,6 +22,7 @@
#include "xfs_error.h"
#include "xfs_inode.h"
#include "xfs_health.h"
+#include "xfs_rtrmap_btree.h"
/* By convention, the rtrmapbt's "AG" number is NULLAGNUMBER. */
static xfs_agnumber_t
@@ -2459,13 +2460,14 @@ xfs_rmap_finish_one_cleanup(
struct xfs_btree_cur *rcur,
int error)
{
- struct xfs_buf *agbp;
+ struct xfs_buf *agbp = NULL;
if (rcur == NULL)
return;
- agbp = rcur->bc_private.a.agbp;
+ if (!(rcur->bc_flags & XFS_BTREE_LONG_PTRS))
+ agbp = rcur->bc_private.a.agbp;
xfs_btree_del_cursor(rcur, error);
- if (error)
+ if (error && agbp)
xfs_trans_brelse(tp, agbp);
}
@@ -2486,20 +2488,21 @@ xfs_rmap_finish_one(
xfs_fsblock_t startblock,
xfs_filblks_t blockcount,
xfs_exntst_t state,
+ bool realtime,
struct xfs_btree_cur **pcur)
{
struct xfs_mount *mp = tp->t_mountp;
struct xfs_btree_cur *rcur;
struct xfs_buf *agbp = NULL;
+ int lockmode;
int error = 0;
xfs_agnumber_t agno;
struct xfs_owner_info oinfo;
xfs_fsblock_t bno;
bool unwritten;
- agno = XFS_FSB_TO_AGNO(mp, startblock);
- ASSERT(agno != NULLAGNUMBER);
- bno = XFS_FSB_TO_AGBNO(mp, startblock);
+ agno = realtime ? NULLAGNUMBER : XFS_FSB_TO_AGNO(mp, startblock);
+ bno = realtime ? startblock : XFS_FSB_TO_AGBNO(mp, startblock);
trace_xfs_rmap_deferred(mp, agno, type, bno, owner, whichfork,
startoff, blockcount, state);
@@ -2518,31 +2521,44 @@ xfs_rmap_finish_one(
*pcur = NULL;
}
if (rcur == NULL) {
- /*
- * Refresh the freelist before we start changing the
- * rmapbt, because a shape change could cause us to
- * allocate blocks.
- */
- error = xfs_free_extent_fix_freelist(tp, agno, &agbp);
- if (error)
- return error;
- if (XFS_IS_CORRUPT(tp->t_mountp, !agbp))
- return -EFSCORRUPTED;
-
- rcur = xfs_rmapbt_init_cursor(mp, tp, agbp, agno);
- if (!rcur) {
- error = -ENOMEM;
- goto out_cur;
+ if (realtime) {
+ lockmode = XFS_ILOCK_EXCL | XFS_ILOCK_RTBITMAP;
+ xfs_ilock(mp->m_rrmapip, lockmode);
+ xfs_trans_ijoin(tp, mp->m_rrmapip, lockmode);
+ rcur = xfs_rtrmapbt_init_cursor(mp, tp, mp->m_rrmapip);
+ if (!rcur) {
+ error = -ENOMEM;
+ goto out_cur;
+ }
+ rcur->bc_private.b.flags = 0;
+ } else {
+ /*
+ * Refresh the freelist before we start changing the
+ * rmapbt, because a shape change could cause us to
+ * allocate blocks.
+ */
+ error = xfs_free_extent_fix_freelist(tp, agno, &agbp);
+ if (error)
+ return error;
+ if (XFS_IS_CORRUPT(tp->t_mountp, !agbp))
+ return -EFSCORRUPTED;
+
+ rcur = xfs_rmapbt_init_cursor(mp, tp, agbp, agno);
+ if (!rcur) {
+ error = -ENOMEM;
+ goto out_cur;
+ }
}
}
*pcur = rcur;
xfs_rmap_ino_owner(&oinfo, owner, whichfork, startoff);
unwritten = state == XFS_EXT_UNWRITTEN;
- bno = XFS_FSB_TO_AGBNO(rcur->bc_mp, startblock);
switch (type) {
case XFS_RMAP_ALLOC:
+ ASSERT(!realtime);
+ /* fall through */
case XFS_RMAP_MAP:
error = xfs_rmap_map(rcur, bno, blockcount, unwritten, &oinfo);
break;
@@ -2551,6 +2567,8 @@ xfs_rmap_finish_one(
&oinfo);
break;
case XFS_RMAP_FREE:
+ ASSERT(!realtime);
+ /* fall through */
case XFS_RMAP_UNMAP:
error = xfs_rmap_unmap(rcur, bno, blockcount, unwritten,
&oinfo);
diff --git a/fs/xfs/libxfs/xfs_rmap.h b/fs/xfs/libxfs/xfs_rmap.h
index 2d4badc4a531..958f9e27dba7 100644
--- a/fs/xfs/libxfs/xfs_rmap.h
+++ b/fs/xfs/libxfs/xfs_rmap.h
@@ -180,7 +180,7 @@ void xfs_rmap_finish_one_cleanup(struct xfs_trans *tp,
int xfs_rmap_finish_one(struct xfs_trans *tp, enum xfs_rmap_intent_type type,
uint64_t owner, int whichfork, xfs_fileoff_t startoff,
xfs_fsblock_t startblock, xfs_filblks_t blockcount,
- xfs_exntst_t state, struct xfs_btree_cur **pcur);
+ xfs_exntst_t state, bool realtime, struct xfs_btree_cur **pcur);
int xfs_rmap_find_left_neighbor(struct xfs_btree_cur *cur, xfs_fsblock_t bno,
uint64_t owner, uint64_t offset, unsigned int flags,
diff --git a/fs/xfs/xfs_log_recover.c b/fs/xfs/xfs_log_recover.c
index e966a7e569be..bca5b1bfae91 100644
--- a/fs/xfs/xfs_log_recover.c
+++ b/fs/xfs/xfs_log_recover.c
@@ -4617,7 +4617,7 @@ xlog_recover_cancel_efi(
/* Recover the RUI if necessary. */
STATIC int
xlog_recover_process_rui(
- struct xfs_mount *mp,
+ struct xfs_trans *parent_tp,
struct xfs_ail *ailp,
struct xfs_log_item *lip)
{
@@ -4632,7 +4632,7 @@ xlog_recover_process_rui(
return 0;
spin_unlock(&ailp->ail_lock);
- error = xfs_rui_recover(mp, ruip);
+ error = xfs_rui_recover(parent_tp, ruip);
spin_lock(&ailp->ail_lock);
return error;
@@ -4861,7 +4861,7 @@ xlog_recover_process_intents(
error = xlog_recover_process_efi(log->l_mp, ailp, lip);
break;
case XFS_LI_RUI:
- error = xlog_recover_process_rui(log->l_mp, ailp, lip);
+ error = xlog_recover_process_rui(parent_tp, ailp, lip);
break;
case XFS_LI_CUI:
error = xlog_recover_process_cui(parent_tp, ailp, lip);
diff --git a/fs/xfs/xfs_rmap_item.c b/fs/xfs/xfs_rmap_item.c
index c7a55011972f..4080b86b8615 100644
--- a/fs/xfs/xfs_rmap_item.c
+++ b/fs/xfs/xfs_rmap_item.c
@@ -324,7 +324,7 @@ xfs_trans_log_finish_rmap_update(
int error;
error = xfs_rmap_finish_one(tp, type, owner, whichfork, startoff,
- startblock, blockcount, state, pcur);
+ startblock, blockcount, state, rt, pcur);
/*
* Mark the transaction dirty, even on error. This ensures the
@@ -494,7 +494,7 @@ const struct xfs_defer_op_type xfs_rmap_update_defer_type = {
*/
int
xfs_rui_recover(
- struct xfs_mount *mp,
+ struct xfs_trans *parent_tp,
struct xfs_rui_log_item *ruip)
{
int i;
@@ -508,6 +508,7 @@ xfs_rui_recover(
xfs_exntst_t state;
struct xfs_trans *tp;
struct xfs_btree_cur *rcur = NULL;
+ struct xfs_mount *mp = parent_tp->t_mountp;
bool rt;
ASSERT(!test_bit(XFS_RUI_RECOVERED, &ruip->rui_flags));
@@ -555,6 +556,12 @@ xfs_rui_recover(
mp->m_rmap_maxlevels, 0, XFS_TRANS_RESERVE, &tp);
if (error)
return error;
+ /*
+ * Recovery stashes all deferred ops during intent processing and
+ * finishes them on completion. Transfer current dfops state to this
+ * transaction and transfer the result back before we return.
+ */
+ xfs_defer_move(tp, parent_tp);
rudp = xfs_trans_get_rud(tp, ruip);
for (i = 0; i < ruip->rui_format.rui_nextents; i++) {
@@ -605,10 +612,12 @@ xfs_rui_recover(
xfs_rmap_finish_one_cleanup(tp, rcur, error);
set_bit(XFS_RUI_RECOVERED, &ruip->rui_flags);
+ xfs_defer_move(parent_tp, tp);
error = xfs_trans_commit(tp);
return error;
abort_error:
+ xfs_defer_move(parent_tp, tp);
xfs_rmap_finish_one_cleanup(tp, rcur, error);
xfs_trans_cancel(tp);
return error;
diff --git a/fs/xfs/xfs_rmap_item.h b/fs/xfs/xfs_rmap_item.h
index 8708e4a5aa5c..2ed916a860fd 100644
--- a/fs/xfs/xfs_rmap_item.h
+++ b/fs/xfs/xfs_rmap_item.h
@@ -82,6 +82,6 @@ int xfs_rui_copy_format(struct xfs_log_iovec *buf,
struct xfs_rui_log_format *dst_rui_fmt);
void xfs_rui_item_free(struct xfs_rui_log_item *);
void xfs_rui_release(struct xfs_rui_log_item *);
-int xfs_rui_recover(struct xfs_mount *mp, struct xfs_rui_log_item *ruip);
+int xfs_rui_recover(struct xfs_trans *parent_tp, struct xfs_rui_log_item *ruip);
#endif /* __XFS_RMAP_ITEM_H__ */
next prev parent reply other threads:[~2020-01-01 1:17 UTC|newest]
Thread overview: 22+ messages / expand[flat|nested] mbox.gz Atom feed top
2020-01-01 1:16 [PATCH v11 00/21] xfs: realtime reverse-mapping support Darrick J. Wong
2020-01-01 1:16 ` [PATCH 01/21] xfs: make iroot_realloc a btree function Darrick J. Wong
2020-01-01 1:16 ` [PATCH 02/21] xfs: support storing records in the inode core root Darrick J. Wong
2020-01-01 1:16 ` [PATCH 03/21] xfs: widen xfs_rmap_irec fields to handle realtime rmapbt Darrick J. Wong
2020-01-01 1:16 ` [PATCH 04/21] xfs: introduce realtime rmap btree definitions Darrick J. Wong
2020-01-01 1:16 ` [PATCH 05/21] xfs: define the on-disk realtime rmap btree format Darrick J. Wong
2020-01-01 1:16 ` [PATCH 06/21] xfs: realtime rmap btree transaction reservations Darrick J. Wong
2020-01-01 1:17 ` [PATCH 07/21] xfs: add realtime rmap btree operations Darrick J. Wong
2020-01-01 1:17 ` [PATCH 08/21] xfs: prepare rmap functions to deal with rtrmapbt Darrick J. Wong
2020-01-01 1:17 ` [PATCH 09/21] xfs: add a realtime flag to the rmap update log redo items Darrick J. Wong
2020-01-01 1:17 ` [PATCH 10/21] xfs: add realtime rmap btree block detection to log recovery Darrick J. Wong
2020-01-01 1:17 ` [PATCH 11/21] xfs: add realtime reverse map inode to superblock Darrick J. Wong
2020-01-01 1:17 ` [PATCH 12/21] xfs: wire up a new inode fork type for the realtime rmap Darrick J. Wong
2020-01-01 1:17 ` Darrick J. Wong [this message]
2020-01-01 1:17 ` [PATCH 14/21] xfs: create routine to allocate and initialize a realtime rmap btree inode Darrick J. Wong
2020-01-01 1:17 ` [PATCH 15/21] xfs: dynamically create the realtime rmapbt inode when attaching rtdev Darrick J. Wong
2020-01-01 1:17 ` [PATCH 16/21] xfs: enable realtime rmap btree Darrick J. Wong
2020-01-01 1:18 ` [PATCH 17/21] xfs: wire up getfsmap to the realtime reverse mapping btree Darrick J. Wong
2020-01-01 1:18 ` [PATCH 18/21] xfs: scrub the realtime rmapbt Darrick J. Wong
2020-01-01 1:18 ` [PATCH 19/21] xfs: cross-reference realtime bitmap to realtime rmapbt scrubber Darrick J. Wong
2020-01-01 1:18 ` [PATCH 20/21] xfs: cross-reference the realtime rmapbt Darrick J. Wong
2020-01-01 1:18 ` [PATCH 21/21] xfs: report realtime rmap btree corruption errors to the health system Darrick J. Wong
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=157784146157.1368137.15012539914173796507.stgit@magnolia \
--to=darrick.wong@oracle.com \
--cc=linux-xfs@vger.kernel.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).