block: add secure discard

Secure discard is the same as discard except that all copies of the
discarded sectors (perhaps created by garbage collection) must also be
erased.

Signed-off-by: Adrian Hunter <[email protected]>
Acked-by: Jens Axboe <[email protected]>
Cc: Kyungmin Park <[email protected]>
Cc: Madhusudhan Chikkature <[email protected]>
Cc: Christoph Hellwig <[email protected]>
Cc: Ben Gardiner <[email protected]>
Cc: <[email protected]>
Signed-off-by: Andrew Morton <[email protected]>
Signed-off-by: Linus Torvalds <[email protected]>
This commit is contained in:
Adrian Hunter 2010-08-11 14:17:49 -07:00 • committed by Linus Torvalds
commit 8d57a98ccd
9 changed files with 45 additions and 7 deletions

View file

@ -114,8 +114,10 @@ static int blkdev_reread_part(struct block_device *bdev)
}
static int blk_ioctl_discard(struct block_device *bdev, uint64_t start,
uint64_t len)
uint64_t len, int secure)
{
unsigned long flags = BLKDEV_IFL_WAIT;
if (start & 511)
return -EINVAL;
if (len & 511)
@ -125,8 +127,9 @@ static int blk_ioctl_discard(struct block_device *bdev, uint64_t start,
if (start + len > (bdev->bd_inode->i_size >> 9))
return -EINVAL;
return blkdev_issue_discard(bdev, start, len, GFP_KERNEL,
BLKDEV_IFL_WAIT);
if (secure)
flags |= BLKDEV_IFL_SECURE;
return blkdev_issue_discard(bdev, start, len, GFP_KERNEL, flags);
}
static int put_ushort(unsigned long arg, unsigned short val)
@ -213,7 +216,8 @@ int blkdev_ioctl(struct block_device *bdev, fmode_t mode, unsigned cmd,
set_device_ro(bdev, n);
return 0;
case BLKDISCARD: {
case BLKDISCARD:
case BLKSECDISCARD: {
uint64_t range[2];
if (!(mode & FMODE_WRITE))
@ -222,7 +226,8 @@ int blkdev_ioctl(struct block_device *bdev, fmode_t mode, unsigned cmd,
if (copy_from_user(range, (void __user *)arg, sizeof(range)))
return -EFAULT;
return blk_ioctl_discard(bdev, range[0], range[1]);
return blk_ioctl_discard(bdev, range[0], range[1],
cmd == BLKSECDISCARD);
}
case HDIO_GETGEO: {