aboutsummaryrefslogtreecommitdiffstats
path: root/fs/block_dev.c
diff options
context:
space:
mode:
Diffstat (limited to 'fs/block_dev.c')
-rw-r--r--fs/block_dev.c139
1 files changed, 93 insertions, 46 deletions
diff --git a/fs/block_dev.c b/fs/block_dev.c
index 606a5259f87f..c1c1b8c3fb99 100644
--- a/fs/block_dev.c
+++ b/fs/block_dev.c
@@ -854,24 +854,6 @@ static inline void bd_unlink_disk_holder(struct block_device *bdev)
854{ } 854{ }
855#endif 855#endif
856 856
857/*
858 * Tries to open block device by device number. Use it ONLY if you
859 * really do not have anything better - i.e. when you are behind a
860 * truly sucky interface and all you are given is a device number. _Never_
861 * to be used for internal purposes. If you ever need it - reconsider
862 * your API.
863 */
864struct block_device *open_by_devnum(dev_t dev, fmode_t mode, void *holder)
865{
866 struct block_device *bdev = bdget(dev);
867 int err = -ENOMEM;
868 if (bdev)
869 err = blkdev_get(bdev, mode, holder);
870 return err ? ERR_PTR(err) : bdev;
871}
872
873EXPORT_SYMBOL(open_by_devnum);
874
875/** 857/**
876 * flush_disk - invalidates all buffer-cache entries on a disk 858 * flush_disk - invalidates all buffer-cache entries on a disk
877 * 859 *
@@ -1132,6 +1114,25 @@ static int __blkdev_get(struct block_device *bdev, fmode_t mode, int for_part)
1132 return ret; 1114 return ret;
1133} 1115}
1134 1116
1117/**
1118 * blkdev_get - open a block device
1119 * @bdev: block_device to open
1120 * @mode: FMODE_* mask
1121 * @holder: exclusive holder identifier
1122 *
1123 * Open @bdev with @mode. If @mode includes %FMODE_EXCL, @bdev is
1124 * open with exclusive access. Specifying %FMODE_EXCL with %NULL
1125 * @holder is invalid. Exclusive opens may nest for the same @holder.
1126 *
1127 * On success, the reference count of @bdev is unchanged. On failure,
1128 * @bdev is put.
1129 *
1130 * CONTEXT:
1131 * Might sleep.
1132 *
1133 * RETURNS:
1134 * 0 on success, -errno on failure.
1135 */
1135int blkdev_get(struct block_device *bdev, fmode_t mode, void *holder) 1136int blkdev_get(struct block_device *bdev, fmode_t mode, void *holder)
1136{ 1137{
1137 struct block_device *whole = NULL; 1138 struct block_device *whole = NULL;
@@ -1186,6 +1187,80 @@ int blkdev_get(struct block_device *bdev, fmode_t mode, void *holder)
1186} 1187}
1187EXPORT_SYMBOL(blkdev_get); 1188EXPORT_SYMBOL(blkdev_get);
1188 1189
1190/**
1191 * blkdev_get_by_path - open a block device by name
1192 * @path: path to the block device to open
1193 * @mode: FMODE_* mask
1194 * @holder: exclusive holder identifier
1195 *
1196 * Open the blockdevice described by the device file at @path. @mode
1197 * and @holder are identical to blkdev_get().
1198 *
1199 * On success, the returned block_device has reference count of one.
1200 *
1201 * CONTEXT:
1202 * Might sleep.
1203 *
1204 * RETURNS:
1205 * Pointer to block_device on success, ERR_PTR(-errno) on failure.
1206 */
1207struct block_device *blkdev_get_by_path(const char *path, fmode_t mode,
1208 void *holder)
1209{
1210 struct block_device *bdev;
1211 int err;
1212
1213 bdev = lookup_bdev(path);
1214 if (IS_ERR(bdev))
1215 return bdev;
1216
1217 err = blkdev_get(bdev, mode, holder);
1218 if (err)
1219 return ERR_PTR(err);
1220
1221 return bdev;
1222}
1223EXPORT_SYMBOL(blkdev_get_by_path);
1224
1225/**
1226 * blkdev_get_by_dev - open a block device by device number
1227 * @dev: device number of block device to open
1228 * @mode: FMODE_* mask
1229 * @holder: exclusive holder identifier
1230 *
1231 * Open the blockdevice described by device number @dev. @mode and
1232 * @holder are identical to blkdev_get().
1233 *
1234 * Use it ONLY if you really do not have anything better - i.e. when
1235 * you are behind a truly sucky interface and all you are given is a
1236 * device number. _Never_ to be used for internal purposes. If you
1237 * ever need it - reconsider your API.
1238 *
1239 * On success, the returned block_device has reference count of one.
1240 *
1241 * CONTEXT:
1242 * Might sleep.
1243 *
1244 * RETURNS:
1245 * Pointer to block_device on success, ERR_PTR(-errno) on failure.
1246 */
1247struct block_device *blkdev_get_by_dev(dev_t dev, fmode_t mode, void *holder)
1248{
1249 struct block_device *bdev;
1250 int err;
1251
1252 bdev = bdget(dev);
1253 if (!bdev)
1254 return ERR_PTR(-ENOMEM);
1255
1256 err = blkdev_get(bdev, mode, holder);
1257 if (err)
1258 return ERR_PTR(err);
1259
1260 return bdev;
1261}
1262EXPORT_SYMBOL(blkdev_get_by_dev);
1263
1189static int blkdev_open(struct inode * inode, struct file * filp) 1264static int blkdev_open(struct inode * inode, struct file * filp)
1190{ 1265{
1191 struct block_device *bdev; 1266 struct block_device *bdev;
@@ -1436,34 +1511,6 @@ fail:
1436} 1511}
1437EXPORT_SYMBOL(lookup_bdev); 1512EXPORT_SYMBOL(lookup_bdev);
1438 1513
1439/**
1440 * open_bdev_exclusive - open a block device by name and set it up for use
1441 *
1442 * @path: special file representing the block device
1443 * @mode: FMODE_... combination to pass be used
1444 * @holder: owner for exclusion
1445 *
1446 * Open the blockdevice described by the special file at @path, claim it
1447 * for the @holder.
1448 */
1449struct block_device *open_bdev_exclusive(const char *path, fmode_t mode, void *holder)
1450{
1451 struct block_device *bdev;
1452 int error;
1453
1454 bdev = lookup_bdev(path);
1455 if (IS_ERR(bdev))
1456 return bdev;
1457
1458 error = blkdev_get(bdev, mode | FMODE_EXCL, holder);
1459 if (error)
1460 return ERR_PTR(error);
1461
1462 return bdev;
1463}
1464
1465EXPORT_SYMBOL(open_bdev_exclusive);
1466
1467int __invalidate_device(struct block_device *bdev) 1514int __invalidate_device(struct block_device *bdev)
1468{ 1515{
1469 struct super_block *sb = get_super(bdev); 1516 struct super_block *sb = get_super(bdev);