Greg Kroah-Hartman | b244131 | 2017-11-01 15:07:57 +0100 | [diff] [blame] | 1 | /* SPDX-License-Identifier: GPL-2.0 */ |
Linus Torvalds | 1da177e | 2005-04-16 15:20:36 -0700 | [diff] [blame] | 2 | #ifndef _LINUX_GENHD_H |
| 3 | #define _LINUX_GENHD_H |
| 4 | |
| 5 | /* |
| 6 | * genhd.h Copyright (C) 1992 Drew Eckhardt |
| 7 | * Generic hard disk header file by |
| 8 | * Drew Eckhardt |
| 9 | * |
| 10 | * <drew@colorado.edu> |
| 11 | */ |
| 12 | |
Linus Torvalds | 1da177e | 2005-04-16 15:20:36 -0700 | [diff] [blame] | 13 | #include <linux/types.h> |
Kay Sievers | edfaa7c | 2007-05-21 22:08:01 +0200 | [diff] [blame] | 14 | #include <linux/kdev_t.h> |
Tejun Heo | e71bf0d | 2008-09-03 09:03:02 +0200 | [diff] [blame] | 15 | #include <linux/rcupdate.h> |
Will Drewry | 6d1d805 | 2010-08-31 15:47:05 -0500 | [diff] [blame] | 16 | #include <linux/slab.h> |
Ming Lei | 6c71013 | 2015-07-16 11:16:45 +0800 | [diff] [blame] | 17 | #include <linux/percpu-refcount.h> |
Andy Shevchenko | 6357978 | 2016-05-20 17:01:24 -0700 | [diff] [blame] | 18 | #include <linux/uuid.h> |
Michael Callahan | dbae2c5 | 2018-07-18 04:47:38 -0700 | [diff] [blame] | 19 | #include <linux/blk_types.h> |
Mikulas Patocka | 1226b8d | 2018-12-06 11:41:20 -0500 | [diff] [blame] | 20 | #include <asm/local.h> |
Linus Torvalds | 1da177e | 2005-04-16 15:20:36 -0700 | [diff] [blame] | 21 | |
Tejun Heo | 548b10e | 2008-08-29 09:01:47 +0200 | [diff] [blame] | 22 | #define dev_to_disk(device) container_of((device), struct gendisk, part0.__dev) |
Tejun Heo | ed9e198 | 2008-08-25 19:56:05 +0900 | [diff] [blame] | 23 | #define dev_to_part(device) container_of((device), struct hd_struct, __dev) |
Tejun Heo | 548b10e | 2008-08-29 09:01:47 +0200 | [diff] [blame] | 24 | #define disk_to_dev(disk) (&(disk)->part0.__dev) |
Tejun Heo | ed9e198 | 2008-08-25 19:56:05 +0900 | [diff] [blame] | 25 | #define part_to_dev(part) (&((part)->__dev)) |
Kay Sievers | edfaa7c | 2007-05-21 22:08:01 +0200 | [diff] [blame] | 26 | |
Boris Burkov | ef45fe4 | 2020-06-01 13:12:05 -0700 | [diff] [blame] | 27 | extern const struct device_type disk_type; |
Kay Sievers | edfaa7c | 2007-05-21 22:08:01 +0200 | [diff] [blame] | 28 | extern struct device_type part_type; |
Kay Sievers | edfaa7c | 2007-05-21 22:08:01 +0200 | [diff] [blame] | 29 | extern struct class block_class; |
| 30 | |
Tejun Heo | 689d6fa | 2008-08-25 19:56:16 +0900 | [diff] [blame] | 31 | #define DISK_MAX_PARTS 256 |
Tejun Heo | 3e1a7ff | 2008-08-25 19:56:17 +0900 | [diff] [blame] | 32 | #define DISK_NAME_LEN 32 |
Tejun Heo | 689d6fa | 2008-08-25 19:56:16 +0900 | [diff] [blame] | 33 | |
David Woodhouse | 34186ef | 2006-04-25 14:07:57 +0100 | [diff] [blame] | 34 | #include <linux/major.h> |
| 35 | #include <linux/device.h> |
| 36 | #include <linux/smp.h> |
| 37 | #include <linux/string.h> |
| 38 | #include <linux/fs.h> |
Kristen Carlson Accardi | 8ce7ad7b | 2007-05-23 13:57:38 -0700 | [diff] [blame] | 39 | #include <linux/workqueue.h> |
David Woodhouse | 34186ef | 2006-04-25 14:07:57 +0100 | [diff] [blame] | 40 | |
Will Drewry | 6d1d805 | 2010-08-31 15:47:05 -0500 | [diff] [blame] | 41 | #define PARTITION_META_INFO_VOLNAMELTH 64 |
Stephen Warren | 1ad7e89 | 2012-11-08 16:12:25 -0800 | [diff] [blame] | 42 | /* |
| 43 | * Enough for the string representation of any kind of UUID plus NULL. |
| 44 | * EFI UUID is 36 characters. MSDOS UUID is 11 characters. |
| 45 | */ |
Andy Shevchenko | 6357978 | 2016-05-20 17:01:24 -0700 | [diff] [blame] | 46 | #define PARTITION_META_INFO_UUIDLTH (UUID_STRING_LEN + 1) |
Will Drewry | 6d1d805 | 2010-08-31 15:47:05 -0500 | [diff] [blame] | 47 | |
| 48 | struct partition_meta_info { |
Stephen Warren | 1ad7e89 | 2012-11-08 16:12:25 -0800 | [diff] [blame] | 49 | char uuid[PARTITION_META_INFO_UUIDLTH]; |
Will Drewry | 6d1d805 | 2010-08-31 15:47:05 -0500 | [diff] [blame] | 50 | u8 volname[PARTITION_META_INFO_VOLNAMELTH]; |
| 51 | }; |
| 52 | |
Linus Torvalds | 1da177e | 2005-04-16 15:20:36 -0700 | [diff] [blame] | 53 | struct hd_struct { |
| 54 | sector_t start_sect; |
Vivek Goyal | c83f6bf | 2012-08-01 12:24:18 +0200 | [diff] [blame] | 55 | /* |
| 56 | * nr_sects is protected by sequence counter. One might extend a |
| 57 | * partition while IO is happening to it and update of nr_sects |
| 58 | * can be non-atomic on 32bit machines with 64bit sector_t. |
| 59 | */ |
Linus Torvalds | 1da177e | 2005-04-16 15:20:36 -0700 | [diff] [blame] | 60 | sector_t nr_sects; |
Ming Lei | 07c4e1e | 2020-05-08 16:17:56 +0800 | [diff] [blame] | 61 | #if BITS_PER_LONG==32 && defined(CONFIG_SMP) |
Vivek Goyal | c83f6bf | 2012-08-01 12:24:18 +0200 | [diff] [blame] | 62 | seqcount_t nr_sects_seq; |
Ming Lei | 07c4e1e | 2020-05-08 16:17:56 +0800 | [diff] [blame] | 63 | #endif |
Ming Lei | 520138c | 2020-05-08 16:17:57 +0800 | [diff] [blame] | 64 | unsigned long stamp; |
Ming Lei | 520138c | 2020-05-08 16:17:57 +0800 | [diff] [blame] | 65 | struct disk_stats __percpu *dkstats; |
Ming Lei | 520138c | 2020-05-08 16:17:57 +0800 | [diff] [blame] | 66 | struct percpu_ref ref; |
| 67 | |
Martin K. Petersen | c72758f | 2009-05-22 17:17:53 -0400 | [diff] [blame] | 68 | sector_t alignment_offset; |
Jens Axboe | a1706ac | 2011-05-30 07:42:51 +0200 | [diff] [blame] | 69 | unsigned int discard_alignment; |
Tejun Heo | ed9e198 | 2008-08-25 19:56:05 +0900 | [diff] [blame] | 70 | struct device __dev; |
Jun'ichi Nomura | 6a4d44c | 2006-03-27 01:17:55 -0800 | [diff] [blame] | 71 | struct kobject *holder_dir; |
Linus Torvalds | 1da177e | 2005-04-16 15:20:36 -0700 | [diff] [blame] | 72 | int policy, partno; |
Will Drewry | 6d1d805 | 2010-08-31 15:47:05 -0500 | [diff] [blame] | 73 | struct partition_meta_info *info; |
Akinobu Mita | c17bb49 | 2006-12-08 02:39:46 -0800 | [diff] [blame] | 74 | #ifdef CONFIG_FAIL_MAKE_REQUEST |
| 75 | int make_it_fail; |
| 76 | #endif |
Yufen Yu | 94a2c3a | 2018-11-28 16:42:01 +0800 | [diff] [blame] | 77 | struct rcu_work rcu_work; |
Linus Torvalds | 1da177e | 2005-04-16 15:20:36 -0700 | [diff] [blame] | 78 | }; |
| 79 | |
Stephen Kitt | 9243c6f | 2020-03-07 15:56:59 +0100 | [diff] [blame] | 80 | /** |
| 81 | * DOC: genhd capability flags |
| 82 | * |
| 83 | * ``GENHD_FL_REMOVABLE`` (0x0001): indicates that the block device |
| 84 | * gives access to removable media. |
| 85 | * When set, the device remains present even when media is not |
| 86 | * inserted. |
| 87 | * Must not be set for devices which are removed entirely when the |
| 88 | * media is removed. |
| 89 | * |
| 90 | * ``GENHD_FL_CD`` (0x0008): the block device is a CD-ROM-style |
| 91 | * device. |
| 92 | * Affects responses to the ``CDROM_GET_CAPABILITY`` ioctl. |
| 93 | * |
| 94 | * ``GENHD_FL_UP`` (0x0010): indicates that the block device is "up", |
| 95 | * with a similar meaning to network interfaces. |
| 96 | * |
| 97 | * ``GENHD_FL_SUPPRESS_PARTITION_INFO`` (0x0020): don't include |
| 98 | * partition information in ``/proc/partitions`` or in the output of |
| 99 | * printk_all_partitions(). |
| 100 | * Used for the null block device and some MMC devices. |
| 101 | * |
| 102 | * ``GENHD_FL_EXT_DEVT`` (0x0040): the driver supports extended |
| 103 | * dynamic ``dev_t``, i.e. it wants extended device numbers |
| 104 | * (``BLOCK_EXT_MAJOR``). |
| 105 | * This affects the maximum number of partitions. |
| 106 | * |
| 107 | * ``GENHD_FL_NATIVE_CAPACITY`` (0x0080): based on information in the |
| 108 | * partition table, the device's capacity has been extended to its |
| 109 | * native capacity; i.e. the device has hidden capacity used by one |
| 110 | * of the partitions (this is a flag used so that native capacity is |
| 111 | * only ever unlocked once). |
| 112 | * |
| 113 | * ``GENHD_FL_BLOCK_EVENTS_ON_EXCL_WRITE`` (0x0100): event polling is |
| 114 | * blocked whenever a writer holds an exclusive lock. |
| 115 | * |
| 116 | * ``GENHD_FL_NO_PART_SCAN`` (0x0200): partition scanning is disabled. |
| 117 | * Used for loop devices in their default settings and some MMC |
| 118 | * devices. |
| 119 | * |
| 120 | * ``GENHD_FL_HIDDEN`` (0x0400): the block device is hidden; it |
| 121 | * doesn't produce events, doesn't appear in sysfs, and doesn't have |
| 122 | * an associated ``bdev``. |
| 123 | * Implies ``GENHD_FL_SUPPRESS_PARTITION_INFO`` and |
| 124 | * ``GENHD_FL_NO_PART_SCAN``. |
| 125 | * Used for multipath devices. |
| 126 | */ |
| 127 | #define GENHD_FL_REMOVABLE 0x0001 |
| 128 | /* 2 is unused (used to be GENHD_FL_DRIVERFS) */ |
| 129 | /* 4 is unused (used to be GENHD_FL_MEDIA_CHANGE_NOTIFY) */ |
| 130 | #define GENHD_FL_CD 0x0008 |
| 131 | #define GENHD_FL_UP 0x0010 |
| 132 | #define GENHD_FL_SUPPRESS_PARTITION_INFO 0x0020 |
| 133 | #define GENHD_FL_EXT_DEVT 0x0040 |
| 134 | #define GENHD_FL_NATIVE_CAPACITY 0x0080 |
| 135 | #define GENHD_FL_BLOCK_EVENTS_ON_EXCL_WRITE 0x0100 |
| 136 | #define GENHD_FL_NO_PART_SCAN 0x0200 |
| 137 | #define GENHD_FL_HIDDEN 0x0400 |
Linus Torvalds | 1da177e | 2005-04-16 15:20:36 -0700 | [diff] [blame] | 138 | |
Tejun Heo | 77ea887 | 2010-12-08 20:57:37 +0100 | [diff] [blame] | 139 | enum { |
| 140 | DISK_EVENT_MEDIA_CHANGE = 1 << 0, /* media changed */ |
| 141 | DISK_EVENT_EJECT_REQUEST = 1 << 1, /* eject requested */ |
| 142 | }; |
| 143 | |
Martin Wilck | c92e2f0 | 2019-03-27 14:51:02 +0100 | [diff] [blame] | 144 | enum { |
| 145 | /* Poll even if events_poll_msecs is unset */ |
| 146 | DISK_EVENT_FLAG_POLL = 1 << 0, |
| 147 | /* Forward events to udev */ |
| 148 | DISK_EVENT_FLAG_UEVENT = 1 << 1, |
| 149 | }; |
| 150 | |
Tejun Heo | 540eed5 | 2008-08-25 19:56:15 +0900 | [diff] [blame] | 151 | struct disk_part_tbl { |
| 152 | struct rcu_head rcu_head; |
| 153 | int len; |
Arnd Bergmann | 4d2deb4 | 2010-02-24 20:01:56 +0100 | [diff] [blame] | 154 | struct hd_struct __rcu *last_lookup; |
| 155 | struct hd_struct __rcu *part[]; |
Tejun Heo | 540eed5 | 2008-08-25 19:56:15 +0900 | [diff] [blame] | 156 | }; |
| 157 | |
Tejun Heo | 77ea887 | 2010-12-08 20:57:37 +0100 | [diff] [blame] | 158 | struct disk_events; |
Vishal Verma | 99e6608 | 2016-01-09 08:36:51 -0800 | [diff] [blame] | 159 | struct badblocks; |
Tejun Heo | 77ea887 | 2010-12-08 20:57:37 +0100 | [diff] [blame] | 160 | |
Martin K. Petersen | 25520d5 | 2015-10-21 13:19:49 -0400 | [diff] [blame] | 161 | struct blk_integrity { |
Eric Biggers | 869ab90 | 2017-03-24 18:03:48 -0700 | [diff] [blame] | 162 | const struct blk_integrity_profile *profile; |
| 163 | unsigned char flags; |
| 164 | unsigned char tuple_size; |
| 165 | unsigned char interval_exp; |
| 166 | unsigned char tag_size; |
Martin K. Petersen | 25520d5 | 2015-10-21 13:19:49 -0400 | [diff] [blame] | 167 | }; |
| 168 | |
Linus Torvalds | 1da177e | 2005-04-16 15:20:36 -0700 | [diff] [blame] | 169 | struct gendisk { |
Tejun Heo | 689d6fa | 2008-08-25 19:56:16 +0900 | [diff] [blame] | 170 | /* major, first_minor and minors are input parameters only, |
| 171 | * don't use directly. Use disk_devt() and disk_max_parts(). |
Tejun Heo | f331c02 | 2008-09-03 09:01:48 +0200 | [diff] [blame] | 172 | */ |
Linus Torvalds | 1da177e | 2005-04-16 15:20:36 -0700 | [diff] [blame] | 173 | int major; /* major number of driver */ |
| 174 | int first_minor; |
| 175 | int minors; /* maximum number of minors, =1 for |
| 176 | * disks that can't be partitioned. */ |
Tejun Heo | f331c02 | 2008-09-03 09:01:48 +0200 | [diff] [blame] | 177 | |
Tejun Heo | 3e1a7ff | 2008-08-25 19:56:17 +0900 | [diff] [blame] | 178 | char disk_name[DISK_NAME_LEN]; /* name of major driver */ |
Tejun Heo | 77ea887 | 2010-12-08 20:57:37 +0100 | [diff] [blame] | 179 | |
Martin Wilck | c92e2f0 | 2019-03-27 14:51:02 +0100 | [diff] [blame] | 180 | unsigned short events; /* supported events */ |
| 181 | unsigned short event_flags; /* flags related to event processing */ |
Tejun Heo | 77ea887 | 2010-12-08 20:57:37 +0100 | [diff] [blame] | 182 | |
Tejun Heo | b5d0b9d | 2008-09-03 09:06:42 +0200 | [diff] [blame] | 183 | /* Array of pointers to partitions indexed by partno. |
Tejun Heo | e71bf0d | 2008-09-03 09:03:02 +0200 | [diff] [blame] | 184 | * Protected with matching bdev lock but stat and other |
| 185 | * non-critical accesses use RCU. Always access through |
| 186 | * helpers. |
| 187 | */ |
Arnd Bergmann | 4d2deb4 | 2010-02-24 20:01:56 +0100 | [diff] [blame] | 188 | struct disk_part_tbl __rcu *part_tbl; |
Tejun Heo | b5d0b9d | 2008-09-03 09:06:42 +0200 | [diff] [blame] | 189 | struct hd_struct part0; |
Tejun Heo | e71bf0d | 2008-09-03 09:03:02 +0200 | [diff] [blame] | 190 | |
Alexey Dobriyan | 83d5cde | 2009-09-21 17:01:13 -0700 | [diff] [blame] | 191 | const struct block_device_operations *fops; |
Linus Torvalds | 1da177e | 2005-04-16 15:20:36 -0700 | [diff] [blame] | 192 | struct request_queue *queue; |
| 193 | void *private_data; |
Linus Torvalds | 1da177e | 2005-04-16 15:20:36 -0700 | [diff] [blame] | 194 | |
| 195 | int flags; |
Jan Kara | 56c0908 | 2018-02-26 13:01:41 +0100 | [diff] [blame] | 196 | struct rw_semaphore lookup_sem; |
Jun'ichi Nomura | 6a4d44c | 2006-03-27 01:17:55 -0800 | [diff] [blame] | 197 | struct kobject *slave_dir; |
Linus Torvalds | 1da177e | 2005-04-16 15:20:36 -0700 | [diff] [blame] | 198 | |
| 199 | struct timer_rand_state *random; |
Linus Torvalds | 1da177e | 2005-04-16 15:20:36 -0700 | [diff] [blame] | 200 | atomic_t sync_io; /* RAID */ |
Tejun Heo | 77ea887 | 2010-12-08 20:57:37 +0100 | [diff] [blame] | 201 | struct disk_events *ev; |
Martin K. Petersen | 7ba1ba1 | 2008-06-30 20:04:41 +0200 | [diff] [blame] | 202 | #ifdef CONFIG_BLK_DEV_INTEGRITY |
Martin K. Petersen | aff34e1 | 2015-10-21 13:19:27 -0400 | [diff] [blame] | 203 | struct kobject integrity_kobj; |
Martin K. Petersen | 25520d5 | 2015-10-21 13:19:49 -0400 | [diff] [blame] | 204 | #endif /* CONFIG_BLK_DEV_INTEGRITY */ |
Christoph Hellwig | a711d91 | 2020-04-25 09:57:00 +0200 | [diff] [blame] | 205 | #if IS_ENABLED(CONFIG_CDROM) |
| 206 | struct cdrom_device_info *cdi; |
| 207 | #endif |
Tejun Heo | 540eed5 | 2008-08-25 19:56:15 +0900 | [diff] [blame] | 208 | int node_id; |
Vishal Verma | 99e6608 | 2016-01-09 08:36:51 -0800 | [diff] [blame] | 209 | struct badblocks *bb; |
Byungchul Park | e319e1f | 2017-10-25 17:56:05 +0900 | [diff] [blame] | 210 | struct lockdep_map lockdep_map; |
Linus Torvalds | 1da177e | 2005-04-16 15:20:36 -0700 | [diff] [blame] | 211 | }; |
| 212 | |
Christoph Hellwig | a711d91 | 2020-04-25 09:57:00 +0200 | [diff] [blame] | 213 | #if IS_REACHABLE(CONFIG_CDROM) |
| 214 | #define disk_to_cdi(disk) ((disk)->cdi) |
| 215 | #else |
| 216 | #define disk_to_cdi(disk) NULL |
| 217 | #endif |
| 218 | |
Tejun Heo | 310a2c1 | 2008-08-25 19:47:17 +0900 | [diff] [blame] | 219 | static inline struct gendisk *part_to_disk(struct hd_struct *part) |
| 220 | { |
Tejun Heo | 548b10e | 2008-08-29 09:01:47 +0200 | [diff] [blame] | 221 | if (likely(part)) { |
| 222 | if (part->partno) |
| 223 | return dev_to_disk(part_to_dev(part)->parent); |
| 224 | else |
| 225 | return dev_to_disk(part_to_dev(part)); |
| 226 | } |
Tejun Heo | 310a2c1 | 2008-08-25 19:47:17 +0900 | [diff] [blame] | 227 | return NULL; |
| 228 | } |
| 229 | |
Tejun Heo | f331c02 | 2008-09-03 09:01:48 +0200 | [diff] [blame] | 230 | static inline int disk_max_parts(struct gendisk *disk) |
| 231 | { |
Tejun Heo | 689d6fa | 2008-08-25 19:56:16 +0900 | [diff] [blame] | 232 | if (disk->flags & GENHD_FL_EXT_DEVT) |
| 233 | return DISK_MAX_PARTS; |
| 234 | return disk->minors; |
Tejun Heo | b5d0b9d | 2008-09-03 09:06:42 +0200 | [diff] [blame] | 235 | } |
| 236 | |
Tejun Heo | d27769e | 2011-08-23 20:01:04 +0200 | [diff] [blame] | 237 | static inline bool disk_part_scan_enabled(struct gendisk *disk) |
Tejun Heo | b5d0b9d | 2008-09-03 09:06:42 +0200 | [diff] [blame] | 238 | { |
Tejun Heo | d27769e | 2011-08-23 20:01:04 +0200 | [diff] [blame] | 239 | return disk_max_parts(disk) > 1 && |
| 240 | !(disk->flags & GENHD_FL_NO_PART_SCAN); |
Tejun Heo | f331c02 | 2008-09-03 09:01:48 +0200 | [diff] [blame] | 241 | } |
| 242 | |
| 243 | static inline dev_t disk_devt(struct gendisk *disk) |
| 244 | { |
Christoph Hellwig | 517bf3c | 2017-11-02 21:29:52 +0300 | [diff] [blame] | 245 | return MKDEV(disk->major, disk->first_minor); |
Tejun Heo | f331c02 | 2008-09-03 09:01:48 +0200 | [diff] [blame] | 246 | } |
| 247 | |
| 248 | static inline dev_t part_devt(struct hd_struct *part) |
| 249 | { |
Tejun Heo | ed9e198 | 2008-08-25 19:56:05 +0900 | [diff] [blame] | 250 | return part_to_dev(part)->devt; |
Tejun Heo | f331c02 | 2008-09-03 09:01:48 +0200 | [diff] [blame] | 251 | } |
| 252 | |
Greg Edwards | 67f2519 | 2017-10-24 11:21:48 -0600 | [diff] [blame] | 253 | extern struct hd_struct *__disk_get_part(struct gendisk *disk, int partno); |
Tejun Heo | e71bf0d | 2008-09-03 09:03:02 +0200 | [diff] [blame] | 254 | extern struct hd_struct *disk_get_part(struct gendisk *disk, int partno); |
| 255 | |
| 256 | static inline void disk_put_part(struct hd_struct *part) |
| 257 | { |
| 258 | if (likely(part)) |
Tejun Heo | ed9e198 | 2008-08-25 19:56:05 +0900 | [diff] [blame] | 259 | put_device(part_to_dev(part)); |
Tejun Heo | e71bf0d | 2008-09-03 09:03:02 +0200 | [diff] [blame] | 260 | } |
| 261 | |
Ming Lei | 07c4e1e | 2020-05-08 16:17:56 +0800 | [diff] [blame] | 262 | static inline void hd_sects_seq_init(struct hd_struct *p) |
| 263 | { |
| 264 | #if BITS_PER_LONG==32 && defined(CONFIG_SMP) |
| 265 | seqcount_init(&p->nr_sects_seq); |
| 266 | #endif |
| 267 | } |
| 268 | |
Tejun Heo | e71bf0d | 2008-09-03 09:03:02 +0200 | [diff] [blame] | 269 | /* |
| 270 | * Smarter partition iterator without context limits. |
| 271 | */ |
| 272 | #define DISK_PITER_REVERSE (1 << 0) /* iterate in the reverse direction */ |
| 273 | #define DISK_PITER_INCL_EMPTY (1 << 1) /* include 0-sized parts */ |
Tejun Heo | b5d0b9d | 2008-09-03 09:06:42 +0200 | [diff] [blame] | 274 | #define DISK_PITER_INCL_PART0 (1 << 2) /* include partition 0 */ |
Tejun Heo | 71982a4 | 2009-04-17 08:34:48 +0200 | [diff] [blame] | 275 | #define DISK_PITER_INCL_EMPTY_PART0 (1 << 3) /* include empty partition 0 */ |
Tejun Heo | e71bf0d | 2008-09-03 09:03:02 +0200 | [diff] [blame] | 276 | |
| 277 | struct disk_part_iter { |
| 278 | struct gendisk *disk; |
| 279 | struct hd_struct *part; |
| 280 | int idx; |
| 281 | unsigned int flags; |
| 282 | }; |
| 283 | |
| 284 | extern void disk_part_iter_init(struct disk_part_iter *piter, |
| 285 | struct gendisk *disk, unsigned int flags); |
| 286 | extern struct hd_struct *disk_part_iter_next(struct disk_part_iter *piter); |
| 287 | extern void disk_part_iter_exit(struct disk_part_iter *piter); |
Linus Torvalds | 10f36b1 | 2020-03-30 11:20:13 -0700 | [diff] [blame] | 288 | extern bool disk_has_partitions(struct gendisk *disk); |
Linus Torvalds | 1da177e | 2005-04-16 15:20:36 -0700 | [diff] [blame] | 289 | |
Petros Koutoupis | 32ca163 | 2009-03-10 08:25:54 +0100 | [diff] [blame] | 290 | /* block/genhd.c */ |
Hannes Reinecke | fef912b | 2018-09-28 08:17:19 +0200 | [diff] [blame] | 291 | extern void device_add_disk(struct device *parent, struct gendisk *disk, |
| 292 | const struct attribute_group **groups); |
Dan Williams | e63a46b | 2016-06-15 18:17:27 -0700 | [diff] [blame] | 293 | static inline void add_disk(struct gendisk *disk) |
| 294 | { |
Hannes Reinecke | fef912b | 2018-09-28 08:17:19 +0200 | [diff] [blame] | 295 | device_add_disk(NULL, disk, NULL); |
Dan Williams | e63a46b | 2016-06-15 18:17:27 -0700 | [diff] [blame] | 296 | } |
Mike Snitzer | fa70d2e | 2018-01-08 22:01:13 -0500 | [diff] [blame] | 297 | extern void device_add_disk_no_queue_reg(struct device *parent, struct gendisk *disk); |
| 298 | static inline void add_disk_no_queue_reg(struct gendisk *disk) |
| 299 | { |
| 300 | device_add_disk_no_queue_reg(NULL, disk); |
| 301 | } |
Dan Williams | e63a46b | 2016-06-15 18:17:27 -0700 | [diff] [blame] | 302 | |
Linus Torvalds | 1da177e | 2005-04-16 15:20:36 -0700 | [diff] [blame] | 303 | extern void del_gendisk(struct gendisk *gp); |
Tejun Heo | cf771cb | 2008-09-03 09:01:09 +0200 | [diff] [blame] | 304 | extern struct gendisk *get_gendisk(dev_t dev, int *partno); |
Tejun Heo | f331c02 | 2008-09-03 09:01:48 +0200 | [diff] [blame] | 305 | extern struct block_device *bdget_disk(struct gendisk *disk, int partno); |
Linus Torvalds | 1da177e | 2005-04-16 15:20:36 -0700 | [diff] [blame] | 306 | |
| 307 | extern void set_device_ro(struct block_device *bdev, int flag); |
| 308 | extern void set_disk_ro(struct gendisk *disk, int flag); |
| 309 | |
Tejun Heo | b7db995 | 2008-08-25 19:56:10 +0900 | [diff] [blame] | 310 | static inline int get_disk_ro(struct gendisk *disk) |
| 311 | { |
| 312 | return disk->part0.policy; |
| 313 | } |
| 314 | |
Tejun Heo | 77ea887 | 2010-12-08 20:57:37 +0100 | [diff] [blame] | 315 | extern void disk_block_events(struct gendisk *disk); |
| 316 | extern void disk_unblock_events(struct gendisk *disk); |
Tejun Heo | 85ef06d | 2011-07-01 16:17:47 +0200 | [diff] [blame] | 317 | extern void disk_flush_events(struct gendisk *disk, unsigned int mask); |
Balbir Singh | e598a72 | 2020-03-13 05:30:05 +0000 | [diff] [blame] | 318 | extern void set_capacity_revalidate_and_notify(struct gendisk *disk, |
| 319 | sector_t size, bool revalidate); |
Tejun Heo | 77ea887 | 2010-12-08 20:57:37 +0100 | [diff] [blame] | 320 | extern unsigned int disk_clear_events(struct gendisk *disk, unsigned int mask); |
| 321 | |
Linus Torvalds | 1da177e | 2005-04-16 15:20:36 -0700 | [diff] [blame] | 322 | /* drivers/char/random.c */ |
Emese Revfy | 0766f78 | 2016-06-20 20:42:34 +0200 | [diff] [blame] | 323 | extern void add_disk_randomness(struct gendisk *disk) __latent_entropy; |
Linus Torvalds | 1da177e | 2005-04-16 15:20:36 -0700 | [diff] [blame] | 324 | extern void rand_initialize_disk(struct gendisk *disk); |
| 325 | |
| 326 | static inline sector_t get_start_sect(struct block_device *bdev) |
| 327 | { |
Tejun Heo | 0762b8b | 2008-08-25 19:56:12 +0900 | [diff] [blame] | 328 | return bdev->bd_part->start_sect; |
Linus Torvalds | 1da177e | 2005-04-16 15:20:36 -0700 | [diff] [blame] | 329 | } |
| 330 | static inline sector_t get_capacity(struct gendisk *disk) |
| 331 | { |
Tejun Heo | 80795ae | 2008-08-25 19:56:07 +0900 | [diff] [blame] | 332 | return disk->part0.nr_sects; |
Linus Torvalds | 1da177e | 2005-04-16 15:20:36 -0700 | [diff] [blame] | 333 | } |
| 334 | static inline void set_capacity(struct gendisk *disk, sector_t size) |
| 335 | { |
Tejun Heo | 80795ae | 2008-08-25 19:56:07 +0900 | [diff] [blame] | 336 | disk->part0.nr_sects = size; |
Linus Torvalds | 1da177e | 2005-04-16 15:20:36 -0700 | [diff] [blame] | 337 | } |
| 338 | |
Christoph Hellwig | 142fe8f | 2019-11-14 15:34:35 +0100 | [diff] [blame] | 339 | int bdev_disk_changed(struct block_device *bdev, bool invalidate); |
Christoph Hellwig | a1548b6 | 2019-11-14 15:34:34 +0100 | [diff] [blame] | 340 | int blk_add_partitions(struct gendisk *disk, struct block_device *bdev); |
Christoph Hellwig | d46430b | 2020-04-14 09:28:57 +0200 | [diff] [blame] | 341 | int blk_drop_partitions(struct block_device *bdev); |
Linus Torvalds | 1da177e | 2005-04-16 15:20:36 -0700 | [diff] [blame] | 342 | |
Byungchul Park | e319e1f | 2017-10-25 17:56:05 +0900 | [diff] [blame] | 343 | extern struct gendisk *__alloc_disk_node(int minors, int node_id); |
Jan Kara | 3079c22 | 2018-02-26 13:01:38 +0100 | [diff] [blame] | 344 | extern struct kobject *get_disk_and_module(struct gendisk *disk); |
Linus Torvalds | 1da177e | 2005-04-16 15:20:36 -0700 | [diff] [blame] | 345 | extern void put_disk(struct gendisk *disk); |
Jan Kara | 9df6c29 | 2018-02-26 13:01:39 +0100 | [diff] [blame] | 346 | extern void put_disk_and_module(struct gendisk *disk); |
Kay Sievers | edfaa7c | 2007-05-21 22:08:01 +0200 | [diff] [blame] | 347 | extern void blk_register_region(dev_t devt, unsigned long range, |
Linus Torvalds | 1da177e | 2005-04-16 15:20:36 -0700 | [diff] [blame] | 348 | struct module *module, |
| 349 | struct kobject *(*probe)(dev_t, int *, void *), |
| 350 | int (*lock)(dev_t, void *), |
| 351 | void *data); |
Kay Sievers | edfaa7c | 2007-05-21 22:08:01 +0200 | [diff] [blame] | 352 | extern void blk_unregister_region(dev_t devt, unsigned long range); |
Linus Torvalds | 1da177e | 2005-04-16 15:20:36 -0700 | [diff] [blame] | 353 | |
Byungchul Park | e319e1f | 2017-10-25 17:56:05 +0900 | [diff] [blame] | 354 | #define alloc_disk_node(minors, node_id) \ |
| 355 | ({ \ |
| 356 | static struct lock_class_key __key; \ |
| 357 | const char *__name; \ |
| 358 | struct gendisk *__disk; \ |
| 359 | \ |
| 360 | __name = "(gendisk_completion)"#minors"("#node_id")"; \ |
| 361 | \ |
| 362 | __disk = __alloc_disk_node(minors, node_id); \ |
| 363 | \ |
| 364 | if (__disk) \ |
| 365 | lockdep_init_map(&__disk->lockdep_map, __name, &__key, 0); \ |
| 366 | \ |
| 367 | __disk; \ |
| 368 | }) |
| 369 | |
| 370 | #define alloc_disk(minors) alloc_disk_node(minors, NUMA_NO_NODE) |
| 371 | |
Christoph Hellwig | 3f1266f | 2020-06-20 09:16:41 +0200 | [diff] [blame] | 372 | int register_blkdev(unsigned int major, const char *name); |
| 373 | void unregister_blkdev(unsigned int major, const char *name); |
| 374 | |
| 375 | int revalidate_disk(struct gendisk *disk); |
| 376 | int check_disk_change(struct block_device *bdev); |
| 377 | int __invalidate_device(struct block_device *bdev, bool kill_dirty); |
| 378 | void bd_set_size(struct block_device *bdev, loff_t size); |
| 379 | |
| 380 | /* for drivers/char/raw.c: */ |
| 381 | int blkdev_ioctl(struct block_device *, fmode_t, unsigned, unsigned long); |
| 382 | long compat_blkdev_ioctl(struct file *, unsigned, unsigned long); |
| 383 | |
| 384 | #ifdef CONFIG_SYSFS |
| 385 | int bd_link_disk_holder(struct block_device *bdev, struct gendisk *disk); |
| 386 | void bd_unlink_disk_holder(struct block_device *bdev, struct gendisk *disk); |
| 387 | #else |
| 388 | static inline int bd_link_disk_holder(struct block_device *bdev, |
| 389 | struct gendisk *disk) |
| 390 | { |
| 391 | return 0; |
| 392 | } |
| 393 | static inline void bd_unlink_disk_holder(struct block_device *bdev, |
| 394 | struct gendisk *disk) |
| 395 | { |
| 396 | } |
| 397 | #endif /* CONFIG_SYSFS */ |
| 398 | |
Christoph Hellwig | 1a4dcfa | 2020-06-20 09:16:43 +0200 | [diff] [blame] | 399 | #ifdef CONFIG_BLOCK |
| 400 | void printk_all_partitions(void); |
| 401 | dev_t blk_lookup_devt(const char *name, int partno); |
Jens Axboe | 87c1efb | 2007-05-11 13:29:54 +0200 | [diff] [blame] | 402 | #else /* CONFIG_BLOCK */ |
Christoph Hellwig | 1a4dcfa | 2020-06-20 09:16:43 +0200 | [diff] [blame] | 403 | static inline void printk_all_partitions(void) |
| 404 | { |
| 405 | } |
Tejun Heo | cf771cb | 2008-09-03 09:01:09 +0200 | [diff] [blame] | 406 | static inline dev_t blk_lookup_devt(const char *name, int partno) |
Kay Sievers | edfaa7c | 2007-05-21 22:08:01 +0200 | [diff] [blame] | 407 | { |
| 408 | dev_t devt = MKDEV(0, 0); |
| 409 | return devt; |
| 410 | } |
Jens Axboe | 87c1efb | 2007-05-11 13:29:54 +0200 | [diff] [blame] | 411 | #endif /* CONFIG_BLOCK */ |
David Howells | 9361401 | 2006-09-30 20:45:40 +0200 | [diff] [blame] | 412 | |
David Woodhouse | a8ae50b | 2008-03-12 17:52:56 +0100 | [diff] [blame] | 413 | #endif /* _LINUX_GENHD_H */ |