xfs
[Top] [All Lists]

[PATCH 0/4] online discard support V3

To: xfs@xxxxxxxxxxx
Subject: [PATCH 0/4] online discard support V3
From: Christoph Hellwig <hch@xxxxxxxxxxxxx>
Date: Wed, 04 May 2011 14:55:13 -0400
User-agent: quilt/0.48-1
Add support for discarding unused blocks at CIL commit time.  The first
patch is the guts of the implementation and relies and the resently
included improved busy extent tracking.  The second patch is an optimization
that helps a lot with performance, and the last two patches submit the
discard requests asynchronously to not stall the log I/O completions threads
and improve performance, but they currently trip over bugs in the block layer.

The performance with these patches is quite bad on the SATA SSDs I tested,
with up to 50% slowdowns on meta data intensive workloads, although ext4 is
much worse and btrfs is almost as bad as bad.  I've demonstrated a prototype
of a vectored discard at LSF that builds on the code subitted here and
only changes the internals of xfs_discard_extents, which brings the performance
back to acceptable levels.

For now my suggestion is to put patches 1 and 2 in to give people a chance
to play with online discard on XFS.  If the block layer issues get fixed
in time we can add patches 3 and 4 later in the 2.6.40 cycle, if not they
will still be needed once we get the proper vectored discard support that
I'm going to start working on soon.

And here's the block layer workaround for the discard merge bug:


Index: xfs/block/blk-core.c
===================================================================
--- xfs.orig/block/blk-core.c   2011-03-30 16:04:45.700659775 +0200
+++ xfs/block/blk-core.c        2011-03-30 16:04:59.775160021 +0200
@@ -1247,7 +1247,7 @@ static int __make_request(struct request
         */
        blk_queue_bounce(q, &bio);
 
-       if (bio->bi_rw & (REQ_FLUSH | REQ_FUA)) {
+       if (bio->bi_rw & (REQ_FLUSH | REQ_FUA | REQ_DISCARD)) {
                spin_lock_irq(q->queue_lock);
                where = ELEVATOR_INSERT_FLUSH;
                goto get_rq;

<Prev in Thread] Current Thread [Next in Thread>