[Devel] [PATCH RH9 7/7] dm/dm-ploop: add find_hole

Andrey Zhadchenko andrey.zhadchenko at virtuozzo.com
Mon Jul 24 10:09:43 MSK 2023


Just iterate over clusters one-by-one calling ploop_bat_entries(),
which will do all our work

https://jira.vzint.dev/browse/PSBM-145746
Signed-off-by: Andrey Zhadchenko <andrey.zhadchenko at virtuozzo.com>
---
 drivers/md/dm-ploop-map.c    | 50 ++++++++++++++++++++++++++++++++++++
 drivers/md/dm-ploop-target.c |  1 +
 drivers/md/dm-ploop.h        |  1 +
 3 files changed, 52 insertions(+)

diff --git a/drivers/md/dm-ploop-map.c b/drivers/md/dm-ploop-map.c
index b9c152f2a636..bd8e2f355203 100644
--- a/drivers/md/dm-ploop-map.c
+++ b/drivers/md/dm-ploop-map.c
@@ -1991,3 +1991,53 @@ int ploop_prepare_reloc_index_wb(struct ploop *ploop,
 	return err;
 }
 ALLOW_ERROR_INJECTION(ploop_prepare_reloc_index_wb, ERRNO);
+
+loff_t ploop_find_hole(struct dm_target *ti, loff_t offset, int whence)
+{
+	struct ploop *ploop = ti->private;
+	u32 clu, dst_clu;
+	loff_t result;
+
+	clu = SEC_TO_CLU(ploop, to_sector(offset) + ploop->skip_off);
+
+	while (clu < ploop->nr_bat_entries) {
+
+		/*
+		 * Assume a locked cluster to have a data.
+		 * In worst case someone will read zeroes
+		 */
+		if (ploop_postpone_if_cluster_locked(ploop, NULL, clu)) {
+			if (whence & SEEK_DATA)
+				break;
+			if (whence & SEEK_HOLE) {
+				clu++;
+				continue;
+			}
+		}
+
+		/*
+		 * It *may* be possible to speed this up by iterating over clusters
+		 * in mapped metadata page, but this is a bit problematic
+		 * since we want to check if cluster is locked
+		 */
+		dst_clu = ploop_bat_entries(ploop, clu, NULL, NULL);
+
+		if (whence & SEEK_DATA && dst_clu != BAT_ENTRY_NONE)
+			break;
+		if (whence & SEEK_HOLE && dst_clu == BAT_ENTRY_NONE)
+			break;
+
+		clu++;
+	}
+
+	result = to_bytes(CLU_TO_SEC(ploop, clu) - ploop->skip_off);
+	if (result < offset)
+		result = offset;
+
+	if (clu >= ploop->nr_bat_entries) {
+		if (whence & SEEK_DATA)
+			result = -ENXIO;
+	}
+
+	return result;
+}
diff --git a/drivers/md/dm-ploop-target.c b/drivers/md/dm-ploop-target.c
index 7d9bd56712cc..a05ad5cb3689 100644
--- a/drivers/md/dm-ploop-target.c
+++ b/drivers/md/dm-ploop-target.c
@@ -619,6 +619,7 @@ static struct target_type ploop_target = {
 	.preresume = ploop_preresume,
 	.clone_and_map_rq = ploop_clone_and_map,
 	.status = ploop_status,
+	.find_hole = ploop_find_hole,
 };
 
 static int __init dm_ploop_init(void)
diff --git a/drivers/md/dm-ploop.h b/drivers/md/dm-ploop.h
index 66882cf407a5..f27764487879 100644
--- a/drivers/md/dm-ploop.h
+++ b/drivers/md/dm-ploop.h
@@ -600,4 +600,5 @@ extern void ploop_index_wb_init(struct ploop_index_wb *piwb,
 extern void ploop_call_rw_iter(struct file *file, loff_t pos, unsigned rw,
 			       struct iov_iter *iter, struct pio *pio);
 extern void ploop_enospc_timer(struct timer_list *timer);
+extern loff_t ploop_find_hole(struct dm_target *ti, loff_t offset, int whence);
 #endif /* __DM_PLOOP_H */
-- 
2.39.3



More information about the Devel mailing list