aboutsummaryrefslogtreecommitdiffstats
path: root/include/linux/elevator.h
diff options
context:
space:
mode:
authorJens Axboe <axboe@fb.com>2017-01-17 08:03:22 -0500
committerJens Axboe <axboe@fb.com>2017-01-17 12:04:20 -0500
commitbd166ef183c263c5ced656d49ef19c7da4adc774 (patch)
tree449bbd3b4e671b370b96e3846b2281116e7089e9 /include/linux/elevator.h
parent2af8cbe30531eca73c8f3ba277f155fc0020b01a (diff)
blk-mq-sched: add framework for MQ capable IO schedulers
This adds a set of hooks that intercepts the blk-mq path of allocating/inserting/issuing/completing requests, allowing us to develop a scheduler within that framework. We reuse the existing elevator scheduler API on the registration side, but augment that with the scheduler flagging support for the blk-mq interfce, and with a separate set of ops hooks for MQ devices. We split driver and scheduler tags, so we can run the scheduling independently of device queue depth. Signed-off-by: Jens Axboe <axboe@fb.com> Reviewed-by: Bart Van Assche <bart.vanassche@sandisk.com> Reviewed-by: Omar Sandoval <osandov@fb.com>
Diffstat (limited to 'include/linux/elevator.h')
-rw-r--r--include/linux/elevator.h32
1 files changed, 32 insertions, 0 deletions
diff --git a/include/linux/elevator.h b/include/linux/elevator.h
index 2a9e966eed03..ecb96fd67c6d 100644
--- a/include/linux/elevator.h
+++ b/include/linux/elevator.h
@@ -77,6 +77,34 @@ struct elevator_ops
77 elevator_registered_fn *elevator_registered_fn; 77 elevator_registered_fn *elevator_registered_fn;
78}; 78};
79 79
80struct blk_mq_alloc_data;
81struct blk_mq_hw_ctx;
82
83struct elevator_mq_ops {
84 int (*init_sched)(struct request_queue *, struct elevator_type *);
85 void (*exit_sched)(struct elevator_queue *);
86
87 bool (*allow_merge)(struct request_queue *, struct request *, struct bio *);
88 bool (*bio_merge)(struct blk_mq_hw_ctx *, struct bio *);
89 int (*request_merge)(struct request_queue *q, struct request **, struct bio *);
90 void (*request_merged)(struct request_queue *, struct request *, int);
91 void (*requests_merged)(struct request_queue *, struct request *, struct request *);
92 struct request *(*get_request)(struct request_queue *, unsigned int, struct blk_mq_alloc_data *);
93 void (*put_request)(struct request *);
94 void (*insert_requests)(struct blk_mq_hw_ctx *, struct list_head *, bool);
95 void (*dispatch_requests)(struct blk_mq_hw_ctx *, struct list_head *);
96 bool (*has_work)(struct blk_mq_hw_ctx *);
97 void (*completed_request)(struct blk_mq_hw_ctx *, struct request *);
98 void (*started_request)(struct request *);
99 void (*requeue_request)(struct request *);
100 struct request *(*former_request)(struct request_queue *, struct request *);
101 struct request *(*next_request)(struct request_queue *, struct request *);
102 int (*get_rq_priv)(struct request_queue *, struct request *);
103 void (*put_rq_priv)(struct request_queue *, struct request *);
104 void (*init_icq)(struct io_cq *);
105 void (*exit_icq)(struct io_cq *);
106};
107
80#define ELV_NAME_MAX (16) 108#define ELV_NAME_MAX (16)
81 109
82struct elv_fs_entry { 110struct elv_fs_entry {
@@ -96,12 +124,14 @@ struct elevator_type
96 /* fields provided by elevator implementation */ 124 /* fields provided by elevator implementation */
97 union { 125 union {
98 struct elevator_ops sq; 126 struct elevator_ops sq;
127 struct elevator_mq_ops mq;
99 } ops; 128 } ops;
100 size_t icq_size; /* see iocontext.h */ 129 size_t icq_size; /* see iocontext.h */
101 size_t icq_align; /* ditto */ 130 size_t icq_align; /* ditto */
102 struct elv_fs_entry *elevator_attrs; 131 struct elv_fs_entry *elevator_attrs;
103 char elevator_name[ELV_NAME_MAX]; 132 char elevator_name[ELV_NAME_MAX];
104 struct module *elevator_owner; 133 struct module *elevator_owner;
134 bool uses_mq;
105 135
106 /* managed by elevator core */ 136 /* managed by elevator core */
107 char icq_cache_name[ELV_NAME_MAX + 5]; /* elvname + "_io_cq" */ 137 char icq_cache_name[ELV_NAME_MAX + 5]; /* elvname + "_io_cq" */
@@ -125,6 +155,7 @@ struct elevator_queue
125 struct kobject kobj; 155 struct kobject kobj;
126 struct mutex sysfs_lock; 156 struct mutex sysfs_lock;
127 unsigned int registered:1; 157 unsigned int registered:1;
158 unsigned int uses_mq:1;
128 DECLARE_HASHTABLE(hash, ELV_HASH_BITS); 159 DECLARE_HASHTABLE(hash, ELV_HASH_BITS);
129}; 160};
130 161
@@ -141,6 +172,7 @@ extern void elv_merge_requests(struct request_queue *, struct request *,
141extern void elv_merged_request(struct request_queue *, struct request *, int); 172extern void elv_merged_request(struct request_queue *, struct request *, int);
142extern void elv_bio_merged(struct request_queue *q, struct request *, 173extern void elv_bio_merged(struct request_queue *q, struct request *,
143 struct bio *); 174 struct bio *);
175extern bool elv_attempt_insert_merge(struct request_queue *, struct request *);
144extern void elv_requeue_request(struct request_queue *, struct request *); 176extern void elv_requeue_request(struct request_queue *, struct request *);
145extern struct request *elv_former_request(struct request_queue *, struct request *); 177extern struct request *elv_former_request(struct request_queue *, struct request *);
146extern struct request *elv_latter_request(struct request_queue *, struct request *); 178extern struct request *elv_latter_request(struct request_queue *, struct request *);