[RH7,4/6] ploop: Introduce may_allow_falloc_discard()

Submitted by Kirill Tkhai on Sept. 3, 2020, 2:12 p.m.

Details

Message ID 159914234085.142757.10547129691296376754.stgit@localhost.localdomain
State New
Series "ploop: Rework queue_settings autoconfig and allow fuse 4K discard"
Headers show

Commit Message

Kirill Tkhai Sept. 3, 2020, 2:12 p.m.
This function say whether it is allowed to switch
to fallocate-based discard with current ploop deltas
or no.

Signed-off-by: Kirill Tkhai <ktkhai@virtuozzo.com>
---
 drivers/block/ploop/dev.c        |   27 +++++++++++++++++++++++++++
 drivers/block/ploop/fmt_ploop1.c |    9 ---------
 drivers/block/ploop/fmt_raw.c    |    3 ---
 drivers/block/ploop/io_kaio.c    |    3 ++-
 include/linux/ploop/ploop.h      |    1 +
 5 files changed, 30 insertions(+), 13 deletions(-)

Patch hide | download patch | download mbox

diff --git a/drivers/block/ploop/dev.c b/drivers/block/ploop/dev.c
index 3358d70a4211..8a0f0a8fe3f7 100644
--- a/drivers/block/ploop/dev.c
+++ b/drivers/block/ploop/dev.c
@@ -3401,6 +3401,30 @@  static void autoconfigure_queue_settings(struct ploop_device *plo)
 	blk_queue_max_write_same_sectors(q, 0);
 }
 
+bool may_allow_falloc_discard(struct ploop_device *plo)
+{
+	struct ploop_delta *delta;
+
+	/*
+	 * V1 format may have clusters unaligned by cluster size.
+	 * But does libploop permit them?!
+	 */
+	if (plo->fmt_version == PLOOP_FMT_V1)
+		return false;
+
+	lockdep_assert_held(&plo->ctl_mutex);
+	if (list_empty(&plo->map.delta_list))
+		return false;
+	/* Base delta is RAW and io is io_direct? */
+	delta = list_last_entry(&plo->map.delta_list,
+				struct ploop_delta, list);
+	if (delta->io.ops->id == PLOOP_IO_DIRECT &&
+	    delta->ops->id == PLOOP_FMT_RAW)
+		return false;
+
+	return true;
+}
+
 static int ploop_add_delta(struct ploop_device * plo, unsigned long arg)
 {
 	int err;
@@ -4215,6 +4239,9 @@  static int ploop_start(struct ploop_device * plo, struct block_device *bdev)
 		plo->free_qmax++;
 	}
 
+	if (!may_allow_falloc_discard(plo))
+		set_bit(PLOOP_S_NO_FALLOC_DISCARD, &plo->state);
+
 	list_for_each_entry_reverse(delta, &plo->map.delta_list, list) {
 		err = delta->ops->start(delta);
 		if (err)
diff --git a/drivers/block/ploop/fmt_ploop1.c b/drivers/block/ploop/fmt_ploop1.c
index ab8e182d60ab..99acad2d6994 100644
--- a/drivers/block/ploop/fmt_ploop1.c
+++ b/drivers/block/ploop/fmt_ploop1.c
@@ -327,15 +327,6 @@  ploop1_open(struct ploop_delta * delta)
 	    ((u64)ph->bd_size + ph->l1_off) << 9)
 		delta->flags |= PLOOP_FMT_PREALLOCATED;
 
-	/* FIXME: is there a better place for this? */
-	if (delta->io.ops->id == PLOOP_IO_KAIO &&
-	    delta->io.files.inode->i_sb->s_magic == FUSE_SUPER_MAGIC)
-		set_bit(PLOOP_S_NO_FALLOC_DISCARD, &delta->plo->state);
-
-	/* TODO: add discard alignment for v1 */
-	if (delta->plo->fmt_version != PLOOP_FMT_V2)
-		set_bit(PLOOP_S_NO_FALLOC_DISCARD, &delta->plo->state);
-
 	return 0;
 
 out_err:
diff --git a/drivers/block/ploop/fmt_raw.c b/drivers/block/ploop/fmt_raw.c
index 65e16aeaf66c..9e0c517a0100 100644
--- a/drivers/block/ploop/fmt_raw.c
+++ b/drivers/block/ploop/fmt_raw.c
@@ -61,9 +61,6 @@  raw_open(struct ploop_delta * delta)
 		return -EINVAL;
 	}
 
-	if (delta->io.ops->id == PLOOP_IO_DIRECT)
-		set_bit(PLOOP_S_NO_FALLOC_DISCARD, &delta->plo->state);
-
 	/* no more allocations at all */
 	delta->flags |= PLOOP_FMT_PREALLOCATED;
 
diff --git a/drivers/block/ploop/io_kaio.c b/drivers/block/ploop/io_kaio.c
index 7d690dbe9124..6436f5c13a0e 100644
--- a/drivers/block/ploop/io_kaio.c
+++ b/drivers/block/ploop/io_kaio.c
@@ -1143,6 +1143,8 @@  static void kaio_queue_settings(struct ploop_io * io, struct request_queue * q)
 		return;
 	}
 
+	/* FUSE default is maintaince-mode discard */
+	set_bit(PLOOP_S_NO_FALLOC_DISCARD, &io->plo->state);
 	blk_set_stacking_limits(&q->limits);
 	/*
 	 * Maintaince mode based discard splits a big bio itself,
@@ -1153,7 +1155,6 @@  static void kaio_queue_settings(struct ploop_io * io, struct request_queue * q)
 	 *
 	 * https://jira.sw.ru/browse/PSBM-95772
 	 */
-	//ploop_set_discard_limits(io->plo);
 	q->limits.max_discard_sectors = UINT_MAX >> 9;
 }
 
diff --git a/include/linux/ploop/ploop.h b/include/linux/ploop/ploop.h
index 2dc0c2690490..16a30076704a 100644
--- a/include/linux/ploop/ploop.h
+++ b/include/linux/ploop/ploop.h
@@ -884,6 +884,7 @@  static inline void ploop_set_discard_limits(struct ploop_device *plo)
 }
 struct map_node;
 
+bool may_allow_falloc_discard(struct ploop_device *plo);
 int ploop_fastmap(struct ploop_map * map, cluster_t block, iblock_t *result);
 void ploop_update_map(struct ploop_map * map, int level, cluster_t block, iblock_t iblk);
 void ploop_update_map_hdr(struct ploop_map * map, u8 *hdr, int hdr_size);