Merge tag 'for-v5.1' of git://git.kernel.org/pub/scm/linux/kernel/git/sre/linux-power...
[linux-2.6-block.git] / fs / xfs / xfs_sysfs.c
CommitLineData
0b61f8a4 1// SPDX-License-Identifier: GPL-2.0
a31b1d3d
BF
2/*
3 * Copyright (c) 2014 Red Hat, Inc.
4 * All Rights Reserved.
a31b1d3d
BF
5 */
6
7#include "xfs.h"
192852be 8#include "xfs_shared.h"
801cc4e1 9#include "xfs_format.h"
baff4e44 10#include "xfs_log_format.h"
801cc4e1 11#include "xfs_trans_resv.h"
192852be 12#include "xfs_sysfs.h"
baff4e44
BF
13#include "xfs_log.h"
14#include "xfs_log_priv.h"
bb230c12 15#include "xfs_stats.h"
801cc4e1 16#include "xfs_mount.h"
a31b1d3d
BF
17
18struct xfs_sysfs_attr {
19 struct attribute attr;
a27c2640
BD
20 ssize_t (*show)(struct kobject *kobject, char *buf);
21 ssize_t (*store)(struct kobject *kobject, const char *buf,
22 size_t count);
a31b1d3d
BF
23};
24
25static inline struct xfs_sysfs_attr *
26to_attr(struct attribute *attr)
27{
28 return container_of(attr, struct xfs_sysfs_attr, attr);
29}
30
31#define XFS_SYSFS_ATTR_RW(name) \
32 static struct xfs_sysfs_attr xfs_sysfs_attr_##name = __ATTR_RW(name)
33#define XFS_SYSFS_ATTR_RO(name) \
34 static struct xfs_sysfs_attr xfs_sysfs_attr_##name = __ATTR_RO(name)
bb230c12
BD
35#define XFS_SYSFS_ATTR_WO(name) \
36 static struct xfs_sysfs_attr xfs_sysfs_attr_##name = __ATTR_WO(name)
a31b1d3d
BF
37
38#define ATTR_LIST(name) &xfs_sysfs_attr_##name.attr
39
a27c2640
BD
40STATIC ssize_t
41xfs_sysfs_object_show(
42 struct kobject *kobject,
43 struct attribute *attr,
44 char *buf)
45{
46 struct xfs_sysfs_attr *xfs_attr = to_attr(attr);
47
48 return xfs_attr->show ? xfs_attr->show(kobject, buf) : 0;
49}
50
51STATIC ssize_t
52xfs_sysfs_object_store(
53 struct kobject *kobject,
54 struct attribute *attr,
55 const char *buf,
56 size_t count)
57{
58 struct xfs_sysfs_attr *xfs_attr = to_attr(attr);
59
60 return xfs_attr->store ? xfs_attr->store(kobject, buf, count) : 0;
61}
62
63static const struct sysfs_ops xfs_sysfs_ops = {
64 .show = xfs_sysfs_object_show,
65 .store = xfs_sysfs_object_store,
66};
67
801cc4e1
BF
68/*
69 * xfs_mount kobject. The mp kobject also serves as the per-mount parent object
70 * that is identified by the fsname under sysfs.
71 */
72
73static inline struct xfs_mount *
74to_mp(struct kobject *kobject)
75{
76 struct xfs_kobj *kobj = to_kobj(kobject);
77
78 return container_of(kobj, struct xfs_mount, m_kobj);
79}
80
801cc4e1 81static struct attribute *xfs_mp_attrs[] = {
801cc4e1
BF
82 NULL,
83};
84
85struct kobj_type xfs_mp_ktype = {
86 .release = xfs_sysfs_release,
87 .sysfs_ops = &xfs_sysfs_ops,
88 .default_attrs = xfs_mp_attrs,
89};
90
65b65735
BF
91#ifdef DEBUG
92/* debug */
93
ccdab3d6
BF
94STATIC ssize_t
95bug_on_assert_store(
96 struct kobject *kobject,
97 const char *buf,
98 size_t count)
99{
100 int ret;
101 int val;
102
103 ret = kstrtoint(buf, 0, &val);
104 if (ret)
105 return ret;
106
107 if (val == 1)
108 xfs_globals.bug_on_assert = true;
109 else if (val == 0)
110 xfs_globals.bug_on_assert = false;
111 else
112 return -EINVAL;
113
114 return count;
115}
116
117STATIC ssize_t
118bug_on_assert_show(
119 struct kobject *kobject,
120 char *buf)
121{
122 return snprintf(buf, PAGE_SIZE, "%d\n", xfs_globals.bug_on_assert ? 1 : 0);
123}
124XFS_SYSFS_ATTR_RW(bug_on_assert);
125
2e227178
BF
126STATIC ssize_t
127log_recovery_delay_store(
a27c2640 128 struct kobject *kobject,
2e227178 129 const char *buf,
a27c2640 130 size_t count)
2e227178
BF
131{
132 int ret;
133 int val;
134
135 ret = kstrtoint(buf, 0, &val);
136 if (ret)
137 return ret;
138
139 if (val < 0 || val > 60)
140 return -EINVAL;
141
142 xfs_globals.log_recovery_delay = val;
143
144 return count;
145}
146
147STATIC ssize_t
148log_recovery_delay_show(
a27c2640
BD
149 struct kobject *kobject,
150 char *buf)
2e227178
BF
151{
152 return snprintf(buf, PAGE_SIZE, "%d\n", xfs_globals.log_recovery_delay);
153}
154XFS_SYSFS_ATTR_RW(log_recovery_delay);
155
dae5cd81
DC
156STATIC ssize_t
157mount_delay_store(
158 struct kobject *kobject,
159 const char *buf,
160 size_t count)
161{
162 int ret;
163 int val;
164
165 ret = kstrtoint(buf, 0, &val);
166 if (ret)
167 return ret;
168
169 if (val < 0 || val > 60)
170 return -EINVAL;
171
172 xfs_globals.mount_delay = val;
173
174 return count;
175}
176
177STATIC ssize_t
178mount_delay_show(
179 struct kobject *kobject,
180 char *buf)
181{
182 return snprintf(buf, PAGE_SIZE, "%d\n", xfs_globals.mount_delay);
183}
184XFS_SYSFS_ATTR_RW(mount_delay);
185
66ae56a5
CH
186static ssize_t
187always_cow_store(
188 struct kobject *kobject,
189 const char *buf,
190 size_t count)
191{
192 ssize_t ret;
193
194 ret = kstrtobool(buf, &xfs_globals.always_cow);
195 if (ret < 0)
196 return ret;
197 return count;
198}
199
200static ssize_t
201always_cow_show(
202 struct kobject *kobject,
203 char *buf)
204{
205 return snprintf(buf, PAGE_SIZE, "%d\n", xfs_globals.always_cow);
206}
207XFS_SYSFS_ATTR_RW(always_cow);
208
65b65735 209static struct attribute *xfs_dbg_attrs[] = {
ccdab3d6 210 ATTR_LIST(bug_on_assert),
2e227178 211 ATTR_LIST(log_recovery_delay),
dae5cd81 212 ATTR_LIST(mount_delay),
66ae56a5 213 ATTR_LIST(always_cow),
65b65735
BF
214 NULL,
215};
216
65b65735
BF
217struct kobj_type xfs_dbg_ktype = {
218 .release = xfs_sysfs_release,
a27c2640 219 .sysfs_ops = &xfs_sysfs_ops,
65b65735
BF
220 .default_attrs = xfs_dbg_attrs,
221};
222
223#endif /* DEBUG */
224
bb230c12
BD
225/* stats */
226
80529c45
BD
227static inline struct xstats *
228to_xstats(struct kobject *kobject)
229{
230 struct xfs_kobj *kobj = to_kobj(kobject);
231
232 return container_of(kobj, struct xstats, xs_kobj);
233}
234
bb230c12
BD
235STATIC ssize_t
236stats_show(
a27c2640
BD
237 struct kobject *kobject,
238 char *buf)
bb230c12 239{
80529c45
BD
240 struct xstats *stats = to_xstats(kobject);
241
242 return xfs_stats_format(stats->xs_stats, buf);
bb230c12
BD
243}
244XFS_SYSFS_ATTR_RO(stats);
245
246STATIC ssize_t
247stats_clear_store(
a27c2640 248 struct kobject *kobject,
bb230c12 249 const char *buf,
a27c2640 250 size_t count)
bb230c12
BD
251{
252 int ret;
253 int val;
80529c45 254 struct xstats *stats = to_xstats(kobject);
bb230c12
BD
255
256 ret = kstrtoint(buf, 0, &val);
257 if (ret)
258 return ret;
259
260 if (val != 1)
261 return -EINVAL;
80529c45
BD
262
263 xfs_stats_clearall(stats->xs_stats);
bb230c12
BD
264 return count;
265}
266XFS_SYSFS_ATTR_WO(stats_clear);
267
268static struct attribute *xfs_stats_attrs[] = {
269 ATTR_LIST(stats),
270 ATTR_LIST(stats_clear),
271 NULL,
272};
273
bb230c12
BD
274struct kobj_type xfs_stats_ktype = {
275 .release = xfs_sysfs_release,
a27c2640 276 .sysfs_ops = &xfs_sysfs_ops,
bb230c12
BD
277 .default_attrs = xfs_stats_attrs,
278};
279
baff4e44
BF
280/* xlog */
281
a27c2640
BD
282static inline struct xlog *
283to_xlog(struct kobject *kobject)
284{
285 struct xfs_kobj *kobj = to_kobj(kobject);
286
287 return container_of(kobj, struct xlog, l_kobj);
288}
289
80d6d698
BF
290STATIC ssize_t
291log_head_lsn_show(
a27c2640
BD
292 struct kobject *kobject,
293 char *buf)
80d6d698 294{
80d6d698
BF
295 int cycle;
296 int block;
a27c2640 297 struct xlog *log = to_xlog(kobject);
80d6d698
BF
298
299 spin_lock(&log->l_icloglock);
300 cycle = log->l_curr_cycle;
301 block = log->l_curr_block;
302 spin_unlock(&log->l_icloglock);
303
304 return snprintf(buf, PAGE_SIZE, "%d:%d\n", cycle, block);
305}
306XFS_SYSFS_ATTR_RO(log_head_lsn);
307
308STATIC ssize_t
309log_tail_lsn_show(
a27c2640
BD
310 struct kobject *kobject,
311 char *buf)
80d6d698 312{
80d6d698
BF
313 int cycle;
314 int block;
a27c2640 315 struct xlog *log = to_xlog(kobject);
80d6d698
BF
316
317 xlog_crack_atomic_lsn(&log->l_tail_lsn, &cycle, &block);
318 return snprintf(buf, PAGE_SIZE, "%d:%d\n", cycle, block);
319}
320XFS_SYSFS_ATTR_RO(log_tail_lsn);
321
322STATIC ssize_t
323reserve_grant_head_show(
a27c2640
BD
324 struct kobject *kobject,
325 char *buf)
326
80d6d698 327{
80d6d698
BF
328 int cycle;
329 int bytes;
a27c2640 330 struct xlog *log = to_xlog(kobject);
80d6d698
BF
331
332 xlog_crack_grant_head(&log->l_reserve_head.grant, &cycle, &bytes);
333 return snprintf(buf, PAGE_SIZE, "%d:%d\n", cycle, bytes);
334}
335XFS_SYSFS_ATTR_RO(reserve_grant_head);
336
337STATIC ssize_t
338write_grant_head_show(
a27c2640
BD
339 struct kobject *kobject,
340 char *buf)
80d6d698 341{
80d6d698
BF
342 int cycle;
343 int bytes;
a27c2640 344 struct xlog *log = to_xlog(kobject);
80d6d698
BF
345
346 xlog_crack_grant_head(&log->l_write_head.grant, &cycle, &bytes);
347 return snprintf(buf, PAGE_SIZE, "%d:%d\n", cycle, bytes);
348}
349XFS_SYSFS_ATTR_RO(write_grant_head);
350
baff4e44 351static struct attribute *xfs_log_attrs[] = {
80d6d698
BF
352 ATTR_LIST(log_head_lsn),
353 ATTR_LIST(log_tail_lsn),
354 ATTR_LIST(reserve_grant_head),
355 ATTR_LIST(write_grant_head),
baff4e44
BF
356 NULL,
357};
358
baff4e44
BF
359struct kobj_type xfs_log_ktype = {
360 .release = xfs_sysfs_release,
a27c2640 361 .sysfs_ops = &xfs_sysfs_ops,
baff4e44
BF
362 .default_attrs = xfs_log_attrs,
363};
192852be
CM
364
365/*
366 * Metadata IO error configuration
367 *
368 * The sysfs structure here is:
369 * ...xfs/<dev>/error/<class>/<errno>/<error_attrs>
370 *
371 * where <class> allows us to discriminate between data IO and metadata IO,
372 * and any other future type of IO (e.g. special inode or directory error
373 * handling) we care to support.
374 */
192852be
CM
375static inline struct xfs_error_cfg *
376to_error_cfg(struct kobject *kobject)
377{
378 struct xfs_kobj *kobj = to_kobj(kobject);
379 return container_of(kobj, struct xfs_error_cfg, kobj);
380}
381
e6b3bb78
CM
382static inline struct xfs_mount *
383err_to_mp(struct kobject *kobject)
384{
385 struct xfs_kobj *kobj = to_kobj(kobject);
386 return container_of(kobj, struct xfs_mount, m_error_kobj);
387}
388
a5ea70d2
CM
389static ssize_t
390max_retries_show(
391 struct kobject *kobject,
392 char *buf)
393{
77169812 394 int retries;
a5ea70d2
CM
395 struct xfs_error_cfg *cfg = to_error_cfg(kobject);
396
ff97f239 397 if (cfg->max_retries == XFS_ERR_RETRY_FOREVER)
77169812
ES
398 retries = -1;
399 else
400 retries = cfg->max_retries;
401
402 return snprintf(buf, PAGE_SIZE, "%d\n", retries);
a5ea70d2
CM
403}
404
405static ssize_t
406max_retries_store(
407 struct kobject *kobject,
408 const char *buf,
409 size_t count)
410{
411 struct xfs_error_cfg *cfg = to_error_cfg(kobject);
412 int ret;
413 int val;
414
415 ret = kstrtoint(buf, 0, &val);
416 if (ret)
417 return ret;
418
419 if (val < -1)
420 return -EINVAL;
421
77169812 422 if (val == -1)
ff97f239 423 cfg->max_retries = XFS_ERR_RETRY_FOREVER;
77169812
ES
424 else
425 cfg->max_retries = val;
a5ea70d2
CM
426 return count;
427}
428XFS_SYSFS_ATTR_RW(max_retries);
429
430static ssize_t
431retry_timeout_seconds_show(
432 struct kobject *kobject,
433 char *buf)
434{
77169812 435 int timeout;
a5ea70d2
CM
436 struct xfs_error_cfg *cfg = to_error_cfg(kobject);
437
77169812
ES
438 if (cfg->retry_timeout == XFS_ERR_RETRY_FOREVER)
439 timeout = -1;
440 else
441 timeout = jiffies_to_msecs(cfg->retry_timeout) / MSEC_PER_SEC;
442
443 return snprintf(buf, PAGE_SIZE, "%d\n", timeout);
a5ea70d2
CM
444}
445
446static ssize_t
447retry_timeout_seconds_store(
448 struct kobject *kobject,
449 const char *buf,
450 size_t count)
451{
452 struct xfs_error_cfg *cfg = to_error_cfg(kobject);
453 int ret;
454 int val;
455
456 ret = kstrtoint(buf, 0, &val);
457 if (ret)
458 return ret;
459
77169812
ES
460 /* 1 day timeout maximum, -1 means infinite */
461 if (val < -1 || val > 86400)
a5ea70d2
CM
462 return -EINVAL;
463
77169812
ES
464 if (val == -1)
465 cfg->retry_timeout = XFS_ERR_RETRY_FOREVER;
466 else {
467 cfg->retry_timeout = msecs_to_jiffies(val * MSEC_PER_SEC);
468 ASSERT(msecs_to_jiffies(val * MSEC_PER_SEC) < LONG_MAX);
469 }
a5ea70d2
CM
470 return count;
471}
472XFS_SYSFS_ATTR_RW(retry_timeout_seconds);
473
e6b3bb78
CM
474static ssize_t
475fail_at_unmount_show(
476 struct kobject *kobject,
477 char *buf)
478{
479 struct xfs_mount *mp = err_to_mp(kobject);
480
481 return snprintf(buf, PAGE_SIZE, "%d\n", mp->m_fail_unmount);
482}
483
484static ssize_t
485fail_at_unmount_store(
486 struct kobject *kobject,
487 const char *buf,
488 size_t count)
489{
490 struct xfs_mount *mp = err_to_mp(kobject);
491 int ret;
492 int val;
493
494 ret = kstrtoint(buf, 0, &val);
495 if (ret)
496 return ret;
497
498 if (val < 0 || val > 1)
499 return -EINVAL;
500
501 mp->m_fail_unmount = val;
502 return count;
503}
504XFS_SYSFS_ATTR_RW(fail_at_unmount);
505
a5ea70d2
CM
506static struct attribute *xfs_error_attrs[] = {
507 ATTR_LIST(max_retries),
508 ATTR_LIST(retry_timeout_seconds),
509 NULL,
510};
511
512
f1b8243c 513static struct kobj_type xfs_error_cfg_ktype = {
192852be
CM
514 .release = xfs_sysfs_release,
515 .sysfs_ops = &xfs_sysfs_ops,
516 .default_attrs = xfs_error_attrs,
517};
518
f1b8243c 519static struct kobj_type xfs_error_ktype = {
192852be 520 .release = xfs_sysfs_release,
e6b3bb78 521 .sysfs_ops = &xfs_sysfs_ops,
192852be
CM
522};
523
ef6a50fb
CM
524/*
525 * Error initialization tables. These need to be ordered in the same
526 * order as the enums used to index the array. All class init tables need to
527 * define a "default" behaviour as the first entry, all other entries can be
528 * empty.
529 */
530struct xfs_error_init {
531 char *name;
532 int max_retries;
a5ea70d2 533 int retry_timeout; /* in seconds */
ef6a50fb
CM
534};
535
536static const struct xfs_error_init xfs_error_meta_init[XFS_ERR_ERRNO_MAX] = {
537 { .name = "default",
e0a431b3 538 .max_retries = XFS_ERR_RETRY_FOREVER,
77169812 539 .retry_timeout = XFS_ERR_RETRY_FOREVER,
ef6a50fb 540 },
e0a431b3
CM
541 { .name = "EIO",
542 .max_retries = XFS_ERR_RETRY_FOREVER,
77169812 543 .retry_timeout = XFS_ERR_RETRY_FOREVER,
e0a431b3
CM
544 },
545 { .name = "ENOSPC",
546 .max_retries = XFS_ERR_RETRY_FOREVER,
77169812 547 .retry_timeout = XFS_ERR_RETRY_FOREVER,
e0a431b3
CM
548 },
549 { .name = "ENODEV",
77169812
ES
550 .max_retries = 0, /* We can't recover from devices disappearing */
551 .retry_timeout = 0,
e0a431b3 552 },
ef6a50fb
CM
553};
554
555static int
556xfs_error_sysfs_init_class(
557 struct xfs_mount *mp,
558 int class,
559 const char *parent_name,
560 struct xfs_kobj *parent_kobj,
561 const struct xfs_error_init init[])
562{
563 struct xfs_error_cfg *cfg;
564 int error;
565 int i;
566
567 ASSERT(class < XFS_ERR_CLASS_MAX);
568
569 error = xfs_sysfs_init(parent_kobj, &xfs_error_ktype,
570 &mp->m_error_kobj, parent_name);
571 if (error)
572 return error;
573
574 for (i = 0; i < XFS_ERR_ERRNO_MAX; i++) {
575 cfg = &mp->m_error_cfg[class][i];
576 error = xfs_sysfs_init(&cfg->kobj, &xfs_error_cfg_ktype,
577 parent_kobj, init[i].name);
578 if (error)
579 goto out_error;
580
581 cfg->max_retries = init[i].max_retries;
77169812
ES
582 if (init[i].retry_timeout == XFS_ERR_RETRY_FOREVER)
583 cfg->retry_timeout = XFS_ERR_RETRY_FOREVER;
584 else
585 cfg->retry_timeout = msecs_to_jiffies(
a5ea70d2 586 init[i].retry_timeout * MSEC_PER_SEC);
ef6a50fb
CM
587 }
588 return 0;
589
590out_error:
591 /* unwind the entries that succeeded */
592 for (i--; i >= 0; i--) {
593 cfg = &mp->m_error_cfg[class][i];
594 xfs_sysfs_del(&cfg->kobj);
595 }
596 xfs_sysfs_del(parent_kobj);
597 return error;
598}
599
192852be
CM
600int
601xfs_error_sysfs_init(
602 struct xfs_mount *mp)
603{
604 int error;
605
606 /* .../xfs/<dev>/error/ */
607 error = xfs_sysfs_init(&mp->m_error_kobj, &xfs_error_ktype,
608 &mp->m_kobj, "error");
ffd40ef6
CM
609 if (error)
610 return error;
611
e6b3bb78
CM
612 error = sysfs_create_file(&mp->m_error_kobj.kobject,
613 ATTR_LIST(fail_at_unmount));
614
615 if (error)
616 goto out_error;
617
ffd40ef6 618 /* .../xfs/<dev>/error/metadata/ */
ef6a50fb
CM
619 error = xfs_error_sysfs_init_class(mp, XFS_ERR_METADATA,
620 "metadata", &mp->m_error_meta_kobj,
621 xfs_error_meta_init);
ffd40ef6
CM
622 if (error)
623 goto out_error;
624
ffd40ef6
CM
625 return 0;
626
ffd40ef6
CM
627out_error:
628 xfs_sysfs_del(&mp->m_error_kobj);
192852be
CM
629 return error;
630}
631
632void
633xfs_error_sysfs_del(
634 struct xfs_mount *mp)
635{
ffd40ef6
CM
636 struct xfs_error_cfg *cfg;
637 int i, j;
638
639 for (i = 0; i < XFS_ERR_CLASS_MAX; i++) {
640 for (j = 0; j < XFS_ERR_ERRNO_MAX; j++) {
641 cfg = &mp->m_error_cfg[i][j];
642
643 xfs_sysfs_del(&cfg->kobj);
644 }
645 }
646 xfs_sysfs_del(&mp->m_error_meta_kobj);
192852be
CM
647 xfs_sysfs_del(&mp->m_error_kobj);
648}
df309390
CM
649
650struct xfs_error_cfg *
651xfs_error_get_cfg(
652 struct xfs_mount *mp,
653 int error_class,
654 int error)
655{
656 struct xfs_error_cfg *cfg;
657
e97f6c54
ES
658 if (error < 0)
659 error = -error;
660
df309390 661 switch (error) {
e0a431b3
CM
662 case EIO:
663 cfg = &mp->m_error_cfg[error_class][XFS_ERR_EIO];
664 break;
665 case ENOSPC:
666 cfg = &mp->m_error_cfg[error_class][XFS_ERR_ENOSPC];
667 break;
668 case ENODEV:
669 cfg = &mp->m_error_cfg[error_class][XFS_ERR_ENODEV];
670 break;
df309390
CM
671 default:
672 cfg = &mp->m_error_cfg[error_class][XFS_ERR_DEFAULT];
673 break;
674 }
675
676 return cfg;
677}