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.c768
1 files changed, 293 insertions, 475 deletions
diff --git a/fs/block_dev.c b/fs/block_dev.c
index 771f23527010..333a7bb4cb9c 100644
--- a/fs/block_dev.c
+++ b/fs/block_dev.c
@@ -433,7 +433,7 @@ static void init_once(void *foo)
433 INIT_LIST_HEAD(&bdev->bd_inodes); 433 INIT_LIST_HEAD(&bdev->bd_inodes);
434 INIT_LIST_HEAD(&bdev->bd_list); 434 INIT_LIST_HEAD(&bdev->bd_list);
435#ifdef CONFIG_SYSFS 435#ifdef CONFIG_SYSFS
436 INIT_LIST_HEAD(&bdev->bd_holder_list); 436 INIT_LIST_HEAD(&bdev->bd_holder_disks);
437#endif 437#endif
438 inode_init_once(&ei->vfs_inode); 438 inode_init_once(&ei->vfs_inode);
439 /* Initialize mutex for freeze. */ 439 /* Initialize mutex for freeze. */
@@ -473,7 +473,7 @@ static const struct super_operations bdev_sops = {
473static struct dentry *bd_mount(struct file_system_type *fs_type, 473static struct dentry *bd_mount(struct file_system_type *fs_type,
474 int flags, const char *dev_name, void *data) 474 int flags, const char *dev_name, void *data)
475{ 475{
476 return mount_pseudo(fs_type, "bdev:", &bdev_sops, 0x62646576); 476 return mount_pseudo(fs_type, "bdev:", &bdev_sops, NULL, 0x62646576);
477} 477}
478 478
479static struct file_system_type bd_type = { 479static struct file_system_type bd_type = {
@@ -669,7 +669,7 @@ static bool bd_may_claim(struct block_device *bdev, struct block_device *whole,
669 else if (bdev->bd_contains == bdev) 669 else if (bdev->bd_contains == bdev)
670 return true; /* is a whole device which isn't held */ 670 return true; /* is a whole device which isn't held */
671 671
672 else if (whole->bd_holder == bd_claim) 672 else if (whole->bd_holder == bd_may_claim)
673 return true; /* is a partition of a device that is being partitioned */ 673 return true; /* is a partition of a device that is being partitioned */
674 else if (whole->bd_holder != NULL) 674 else if (whole->bd_holder != NULL)
675 return false; /* is a partition of a held device */ 675 return false; /* is a partition of a held device */
@@ -781,439 +781,142 @@ static struct block_device *bd_start_claiming(struct block_device *bdev,
781 } 781 }
782} 782}
783 783
784/* releases bdev_lock */ 784#ifdef CONFIG_SYSFS
785static void __bd_abort_claiming(struct block_device *whole, void *holder) 785struct bd_holder_disk {
786{ 786 struct list_head list;
787 BUG_ON(whole->bd_claiming != holder); 787 struct gendisk *disk;
788 whole->bd_claiming = NULL; 788 int refcnt;
789 wake_up_bit(&whole->bd_claiming, 0); 789};
790
791 spin_unlock(&bdev_lock);
792 bdput(whole);
793}
794
795/**
796 * bd_abort_claiming - abort claiming a block device
797 * @whole: whole block device returned by bd_start_claiming()
798 * @holder: holder trying to claim @bdev
799 *
800 * Abort a claiming block started by bd_start_claiming(). Note that
801 * @whole is not the block device to be claimed but the whole device
802 * returned by bd_start_claiming().
803 *
804 * CONTEXT:
805 * Grabs and releases bdev_lock.
806 */
807static void bd_abort_claiming(struct block_device *whole, void *holder)
808{
809 spin_lock(&bdev_lock);
810 __bd_abort_claiming(whole, holder); /* releases bdev_lock */
811}
812
813/* increment holders when we have a legitimate claim. requires bdev_lock */
814static void __bd_claim(struct block_device *bdev, struct block_device *whole,
815 void *holder)
816{
817 /* note that for a whole device bd_holders
818 * will be incremented twice, and bd_holder will
819 * be set to bd_claim before being set to holder
820 */
821 whole->bd_holders++;
822 whole->bd_holder = bd_claim;
823 bdev->bd_holders++;
824 bdev->bd_holder = holder;
825}
826
827/**
828 * bd_finish_claiming - finish claiming a block device
829 * @bdev: block device of interest (passed to bd_start_claiming())
830 * @whole: whole block device returned by bd_start_claiming()
831 * @holder: holder trying to claim @bdev
832 *
833 * Finish a claiming block started by bd_start_claiming().
834 *
835 * CONTEXT:
836 * Grabs and releases bdev_lock.
837 */
838static void bd_finish_claiming(struct block_device *bdev,
839 struct block_device *whole, void *holder)
840{
841 spin_lock(&bdev_lock);
842 BUG_ON(!bd_may_claim(bdev, whole, holder));
843 __bd_claim(bdev, whole, holder);
844 __bd_abort_claiming(whole, holder); /* not actually an abort */
845}
846 790
847/** 791static struct bd_holder_disk *bd_find_holder_disk(struct block_device *bdev,
848 * bd_claim - claim a block device 792 struct gendisk *disk)
849 * @bdev: block device to claim
850 * @holder: holder trying to claim @bdev
851 *
852 * Try to claim @bdev which must have been opened successfully.
853 *
854 * CONTEXT:
855 * Might sleep.
856 *
857 * RETURNS:
858 * 0 if successful, -EBUSY if @bdev is already claimed.
859 */
860int bd_claim(struct block_device *bdev, void *holder)
861{ 793{
862 struct block_device *whole = bdev->bd_contains; 794 struct bd_holder_disk *holder;
863 int res;
864 795
865 might_sleep(); 796 list_for_each_entry(holder, &bdev->bd_holder_disks, list)
866 797 if (holder->disk == disk)
867 spin_lock(&bdev_lock); 798 return holder;
868 res = bd_prepare_to_claim(bdev, whole, holder); 799 return NULL;
869 if (res == 0)
870 __bd_claim(bdev, whole, holder);
871 spin_unlock(&bdev_lock);
872
873 return res;
874}
875EXPORT_SYMBOL(bd_claim);
876
877void bd_release(struct block_device *bdev)
878{
879 spin_lock(&bdev_lock);
880 if (!--bdev->bd_contains->bd_holders)
881 bdev->bd_contains->bd_holder = NULL;
882 if (!--bdev->bd_holders)
883 bdev->bd_holder = NULL;
884 spin_unlock(&bdev_lock);
885} 800}
886 801
887EXPORT_SYMBOL(bd_release);
888
889#ifdef CONFIG_SYSFS
890/*
891 * Functions for bd_claim_by_kobject / bd_release_from_kobject
892 *
893 * If a kobject is passed to bd_claim_by_kobject()
894 * and the kobject has a parent directory,
895 * following symlinks are created:
896 * o from the kobject to the claimed bdev
897 * o from "holders" directory of the bdev to the parent of the kobject
898 * bd_release_from_kobject() removes these symlinks.
899 *
900 * Example:
901 * If /dev/dm-0 maps to /dev/sda, kobject corresponding to
902 * /sys/block/dm-0/slaves is passed to bd_claim_by_kobject(), then:
903 * /sys/block/dm-0/slaves/sda --> /sys/block/sda
904 * /sys/block/sda/holders/dm-0 --> /sys/block/dm-0
905 */
906
907static int add_symlink(struct kobject *from, struct kobject *to) 802static int add_symlink(struct kobject *from, struct kobject *to)
908{ 803{
909 if (!from || !to)
910 return 0;
911 return sysfs_create_link(from, to, kobject_name(to)); 804 return sysfs_create_link(from, to, kobject_name(to));
912} 805}
913 806
914static void del_symlink(struct kobject *from, struct kobject *to) 807static void del_symlink(struct kobject *from, struct kobject *to)
915{ 808{
916 if (!from || !to)
917 return;
918 sysfs_remove_link(from, kobject_name(to)); 809 sysfs_remove_link(from, kobject_name(to));
919} 810}
920 811
921/*
922 * 'struct bd_holder' contains pointers to kobjects symlinked by
923 * bd_claim_by_kobject.
924 * It's connected to bd_holder_list which is protected by bdev->bd_sem.
925 */
926struct bd_holder {
927 struct list_head list; /* chain of holders of the bdev */
928 int count; /* references from the holder */
929 struct kobject *sdir; /* holder object, e.g. "/block/dm-0/slaves" */
930 struct kobject *hdev; /* e.g. "/block/dm-0" */
931 struct kobject *hdir; /* e.g. "/block/sda/holders" */
932 struct kobject *sdev; /* e.g. "/block/sda" */
933};
934
935/*
936 * Get references of related kobjects at once.
937 * Returns 1 on success. 0 on failure.
938 *
939 * Should call bd_holder_release_dirs() after successful use.
940 */
941static int bd_holder_grab_dirs(struct block_device *bdev,
942 struct bd_holder *bo)
943{
944 if (!bdev || !bo)
945 return 0;
946
947 bo->sdir = kobject_get(bo->sdir);
948 if (!bo->sdir)
949 return 0;
950
951 bo->hdev = kobject_get(bo->sdir->parent);
952 if (!bo->hdev)
953 goto fail_put_sdir;
954
955 bo->sdev = kobject_get(&part_to_dev(bdev->bd_part)->kobj);
956 if (!bo->sdev)
957 goto fail_put_hdev;
958
959 bo->hdir = kobject_get(bdev->bd_part->holder_dir);
960 if (!bo->hdir)
961 goto fail_put_sdev;
962
963 return 1;
964
965fail_put_sdev:
966 kobject_put(bo->sdev);
967fail_put_hdev:
968 kobject_put(bo->hdev);
969fail_put_sdir:
970 kobject_put(bo->sdir);
971
972 return 0;
973}
974
975/* Put references of related kobjects at once. */
976static void bd_holder_release_dirs(struct bd_holder *bo)
977{
978 kobject_put(bo->hdir);
979 kobject_put(bo->sdev);
980 kobject_put(bo->hdev);
981 kobject_put(bo->sdir);
982}
983
984static struct bd_holder *alloc_bd_holder(struct kobject *kobj)
985{
986 struct bd_holder *bo;
987
988 bo = kzalloc(sizeof(*bo), GFP_KERNEL);
989 if (!bo)
990 return NULL;
991
992 bo->count = 1;
993 bo->sdir = kobj;
994
995 return bo;
996}
997
998static void free_bd_holder(struct bd_holder *bo)
999{
1000 kfree(bo);
1001}
1002
1003/** 812/**
1004 * find_bd_holder - find matching struct bd_holder from the block device 813 * bd_link_disk_holder - create symlinks between holding disk and slave bdev
814 * @bdev: the claimed slave bdev
815 * @disk: the holding disk
1005 * 816 *
1006 * @bdev: struct block device to be searched 817 * DON'T USE THIS UNLESS YOU'RE ALREADY USING IT.
1007 * @bo: target struct bd_holder
1008 * 818 *
1009 * Returns matching entry with @bo in @bdev->bd_holder_list. 819 * This functions creates the following sysfs symlinks.
1010 * If found, increment the reference count and return the pointer. 820 *
1011 * If not found, returns NULL. 821 * - from "slaves" directory of the holder @disk to the claimed @bdev
1012 */ 822 * - from "holders" directory of the @bdev to the holder @disk
1013static struct bd_holder *find_bd_holder(struct block_device *bdev, 823 *
1014 struct bd_holder *bo) 824 * For example, if /dev/dm-0 maps to /dev/sda and disk for dm-0 is
1015{ 825 * passed to bd_link_disk_holder(), then:
1016 struct bd_holder *tmp;
1017
1018 list_for_each_entry(tmp, &bdev->bd_holder_list, list)
1019 if (tmp->sdir == bo->sdir) {
1020 tmp->count++;
1021 return tmp;
1022 }
1023
1024 return NULL;
1025}
1026
1027/**
1028 * add_bd_holder - create sysfs symlinks for bd_claim() relationship
1029 * 826 *
1030 * @bdev: block device to be bd_claimed 827 * /sys/block/dm-0/slaves/sda --> /sys/block/sda
1031 * @bo: preallocated and initialized by alloc_bd_holder() 828 * /sys/block/sda/holders/dm-0 --> /sys/block/dm-0
1032 * 829 *
1033 * Add @bo to @bdev->bd_holder_list, create symlinks. 830 * The caller must have claimed @bdev before calling this function and
831 * ensure that both @bdev and @disk are valid during the creation and
832 * lifetime of these symlinks.
1034 * 833 *
1035 * Returns 0 if symlinks are created. 834 * CONTEXT:
1036 * Returns -ve if something fails. 835 * Might sleep.
836 *
837 * RETURNS:
838 * 0 on success, -errno on failure.
1037 */ 839 */
1038static int add_bd_holder(struct block_device *bdev, struct bd_holder *bo) 840int bd_link_disk_holder(struct block_device *bdev, struct gendisk *disk)
1039{ 841{
1040 int err; 842 struct bd_holder_disk *holder;
843 int ret = 0;
1041 844
1042 if (!bo) 845 mutex_lock(&bdev->bd_mutex);
1043 return -EINVAL;
1044 846
1045 if (!bd_holder_grab_dirs(bdev, bo)) 847 WARN_ON_ONCE(!bdev->bd_holder);
1046 return -EBUSY;
1047 848
1048 err = add_symlink(bo->sdir, bo->sdev); 849 /* FIXME: remove the following once add_disk() handles errors */
1049 if (err) 850 if (WARN_ON(!disk->slave_dir || !bdev->bd_part->holder_dir))
1050 return err; 851 goto out_unlock;
1051 852
1052 err = add_symlink(bo->hdir, bo->hdev); 853 holder = bd_find_holder_disk(bdev, disk);
1053 if (err) { 854 if (holder) {
1054 del_symlink(bo->sdir, bo->sdev); 855 holder->refcnt++;
1055 return err; 856 goto out_unlock;
1056 } 857 }
1057 858
1058 list_add_tail(&bo->list, &bdev->bd_holder_list); 859 holder = kzalloc(sizeof(*holder), GFP_KERNEL);
1059 return 0; 860 if (!holder) {
1060} 861 ret = -ENOMEM;
1061 862 goto out_unlock;
1062/**
1063 * del_bd_holder - delete sysfs symlinks for bd_claim() relationship
1064 *
1065 * @bdev: block device to be bd_claimed
1066 * @kobj: holder's kobject
1067 *
1068 * If there is matching entry with @kobj in @bdev->bd_holder_list
1069 * and no other bd_claim() from the same kobject,
1070 * remove the struct bd_holder from the list, delete symlinks for it.
1071 *
1072 * Returns a pointer to the struct bd_holder when it's removed from the list
1073 * and ready to be freed.
1074 * Returns NULL if matching claim isn't found or there is other bd_claim()
1075 * by the same kobject.
1076 */
1077static struct bd_holder *del_bd_holder(struct block_device *bdev,
1078 struct kobject *kobj)
1079{
1080 struct bd_holder *bo;
1081
1082 list_for_each_entry(bo, &bdev->bd_holder_list, list) {
1083 if (bo->sdir == kobj) {
1084 bo->count--;
1085 BUG_ON(bo->count < 0);
1086 if (!bo->count) {
1087 list_del(&bo->list);
1088 del_symlink(bo->sdir, bo->sdev);
1089 del_symlink(bo->hdir, bo->hdev);
1090 bd_holder_release_dirs(bo);
1091 return bo;
1092 }
1093 break;
1094 }
1095 } 863 }
1096 864
1097 return NULL; 865 INIT_LIST_HEAD(&holder->list);
1098} 866 holder->disk = disk;
1099 867 holder->refcnt = 1;
1100/**
1101 * bd_claim_by_kobject - bd_claim() with additional kobject signature
1102 *
1103 * @bdev: block device to be claimed
1104 * @holder: holder's signature
1105 * @kobj: holder's kobject
1106 *
1107 * Do bd_claim() and if it succeeds, create sysfs symlinks between
1108 * the bdev and the holder's kobject.
1109 * Use bd_release_from_kobject() when relesing the claimed bdev.
1110 *
1111 * Returns 0 on success. (same as bd_claim())
1112 * Returns errno on failure.
1113 */
1114static int bd_claim_by_kobject(struct block_device *bdev, void *holder,
1115 struct kobject *kobj)
1116{
1117 int err;
1118 struct bd_holder *bo, *found;
1119
1120 if (!kobj)
1121 return -EINVAL;
1122
1123 bo = alloc_bd_holder(kobj);
1124 if (!bo)
1125 return -ENOMEM;
1126 868
1127 mutex_lock(&bdev->bd_mutex); 869 ret = add_symlink(disk->slave_dir, &part_to_dev(bdev->bd_part)->kobj);
870 if (ret)
871 goto out_free;
1128 872
1129 err = bd_claim(bdev, holder); 873 ret = add_symlink(bdev->bd_part->holder_dir, &disk_to_dev(disk)->kobj);
1130 if (err) 874 if (ret)
1131 goto fail; 875 goto out_del;
1132 876
1133 found = find_bd_holder(bdev, bo); 877 list_add(&holder->list, &bdev->bd_holder_disks);
1134 if (found) 878 goto out_unlock;
1135 goto fail;
1136 879
1137 err = add_bd_holder(bdev, bo); 880out_del:
1138 if (err) 881 del_symlink(disk->slave_dir, &part_to_dev(bdev->bd_part)->kobj);
1139 bd_release(bdev); 882out_free:
1140 else 883 kfree(holder);
1141 bo = NULL; 884out_unlock:
1142fail:
1143 mutex_unlock(&bdev->bd_mutex); 885 mutex_unlock(&bdev->bd_mutex);
1144 free_bd_holder(bo); 886 return ret;
1145 return err;
1146} 887}
888EXPORT_SYMBOL_GPL(bd_link_disk_holder);
1147 889
1148/** 890/**
1149 * bd_release_from_kobject - bd_release() with additional kobject signature 891 * bd_unlink_disk_holder - destroy symlinks created by bd_link_disk_holder()
892 * @bdev: the calimed slave bdev
893 * @disk: the holding disk
1150 * 894 *
1151 * @bdev: block device to be released 895 * DON'T USE THIS UNLESS YOU'RE ALREADY USING IT.
1152 * @kobj: holder's kobject
1153 * 896 *
1154 * Do bd_release() and remove sysfs symlinks created by bd_claim_by_kobject(). 897 * CONTEXT:
898 * Might sleep.
1155 */ 899 */
1156static void bd_release_from_kobject(struct block_device *bdev, 900void bd_unlink_disk_holder(struct block_device *bdev, struct gendisk *disk)
1157 struct kobject *kobj)
1158{ 901{
1159 if (!kobj) 902 struct bd_holder_disk *holder;
1160 return;
1161 903
1162 mutex_lock(&bdev->bd_mutex); 904 mutex_lock(&bdev->bd_mutex);
1163 bd_release(bdev);
1164 free_bd_holder(del_bd_holder(bdev, kobj));
1165 mutex_unlock(&bdev->bd_mutex);
1166}
1167 905
1168/** 906 holder = bd_find_holder_disk(bdev, disk);
1169 * bd_claim_by_disk - wrapper function for bd_claim_by_kobject()
1170 *
1171 * @bdev: block device to be claimed
1172 * @holder: holder's signature
1173 * @disk: holder's gendisk
1174 *
1175 * Call bd_claim_by_kobject() with getting @disk->slave_dir.
1176 */
1177int bd_claim_by_disk(struct block_device *bdev, void *holder,
1178 struct gendisk *disk)
1179{
1180 return bd_claim_by_kobject(bdev, holder, kobject_get(disk->slave_dir));
1181}
1182EXPORT_SYMBOL_GPL(bd_claim_by_disk);
1183 907
1184/** 908 if (!WARN_ON_ONCE(holder == NULL) && !--holder->refcnt) {
1185 * bd_release_from_disk - wrapper function for bd_release_from_kobject() 909 del_symlink(disk->slave_dir, &part_to_dev(bdev->bd_part)->kobj);
1186 * 910 del_symlink(bdev->bd_part->holder_dir,
1187 * @bdev: block device to be claimed 911 &disk_to_dev(disk)->kobj);
1188 * @disk: holder's gendisk 912 list_del_init(&holder->list);
1189 * 913 kfree(holder);
1190 * Call bd_release_from_kobject() and put @disk->slave_dir. 914 }
1191 */
1192void bd_release_from_disk(struct block_device *bdev, struct gendisk *disk)
1193{
1194 bd_release_from_kobject(bdev, disk->slave_dir);
1195 kobject_put(disk->slave_dir);
1196}
1197EXPORT_SYMBOL_GPL(bd_release_from_disk);
1198#endif
1199 915
1200/* 916 mutex_unlock(&bdev->bd_mutex);
1201 * Tries to open block device by device number. Use it ONLY if you
1202 * really do not have anything better - i.e. when you are behind a
1203 * truly sucky interface and all you are given is a device number. _Never_
1204 * to be used for internal purposes. If you ever need it - reconsider
1205 * your API.
1206 */
1207struct block_device *open_by_devnum(dev_t dev, fmode_t mode)
1208{
1209 struct block_device *bdev = bdget(dev);
1210 int err = -ENOMEM;
1211 if (bdev)
1212 err = blkdev_get(bdev, mode);
1213 return err ? ERR_PTR(err) : bdev;
1214} 917}
1215 918EXPORT_SYMBOL_GPL(bd_unlink_disk_holder);
1216EXPORT_SYMBOL(open_by_devnum); 919#endif
1217 920
1218/** 921/**
1219 * flush_disk - invalidates all buffer-cache entries on a disk 922 * flush_disk - invalidates all buffer-cache entries on a disk
@@ -1309,10 +1012,11 @@ int check_disk_change(struct block_device *bdev)
1309{ 1012{
1310 struct gendisk *disk = bdev->bd_disk; 1013 struct gendisk *disk = bdev->bd_disk;
1311 const struct block_device_operations *bdops = disk->fops; 1014 const struct block_device_operations *bdops = disk->fops;
1015 unsigned int events;
1312 1016
1313 if (!bdops->media_changed) 1017 events = disk_clear_events(disk, DISK_EVENT_MEDIA_CHANGE |
1314 return 0; 1018 DISK_EVENT_EJECT_REQUEST);
1315 if (!bdops->media_changed(bdev->bd_disk)) 1019 if (!(events & DISK_EVENT_MEDIA_CHANGE))
1316 return 0; 1020 return 0;
1317 1021
1318 flush_disk(bdev); 1022 flush_disk(bdev);
@@ -1475,17 +1179,171 @@ static int __blkdev_get(struct block_device *bdev, fmode_t mode, int for_part)
1475 return ret; 1179 return ret;
1476} 1180}
1477 1181
1478int blkdev_get(struct block_device *bdev, fmode_t mode) 1182/**
1183 * blkdev_get - open a block device
1184 * @bdev: block_device to open
1185 * @mode: FMODE_* mask
1186 * @holder: exclusive holder identifier
1187 *
1188 * Open @bdev with @mode. If @mode includes %FMODE_EXCL, @bdev is
1189 * open with exclusive access. Specifying %FMODE_EXCL with %NULL
1190 * @holder is invalid. Exclusive opens may nest for the same @holder.
1191 *
1192 * On success, the reference count of @bdev is unchanged. On failure,
1193 * @bdev is put.
1194 *
1195 * CONTEXT:
1196 * Might sleep.
1197 *
1198 * RETURNS:
1199 * 0 on success, -errno on failure.
1200 */
1201int blkdev_get(struct block_device *bdev, fmode_t mode, void *holder)
1479{ 1202{
1480 return __blkdev_get(bdev, mode, 0); 1203 struct block_device *whole = NULL;
1204 int res;
1205
1206 WARN_ON_ONCE((mode & FMODE_EXCL) && !holder);
1207
1208 if ((mode & FMODE_EXCL) && holder) {
1209 whole = bd_start_claiming(bdev, holder);
1210 if (IS_ERR(whole)) {
1211 bdput(bdev);
1212 return PTR_ERR(whole);
1213 }
1214 }
1215
1216 res = __blkdev_get(bdev, mode, 0);
1217
1218 /* __blkdev_get() may alter read only status, check it afterwards */
1219 if (!res && (mode & FMODE_WRITE) && bdev_read_only(bdev)) {
1220 __blkdev_put(bdev, mode, 0);
1221 res = -EACCES;
1222 }
1223
1224 if (whole) {
1225 /* finish claiming */
1226 mutex_lock(&bdev->bd_mutex);
1227 spin_lock(&bdev_lock);
1228
1229 if (!res) {
1230 BUG_ON(!bd_may_claim(bdev, whole, holder));
1231 /*
1232 * Note that for a whole device bd_holders
1233 * will be incremented twice, and bd_holder
1234 * will be set to bd_may_claim before being
1235 * set to holder
1236 */
1237 whole->bd_holders++;
1238 whole->bd_holder = bd_may_claim;
1239 bdev->bd_holders++;
1240 bdev->bd_holder = holder;
1241 }
1242
1243 /* tell others that we're done */
1244 BUG_ON(whole->bd_claiming != holder);
1245 whole->bd_claiming = NULL;
1246 wake_up_bit(&whole->bd_claiming, 0);
1247
1248 spin_unlock(&bdev_lock);
1249
1250 /*
1251 * Block event polling for write claims. Any write
1252 * holder makes the write_holder state stick until all
1253 * are released. This is good enough and tracking
1254 * individual writeable reference is too fragile given
1255 * the way @mode is used in blkdev_get/put().
1256 */
1257 if (!res && (mode & FMODE_WRITE) && !bdev->bd_write_holder) {
1258 bdev->bd_write_holder = true;
1259 disk_block_events(bdev->bd_disk);
1260 }
1261
1262 mutex_unlock(&bdev->bd_mutex);
1263 bdput(whole);
1264 }
1265
1266 return res;
1481} 1267}
1482EXPORT_SYMBOL(blkdev_get); 1268EXPORT_SYMBOL(blkdev_get);
1483 1269
1270/**
1271 * blkdev_get_by_path - open a block device by name
1272 * @path: path to the block device to open
1273 * @mode: FMODE_* mask
1274 * @holder: exclusive holder identifier
1275 *
1276 * Open the blockdevice described by the device file at @path. @mode
1277 * and @holder are identical to blkdev_get().
1278 *
1279 * On success, the returned block_device has reference count of one.
1280 *
1281 * CONTEXT:
1282 * Might sleep.
1283 *
1284 * RETURNS:
1285 * Pointer to block_device on success, ERR_PTR(-errno) on failure.
1286 */
1287struct block_device *blkdev_get_by_path(const char *path, fmode_t mode,
1288 void *holder)
1289{
1290 struct block_device *bdev;
1291 int err;
1292
1293 bdev = lookup_bdev(path);
1294 if (IS_ERR(bdev))
1295 return bdev;
1296
1297 err = blkdev_get(bdev, mode, holder);
1298 if (err)
1299 return ERR_PTR(err);
1300
1301 return bdev;
1302}
1303EXPORT_SYMBOL(blkdev_get_by_path);
1304
1305/**
1306 * blkdev_get_by_dev - open a block device by device number
1307 * @dev: device number of block device to open
1308 * @mode: FMODE_* mask
1309 * @holder: exclusive holder identifier
1310 *
1311 * Open the blockdevice described by device number @dev. @mode and
1312 * @holder are identical to blkdev_get().
1313 *
1314 * Use it ONLY if you really do not have anything better - i.e. when
1315 * you are behind a truly sucky interface and all you are given is a
1316 * device number. _Never_ to be used for internal purposes. If you
1317 * ever need it - reconsider your API.
1318 *
1319 * On success, the returned block_device has reference count of one.
1320 *
1321 * CONTEXT:
1322 * Might sleep.
1323 *
1324 * RETURNS:
1325 * Pointer to block_device on success, ERR_PTR(-errno) on failure.
1326 */
1327struct block_device *blkdev_get_by_dev(dev_t dev, fmode_t mode, void *holder)
1328{
1329 struct block_device *bdev;
1330 int err;
1331
1332 bdev = bdget(dev);
1333 if (!bdev)
1334 return ERR_PTR(-ENOMEM);
1335
1336 err = blkdev_get(bdev, mode, holder);
1337 if (err)
1338 return ERR_PTR(err);
1339
1340 return bdev;
1341}
1342EXPORT_SYMBOL(blkdev_get_by_dev);
1343
1484static int blkdev_open(struct inode * inode, struct file * filp) 1344static int blkdev_open(struct inode * inode, struct file * filp)
1485{ 1345{
1486 struct block_device *whole = NULL;
1487 struct block_device *bdev; 1346 struct block_device *bdev;
1488 int res;
1489 1347
1490 /* 1348 /*
1491 * Preserve backwards compatibility and allow large file access 1349 * Preserve backwards compatibility and allow large file access
@@ -1506,26 +1364,9 @@ static int blkdev_open(struct inode * inode, struct file * filp)
1506 if (bdev == NULL) 1364 if (bdev == NULL)
1507 return -ENOMEM; 1365 return -ENOMEM;
1508 1366
1509 if (filp->f_mode & FMODE_EXCL) {
1510 whole = bd_start_claiming(bdev, filp);
1511 if (IS_ERR(whole)) {
1512 bdput(bdev);
1513 return PTR_ERR(whole);
1514 }
1515 }
1516
1517 filp->f_mapping = bdev->bd_inode->i_mapping; 1367 filp->f_mapping = bdev->bd_inode->i_mapping;
1518 1368
1519 res = blkdev_get(bdev, filp->f_mode); 1369 return blkdev_get(bdev, filp->f_mode, filp);
1520
1521 if (whole) {
1522 if (res == 0)
1523 bd_finish_claiming(bdev, whole, filp);
1524 else
1525 bd_abort_claiming(whole, filp);
1526 }
1527
1528 return res;
1529} 1370}
1530 1371
1531static int __blkdev_put(struct block_device *bdev, fmode_t mode, int for_part) 1372static int __blkdev_put(struct block_device *bdev, fmode_t mode, int for_part)
@@ -1539,6 +1380,7 @@ static int __blkdev_put(struct block_device *bdev, fmode_t mode, int for_part)
1539 bdev->bd_part_count--; 1380 bdev->bd_part_count--;
1540 1381
1541 if (!--bdev->bd_openers) { 1382 if (!--bdev->bd_openers) {
1383 WARN_ON_ONCE(bdev->bd_holders);
1542 sync_blockdev(bdev); 1384 sync_blockdev(bdev);
1543 kill_bdev(bdev); 1385 kill_bdev(bdev);
1544 } 1386 }
@@ -1569,6 +1411,44 @@ static int __blkdev_put(struct block_device *bdev, fmode_t mode, int for_part)
1569 1411
1570int blkdev_put(struct block_device *bdev, fmode_t mode) 1412int blkdev_put(struct block_device *bdev, fmode_t mode)
1571{ 1413{
1414 if (mode & FMODE_EXCL) {
1415 bool bdev_free;
1416
1417 /*
1418 * Release a claim on the device. The holder fields
1419 * are protected with bdev_lock. bd_mutex is to
1420 * synchronize disk_holder unlinking.
1421 */
1422 mutex_lock(&bdev->bd_mutex);
1423 spin_lock(&bdev_lock);
1424
1425 WARN_ON_ONCE(--bdev->bd_holders < 0);
1426 WARN_ON_ONCE(--bdev->bd_contains->bd_holders < 0);
1427
1428 /* bd_contains might point to self, check in a separate step */
1429 if ((bdev_free = !bdev->bd_holders))
1430 bdev->bd_holder = NULL;
1431 if (!bdev->bd_contains->bd_holders)
1432 bdev->bd_contains->bd_holder = NULL;
1433
1434 spin_unlock(&bdev_lock);
1435
1436 /*
1437 * If this was the last claim, remove holder link and
1438 * unblock evpoll if it was a write holder.
1439 */
1440 if (bdev_free) {
1441 if (bdev->bd_write_holder) {
1442 disk_unblock_events(bdev->bd_disk);
1443 bdev->bd_write_holder = false;
1444 } else
1445 disk_check_events(bdev->bd_disk);
1446 }
1447
1448 mutex_unlock(&bdev->bd_mutex);
1449 } else
1450 disk_check_events(bdev->bd_disk);
1451
1572 return __blkdev_put(bdev, mode, 0); 1452 return __blkdev_put(bdev, mode, 0);
1573} 1453}
1574EXPORT_SYMBOL(blkdev_put); 1454EXPORT_SYMBOL(blkdev_put);
@@ -1576,8 +1456,7 @@ EXPORT_SYMBOL(blkdev_put);
1576static int blkdev_close(struct inode * inode, struct file * filp) 1456static int blkdev_close(struct inode * inode, struct file * filp)
1577{ 1457{
1578 struct block_device *bdev = I_BDEV(filp->f_mapping->host); 1458 struct block_device *bdev = I_BDEV(filp->f_mapping->host);
1579 if (bdev->bd_holder == filp) 1459
1580 bd_release(bdev);
1581 return blkdev_put(bdev, filp->f_mode); 1460 return blkdev_put(bdev, filp->f_mode);
1582} 1461}
1583 1462
@@ -1722,67 +1601,6 @@ fail:
1722} 1601}
1723EXPORT_SYMBOL(lookup_bdev); 1602EXPORT_SYMBOL(lookup_bdev);
1724 1603
1725/**
1726 * open_bdev_exclusive - open a block device by name and set it up for use
1727 *
1728 * @path: special file representing the block device
1729 * @mode: FMODE_... combination to pass be used
1730 * @holder: owner for exclusion
1731 *
1732 * Open the blockdevice described by the special file at @path, claim it
1733 * for the @holder.
1734 */
1735struct block_device *open_bdev_exclusive(const char *path, fmode_t mode, void *holder)
1736{
1737 struct block_device *bdev, *whole;
1738 int error;
1739
1740 bdev = lookup_bdev(path);
1741 if (IS_ERR(bdev))
1742 return bdev;
1743
1744 whole = bd_start_claiming(bdev, holder);
1745 if (IS_ERR(whole)) {
1746 bdput(bdev);
1747 return whole;
1748 }
1749
1750 error = blkdev_get(bdev, mode);
1751 if (error)
1752 goto out_abort_claiming;
1753
1754 error = -EACCES;
1755 if ((mode & FMODE_WRITE) && bdev_read_only(bdev))
1756 goto out_blkdev_put;
1757
1758 bd_finish_claiming(bdev, whole, holder);
1759 return bdev;
1760
1761out_blkdev_put:
1762 blkdev_put(bdev, mode);
1763out_abort_claiming:
1764 bd_abort_claiming(whole, holder);
1765 return ERR_PTR(error);
1766}
1767
1768EXPORT_SYMBOL(open_bdev_exclusive);
1769
1770/**
1771 * close_bdev_exclusive - close a blockdevice opened by open_bdev_exclusive()
1772 *
1773 * @bdev: blockdevice to close
1774 * @mode: mode, must match that used to open.
1775 *
1776 * This is the counterpart to open_bdev_exclusive().
1777 */
1778void close_bdev_exclusive(struct block_device *bdev, fmode_t mode)
1779{
1780 bd_release(bdev);
1781 blkdev_put(bdev, mode);
1782}
1783
1784EXPORT_SYMBOL(close_bdev_exclusive);
1785
1786int __invalidate_device(struct block_device *bdev) 1604int __invalidate_device(struct block_device *bdev)
1787{ 1605{
1788 struct super_block *sb = get_super(bdev); 1606 struct super_block *sb = get_super(bdev);