From: "Darrick J. Wong" <darrick.wong@oracle.com>
To: darrick.wong@oracle.com
Cc: linux-xfs@vger.kernel.org
Subject: [PATCH 3/3] xfs: log EFIs for all btree blocks being used to stage a btree
Date: Wed, 09 Oct 2019 09:50:06 -0700 [thread overview]
Message-ID: <157063980635.2914891.10711621853635545427.stgit@magnolia> (raw)
In-Reply-To: <157063978750.2914891.14339604572380248276.stgit@magnolia>
From: Darrick J. Wong <darrick.wong@oracle.com>
We need to log EFIs for every extent that we allocate for the purpose of
staging a new btree so that if we fail then the blocks will be freed
during log recovery.
Signed-off-by: Darrick J. Wong <darrick.wong@oracle.com>
---
fs/xfs/scrub/repair.c | 37 +++++++++++++++++++++++++++++++++++--
fs/xfs/scrub/repair.h | 4 +++-
fs/xfs/xfs_extfree_item.c | 2 --
3 files changed, 38 insertions(+), 5 deletions(-)
diff --git a/fs/xfs/scrub/repair.c b/fs/xfs/scrub/repair.c
index beebd484c5f3..49cea124148b 100644
--- a/fs/xfs/scrub/repair.c
+++ b/fs/xfs/scrub/repair.c
@@ -25,6 +25,8 @@
#include "xfs_ag_resv.h"
#include "xfs_quota.h"
#include "xfs_bmap.h"
+#include "xfs_defer.h"
+#include "xfs_extfree_item.h"
#include "scrub/scrub.h"
#include "scrub/common.h"
#include "scrub/trace.h"
@@ -412,7 +414,8 @@ int
xrep_newbt_add_reservation(
struct xrep_newbt *xnr,
xfs_fsblock_t fsbno,
- xfs_extlen_t len)
+ xfs_extlen_t len,
+ void *priv)
{
struct xrep_newbt_resv *resv;
@@ -424,6 +427,7 @@ xrep_newbt_add_reservation(
resv->fsbno = fsbno;
resv->len = len;
resv->used = 0;
+ resv->priv = priv;
list_add_tail(&resv->list, &xnr->reservations);
return 0;
}
@@ -434,6 +438,7 @@ xrep_newbt_reserve_space(
struct xrep_newbt *xnr,
uint64_t nr_blocks)
{
+ const struct xfs_defer_op_type *efi_type = &xfs_extent_free_defer_type;
struct xfs_scrub *sc = xnr->sc;
xfs_alloctype_t type;
xfs_fsblock_t alloc_hint = xnr->alloc_hint;
@@ -442,6 +447,7 @@ xrep_newbt_reserve_space(
type = sc->ip ? XFS_ALLOCTYPE_START_BNO : XFS_ALLOCTYPE_NEAR_BNO;
while (nr_blocks > 0 && !error) {
+ struct xfs_extent_free_item efi_item;
struct xfs_alloc_arg args = {
.tp = sc->tp,
.mp = sc->mp,
@@ -453,6 +459,7 @@ xrep_newbt_reserve_space(
.prod = nr_blocks,
.resv = xnr->resv,
};
+ void *efi;
error = xfs_alloc_vextent(&args);
if (error)
@@ -465,7 +472,20 @@ xrep_newbt_reserve_space(
XFS_FSB_TO_AGBNO(sc->mp, args.fsbno),
args.len, xnr->oinfo.oi_owner);
- error = xrep_newbt_add_reservation(xnr, args.fsbno, args.len);
+ /*
+ * Log a deferred free item for each extent we allocate so that
+ * we can get all of the space back if we crash before we can
+ * commit the new btree.
+ */
+ efi_item.xefi_startblock = args.fsbno;
+ efi_item.xefi_blockcount = args.len;
+ efi_item.xefi_oinfo = xnr->oinfo;
+ efi_item.xefi_skip_discard = true;
+ efi = efi_type->create_intent(sc->tp, 1);
+ efi_type->log_item(sc->tp, efi, &efi_item.xefi_list);
+
+ error = xrep_newbt_add_reservation(xnr, args.fsbno, args.len,
+ efi);
if (error)
break;
@@ -487,6 +507,7 @@ xrep_newbt_destroy(
struct xrep_newbt *xnr,
int error)
{
+ const struct xfs_defer_op_type *efi_type = &xfs_extent_free_defer_type;
struct xfs_scrub *sc = xnr->sc;
struct xrep_newbt_resv *resv, *n;
@@ -494,6 +515,17 @@ xrep_newbt_destroy(
goto junkit;
list_for_each_entry_safe(resv, n, &xnr->reservations, list) {
+ struct xfs_efd_log_item *efd;
+
+ /*
+ * Log a deferred free done for each extent we allocated now
+ * that we've linked the block into the filesystem. We cheat
+ * since we know that log recovery has never looked at the
+ * extents attached to an EFD.
+ */
+ efd = efi_type->create_done(sc->tp, resv->priv, 0);
+ set_bit(XFS_LI_DIRTY, &efd->efd_item.li_flags);
+
/* Free every block we didn't use. */
resv->fsbno += resv->used;
resv->len -= resv->used;
@@ -515,6 +547,7 @@ xrep_newbt_destroy(
junkit:
list_for_each_entry_safe(resv, n, &xnr->reservations, list) {
+ efi_type->abort_intent(resv->priv);
list_del(&resv->list);
kmem_free(resv);
}
diff --git a/fs/xfs/scrub/repair.h b/fs/xfs/scrub/repair.h
index ab6c1199ecc0..cb86281de28b 100644
--- a/fs/xfs/scrub/repair.h
+++ b/fs/xfs/scrub/repair.h
@@ -67,6 +67,8 @@ struct xrep_newbt_resv {
/* Link to list of extents that we've reserved. */
struct list_head list;
+ void *priv;
+
/* FSB of the block we reserved. */
xfs_fsblock_t fsbno;
@@ -112,7 +114,7 @@ void xrep_newbt_init_ag(struct xrep_newbt *xba, struct xfs_scrub *sc,
void xrep_newbt_init_inode(struct xrep_newbt *xba, struct xfs_scrub *sc,
int whichfork, const struct xfs_owner_info *oinfo);
int xrep_newbt_add_reservation(struct xrep_newbt *xba, xfs_fsblock_t fsbno,
- xfs_extlen_t len);
+ xfs_extlen_t len, void *priv);
int xrep_newbt_reserve_space(struct xrep_newbt *xba, uint64_t nr_blocks);
void xrep_newbt_destroy(struct xrep_newbt *xba, int error);
int xrep_newbt_alloc_block(struct xfs_btree_cur *cur, struct xrep_newbt *xba,
diff --git a/fs/xfs/xfs_extfree_item.c b/fs/xfs/xfs_extfree_item.c
index e44efc41a041..1e49936afbfb 100644
--- a/fs/xfs/xfs_extfree_item.c
+++ b/fs/xfs/xfs_extfree_item.c
@@ -328,8 +328,6 @@ xfs_trans_get_efd(
{
struct xfs_efd_log_item *efdp;
- ASSERT(nextents > 0);
-
if (nextents > XFS_EFD_MAX_FAST_EXTENTS) {
efdp = kmem_zalloc(sizeof(struct xfs_efd_log_item) +
(nextents - 1) * sizeof(struct xfs_extent),
next prev parent reply other threads:[~2019-10-09 16:50 UTC|newest]
Thread overview: 16+ messages / expand[flat|nested] mbox.gz Atom feed top
2019-10-09 16:49 [PATCH 0/3] xfs: prepare repair for bulk loading Darrick J. Wong
2019-10-09 16:49 ` [PATCH 1/3] xfs: add debug knobs to control btree bulk load slack factors Darrick J. Wong
2019-10-25 14:19 ` Brian Foster
2019-10-25 16:39 ` Darrick J. Wong
2019-10-09 16:49 ` [PATCH 2/3] xfs: implement block reservation accounting for btrees we're staging Darrick J. Wong
2019-10-25 14:22 ` Brian Foster
2019-10-25 16:35 ` Darrick J. Wong
2019-10-25 17:35 ` Brian Foster
2019-10-25 20:52 ` Darrick J. Wong
2020-02-27 15:51 ` Darrick J. Wong
2019-10-09 16:50 ` Darrick J. Wong [this message]
2019-10-25 14:24 ` [PATCH 3/3] xfs: log EFIs for all btree blocks being used to stage a btree Brian Foster
2019-10-25 16:22 ` Darrick J. Wong
2019-10-25 17:36 ` Brian Foster
-- strict thread matches above, loose matches on Subject: below --
2019-10-29 23:31 [PATCH v2 0/3] xfs: prepare repair for bulk loading Darrick J. Wong
2019-10-29 23:31 ` [PATCH 3/3] xfs: log EFIs for all btree blocks being used to stage a btree Darrick J. Wong
2020-01-01 1:02 [PATCH v2 0/3] xfs: prepare repair for bulk loading Darrick J. Wong
2020-01-01 1:02 ` [PATCH 3/3] xfs: log EFIs for all btree blocks being used to stage a btree 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=157063980635.2914891.10711621853635545427.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).