[Devel] [PATCH RH8] ploop: Do not forget to update cached md0 page copy
Kirill Tkhai
ktkhai at virtuozzo.com
Wed May 5 19:41:02 MSK 2021
We mustn't have obsolete data in cached pages.
In this BUG this resulted in that next update
of page 0 metadata overwrites header on disk
with old value.
https://jira.sw.ru/browse/PSBM-129136
Signed-off-by: Kirill Tkhai <ktkhai at virtuozzo.com>
---
drivers/md/dm-ploop-cmd.c | 27 +++++++++++++++++++--------
drivers/md/dm-ploop.h | 1 +
2 files changed, 20 insertions(+), 8 deletions(-)
diff --git a/drivers/md/dm-ploop-cmd.c b/drivers/md/dm-ploop-cmd.c
index 0b8ef1382717..f259ff5d7652 100644
--- a/drivers/md/dm-ploop-cmd.c
+++ b/drivers/md/dm-ploop-cmd.c
@@ -313,6 +313,8 @@ static int ploop_grow_update_header(struct ploop *ploop,
{
unsigned int size, first_block_off, cluster_log = ploop->cluster_log;
struct ploop_pvd_header *hdr;
+ u32 nr_be, offset;
+ u64 sectors;
int ret;
/* hdr is in the same page as bat_entries[0] index */
@@ -327,13 +329,21 @@ static int ploop_grow_update_header(struct ploop *ploop,
hdr = kmap_atomic(piwb->bat_page);
/* TODO: head and cylinders */
- hdr->m_Size = cpu_to_le32(cmd->resize.nr_bat_entries);
- hdr->m_SizeInSectors_v2 = cpu_to_le64(cmd->resize.new_size);
- hdr->m_FirstBlockOffset = cpu_to_le32(first_block_off);
+ nr_be = hdr->m_Size = cpu_to_le32(cmd->resize.nr_bat_entries);
+ sectors = hdr->m_SizeInSectors_v2 = cpu_to_le64(cmd->resize.new_size);
+ offset = hdr->m_FirstBlockOffset = cpu_to_le32(first_block_off);
kunmap_atomic(hdr);
ploop_submit_index_wb_sync(ploop, piwb);
ret = blk_status_to_errno(piwb->bi_status);
+ if (!ret) {
+ /* Now update our cached page */
+ hdr = kmap_atomic(cmd->resize.md0->page);
+ hdr->m_Size = nr_be;
+ hdr->m_SizeInSectors_v2 = sectors;
+ hdr->m_FirstBlockOffset = offset;
+ kunmap_atomic(hdr);
+ }
ploop_reset_bat_update(piwb);
return ret;
@@ -463,7 +473,7 @@ static int ploop_resize(struct ploop *ploop, u64 new_size)
unsigned int hb_nr, size, cluster_log = ploop->cluster_log;
struct ploop_cmd cmd = { .resize.md_pages_root = RB_ROOT };
struct ploop_pvd_header *hdr;
- struct md_page *md;
+ struct md_page *md0;
int ret = -ENOMEM;
u64 old_size;
@@ -472,12 +482,12 @@ static int ploop_resize(struct ploop *ploop, u64 new_size)
if (ploop_is_ro(ploop))
return -EROFS;
- md = md_page_find(ploop, 0);
- if (WARN_ON(!md))
+ md0 = md_page_find(ploop, 0);
+ if (WARN_ON(!md0))
return -EIO;
- hdr = kmap(md->page);
+ hdr = kmap(md0->page);
old_size = le64_to_cpu(hdr->m_SizeInSectors_v2);
- kunmap(md->page);
+ kunmap(md0->page);
if (old_size == new_size)
return 0;
@@ -528,6 +538,7 @@ static int ploop_resize(struct ploop *ploop, u64 new_size)
cmd.resize.nr_bat_entries = nr_bat_entries;
cmd.resize.hb_nr = hb_nr;
cmd.resize.new_size = new_size;
+ cmd.resize.md0 = md0;
cmd.retval = 0;
cmd.type = PLOOP_CMD_RESIZE;
cmd.ploop = ploop;
diff --git a/drivers/md/dm-ploop.h b/drivers/md/dm-ploop.h
index e2af133c45a2..466f1506741e 100644
--- a/drivers/md/dm-ploop.h
+++ b/drivers/md/dm-ploop.h
@@ -57,6 +57,7 @@ struct ploop_cmd {
u64 new_size;
/* Preallocated data */
struct rb_root md_pages_root;
+ struct md_page *md0;
void *holes_bitmap;
#define PLOOP_GROW_STAGE_INITIAL 0
unsigned int stage;
More information about the Devel
mailing list