Blame view

block/blk-mq-debugfs.c 24.4 KB
8c16567d8   Christoph Hellwig   block: switch all...
1
  // SPDX-License-Identifier: GPL-2.0
07e4fead4   Omar Sandoval   blk-mq: create de...
2
3
  /*
   * Copyright (C) 2017 Facebook
07e4fead4   Omar Sandoval   blk-mq: create de...
4
5
6
7
8
9
10
   */
  
  #include <linux/kernel.h>
  #include <linux/blkdev.h>
  #include <linux/debugfs.h>
  
  #include <linux/blk-mq.h>
18fbda91c   Omar Sandoval   block: use same b...
11
  #include "blk.h"
07e4fead4   Omar Sandoval   blk-mq: create de...
12
  #include "blk-mq.h"
d173a2516   Omar Sandoval   blk-mq: move debu...
13
  #include "blk-mq-debugfs.h"
d96b37c0a   Omar Sandoval   blk-mq: move tags...
14
  #include "blk-mq-tag.h"
cc56694f1   Ming Lei   blk-mq-debugfs: s...
15
  #include "blk-rq-qos.h"
07e4fead4   Omar Sandoval   blk-mq: create de...
16

1209cb7fa   Bart Van Assche   blk-mq-debugfs: R...
17
18
19
  static void print_stat(struct seq_file *m, struct blk_rq_stat *stat)
  {
  	if (stat->nr_samples) {
315eb6566   Pavel Begunkov   blk-mq/debugfs: F...
20
  		seq_printf(m, "samples=%d, mean=%llu, min=%llu, max=%llu",
1209cb7fa   Bart Van Assche   blk-mq-debugfs: R...
21
22
23
24
25
26
27
28
29
30
  			   stat->nr_samples, stat->mean, stat->min, stat->max);
  	} else {
  		seq_puts(m, "samples=0");
  	}
  }
  
  static int queue_poll_stat_show(void *data, struct seq_file *m)
  {
  	struct request_queue *q = data;
  	int bucket;
243d9f78d   Chaitanya Kulkarni   block: code clean...
31
32
33
  	for (bucket = 0; bucket < (BLK_MQ_POLL_STATS_BKTS / 2); bucket++) {
  		seq_printf(m, "read  (%d Bytes): ", 1 << (9 + bucket));
  		print_stat(m, &q->poll_stat[2 * bucket]);
1209cb7fa   Bart Van Assche   blk-mq-debugfs: R...
34
35
  		seq_puts(m, "
  ");
243d9f78d   Chaitanya Kulkarni   block: code clean...
36
37
  		seq_printf(m, "write (%d Bytes): ",  1 << (9 + bucket));
  		print_stat(m, &q->poll_stat[2 * bucket + 1]);
1209cb7fa   Bart Van Assche   blk-mq-debugfs: R...
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
  		seq_puts(m, "
  ");
  	}
  	return 0;
  }
  
  static void *queue_requeue_list_start(struct seq_file *m, loff_t *pos)
  	__acquires(&q->requeue_lock)
  {
  	struct request_queue *q = m->private;
  
  	spin_lock_irq(&q->requeue_lock);
  	return seq_list_start(&q->requeue_list, *pos);
  }
  
  static void *queue_requeue_list_next(struct seq_file *m, void *v, loff_t *pos)
  {
  	struct request_queue *q = m->private;
  
  	return seq_list_next(v, &q->requeue_list, pos);
  }
  
  static void queue_requeue_list_stop(struct seq_file *m, void *v)
  	__releases(&q->requeue_lock)
  {
  	struct request_queue *q = m->private;
  
  	spin_unlock_irq(&q->requeue_lock);
  }
  
  static const struct seq_operations queue_requeue_list_seq_ops = {
  	.start	= queue_requeue_list_start,
  	.next	= queue_requeue_list_next,
  	.stop	= queue_requeue_list_stop,
  	.show	= blk_mq_debugfs_rq_show,
  };
91d68905a   Bart Van Assche   blk-mq: Export qu...
74
75
76
77
78
79
80
81
82
83
  static int blk_flags_show(struct seq_file *m, const unsigned long flags,
  			  const char *const *flag_name, int flag_name_count)
  {
  	bool sep = false;
  	int i;
  
  	for (i = 0; i < sizeof(flags) * BITS_PER_BYTE; i++) {
  		if (!(flags & BIT(i)))
  			continue;
  		if (sep)
bec03d6b9   Omar Sandoval   blk-mq-debugfs: s...
84
  			seq_puts(m, "|");
91d68905a   Bart Van Assche   blk-mq: Export qu...
85
86
87
88
89
90
  		sep = true;
  		if (i < flag_name_count && flag_name[i])
  			seq_puts(m, flag_name[i]);
  		else
  			seq_printf(m, "%d", i);
  	}
91d68905a   Bart Van Assche   blk-mq: Export qu...
91
92
  	return 0;
  }
cd84a62e0   Bart Van Assche   block, scsi: Chan...
93
94
95
96
97
98
99
100
  static int queue_pm_only_show(void *data, struct seq_file *m)
  {
  	struct request_queue *q = data;
  
  	seq_printf(m, "%d
  ", atomic_read(&q->pm_only));
  	return 0;
  }
1a435111f   Omar Sandoval   blk-mq-debugfs: c...
101
  #define QUEUE_FLAG_NAME(name) [QUEUE_FLAG_##name] = #name
91d68905a   Bart Van Assche   blk-mq: Export qu...
102
  static const char *const blk_queue_flag_name[] = {
1a435111f   Omar Sandoval   blk-mq-debugfs: c...
103
  	QUEUE_FLAG_NAME(STOPPED),
1a435111f   Omar Sandoval   blk-mq-debugfs: c...
104
  	QUEUE_FLAG_NAME(DYING),
1a435111f   Omar Sandoval   blk-mq-debugfs: c...
105
106
107
  	QUEUE_FLAG_NAME(NOMERGES),
  	QUEUE_FLAG_NAME(SAME_COMP),
  	QUEUE_FLAG_NAME(FAIL_IO),
1a435111f   Omar Sandoval   blk-mq-debugfs: c...
108
109
110
111
112
113
114
115
116
  	QUEUE_FLAG_NAME(NONROT),
  	QUEUE_FLAG_NAME(IO_STAT),
  	QUEUE_FLAG_NAME(DISCARD),
  	QUEUE_FLAG_NAME(NOXMERGES),
  	QUEUE_FLAG_NAME(ADD_RANDOM),
  	QUEUE_FLAG_NAME(SECERASE),
  	QUEUE_FLAG_NAME(SAME_FORCE),
  	QUEUE_FLAG_NAME(DEAD),
  	QUEUE_FLAG_NAME(INIT_DONE),
1cb039f3d   Christoph Hellwig   bdi: replace BDI_...
117
  	QUEUE_FLAG_NAME(STABLE_WRITES),
1a435111f   Omar Sandoval   blk-mq-debugfs: c...
118
119
120
  	QUEUE_FLAG_NAME(POLL),
  	QUEUE_FLAG_NAME(WC),
  	QUEUE_FLAG_NAME(FUA),
1a435111f   Omar Sandoval   blk-mq-debugfs: c...
121
122
123
124
  	QUEUE_FLAG_NAME(DAX),
  	QUEUE_FLAG_NAME(STATS),
  	QUEUE_FLAG_NAME(POLL_STATS),
  	QUEUE_FLAG_NAME(REGISTERED),
22d538213   Bart Van Assche   blk-mq-debugfs: A...
125
126
  	QUEUE_FLAG_NAME(SCSI_PASSTHROUGH),
  	QUEUE_FLAG_NAME(QUIESCED),
bfe373f60   Hou Tao   blk-mq-debugfs: u...
127
128
129
  	QUEUE_FLAG_NAME(PCI_P2PDMA),
  	QUEUE_FLAG_NAME(ZONE_RESETALL),
  	QUEUE_FLAG_NAME(RQ_ALLOC_TIME),
bfb39e6d6   Andres Freund   block: add debugf...
130
  	QUEUE_FLAG_NAME(NOWAIT),
91d68905a   Bart Van Assche   blk-mq: Export qu...
131
  };
1a435111f   Omar Sandoval   blk-mq-debugfs: c...
132
  #undef QUEUE_FLAG_NAME
91d68905a   Bart Van Assche   blk-mq: Export qu...
133

f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
134
  static int queue_state_show(void *data, struct seq_file *m)
91d68905a   Bart Van Assche   blk-mq: Export qu...
135
  {
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
136
  	struct request_queue *q = data;
91d68905a   Bart Van Assche   blk-mq: Export qu...
137
138
139
  
  	blk_flags_show(m, q->queue_flags, blk_queue_flag_name,
  		       ARRAY_SIZE(blk_queue_flag_name));
fd07dc818   Bart Van Assche   blk-mq: Make blk_...
140
141
  	seq_puts(m, "
  ");
91d68905a   Bart Van Assche   blk-mq: Export qu...
142
143
  	return 0;
  }
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
144
145
  static ssize_t queue_state_write(void *data, const char __user *buf,
  				 size_t count, loff_t *ppos)
91d68905a   Bart Van Assche   blk-mq: Export qu...
146
  {
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
147
  	struct request_queue *q = data;
71b90511c   Omar Sandoval   blk-mq-debugfs: d...
148
  	char opbuf[16] = { }, *op;
91d68905a   Bart Van Assche   blk-mq: Export qu...
149

18d4d7d05   Bart Van Assche   blk-mq: Do not in...
150
151
152
153
154
155
156
  	/*
  	 * The "state" attribute is removed after blk_cleanup_queue() has called
  	 * blk_mq_free_queue(). Return if QUEUE_FLAG_DEAD has been set to avoid
  	 * triggering a use-after-free.
  	 */
  	if (blk_queue_dead(q))
  		return -ENOENT;
71b90511c   Omar Sandoval   blk-mq-debugfs: d...
157
  	if (count >= sizeof(opbuf)) {
c7e4145ae   Omar Sandoval   blk-mq-debugfs: e...
158
159
160
161
  		pr_err("%s: operation too long
  ", __func__);
  		goto inval;
  	}
71b90511c   Omar Sandoval   blk-mq-debugfs: d...
162
  	if (copy_from_user(opbuf, buf, count))
91d68905a   Bart Van Assche   blk-mq: Export qu...
163
  		return -EFAULT;
71b90511c   Omar Sandoval   blk-mq-debugfs: d...
164
  	op = strstrip(opbuf);
91d68905a   Bart Van Assche   blk-mq: Export qu...
165
166
167
168
  	if (strcmp(op, "run") == 0) {
  		blk_mq_run_hw_queues(q, true);
  	} else if (strcmp(op, "start") == 0) {
  		blk_mq_start_stopped_hw_queues(q, true);
edea55abb   Bart Van Assche   blk-mq-debugfs: A...
169
170
  	} else if (strcmp(op, "kick") == 0) {
  		blk_mq_kick_requeue_list(q);
91d68905a   Bart Van Assche   blk-mq: Export qu...
171
  	} else {
c7e4145ae   Omar Sandoval   blk-mq-debugfs: e...
172
173
174
  		pr_err("%s: unsupported operation '%s'
  ", __func__, op);
  inval:
edea55abb   Bart Van Assche   blk-mq-debugfs: A...
175
176
  		pr_err("%s: use 'run', 'start' or 'kick'
  ", __func__);
91d68905a   Bart Van Assche   blk-mq: Export qu...
177
178
  		return -EINVAL;
  	}
c7e4145ae   Omar Sandoval   blk-mq-debugfs: e...
179
  	return count;
91d68905a   Bart Van Assche   blk-mq: Export qu...
180
  }
f793dfd3f   Jens Axboe   blk-mq: expose wr...
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
  static int queue_write_hint_show(void *data, struct seq_file *m)
  {
  	struct request_queue *q = data;
  	int i;
  
  	for (i = 0; i < BLK_MAX_WRITE_HINTS; i++)
  		seq_printf(m, "hint%d: %llu
  ", i, q->write_hints[i]);
  
  	return 0;
  }
  
  static ssize_t queue_write_hint_store(void *data, const char __user *buf,
  				      size_t count, loff_t *ppos)
  {
  	struct request_queue *q = data;
  	int i;
  
  	for (i = 0; i < BLK_MAX_WRITE_HINTS; i++)
  		q->write_hints[i] = 0;
  
  	return count;
  }
1209cb7fa   Bart Van Assche   blk-mq-debugfs: R...
204
205
206
  static const struct blk_mq_debugfs_attr blk_mq_debugfs_queue_attrs[] = {
  	{ "poll_stat", 0400, queue_poll_stat_show },
  	{ "requeue_list", 0400, .seq_ops = &queue_requeue_list_seq_ops },
cd84a62e0   Bart Van Assche   block, scsi: Chan...
207
  	{ "pm_only", 0600, queue_pm_only_show, NULL },
1209cb7fa   Bart Van Assche   blk-mq-debugfs: R...
208
209
  	{ "state", 0600, queue_state_show, queue_state_write },
  	{ "write_hints", 0600, queue_write_hint_show, queue_write_hint_store },
18bc42308   Bart Van Assche   blk-mq-debugfs: S...
210
  	{ "zone_wlock", 0400, queue_zone_wlock_show, NULL },
1209cb7fa   Bart Van Assche   blk-mq-debugfs: R...
211
212
  	{ },
  };
34dbad5d2   Omar Sandoval   blk-stat: convert...
213

1a435111f   Omar Sandoval   blk-mq-debugfs: c...
214
  #define HCTX_STATE_NAME(name) [BLK_MQ_S_##name] = #name
f5c0b0910   Bart Van Assche   blk-mq: Show symb...
215
  static const char *const hctx_state_name[] = {
1a435111f   Omar Sandoval   blk-mq-debugfs: c...
216
217
218
  	HCTX_STATE_NAME(STOPPED),
  	HCTX_STATE_NAME(TAG_ACTIVE),
  	HCTX_STATE_NAME(SCHED_RESTART),
bf0beec06   Ming Lei   blk-mq: drain I/O...
219
  	HCTX_STATE_NAME(INACTIVE),
f5c0b0910   Bart Van Assche   blk-mq: Show symb...
220
  };
1a435111f   Omar Sandoval   blk-mq-debugfs: c...
221
  #undef HCTX_STATE_NAME
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
222
  static int hctx_state_show(void *data, struct seq_file *m)
9abb2ad21   Omar Sandoval   blk-mq: add hctx-...
223
  {
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
224
  	struct blk_mq_hw_ctx *hctx = data;
9abb2ad21   Omar Sandoval   blk-mq: add hctx-...
225

f5c0b0910   Bart Van Assche   blk-mq: Show symb...
226
227
  	blk_flags_show(m, hctx->state, hctx_state_name,
  		       ARRAY_SIZE(hctx_state_name));
fd07dc818   Bart Van Assche   blk-mq: Make blk_...
228
229
  	seq_puts(m, "
  ");
9abb2ad21   Omar Sandoval   blk-mq: add hctx-...
230
231
  	return 0;
  }
1a435111f   Omar Sandoval   blk-mq-debugfs: c...
232
  #define BLK_TAG_ALLOC_NAME(name) [BLK_TAG_ALLOC_##name] = #name
f5c0b0910   Bart Van Assche   blk-mq: Show symb...
233
  static const char *const alloc_policy_name[] = {
1a435111f   Omar Sandoval   blk-mq-debugfs: c...
234
235
  	BLK_TAG_ALLOC_NAME(FIFO),
  	BLK_TAG_ALLOC_NAME(RR),
f5c0b0910   Bart Van Assche   blk-mq: Show symb...
236
  };
1a435111f   Omar Sandoval   blk-mq-debugfs: c...
237
  #undef BLK_TAG_ALLOC_NAME
f5c0b0910   Bart Van Assche   blk-mq: Show symb...
238

1a435111f   Omar Sandoval   blk-mq-debugfs: c...
239
  #define HCTX_FLAG_NAME(name) [ilog2(BLK_MQ_F_##name)] = #name
f5c0b0910   Bart Van Assche   blk-mq: Show symb...
240
  static const char *const hctx_flag_name[] = {
1a435111f   Omar Sandoval   blk-mq-debugfs: c...
241
  	HCTX_FLAG_NAME(SHOULD_MERGE),
51db1c37e   Ming Lei   blk-mq: Rename BL...
242
  	HCTX_FLAG_NAME(TAG_QUEUE_SHARED),
1a435111f   Omar Sandoval   blk-mq-debugfs: c...
243
244
  	HCTX_FLAG_NAME(BLOCKING),
  	HCTX_FLAG_NAME(NO_SCHED),
bf0beec06   Ming Lei   blk-mq: drain I/O...
245
  	HCTX_FLAG_NAME(STACKING),
847c76518   John Garry   blk-mq-debugfs: A...
246
  	HCTX_FLAG_NAME(TAG_HCTX_SHARED),
f5c0b0910   Bart Van Assche   blk-mq: Show symb...
247
  };
1a435111f   Omar Sandoval   blk-mq-debugfs: c...
248
  #undef HCTX_FLAG_NAME
f5c0b0910   Bart Van Assche   blk-mq: Show symb...
249

f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
250
  static int hctx_flags_show(void *data, struct seq_file *m)
9abb2ad21   Omar Sandoval   blk-mq: add hctx-...
251
  {
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
252
  	struct blk_mq_hw_ctx *hctx = data;
f5c0b0910   Bart Van Assche   blk-mq: Show symb...
253
  	const int alloc_policy = BLK_MQ_FLAG_TO_ALLOC_POLICY(hctx->flags);
9abb2ad21   Omar Sandoval   blk-mq: add hctx-...
254

f5c0b0910   Bart Van Assche   blk-mq: Show symb...
255
256
257
258
259
260
261
262
263
264
  	seq_puts(m, "alloc_policy=");
  	if (alloc_policy < ARRAY_SIZE(alloc_policy_name) &&
  	    alloc_policy_name[alloc_policy])
  		seq_puts(m, alloc_policy_name[alloc_policy]);
  	else
  		seq_printf(m, "%d", alloc_policy);
  	seq_puts(m, " ");
  	blk_flags_show(m,
  		       hctx->flags ^ BLK_ALLOC_POLICY_TO_MQ_FLAG(alloc_policy),
  		       hctx_flag_name, ARRAY_SIZE(hctx_flag_name));
fd07dc818   Bart Van Assche   blk-mq: Make blk_...
265
266
  	seq_puts(m, "
  ");
9abb2ad21   Omar Sandoval   blk-mq: add hctx-...
267
268
  	return 0;
  }
1a435111f   Omar Sandoval   blk-mq-debugfs: c...
269
  #define CMD_FLAG_NAME(name) [__REQ_##name] = #name
8658dca8b   Bart Van Assche   blk-mq: Show oper...
270
  static const char *const cmd_flag_name[] = {
1a435111f   Omar Sandoval   blk-mq-debugfs: c...
271
272
273
274
275
276
277
278
279
280
281
282
283
  	CMD_FLAG_NAME(FAILFAST_DEV),
  	CMD_FLAG_NAME(FAILFAST_TRANSPORT),
  	CMD_FLAG_NAME(FAILFAST_DRIVER),
  	CMD_FLAG_NAME(SYNC),
  	CMD_FLAG_NAME(META),
  	CMD_FLAG_NAME(PRIO),
  	CMD_FLAG_NAME(NOMERGE),
  	CMD_FLAG_NAME(IDLE),
  	CMD_FLAG_NAME(INTEGRITY),
  	CMD_FLAG_NAME(FUA),
  	CMD_FLAG_NAME(PREFLUSH),
  	CMD_FLAG_NAME(RAHEAD),
  	CMD_FLAG_NAME(BACKGROUND),
22d538213   Bart Van Assche   blk-mq-debugfs: A...
284
  	CMD_FLAG_NAME(NOWAIT),
1c26010c5   Jianchao Wang   blk-mq: fix the c...
285
286
  	CMD_FLAG_NAME(NOUNMAP),
  	CMD_FLAG_NAME(HIPRI),
8658dca8b   Bart Van Assche   blk-mq: Show oper...
287
  };
1a435111f   Omar Sandoval   blk-mq-debugfs: c...
288
  #undef CMD_FLAG_NAME
8658dca8b   Bart Van Assche   blk-mq: Show oper...
289

1a435111f   Omar Sandoval   blk-mq-debugfs: c...
290
  #define RQF_NAME(name) [ilog2((__force u32)RQF_##name)] = #name
8658dca8b   Bart Van Assche   blk-mq: Show oper...
291
  static const char *const rqf_name[] = {
1a435111f   Omar Sandoval   blk-mq-debugfs: c...
292
  	RQF_NAME(SORTED),
85ba3effc   Jens Axboe   blk-mq: add missi...
293
  	RQF_NAME(STARTED),
1a435111f   Omar Sandoval   blk-mq-debugfs: c...
294
295
296
297
298
  	RQF_NAME(SOFTBARRIER),
  	RQF_NAME(FLUSH_SEQ),
  	RQF_NAME(MIXED_MERGE),
  	RQF_NAME(MQ_INFLIGHT),
  	RQF_NAME(DONTPREP),
1a435111f   Omar Sandoval   blk-mq-debugfs: c...
299
300
301
302
303
304
305
306
307
  	RQF_NAME(FAILED),
  	RQF_NAME(QUIET),
  	RQF_NAME(ELVPRIV),
  	RQF_NAME(IO_STAT),
  	RQF_NAME(ALLOCED),
  	RQF_NAME(PM),
  	RQF_NAME(HASHED),
  	RQF_NAME(STATS),
  	RQF_NAME(SPECIAL_PAYLOAD),
5d75d3f2e   Jens Axboe   blk-mq: add a few...
308
  	RQF_NAME(ZONE_WRITE_LOCKED),
76a86f9d0   Jens Axboe   block: remove REQ...
309
  	RQF_NAME(MQ_POLL_SLEPT),
8658dca8b   Bart Van Assche   blk-mq: Show oper...
310
  };
1a435111f   Omar Sandoval   blk-mq-debugfs: c...
311
  #undef RQF_NAME
8658dca8b   Bart Van Assche   blk-mq: Show oper...
312

ec6dcf63c   Bart Van Assche   blk-mq-debugfs: S...
313
314
315
316
317
318
319
320
  static const char *const blk_mq_rq_state_name_array[] = {
  	[MQ_RQ_IDLE]		= "idle",
  	[MQ_RQ_IN_FLIGHT]	= "in_flight",
  	[MQ_RQ_COMPLETE]	= "complete",
  };
  
  static const char *blk_mq_rq_state_name(enum mq_rq_state rq_state)
  {
a1e791886   Dan Carpenter   blk-mq-debugfs: O...
321
  	if (WARN_ON_ONCE((unsigned int)rq_state >=
ec6dcf63c   Bart Van Assche   blk-mq-debugfs: S...
322
323
324
325
  			 ARRAY_SIZE(blk_mq_rq_state_name_array)))
  		return "(?)";
  	return blk_mq_rq_state_name_array[rq_state];
  }
daaadb3e9   Omar Sandoval   mq-deadline: add ...
326
  int __blk_mq_debugfs_rq_show(struct seq_file *m, struct request *rq)
950cd7e9f   Omar Sandoval   blk-mq: move hctx...
327
  {
2836ee4b1   Bart Van Assche   blk-mq: Add blk_m...
328
  	const struct blk_mq_ops *const mq_ops = rq->q->mq_ops;
f9bc64a0f   Chaitanya Kulkarni   block: use req_op...
329
  	const unsigned int op = req_op(rq);
874c893bf   Chaitanya Kulkarni   block: use blk_op...
330
  	const char *op_str = blk_op_str(op);
950cd7e9f   Omar Sandoval   blk-mq: move hctx...
331

8658dca8b   Bart Van Assche   blk-mq: Show oper...
332
  	seq_printf(m, "%p {.op=", rq);
874c893bf   Chaitanya Kulkarni   block: use blk_op...
333
  	if (strcmp(op_str, "UNKNOWN") == 0)
3f6d385f8   Chaitanya Kulkarni   block: use right ...
334
  		seq_printf(m, "%u", op);
8658dca8b   Bart Van Assche   blk-mq: Show oper...
335
  	else
874c893bf   Chaitanya Kulkarni   block: use blk_op...
336
  		seq_printf(m, "%s", op_str);
8658dca8b   Bart Van Assche   blk-mq: Show oper...
337
338
339
340
341
342
  	seq_puts(m, ", .cmd_flags=");
  	blk_flags_show(m, rq->cmd_flags & ~REQ_OP_MASK, cmd_flag_name,
  		       ARRAY_SIZE(cmd_flag_name));
  	seq_puts(m, ", .rq_flags=");
  	blk_flags_show(m, (__force unsigned int)rq->rq_flags, rqf_name,
  		       ARRAY_SIZE(rqf_name));
ec6dcf63c   Bart Van Assche   blk-mq-debugfs: S...
343
  	seq_printf(m, ", .state=%s", blk_mq_rq_state_name(blk_mq_rq_state(rq)));
2836ee4b1   Bart Van Assche   blk-mq: Add blk_m...
344
  	seq_printf(m, ", .tag=%d, .internal_tag=%d", rq->tag,
8658dca8b   Bart Van Assche   blk-mq: Show oper...
345
  		   rq->internal_tag);
2836ee4b1   Bart Van Assche   blk-mq: Add blk_m...
346
347
348
349
  	if (mq_ops->show_rq)
  		mq_ops->show_rq(m, rq);
  	seq_puts(m, "}
  ");
950cd7e9f   Omar Sandoval   blk-mq: move hctx...
350
351
  	return 0;
  }
daaadb3e9   Omar Sandoval   mq-deadline: add ...
352
353
354
355
356
357
  EXPORT_SYMBOL_GPL(__blk_mq_debugfs_rq_show);
  
  int blk_mq_debugfs_rq_show(struct seq_file *m, void *v)
  {
  	return __blk_mq_debugfs_rq_show(m, list_entry_rq(v));
  }
16b738f65   Omar Sandoval   kyber: add debugf...
358
  EXPORT_SYMBOL_GPL(blk_mq_debugfs_rq_show);
950cd7e9f   Omar Sandoval   blk-mq: move hctx...
359
360
  
  static void *hctx_dispatch_start(struct seq_file *m, loff_t *pos)
f3bcb0e60   Bart Van Assche   blk-mq-debugfs: A...
361
  	__acquires(&hctx->lock)
950cd7e9f   Omar Sandoval   blk-mq: move hctx...
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
  {
  	struct blk_mq_hw_ctx *hctx = m->private;
  
  	spin_lock(&hctx->lock);
  	return seq_list_start(&hctx->dispatch, *pos);
  }
  
  static void *hctx_dispatch_next(struct seq_file *m, void *v, loff_t *pos)
  {
  	struct blk_mq_hw_ctx *hctx = m->private;
  
  	return seq_list_next(v, &hctx->dispatch, pos);
  }
  
  static void hctx_dispatch_stop(struct seq_file *m, void *v)
f3bcb0e60   Bart Van Assche   blk-mq-debugfs: A...
377
  	__releases(&hctx->lock)
950cd7e9f   Omar Sandoval   blk-mq: move hctx...
378
379
380
381
382
383
384
385
386
387
388
389
  {
  	struct blk_mq_hw_ctx *hctx = m->private;
  
  	spin_unlock(&hctx->lock);
  }
  
  static const struct seq_operations hctx_dispatch_seq_ops = {
  	.start	= hctx_dispatch_start,
  	.next	= hctx_dispatch_next,
  	.stop	= hctx_dispatch_stop,
  	.show	= blk_mq_debugfs_rq_show,
  };
2720bab50   Bart Van Assche   blk-mq-debugfs: S...
390
391
392
393
394
395
396
  struct show_busy_params {
  	struct seq_file		*m;
  	struct blk_mq_hw_ctx	*hctx;
  };
  
  /*
   * Note: the state of a request may change while this function is in progress,
7baa85727   Jens Axboe   blk-mq-tag: chang...
397
398
   * e.g. due to a concurrent blk_mq_finish_request() call. Returns true to
   * keep iterating requests.
2720bab50   Bart Van Assche   blk-mq-debugfs: S...
399
   */
7baa85727   Jens Axboe   blk-mq-tag: chang...
400
  static bool hctx_show_busy_rq(struct request *rq, void *data, bool reserved)
2720bab50   Bart Van Assche   blk-mq-debugfs: S...
401
402
  {
  	const struct show_busy_params *params = data;
ea4f995ee   Jens Axboe   blk-mq: cache req...
403
  	if (rq->mq_hctx == params->hctx)
b5fc1e8be   Hou Tao   blk-mq: remove po...
404
  		__blk_mq_debugfs_rq_show(params->m, rq);
7baa85727   Jens Axboe   blk-mq-tag: chang...
405
406
  
  	return true;
2720bab50   Bart Van Assche   blk-mq-debugfs: S...
407
408
409
410
411
412
413
414
415
416
417
418
  }
  
  static int hctx_busy_show(void *data, struct seq_file *m)
  {
  	struct blk_mq_hw_ctx *hctx = data;
  	struct show_busy_params params = { .m = m, .hctx = hctx };
  
  	blk_mq_tagset_busy_iter(hctx->queue->tag_set, hctx_show_busy_rq,
  				&params);
  
  	return 0;
  }
346fc1089   Ming Lei   blk-mq: export hc...
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
  static const char *const hctx_types[] = {
  	[HCTX_TYPE_DEFAULT]	= "default",
  	[HCTX_TYPE_READ]	= "read",
  	[HCTX_TYPE_POLL]	= "poll",
  };
  
  static int hctx_type_show(void *data, struct seq_file *m)
  {
  	struct blk_mq_hw_ctx *hctx = data;
  
  	BUILD_BUG_ON(ARRAY_SIZE(hctx_types) != HCTX_MAX_TYPES);
  	seq_printf(m, "%s
  ", hctx_types[hctx->type]);
  	return 0;
  }
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
434
  static int hctx_ctx_map_show(void *data, struct seq_file *m)
0bfa5288a   Omar Sandoval   blk-mq: export so...
435
  {
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
436
  	struct blk_mq_hw_ctx *hctx = data;
0bfa5288a   Omar Sandoval   blk-mq: export so...
437
438
439
440
  
  	sbitmap_bitmap_show(&hctx->ctx_map, m);
  	return 0;
  }
d96b37c0a   Omar Sandoval   blk-mq: move tags...
441
442
443
444
445
446
447
448
449
450
451
452
453
454
  static void blk_mq_debugfs_tags_show(struct seq_file *m,
  				     struct blk_mq_tags *tags)
  {
  	seq_printf(m, "nr_tags=%u
  ", tags->nr_tags);
  	seq_printf(m, "nr_reserved_tags=%u
  ", tags->nr_reserved_tags);
  	seq_printf(m, "active_queues=%d
  ",
  		   atomic_read(&tags->active_queues));
  
  	seq_puts(m, "
  bitmap_tags:
  ");
222a5ae03   John Garry   blk-mq: Use point...
455
  	sbitmap_queue_show(tags->bitmap_tags, m);
d96b37c0a   Omar Sandoval   blk-mq: move tags...
456
457
458
459
460
  
  	if (tags->nr_reserved_tags) {
  		seq_puts(m, "
  breserved_tags:
  ");
222a5ae03   John Garry   blk-mq: Use point...
461
  		sbitmap_queue_show(tags->breserved_tags, m);
d96b37c0a   Omar Sandoval   blk-mq: move tags...
462
463
  	}
  }
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
464
  static int hctx_tags_show(void *data, struct seq_file *m)
d96b37c0a   Omar Sandoval   blk-mq: move tags...
465
  {
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
466
  	struct blk_mq_hw_ctx *hctx = data;
d96b37c0a   Omar Sandoval   blk-mq: move tags...
467
  	struct request_queue *q = hctx->queue;
8c0f14eab   Bart Van Assche   blk-mq-debug: Mak...
468
  	int res;
d96b37c0a   Omar Sandoval   blk-mq: move tags...
469

8c0f14eab   Bart Van Assche   blk-mq-debug: Mak...
470
471
472
  	res = mutex_lock_interruptible(&q->sysfs_lock);
  	if (res)
  		goto out;
d96b37c0a   Omar Sandoval   blk-mq: move tags...
473
474
475
  	if (hctx->tags)
  		blk_mq_debugfs_tags_show(m, hctx->tags);
  	mutex_unlock(&q->sysfs_lock);
8c0f14eab   Bart Van Assche   blk-mq-debug: Mak...
476
477
  out:
  	return res;
d96b37c0a   Omar Sandoval   blk-mq: move tags...
478
  }
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
479
  static int hctx_tags_bitmap_show(void *data, struct seq_file *m)
d7e3621ad   Omar Sandoval   blk-mq: add tags ...
480
  {
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
481
  	struct blk_mq_hw_ctx *hctx = data;
d7e3621ad   Omar Sandoval   blk-mq: add tags ...
482
  	struct request_queue *q = hctx->queue;
8c0f14eab   Bart Van Assche   blk-mq-debug: Mak...
483
  	int res;
d7e3621ad   Omar Sandoval   blk-mq: add tags ...
484

8c0f14eab   Bart Van Assche   blk-mq-debug: Mak...
485
486
487
  	res = mutex_lock_interruptible(&q->sysfs_lock);
  	if (res)
  		goto out;
d7e3621ad   Omar Sandoval   blk-mq: add tags ...
488
  	if (hctx->tags)
222a5ae03   John Garry   blk-mq: Use point...
489
  		sbitmap_bitmap_show(&hctx->tags->bitmap_tags->sb, m);
d7e3621ad   Omar Sandoval   blk-mq: add tags ...
490
  	mutex_unlock(&q->sysfs_lock);
8c0f14eab   Bart Van Assche   blk-mq-debug: Mak...
491
492
493
  
  out:
  	return res;
d7e3621ad   Omar Sandoval   blk-mq: add tags ...
494
  }
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
495
  static int hctx_sched_tags_show(void *data, struct seq_file *m)
d96b37c0a   Omar Sandoval   blk-mq: move tags...
496
  {
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
497
  	struct blk_mq_hw_ctx *hctx = data;
d96b37c0a   Omar Sandoval   blk-mq: move tags...
498
  	struct request_queue *q = hctx->queue;
8c0f14eab   Bart Van Assche   blk-mq-debug: Mak...
499
  	int res;
d96b37c0a   Omar Sandoval   blk-mq: move tags...
500

8c0f14eab   Bart Van Assche   blk-mq-debug: Mak...
501
502
503
  	res = mutex_lock_interruptible(&q->sysfs_lock);
  	if (res)
  		goto out;
d96b37c0a   Omar Sandoval   blk-mq: move tags...
504
505
506
  	if (hctx->sched_tags)
  		blk_mq_debugfs_tags_show(m, hctx->sched_tags);
  	mutex_unlock(&q->sysfs_lock);
8c0f14eab   Bart Van Assche   blk-mq-debug: Mak...
507
508
  out:
  	return res;
d96b37c0a   Omar Sandoval   blk-mq: move tags...
509
  }
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
510
  static int hctx_sched_tags_bitmap_show(void *data, struct seq_file *m)
d7e3621ad   Omar Sandoval   blk-mq: add tags ...
511
  {
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
512
  	struct blk_mq_hw_ctx *hctx = data;
d7e3621ad   Omar Sandoval   blk-mq: add tags ...
513
  	struct request_queue *q = hctx->queue;
8c0f14eab   Bart Van Assche   blk-mq-debug: Mak...
514
  	int res;
d7e3621ad   Omar Sandoval   blk-mq: add tags ...
515

8c0f14eab   Bart Van Assche   blk-mq-debug: Mak...
516
517
518
  	res = mutex_lock_interruptible(&q->sysfs_lock);
  	if (res)
  		goto out;
d7e3621ad   Omar Sandoval   blk-mq: add tags ...
519
  	if (hctx->sched_tags)
222a5ae03   John Garry   blk-mq: Use point...
520
  		sbitmap_bitmap_show(&hctx->sched_tags->bitmap_tags->sb, m);
d7e3621ad   Omar Sandoval   blk-mq: add tags ...
521
  	mutex_unlock(&q->sysfs_lock);
8c0f14eab   Bart Van Assche   blk-mq-debug: Mak...
522
523
524
  
  out:
  	return res;
d7e3621ad   Omar Sandoval   blk-mq: add tags ...
525
  }
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
526
  static int hctx_io_poll_show(void *data, struct seq_file *m)
be2154731   Omar Sandoval   blk-mq: move hctx...
527
  {
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
528
  	struct blk_mq_hw_ctx *hctx = data;
be2154731   Omar Sandoval   blk-mq: move hctx...
529
530
531
532
533
534
535
536
537
  
  	seq_printf(m, "considered=%lu
  ", hctx->poll_considered);
  	seq_printf(m, "invoked=%lu
  ", hctx->poll_invoked);
  	seq_printf(m, "success=%lu
  ", hctx->poll_success);
  	return 0;
  }
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
538
  static ssize_t hctx_io_poll_write(void *data, const char __user *buf,
be2154731   Omar Sandoval   blk-mq: move hctx...
539
540
  				  size_t count, loff_t *ppos)
  {
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
541
  	struct blk_mq_hw_ctx *hctx = data;
be2154731   Omar Sandoval   blk-mq: move hctx...
542
543
544
545
  
  	hctx->poll_considered = hctx->poll_invoked = hctx->poll_success = 0;
  	return count;
  }
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
546
  static int hctx_dispatched_show(void *data, struct seq_file *m)
be2154731   Omar Sandoval   blk-mq: move hctx...
547
  {
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
548
  	struct blk_mq_hw_ctx *hctx = data;
be2154731   Omar Sandoval   blk-mq: move hctx...
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
  	int i;
  
  	seq_printf(m, "%8u\t%lu
  ", 0U, hctx->dispatched[0]);
  
  	for (i = 1; i < BLK_MQ_MAX_DISPATCH_ORDER - 1; i++) {
  		unsigned int d = 1U << (i - 1);
  
  		seq_printf(m, "%8u\t%lu
  ", d, hctx->dispatched[i]);
  	}
  
  	seq_printf(m, "%8u+\t%lu
  ", 1U << (i - 1), hctx->dispatched[i]);
  	return 0;
  }
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
565
  static ssize_t hctx_dispatched_write(void *data, const char __user *buf,
be2154731   Omar Sandoval   blk-mq: move hctx...
566
567
  				     size_t count, loff_t *ppos)
  {
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
568
  	struct blk_mq_hw_ctx *hctx = data;
be2154731   Omar Sandoval   blk-mq: move hctx...
569
570
571
572
573
574
  	int i;
  
  	for (i = 0; i < BLK_MQ_MAX_DISPATCH_ORDER; i++)
  		hctx->dispatched[i] = 0;
  	return count;
  }
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
575
  static int hctx_queued_show(void *data, struct seq_file *m)
4a46f05eb   Omar Sandoval   blk-mq: move hctx...
576
  {
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
577
  	struct blk_mq_hw_ctx *hctx = data;
4a46f05eb   Omar Sandoval   blk-mq: move hctx...
578
579
580
581
582
  
  	seq_printf(m, "%lu
  ", hctx->queued);
  	return 0;
  }
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
583
  static ssize_t hctx_queued_write(void *data, const char __user *buf,
4a46f05eb   Omar Sandoval   blk-mq: move hctx...
584
585
  				 size_t count, loff_t *ppos)
  {
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
586
  	struct blk_mq_hw_ctx *hctx = data;
4a46f05eb   Omar Sandoval   blk-mq: move hctx...
587
588
589
590
  
  	hctx->queued = 0;
  	return count;
  }
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
591
  static int hctx_run_show(void *data, struct seq_file *m)
4a46f05eb   Omar Sandoval   blk-mq: move hctx...
592
  {
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
593
  	struct blk_mq_hw_ctx *hctx = data;
4a46f05eb   Omar Sandoval   blk-mq: move hctx...
594
595
596
597
598
  
  	seq_printf(m, "%lu
  ", hctx->run);
  	return 0;
  }
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
599
600
  static ssize_t hctx_run_write(void *data, const char __user *buf, size_t count,
  			      loff_t *ppos)
4a46f05eb   Omar Sandoval   blk-mq: move hctx...
601
  {
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
602
  	struct blk_mq_hw_ctx *hctx = data;
4a46f05eb   Omar Sandoval   blk-mq: move hctx...
603
604
605
606
  
  	hctx->run = 0;
  	return count;
  }
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
607
  static int hctx_active_show(void *data, struct seq_file *m)
4a46f05eb   Omar Sandoval   blk-mq: move hctx...
608
  {
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
609
  	struct blk_mq_hw_ctx *hctx = data;
4a46f05eb   Omar Sandoval   blk-mq: move hctx...
610
611
612
613
614
  
  	seq_printf(m, "%d
  ", atomic_read(&hctx->nr_active));
  	return 0;
  }
6e7687173   Ming Lei   blk-mq: dequeue r...
615
616
617
618
619
620
621
622
  static int hctx_dispatch_busy_show(void *data, struct seq_file *m)
  {
  	struct blk_mq_hw_ctx *hctx = data;
  
  	seq_printf(m, "%u
  ", hctx->dispatch_busy);
  	return 0;
  }
c16d6b5a9   Ming Lei   blk-mq: fix dispa...
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
  #define CTX_RQ_SEQ_OPS(name, type)					\
  static void *ctx_##name##_rq_list_start(struct seq_file *m, loff_t *pos) \
  	__acquires(&ctx->lock)						\
  {									\
  	struct blk_mq_ctx *ctx = m->private;				\
  									\
  	spin_lock(&ctx->lock);						\
  	return seq_list_start(&ctx->rq_lists[type], *pos);		\
  }									\
  									\
  static void *ctx_##name##_rq_list_next(struct seq_file *m, void *v,	\
  				     loff_t *pos)			\
  {									\
  	struct blk_mq_ctx *ctx = m->private;				\
  									\
  	return seq_list_next(v, &ctx->rq_lists[type], pos);		\
  }									\
  									\
  static void ctx_##name##_rq_list_stop(struct seq_file *m, void *v)	\
  	__releases(&ctx->lock)						\
  {									\
  	struct blk_mq_ctx *ctx = m->private;				\
  									\
  	spin_unlock(&ctx->lock);					\
  }									\
  									\
  static const struct seq_operations ctx_##name##_rq_list_seq_ops = {	\
  	.start	= ctx_##name##_rq_list_start,				\
  	.next	= ctx_##name##_rq_list_next,				\
  	.stop	= ctx_##name##_rq_list_stop,				\
  	.show	= blk_mq_debugfs_rq_show,				\
  }
  
  CTX_RQ_SEQ_OPS(default, HCTX_TYPE_DEFAULT);
  CTX_RQ_SEQ_OPS(read, HCTX_TYPE_READ);
  CTX_RQ_SEQ_OPS(poll, HCTX_TYPE_POLL);
950cd7e9f   Omar Sandoval   blk-mq: move hctx...
659

f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
660
  static int ctx_dispatched_show(void *data, struct seq_file *m)
4a46f05eb   Omar Sandoval   blk-mq: move hctx...
661
  {
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
662
  	struct blk_mq_ctx *ctx = data;
4a46f05eb   Omar Sandoval   blk-mq: move hctx...
663
664
665
666
667
  
  	seq_printf(m, "%lu %lu
  ", ctx->rq_dispatched[1], ctx->rq_dispatched[0]);
  	return 0;
  }
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
668
  static ssize_t ctx_dispatched_write(void *data, const char __user *buf,
4a46f05eb   Omar Sandoval   blk-mq: move hctx...
669
670
  				    size_t count, loff_t *ppos)
  {
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
671
  	struct blk_mq_ctx *ctx = data;
4a46f05eb   Omar Sandoval   blk-mq: move hctx...
672
673
674
675
  
  	ctx->rq_dispatched[0] = ctx->rq_dispatched[1] = 0;
  	return count;
  }
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
676
  static int ctx_merged_show(void *data, struct seq_file *m)
4a46f05eb   Omar Sandoval   blk-mq: move hctx...
677
  {
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
678
  	struct blk_mq_ctx *ctx = data;
4a46f05eb   Omar Sandoval   blk-mq: move hctx...
679
680
681
682
683
  
  	seq_printf(m, "%lu
  ", ctx->rq_merged);
  	return 0;
  }
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
684
685
  static ssize_t ctx_merged_write(void *data, const char __user *buf,
  				size_t count, loff_t *ppos)
4a46f05eb   Omar Sandoval   blk-mq: move hctx...
686
  {
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
687
  	struct blk_mq_ctx *ctx = data;
4a46f05eb   Omar Sandoval   blk-mq: move hctx...
688
689
690
691
  
  	ctx->rq_merged = 0;
  	return count;
  }
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
692
  static int ctx_completed_show(void *data, struct seq_file *m)
4a46f05eb   Omar Sandoval   blk-mq: move hctx...
693
  {
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
694
  	struct blk_mq_ctx *ctx = data;
4a46f05eb   Omar Sandoval   blk-mq: move hctx...
695
696
697
698
699
  
  	seq_printf(m, "%lu %lu
  ", ctx->rq_completed[1], ctx->rq_completed[0]);
  	return 0;
  }
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
700
701
  static ssize_t ctx_completed_write(void *data, const char __user *buf,
  				   size_t count, loff_t *ppos)
4a46f05eb   Omar Sandoval   blk-mq: move hctx...
702
  {
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
703
704
705
706
  	struct blk_mq_ctx *ctx = data;
  
  	ctx->rq_completed[0] = ctx->rq_completed[1] = 0;
  	return count;
4a46f05eb   Omar Sandoval   blk-mq: move hctx...
707
  }
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
708
709
710
711
712
713
714
715
716
717
  static int blk_mq_debugfs_show(struct seq_file *m, void *v)
  {
  	const struct blk_mq_debugfs_attr *attr = m->private;
  	void *data = d_inode(m->file->f_path.dentry->d_parent)->i_private;
  
  	return attr->show(data, m);
  }
  
  static ssize_t blk_mq_debugfs_write(struct file *file, const char __user *buf,
  				    size_t count, loff_t *ppos)
4a46f05eb   Omar Sandoval   blk-mq: move hctx...
718
719
  {
  	struct seq_file *m = file->private_data;
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
720
721
  	const struct blk_mq_debugfs_attr *attr = m->private;
  	void *data = d_inode(file->f_path.dentry->d_parent)->i_private;
4a46f05eb   Omar Sandoval   blk-mq: move hctx...
722

6b136a24b   Eryu Guan   blk-mq-debugfs: d...
723
724
725
726
727
  	/*
  	 * Attributes that only implement .seq_ops are read-only and 'attr' is
  	 * the same with 'data' in this case.
  	 */
  	if (attr == data || !attr->write)
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
  		return -EPERM;
  
  	return attr->write(data, buf, count, ppos);
  }
  
  static int blk_mq_debugfs_open(struct inode *inode, struct file *file)
  {
  	const struct blk_mq_debugfs_attr *attr = inode->i_private;
  	void *data = d_inode(file->f_path.dentry->d_parent)->i_private;
  	struct seq_file *m;
  	int ret;
  
  	if (attr->seq_ops) {
  		ret = seq_open(file, attr->seq_ops);
  		if (!ret) {
  			m = file->private_data;
  			m->private = data;
  		}
  		return ret;
  	}
  
  	if (WARN_ON_ONCE(!attr->show))
  		return -EPERM;
  
  	return single_open(file, blk_mq_debugfs_show, inode->i_private);
4a46f05eb   Omar Sandoval   blk-mq: move hctx...
753
  }
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
754
755
756
757
758
759
  static int blk_mq_debugfs_release(struct inode *inode, struct file *file)
  {
  	const struct blk_mq_debugfs_attr *attr = inode->i_private;
  
  	if (attr->show)
  		return single_release(inode, file);
ee1e03598   Chaitanya Kulkarni   block: get rid of...
760
761
  
  	return seq_release(inode, file);
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
762
  }
f84659339   Bart Van Assche   blk-mq-debugfs: D...
763
  static const struct file_operations blk_mq_debugfs_fops = {
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
764
  	.open		= blk_mq_debugfs_open,
4a46f05eb   Omar Sandoval   blk-mq: move hctx...
765
  	.read		= seq_read,
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
766
  	.write		= blk_mq_debugfs_write,
4a46f05eb   Omar Sandoval   blk-mq: move hctx...
767
  	.llseek		= seq_lseek,
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
768
  	.release	= blk_mq_debugfs_release,
4a46f05eb   Omar Sandoval   blk-mq: move hctx...
769
  };
07e4fead4   Omar Sandoval   blk-mq: create de...
770
  static const struct blk_mq_debugfs_attr blk_mq_debugfs_hctx_attrs[] = {
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
771
772
773
  	{"state", 0400, hctx_state_show},
  	{"flags", 0400, hctx_flags_show},
  	{"dispatch", 0400, .seq_ops = &hctx_dispatch_seq_ops},
2720bab50   Bart Van Assche   blk-mq-debugfs: S...
774
  	{"busy", 0400, hctx_busy_show},
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
775
776
777
778
779
780
781
782
783
784
  	{"ctx_map", 0400, hctx_ctx_map_show},
  	{"tags", 0400, hctx_tags_show},
  	{"tags_bitmap", 0400, hctx_tags_bitmap_show},
  	{"sched_tags", 0400, hctx_sched_tags_show},
  	{"sched_tags_bitmap", 0400, hctx_sched_tags_bitmap_show},
  	{"io_poll", 0600, hctx_io_poll_show, hctx_io_poll_write},
  	{"dispatched", 0600, hctx_dispatched_show, hctx_dispatched_write},
  	{"queued", 0600, hctx_queued_show, hctx_queued_write},
  	{"run", 0600, hctx_run_show, hctx_run_write},
  	{"active", 0400, hctx_active_show},
6e7687173   Ming Lei   blk-mq: dequeue r...
785
  	{"dispatch_busy", 0400, hctx_dispatch_busy_show},
346fc1089   Ming Lei   blk-mq: export hc...
786
  	{"type", 0400, hctx_type_show},
72f2f8f69   Bart Van Assche   blk-mq-debug: Int...
787
  	{},
07e4fead4   Omar Sandoval   blk-mq: create de...
788
789
790
  };
  
  static const struct blk_mq_debugfs_attr blk_mq_debugfs_ctx_attrs[] = {
c16d6b5a9   Ming Lei   blk-mq: fix dispa...
791
792
793
  	{"default_rq_list", 0400, .seq_ops = &ctx_default_rq_list_seq_ops},
  	{"read_rq_list", 0400, .seq_ops = &ctx_read_rq_list_seq_ops},
  	{"poll_rq_list", 0400, .seq_ops = &ctx_poll_rq_list_seq_ops},
f57de23ac   Omar Sandoval   blk-mq-debugfs: g...
794
795
796
  	{"dispatched", 0600, ctx_dispatched_show, ctx_dispatched_write},
  	{"merged", 0600, ctx_merged_show, ctx_merged_write},
  	{"completed", 0600, ctx_completed_show, ctx_completed_write},
72f2f8f69   Bart Van Assche   blk-mq-debug: Int...
797
  	{},
07e4fead4   Omar Sandoval   blk-mq: create de...
798
  };
6cfc0081b   Greg Kroah-Hartman   blk-mq: no need t...
799
  static void debugfs_create_files(struct dentry *parent, void *data,
9c1051aac   Omar Sandoval   blk-mq: untangle ...
800
801
  				 const struct blk_mq_debugfs_attr *attr)
  {
36991ca68   Greg Kroah-Hartman   blk-mq: protect d...
802
  	if (IS_ERR_OR_NULL(parent))
6cfc0081b   Greg Kroah-Hartman   blk-mq: no need t...
803
  		return;
36991ca68   Greg Kroah-Hartman   blk-mq: protect d...
804

9c1051aac   Omar Sandoval   blk-mq: untangle ...
805
  	d_inode(parent)->i_private = data;
6cfc0081b   Greg Kroah-Hartman   blk-mq: no need t...
806
807
808
  	for (; attr->name; attr++)
  		debugfs_create_file(attr->name, attr->mode, parent,
  				    (void *)attr, &blk_mq_debugfs_fops);
9c1051aac   Omar Sandoval   blk-mq: untangle ...
809
  }
6cfc0081b   Greg Kroah-Hartman   blk-mq: no need t...
810
  void blk_mq_debugfs_register(struct request_queue *q)
07e4fead4   Omar Sandoval   blk-mq: create de...
811
  {
9c1051aac   Omar Sandoval   blk-mq: untangle ...
812
813
  	struct blk_mq_hw_ctx *hctx;
  	int i;
6cfc0081b   Greg Kroah-Hartman   blk-mq: no need t...
814
  	debugfs_create_files(q->debugfs_dir, q, blk_mq_debugfs_queue_attrs);
07e4fead4   Omar Sandoval   blk-mq: create de...
815

9c1051aac   Omar Sandoval   blk-mq: untangle ...
816
  	/*
70e62f4ba   Omar Sandoval   blk-mq-debugfs: f...
817
  	 * blk_mq_init_sched() attempted to do this already, but q->debugfs_dir
9c1051aac   Omar Sandoval   blk-mq: untangle ...
818
819
820
  	 * didn't exist yet (because we don't know what to name the directory
  	 * until the queue is registered to a gendisk).
  	 */
70e62f4ba   Omar Sandoval   blk-mq-debugfs: f...
821
822
823
824
  	if (q->elevator && !q->sched_debugfs_dir)
  		blk_mq_debugfs_register_sched(q);
  
  	/* Similarly, blk_mq_init_hctx() couldn't do this previously. */
9c1051aac   Omar Sandoval   blk-mq: untangle ...
825
  	queue_for_each_hw_ctx(q, hctx, i) {
6cfc0081b   Greg Kroah-Hartman   blk-mq: no need t...
826
827
828
829
  		if (!hctx->debugfs_dir)
  			blk_mq_debugfs_register_hctx(q, hctx);
  		if (q->elevator && !hctx->sched_debugfs_dir)
  			blk_mq_debugfs_register_sched_hctx(q, hctx);
9c1051aac   Omar Sandoval   blk-mq: untangle ...
830
  	}
cc56694f1   Ming Lei   blk-mq-debugfs: s...
831
832
833
834
835
836
837
838
  	if (q->rq_qos) {
  		struct rq_qos *rqos = q->rq_qos;
  
  		while (rqos) {
  			blk_mq_debugfs_register_rqos(rqos);
  			rqos = rqos->next;
  		}
  	}
07e4fead4   Omar Sandoval   blk-mq: create de...
839
840
841
842
  }
  
  void blk_mq_debugfs_unregister(struct request_queue *q)
  {
d332ce091   Omar Sandoval   blk-mq-debugfs: a...
843
  	q->sched_debugfs_dir = NULL;
07e4fead4   Omar Sandoval   blk-mq: create de...
844
  }
6cfc0081b   Greg Kroah-Hartman   blk-mq: no need t...
845
846
  static void blk_mq_debugfs_register_ctx(struct blk_mq_hw_ctx *hctx,
  					struct blk_mq_ctx *ctx)
07e4fead4   Omar Sandoval   blk-mq: create de...
847
848
849
  {
  	struct dentry *ctx_dir;
  	char name[20];
07e4fead4   Omar Sandoval   blk-mq: create de...
850
851
  
  	snprintf(name, sizeof(name), "cpu%u", ctx->cpu);
9c1051aac   Omar Sandoval   blk-mq: untangle ...
852
  	ctx_dir = debugfs_create_dir(name, hctx->debugfs_dir);
07e4fead4   Omar Sandoval   blk-mq: create de...
853

6cfc0081b   Greg Kroah-Hartman   blk-mq: no need t...
854
  	debugfs_create_files(ctx_dir, ctx, blk_mq_debugfs_ctx_attrs);
07e4fead4   Omar Sandoval   blk-mq: create de...
855
  }
6cfc0081b   Greg Kroah-Hartman   blk-mq: no need t...
856
857
  void blk_mq_debugfs_register_hctx(struct request_queue *q,
  				  struct blk_mq_hw_ctx *hctx)
07e4fead4   Omar Sandoval   blk-mq: create de...
858
859
  {
  	struct blk_mq_ctx *ctx;
07e4fead4   Omar Sandoval   blk-mq: create de...
860
861
  	char name[20];
  	int i;
88aabbd7e   Omar Sandoval   blk-mq-debugfs: r...
862
  	snprintf(name, sizeof(name), "hctx%u", hctx->queue_num);
9c1051aac   Omar Sandoval   blk-mq: untangle ...
863
  	hctx->debugfs_dir = debugfs_create_dir(name, q->debugfs_dir);
07e4fead4   Omar Sandoval   blk-mq: create de...
864

6cfc0081b   Greg Kroah-Hartman   blk-mq: no need t...
865
  	debugfs_create_files(hctx->debugfs_dir, hctx, blk_mq_debugfs_hctx_attrs);
9c1051aac   Omar Sandoval   blk-mq: untangle ...
866

6cfc0081b   Greg Kroah-Hartman   blk-mq: no need t...
867
868
  	hctx_for_each_ctx(hctx, ctx, i)
  		blk_mq_debugfs_register_ctx(hctx, ctx);
9c1051aac   Omar Sandoval   blk-mq: untangle ...
869
870
871
872
873
  }
  
  void blk_mq_debugfs_unregister_hctx(struct blk_mq_hw_ctx *hctx)
  {
  	debugfs_remove_recursive(hctx->debugfs_dir);
d332ce091   Omar Sandoval   blk-mq-debugfs: a...
874
  	hctx->sched_debugfs_dir = NULL;
9c1051aac   Omar Sandoval   blk-mq: untangle ...
875
  	hctx->debugfs_dir = NULL;
07e4fead4   Omar Sandoval   blk-mq: create de...
876
  }
6cfc0081b   Greg Kroah-Hartman   blk-mq: no need t...
877
  void blk_mq_debugfs_register_hctxs(struct request_queue *q)
07e4fead4   Omar Sandoval   blk-mq: create de...
878
879
880
  {
  	struct blk_mq_hw_ctx *hctx;
  	int i;
6cfc0081b   Greg Kroah-Hartman   blk-mq: no need t...
881
882
  	queue_for_each_hw_ctx(q, hctx, i)
  		blk_mq_debugfs_register_hctx(q, hctx);
07e4fead4   Omar Sandoval   blk-mq: create de...
883
  }
9c1051aac   Omar Sandoval   blk-mq: untangle ...
884
  void blk_mq_debugfs_unregister_hctxs(struct request_queue *q)
07e4fead4   Omar Sandoval   blk-mq: create de...
885
  {
9c1051aac   Omar Sandoval   blk-mq: untangle ...
886
887
888
889
890
  	struct blk_mq_hw_ctx *hctx;
  	int i;
  
  	queue_for_each_hw_ctx(q, hctx, i)
  		blk_mq_debugfs_unregister_hctx(hctx);
07e4fead4   Omar Sandoval   blk-mq: create de...
891
  }
d332ce091   Omar Sandoval   blk-mq-debugfs: a...
892

6cfc0081b   Greg Kroah-Hartman   blk-mq: no need t...
893
  void blk_mq_debugfs_register_sched(struct request_queue *q)
d332ce091   Omar Sandoval   blk-mq-debugfs: a...
894
895
  {
  	struct elevator_type *e = q->elevator->type;
7e41c3c9b   Greg Kroah-Hartman   blk-mq: fix up pl...
896
897
898
899
900
901
  	/*
  	 * If the parent directory has not been created yet, return, we will be
  	 * called again later on and the directory/files will be created then.
  	 */
  	if (!q->debugfs_dir)
  		return;
d332ce091   Omar Sandoval   blk-mq-debugfs: a...
902
  	if (!e->queue_debugfs_attrs)
6cfc0081b   Greg Kroah-Hartman   blk-mq: no need t...
903
  		return;
d332ce091   Omar Sandoval   blk-mq-debugfs: a...
904
905
  
  	q->sched_debugfs_dir = debugfs_create_dir("sched", q->debugfs_dir);
d332ce091   Omar Sandoval   blk-mq-debugfs: a...
906

6cfc0081b   Greg Kroah-Hartman   blk-mq: no need t...
907
  	debugfs_create_files(q->sched_debugfs_dir, q, e->queue_debugfs_attrs);
d332ce091   Omar Sandoval   blk-mq-debugfs: a...
908
909
910
911
912
913
914
  }
  
  void blk_mq_debugfs_unregister_sched(struct request_queue *q)
  {
  	debugfs_remove_recursive(q->sched_debugfs_dir);
  	q->sched_debugfs_dir = NULL;
  }
cc56694f1   Ming Lei   blk-mq-debugfs: s...
915
916
917
918
919
  void blk_mq_debugfs_unregister_rqos(struct rq_qos *rqos)
  {
  	debugfs_remove_recursive(rqos->debugfs_dir);
  	rqos->debugfs_dir = NULL;
  }
6cfc0081b   Greg Kroah-Hartman   blk-mq: no need t...
920
  void blk_mq_debugfs_register_rqos(struct rq_qos *rqos)
cc56694f1   Ming Lei   blk-mq-debugfs: s...
921
922
923
  {
  	struct request_queue *q = rqos->q;
  	const char *dir_name = rq_qos_id_to_name(rqos->id);
cc56694f1   Ming Lei   blk-mq-debugfs: s...
924
  	if (rqos->debugfs_dir || !rqos->ops->debugfs_attrs)
6cfc0081b   Greg Kroah-Hartman   blk-mq: no need t...
925
  		return;
cc56694f1   Ming Lei   blk-mq-debugfs: s...
926

6cfc0081b   Greg Kroah-Hartman   blk-mq: no need t...
927
  	if (!q->rqos_debugfs_dir)
cc56694f1   Ming Lei   blk-mq-debugfs: s...
928
929
  		q->rqos_debugfs_dir = debugfs_create_dir("rqos",
  							 q->debugfs_dir);
cc56694f1   Ming Lei   blk-mq-debugfs: s...
930
931
932
  
  	rqos->debugfs_dir = debugfs_create_dir(dir_name,
  					       rqos->q->rqos_debugfs_dir);
cc56694f1   Ming Lei   blk-mq-debugfs: s...
933

6cfc0081b   Greg Kroah-Hartman   blk-mq: no need t...
934
  	debugfs_create_files(rqos->debugfs_dir, rqos, rqos->ops->debugfs_attrs);
cc56694f1   Ming Lei   blk-mq-debugfs: s...
935
936
937
938
939
940
941
  }
  
  void blk_mq_debugfs_unregister_queue_rqos(struct request_queue *q)
  {
  	debugfs_remove_recursive(q->rqos_debugfs_dir);
  	q->rqos_debugfs_dir = NULL;
  }
6cfc0081b   Greg Kroah-Hartman   blk-mq: no need t...
942
943
  void blk_mq_debugfs_register_sched_hctx(struct request_queue *q,
  					struct blk_mq_hw_ctx *hctx)
d332ce091   Omar Sandoval   blk-mq-debugfs: a...
944
945
  {
  	struct elevator_type *e = q->elevator->type;
d332ce091   Omar Sandoval   blk-mq-debugfs: a...
946
  	if (!e->hctx_debugfs_attrs)
6cfc0081b   Greg Kroah-Hartman   blk-mq: no need t...
947
  		return;
d332ce091   Omar Sandoval   blk-mq-debugfs: a...
948
949
950
  
  	hctx->sched_debugfs_dir = debugfs_create_dir("sched",
  						     hctx->debugfs_dir);
6cfc0081b   Greg Kroah-Hartman   blk-mq: no need t...
951
952
  	debugfs_create_files(hctx->sched_debugfs_dir, hctx,
  			     e->hctx_debugfs_attrs);
d332ce091   Omar Sandoval   blk-mq-debugfs: a...
953
954
955
956
957
958
959
  }
  
  void blk_mq_debugfs_unregister_sched_hctx(struct blk_mq_hw_ctx *hctx)
  {
  	debugfs_remove_recursive(hctx->sched_debugfs_dir);
  	hctx->sched_debugfs_dir = NULL;
  }