mirror of https://lore.kernel.org/lkml/
 help / color / mirror / Atom feed
* [PATCH] ceph: write back a cap snap's dirty pages as soon as it is finished
@ 2026-11-09  0:28 Xiubo Li via B4 Relay
  0 siblings, 0 replies; only message in thread
From: Xiubo Li via B4 Relay @ 2026-11-09  0:28 UTC (permalink / raw)
  To: Ilya Dryomov, Alex Markuze, Viacheslav Dubeyko, Milind Changire
  Cc: ceph-devel, linux-kernel, Xiubo Li

From: Xiubo Li <xiubo.li@clyso.com>

When a snapshot is taken while an inode has dirty pages, the pages
move to a cap snap, which can only be flushed to the MDS once they have
been written back.  __ceph_finish_cap_snap() starts writeback at once
when the cap snap has no dirty pages of its own but the inode still has
some, but when the cap snap has some it starts nothing: its pages wait
for periodic writeback, up to dirty_expire_centisecs, or for the next
write to one of them.  ceph-fuse flushes the buffered data at once in
both cases.

With lazy I/O that loses data from the snapshot.  Several clients
buffer writes to one file then, and when another one writes to the
same object with the new snap context first, the OSD clones the object
for the snapshot on that write; what this client writes with the old
snap context after it goes to the head only.  With two lazy writers
that each dirty a page, take a snapshot and write again, the snapshot
had zeros instead of the first client's data whenever the second
client's new write reached the OSD first, as the OSD op history shows:

  client.4157.0:4 [write 4096~2000] snapc 2=[2]
  client.4156.0:3 [write 0~2000] snapc 1=[]

Start writeback of the cap snap's pages at once, too, as ceph-fuse does.
This also gets the cap snap to the MDS sooner without lazy I/O.

Fixes: 2d12ad950b0c ("ceph: trigger to flush the buffer when making snapshot")
Signed-off-by: Xiubo Li <xiubo.li@clyso.com>
---
When a snapshot is taken while an inode has dirty pages, the kernel
client leaves the cap snap's pages for periodic writeback, while
ceph-fuse flushes them at once.  With lazy I/O another client may write
to the same objects with the new snap context first, and what this
client writes with the old one afterwards misses the snapshot.
---
 fs/ceph/snap.c | 9 +++++++++
 1 file changed, 9 insertions(+)

diff --git a/fs/ceph/snap.c b/fs/ceph/snap.c
index f59b83a97d52..e44378b07fd3 100644
--- a/fs/ceph/snap.c
+++ b/fs/ceph/snap.c
@@ -683,6 +683,15 @@ int __ceph_finish_cap_snap(struct ceph_inode_info *ci,
 		      capsnap->context->seq,
 		      ceph_cap_string(capsnap->dirty),
 		      capsnap->size, capsnap->dirty_pages);
+		/*
+		 * Write them back now, not when writeback or the next
+		 * write to them gets to it: they belong to the snapshot,
+		 * and with lazy I/O another client may already write to
+		 * the same objects with the new snap context.  Its first
+		 * write clones the objects for the snapshot, and what we
+		 * write with the old one after that misses the snapshot.
+		 */
+		ceph_queue_writeback(inode);
 		return 0;
 	}
 

---
base-commit: 5dcec86cc31f8144857c0d9bf2a7fa13b6e6f531
change-id: 20261108-ceph-capsnap-writeback-51ea200d5b59

Best regards,
--  
Xiubo Li <xiubo.li@clyso.com>



^ permalink raw reply	[flat|nested] only message in thread

only message in thread, other threads:[~2026-11-09  0:28 UTC | newest]

Thread overview: (only message) (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2026-11-09  0:28 [PATCH] ceph: write back a cap snap's dirty pages as soon as it is finished Xiubo Li via B4 Relay

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox

all inboxes | Powered by JetHome®