Skip to content

Commit

Permalink
---
Browse files Browse the repository at this point in the history
yaml
---
r: 161227
b: refs/heads/master
c: 746cd1e
h: refs/heads/master
i:
  161225: 780c9bf
  161223: a6a097f
v: v3
  • Loading branch information
Christoph Hellwig authored and Jens Axboe committed Sep 14, 2009
1 parent 6d437c7 commit 122b81f
Show file tree
Hide file tree
Showing 7 changed files with 38 additions and 68 deletions.
2 changes: 1 addition & 1 deletion [refs]
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
---
refs/heads/master: 3d2257f157c2324acbc0fa0fa54e8626a987edd2
refs/heads/master: 746cd1e7e4a555ddaee53b19a46e05c9c61eaf09
31 changes: 19 additions & 12 deletions trunk/block/blk-barrier.c
Original file line number Diff line number Diff line change
Expand Up @@ -348,6 +348,9 @@ static void blkdev_discard_end_io(struct bio *bio, int err)
clear_bit(BIO_UPTODATE, &bio->bi_flags);
}

if (bio->bi_private)
complete(bio->bi_private);

bio_put(bio);
}

Expand All @@ -357,34 +360,35 @@ static void blkdev_discard_end_io(struct bio *bio, int err)
* @sector: start sector
* @nr_sects: number of sectors to discard
* @gfp_mask: memory allocation flags (for bio_alloc)
* @flags: DISCARD_FL_* flags to control behaviour
*
* Description:
* Issue a discard request for the sectors in question. Does not wait.
* Issue a discard request for the sectors in question.
*/
int blkdev_issue_discard(struct block_device *bdev,
sector_t sector, sector_t nr_sects, gfp_t gfp_mask)
int blkdev_issue_discard(struct block_device *bdev, sector_t sector,
sector_t nr_sects, gfp_t gfp_mask, int flags)
{
struct request_queue *q;
struct bio *bio;
DECLARE_COMPLETION_ONSTACK(wait);
struct request_queue *q = bdev_get_queue(bdev);
int type = flags & DISCARD_FL_BARRIER ?
DISCARD_BARRIER : DISCARD_NOBARRIER;
int ret = 0;

if (bdev->bd_disk == NULL)
return -ENXIO;

q = bdev_get_queue(bdev);
if (!q)
return -ENXIO;

if (!q->prepare_discard_fn)
return -EOPNOTSUPP;

while (nr_sects && !ret) {
bio = bio_alloc(gfp_mask, 0);
struct bio *bio = bio_alloc(gfp_mask, 0);
if (!bio)
return -ENOMEM;

bio->bi_end_io = blkdev_discard_end_io;
bio->bi_bdev = bdev;
if (flags & DISCARD_FL_WAIT)
bio->bi_private = &wait;

bio->bi_sector = sector;

Expand All @@ -396,10 +400,13 @@ int blkdev_issue_discard(struct block_device *bdev,
bio->bi_size = nr_sects << 9;
nr_sects = 0;
}

bio_get(bio);
submit_bio(DISCARD_BARRIER, bio);
submit_bio(type, bio);

if (flags & DISCARD_FL_WAIT)
wait_for_completion(&wait);

/* Check if it failed immediately */
if (bio_flagged(bio, BIO_EOPNOTSUPP))
ret = -EOPNOTSUPP;
else if (!bio_flagged(bio, BIO_UPTODATE))
Expand Down
49 changes: 2 additions & 47 deletions trunk/block/ioctl.c
Original file line number Diff line number Diff line change
Expand Up @@ -112,22 +112,9 @@ static int blkdev_reread_part(struct block_device *bdev)
return res;
}

static void blk_ioc_discard_endio(struct bio *bio, int err)
{
if (err) {
if (err == -EOPNOTSUPP)
set_bit(BIO_EOPNOTSUPP, &bio->bi_flags);
clear_bit(BIO_UPTODATE, &bio->bi_flags);
}
complete(bio->bi_private);
}

static int blk_ioctl_discard(struct block_device *bdev, uint64_t start,
uint64_t len)
{
struct request_queue *q = bdev_get_queue(bdev);
int ret = 0;

if (start & 511)
return -EINVAL;
if (len & 511)
Expand All @@ -137,40 +124,8 @@ static int blk_ioctl_discard(struct block_device *bdev, uint64_t start,

if (start + len > (bdev->bd_inode->i_size >> 9))
return -EINVAL;

if (!q->prepare_discard_fn)
return -EOPNOTSUPP;

while (len && !ret) {
DECLARE_COMPLETION_ONSTACK(wait);
struct bio *bio;

bio = bio_alloc(GFP_KERNEL, 0);

bio->bi_end_io = blk_ioc_discard_endio;
bio->bi_bdev = bdev;
bio->bi_private = &wait;
bio->bi_sector = start;

if (len > queue_max_hw_sectors(q)) {
bio->bi_size = queue_max_hw_sectors(q) << 9;
len -= queue_max_hw_sectors(q);
start += queue_max_hw_sectors(q);
} else {
bio->bi_size = len << 9;
len = 0;
}
submit_bio(DISCARD_NOBARRIER, bio);

wait_for_completion(&wait);

if (bio_flagged(bio, BIO_EOPNOTSUPP))
ret = -EOPNOTSUPP;
else if (!bio_flagged(bio, BIO_UPTODATE))
ret = -EIO;
bio_put(bio);
}
return ret;
return blkdev_issue_discard(bdev, start, len, GFP_KERNEL,
DISCARD_FL_WAIT);
}

static int put_ushort(unsigned long arg, unsigned short val)
Expand Down
3 changes: 2 additions & 1 deletion trunk/fs/btrfs/extent-tree.c
Original file line number Diff line number Diff line change
Expand Up @@ -1511,7 +1511,8 @@ static int remove_extent_backref(struct btrfs_trans_handle *trans,
static void btrfs_issue_discard(struct block_device *bdev,
u64 start, u64 len)
{
blkdev_issue_discard(bdev, start >> 9, len >> 9, GFP_KERNEL);
blkdev_issue_discard(bdev, start >> 9, len >> 9, GFP_KERNEL,
DISCARD_FL_BARRIER);
}
#endif

Expand Down
6 changes: 4 additions & 2 deletions trunk/fs/gfs2/rgrp.c
Original file line number Diff line number Diff line change
Expand Up @@ -857,7 +857,8 @@ static void gfs2_rgrp_send_discards(struct gfs2_sbd *sdp, u64 offset,
goto start_new_extent;
if ((start + nr_sects) != blk) {
rv = blkdev_issue_discard(bdev, start,
nr_sects, GFP_NOFS);
nr_sects, GFP_NOFS,
DISCARD_FL_BARRIER);
if (rv)
goto fail;
nr_sects = 0;
Expand All @@ -871,7 +872,8 @@ static void gfs2_rgrp_send_discards(struct gfs2_sbd *sdp, u64 offset,
}
}
if (nr_sects) {
rv = blkdev_issue_discard(bdev, start, nr_sects, GFP_NOFS);
rv = blkdev_issue_discard(bdev, start, nr_sects, GFP_NOFS,
DISCARD_FL_BARRIER);
if (rv)
goto fail;
}
Expand Down
9 changes: 6 additions & 3 deletions trunk/include/linux/blkdev.h
Original file line number Diff line number Diff line change
Expand Up @@ -998,15 +998,18 @@ static inline struct request *blk_map_queue_find_tag(struct blk_queue_tag *bqt,
}

extern int blkdev_issue_flush(struct block_device *, sector_t *);
extern int blkdev_issue_discard(struct block_device *,
sector_t sector, sector_t nr_sects, gfp_t);
#define DISCARD_FL_WAIT 0x01 /* wait for completion */
#define DISCARD_FL_BARRIER 0x02 /* issue DISCARD_BARRIER request */
extern int blkdev_issue_discard(struct block_device *, sector_t sector,
sector_t nr_sects, gfp_t, int flags);

static inline int sb_issue_discard(struct super_block *sb,
sector_t block, sector_t nr_blocks)
{
block <<= (sb->s_blocksize_bits - 9);
nr_blocks <<= (sb->s_blocksize_bits - 9);
return blkdev_issue_discard(sb->s_bdev, block, nr_blocks, GFP_KERNEL);
return blkdev_issue_discard(sb->s_bdev, block, nr_blocks, GFP_KERNEL,
DISCARD_FL_BARRIER);
}

extern int blk_verify_command(unsigned char *cmd, fmode_t has_write_perm);
Expand Down
6 changes: 4 additions & 2 deletions trunk/mm/swapfile.c
Original file line number Diff line number Diff line change
Expand Up @@ -161,7 +161,8 @@ static int discard_swap(struct swap_info_struct *si)
}

err = blkdev_issue_discard(si->bdev, start_block,
nr_blocks, GFP_KERNEL);
nr_blocks, GFP_KERNEL,
DISCARD_FL_BARRIER);
if (err)
break;

Expand Down Expand Up @@ -200,7 +201,8 @@ static void discard_swap_cluster(struct swap_info_struct *si,
start_block <<= PAGE_SHIFT - 9;
nr_blocks <<= PAGE_SHIFT - 9;
if (blkdev_issue_discard(si->bdev, start_block,
nr_blocks, GFP_NOIO))
nr_blocks, GFP_NOIO,
DISCARD_FL_BARRIER))
break;
}

Expand Down

0 comments on commit 122b81f

Please sign in to comment.