Whamcloud - gitweb
cf0ee83a91efb98489b279ac65969f13d636b358
[fs/lustre-release.git] / lustre / osp / lproc_osp.c
1 /*
2  * GPL HEADER START
3  *
4  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
5  *
6  * This program is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License version 2 only,
8  * as published by the Free Software Foundation.
9  *
10  * This program is distributed in the hope that it will be useful, but
11  * WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13  * General Public License version 2 for more details (a copy is included
14  * in the LICENSE file that accompanied this code).
15  *
16  * You should have received a copy of the GNU General Public License
17  * version 2 along with this program; If not, see
18  * http://www.gnu.org/licenses/gpl-2.0.html
19  *
20  * GPL HEADER END
21  */
22 /*
23  * Copyright (c) 2007, 2010, Oracle and/or its affiliates. All rights reserved.
24  * Use is subject to license terms.
25  *
26  * Copyright (c) 2012, 2015, Intel Corporation.
27  */
28 /*
29  * This file is part of Lustre, http://www.lustre.org/
30  * Lustre is a trademark of Sun Microsystems, Inc.
31  *
32  * lustre/osp/lproc_osp.c
33  *
34  * Lustre OST Proxy Device (OSP), procfs functions
35  *
36  * Author: Alex Zhuravlev <alexey.zhuravlev@intel.com>
37  */
38
39 #define DEBUG_SUBSYSTEM S_CLASS
40
41 #include "osp_internal.h"
42
43 #ifdef CONFIG_PROC_FS
44 /**
45  * Show OSP active status
46  *
47  * \param[in] m         seq_file handle
48  * \param[in] data      unused for single entry
49  * \retval              0 on success
50  * \retval              negative number on error
51  */
52 static int osp_active_seq_show(struct seq_file *m, void *data)
53 {
54         struct obd_device       *dev = m->private;
55
56         LPROCFS_CLIMP_CHECK(dev);
57         seq_printf(m, "%d\n", !dev->u.cli.cl_import->imp_deactive);
58         LPROCFS_CLIMP_EXIT(dev);
59         return 0;
60 }
61
62 /**
63  * Activate/Deactivate OSP
64  *
65  * \param[in] file      proc file
66  * \param[in] buffer    string, which is "1" or "0" to activate/deactivate OSP
67  * \param[in] count     \a buffer length
68  * \param[in] off       unused for single entry
69  * \retval              \a count on success
70  * \retval              negative number on error
71  */
72 static ssize_t
73 osp_active_seq_write(struct file *file, const char __user *buffer,
74                         size_t count, loff_t *off)
75 {
76         struct seq_file   *m = file->private_data;
77         struct obd_device *dev = m->private;
78         int                val, rc;
79
80         rc = lprocfs_write_helper(buffer, count, &val);
81         if (rc)
82                 return rc;
83         if (val < 0 || val > 1)
84                 return -ERANGE;
85
86         LPROCFS_CLIMP_CHECK(dev);
87         /* opposite senses */
88         if (dev->u.cli.cl_import->imp_deactive == val)
89                 rc = ptlrpc_set_import_active(dev->u.cli.cl_import, val);
90         else
91                 CDEBUG(D_CONFIG, "activate %d: ignoring repeat request\n",
92                        val);
93
94         LPROCFS_CLIMP_EXIT(dev);
95         return count;
96 }
97 LPROC_SEQ_FOPS(osp_active);
98
99 /**
100  * Show number of RPCs in flight
101  *
102  * \param[in] m         seq_file handle
103  * \param[in] data      unused for single entry
104  * \retval              0 on success
105  * \retval              negative number on error
106  */
107 static int osp_syn_in_flight_seq_show(struct seq_file *m, void *data)
108 {
109         struct obd_device       *dev = m->private;
110         struct osp_device       *osp = lu2osp_dev(dev->obd_lu_dev);
111
112         if (osp == NULL)
113                 return -EINVAL;
114
115         seq_printf(m, "%u\n", osp->opd_syn_rpc_in_flight);
116         return 0;
117 }
118 LPROC_SEQ_FOPS_RO(osp_syn_in_flight);
119
120 /**
121  * Show number of RPCs in processing (including uncommitted by OST)
122  *
123  * \param[in] m         seq_file handle
124  * \param[in] data      unused for single entry
125  * \retval              0 on success
126  * \retval              negative number on error
127  */
128 static int osp_syn_in_prog_seq_show(struct seq_file *m, void *data)
129 {
130         struct obd_device       *dev = m->private;
131         struct osp_device       *osp = lu2osp_dev(dev->obd_lu_dev);
132
133         if (osp == NULL)
134                 return -EINVAL;
135
136         seq_printf(m, "%u\n", osp->opd_syn_rpc_in_progress);
137         return 0;
138 }
139 LPROC_SEQ_FOPS_RO(osp_syn_in_prog);
140
141 /**
142  * Show number of changes to sync
143  *
144  * \param[in] m         seq_file handle
145  * \param[in] data      unused for single entry
146  * \retval              0 on success
147  * \retval              negative number on error
148  */
149 static int osp_syn_changes_seq_show(struct seq_file *m, void *data)
150 {
151         struct obd_device       *dev = m->private;
152         struct osp_device       *osp = lu2osp_dev(dev->obd_lu_dev);
153
154         if (osp == NULL)
155                 return -EINVAL;
156
157         seq_printf(m, "%lu\n", osp->opd_syn_changes);
158         return 0;
159 }
160
161 /**
162  * Sync changes
163  *
164  * \param[in] file      proc file
165  * \param[in] buffer    unused because any input will do
166  * \param[in] count     \a buffer length
167  * \param[in] off       unused for single entry
168  * \retval              \a count on success
169  * \retval              negative number on error
170  */
171 static ssize_t osp_syn_changes_seq_write(struct file *file,
172                                          const char __user *buffer,
173                                          size_t count, loff_t *off)
174 {
175         struct seq_file         *m      = file->private_data;
176         struct obd_device       *dev    = m->private;
177         struct osp_device       *osp    = lu2osp_dev(dev->obd_lu_dev);
178         struct lu_env            env;
179         int                      rc;
180
181         rc = lu_env_init(&env, LCT_LOCAL);
182         if (rc != 0)
183                 return rc;
184
185         rc = dt_sync(&env, &osp->opd_dt_dev);
186         lu_env_fini(&env);
187
188         return rc == 0 ? count : rc;
189 }
190 LPROC_SEQ_FOPS(osp_syn_changes);
191
192 /**
193  * Show maximum number of RPCs in flight allowed
194  *
195  * \param[in] m         seq_file handle
196  * \param[in] data      unused for single entry
197  * \retval              0 on success
198  * \retval              negative number on error
199  */
200 static int osp_max_rpcs_in_flight_seq_show(struct seq_file *m, void *data)
201 {
202         struct obd_device       *dev = m->private;
203         struct osp_device       *osp = lu2osp_dev(dev->obd_lu_dev);
204
205         if (osp == NULL)
206                 return -EINVAL;
207
208         seq_printf(m, "%u\n", osp->opd_syn_max_rpc_in_flight);
209         return 0;
210 }
211
212 /**
213  * Change maximum number of RPCs in flight allowed
214  *
215  * \param[in] file      proc file
216  * \param[in] buffer    string which represents maximum number
217  * \param[in] count     \a buffer length
218  * \param[in] off       unused for single entry
219  * \retval              \a count on success
220  * \retval              negative number on error
221  */
222 static ssize_t
223 osp_max_rpcs_in_flight_seq_write(struct file *file, const char __user *buffer,
224                                 size_t count, loff_t *off)
225 {
226         struct seq_file         *m = file->private_data;
227         struct obd_device       *dev = m->private;
228         struct osp_device       *osp = lu2osp_dev(dev->obd_lu_dev);
229         int                      val, rc;
230
231         if (osp == NULL)
232                 return -EINVAL;
233
234         rc = lprocfs_write_helper(buffer, count, &val);
235         if (rc)
236                 return rc;
237
238         if (val < 1)
239                 return -ERANGE;
240
241         osp->opd_syn_max_rpc_in_flight = val;
242         return count;
243 }
244 LPROC_SEQ_FOPS(osp_max_rpcs_in_flight);
245
246 /**
247  * Show maximum number of RPCs in processing allowed
248  *
249  * \param[in] m         seq_file handle
250  * \param[in] data      unused
251  * \retval              0 on success
252  * \retval              negative number on error
253  */
254 static int osp_max_rpcs_in_prog_seq_show(struct seq_file *m, void *data)
255 {
256         struct obd_device       *dev = m->private;
257         struct osp_device       *osp = lu2osp_dev(dev->obd_lu_dev);
258
259         if (osp == NULL)
260                 return -EINVAL;
261
262         seq_printf(m, "%u\n", osp->opd_syn_max_rpc_in_progress);
263         return 0;
264 }
265
266 /**
267  * Change maximum number of RPCs in processing allowed
268  *
269  * \param[in] file      proc file
270  * \param[in] buffer    string which represents maximum number
271  * \param[in] count     \a buffer length
272  * \param[in] off       unused for single entry
273  * \retval              \a count on success
274  * \retval              negative number on error
275  */
276 static ssize_t
277 osp_max_rpcs_in_prog_seq_write(struct file *file, const char __user *buffer,
278                                 size_t count, loff_t *off)
279 {
280         struct seq_file         *m = file->private_data;
281         struct obd_device       *dev = m->private;
282         struct osp_device       *osp = lu2osp_dev(dev->obd_lu_dev);
283         int                      val, rc;
284
285         if (osp == NULL)
286                 return -EINVAL;
287
288         rc = lprocfs_write_helper(buffer, count, &val);
289         if (rc)
290                 return rc;
291
292         if (val < 1)
293                 return -ERANGE;
294
295         osp->opd_syn_max_rpc_in_progress = val;
296
297         return count;
298 }
299 LPROC_SEQ_FOPS(osp_max_rpcs_in_prog);
300
301 /**
302  * Show number of objects to precreate next time
303  *
304  * \param[in] m         seq_file handle
305  * \param[in] data      unused for single entry
306  * \retval              0 on success
307  * \retval              negative number on error
308  */
309 static int osp_create_count_seq_show(struct seq_file *m, void *data)
310 {
311         struct obd_device *obd = m->private;
312         struct osp_device *osp = lu2osp_dev(obd->obd_lu_dev);
313
314         if (osp == NULL || osp->opd_pre == NULL)
315                 return 0;
316
317         seq_printf(m, "%d\n", osp->opd_pre_create_count);
318         return 0;
319 }
320
321 /**
322  * Change number of objects to precreate next time
323  *
324  * \param[in] file      proc file
325  * \param[in] buffer    string which represents number of objects to precreate
326  * \param[in] count     \a buffer length
327  * \param[in] off       unused for single entry
328  * \retval              \a count on success
329  * \retval              negative number on error
330  */
331 static ssize_t
332 osp_create_count_seq_write(struct file *file, const char __user *buffer,
333                                 size_t count, loff_t *off)
334 {
335         struct seq_file         *m = file->private_data;
336         struct obd_device       *obd = m->private;
337         struct osp_device       *osp = lu2osp_dev(obd->obd_lu_dev);
338         int                      val, rc, i;
339
340         if (osp == NULL || osp->opd_pre == NULL)
341                 return 0;
342
343         rc = lprocfs_write_helper(buffer, count, &val);
344         if (rc)
345                 return rc;
346
347         /* The MDT ALWAYS needs to limit the precreate count to
348          * OST_MAX_PRECREATE, and the constant cannot be changed
349          * because it is a value shared between the OSP and OST
350          * that is the maximum possible number of objects that will
351          * ever be handled by MDT->OST recovery processing.
352          *
353          * If the OST ever gets a request to delete more orphans,
354          * this implies that something has gone badly on the MDT
355          * and the OST will refuse to delete so much data from the
356          * filesystem as a safety measure. */
357         if (val < OST_MIN_PRECREATE || val > OST_MAX_PRECREATE)
358                 return -ERANGE;
359         if (val > osp->opd_pre_max_create_count)
360                 return -ERANGE;
361
362         for (i = 1; (i << 1) <= val; i <<= 1)
363                 ;
364         osp->opd_pre_create_count = i;
365
366         return count;
367 }
368 LPROC_SEQ_FOPS(osp_create_count);
369
370 /**
371  * Show maximum number of objects to precreate
372  *
373  * \param[in] m         seq_file handle
374  * \param[in] data      unused for single entry
375  * \retval              0 on success
376  * \retval              negative number on error
377  */
378 static int osp_max_create_count_seq_show(struct seq_file *m, void *data)
379 {
380         struct obd_device *obd = m->private;
381         struct osp_device *osp = lu2osp_dev(obd->obd_lu_dev);
382
383         if (osp == NULL || osp->opd_pre == NULL)
384                 return 0;
385
386         seq_printf(m, "%d\n", osp->opd_pre_max_create_count);
387         return 0;
388 }
389
390 /**
391  * Change maximum number of objects to precreate
392  *
393  * \param[in] file      proc file
394  * \param[in] buffer    string which represents maximum number
395  * \param[in] count     \a buffer length
396  * \param[in] off       unused for single entry
397  * \retval              \a count on success
398  * \retval              negative number on error
399  */
400 static ssize_t
401 osp_max_create_count_seq_write(struct file *file, const char __user *buffer,
402                                 size_t count, loff_t *off)
403 {
404         struct seq_file         *m = file->private_data;
405         struct obd_device       *obd = m->private;
406         struct osp_device       *osp = lu2osp_dev(obd->obd_lu_dev);
407         int                      val, rc;
408
409         if (osp == NULL || osp->opd_pre == NULL)
410                 return 0;
411
412         rc = lprocfs_write_helper(buffer, count, &val);
413         if (rc)
414                 return rc;
415
416         if (val < 0)
417                 return -ERANGE;
418         if (val > OST_MAX_PRECREATE)
419                 return -ERANGE;
420
421         if (osp->opd_pre_create_count > val)
422                 osp->opd_pre_create_count = val;
423
424         osp->opd_pre_max_create_count = val;
425
426         return count;
427 }
428 LPROC_SEQ_FOPS(osp_max_create_count);
429
430 /**
431  * Show last id to assign in creation
432  *
433  * \param[in] m         seq_file handle
434  * \param[in] data      unused for single entry
435  * \retval              0 on success
436  * \retval              negative number on error
437  */
438 static int osp_prealloc_next_id_seq_show(struct seq_file *m, void *data)
439 {
440         struct obd_device *obd = m->private;
441         struct osp_device *osp = lu2osp_dev(obd->obd_lu_dev);
442
443         if (osp == NULL || osp->opd_pre == NULL)
444                 return 0;
445
446         seq_printf(m, "%u\n", fid_oid(&osp->opd_pre_used_fid) + 1);
447         return 0;
448 }
449 LPROC_SEQ_FOPS_RO(osp_prealloc_next_id);
450
451 /**
452  * Show last created id OST reported
453  *
454  * \param[in] m         seq_file handle
455  * \param[in] data      unused for single entry
456  * \retval              0 on success
457  * \retval              negative number on error
458  */
459 static int osp_prealloc_last_id_seq_show(struct seq_file *m, void *data)
460 {
461         struct obd_device *obd = m->private;
462         struct osp_device *osp = lu2osp_dev(obd->obd_lu_dev);
463
464         if (osp == NULL || osp->opd_pre == NULL)
465                 return 0;
466
467         seq_printf(m, "%u\n", fid_oid(&osp->opd_pre_last_created_fid));
468         return 0;
469 }
470 LPROC_SEQ_FOPS_RO(osp_prealloc_last_id);
471
472 /**
473  * Show next FID sequence to precreate
474  *
475  * \param[in] m         seq_file handle
476  * \param[in] data      unused for single entry
477  * \retval              0 on success
478  * \retval              negative number on error
479  */
480 static int osp_prealloc_next_seq_seq_show(struct seq_file *m, void *data)
481 {
482         struct obd_device *obd = m->private;
483         struct osp_device *osp = lu2osp_dev(obd->obd_lu_dev);
484
485         if (osp == NULL || osp->opd_pre == NULL)
486                 return 0;
487
488         seq_printf(m, LPX64"\n", fid_seq(&osp->opd_pre_used_fid));
489         return 0;
490 }
491 LPROC_SEQ_FOPS_RO(osp_prealloc_next_seq);
492
493 /**
494  * Show last created FID sequence OST reported
495  *
496  * \param[in] m         seq_file handle
497  * \param[in] data      unused for single entry
498  * \retval              0 on success
499  * \retval              negative number on error
500  */
501 static int osp_prealloc_last_seq_seq_show(struct seq_file *m, void *data)
502 {
503         struct obd_device *obd = m->private;
504         struct osp_device *osp = lu2osp_dev(obd->obd_lu_dev);
505
506         if (osp == NULL || osp->opd_pre == NULL)
507                 return 0;
508
509         seq_printf(m, LPX64"\n",
510                    fid_seq(&osp->opd_pre_last_created_fid));
511         return 0;
512 }
513 LPROC_SEQ_FOPS_RO(osp_prealloc_last_seq);
514
515 /**
516  * Show the number of ids reserved by declare
517  *
518  * \param[in] m         seq_file handle
519  * \param[in] data      unused for single entry
520  * \retval              0 on success
521  * \retval              negative number on error
522  */
523 static int osp_prealloc_reserved_seq_show(struct seq_file *m, void *data)
524 {
525         struct obd_device *obd = m->private;
526         struct osp_device *osp = lu2osp_dev(obd->obd_lu_dev);
527
528         if (osp == NULL || osp->opd_pre == NULL)
529                 return 0;
530
531         seq_printf(m, LPU64"\n", osp->opd_pre_reserved);
532         return 0;
533 }
534 LPROC_SEQ_FOPS_RO(osp_prealloc_reserved);
535
536 /**
537  * Show interval (in seconds) to update statfs data
538  *
539  * \param[in] m         seq_file handle
540  * \param[in] data      unused for single entry
541  * \retval              0 on success
542  * \retval              negative number on error
543  */
544 static int osp_maxage_seq_show(struct seq_file *m, void *data)
545 {
546         struct obd_device       *dev = m->private;
547         struct osp_device       *osp = lu2osp_dev(dev->obd_lu_dev);
548
549         if (osp == NULL)
550                 return -EINVAL;
551
552         seq_printf(m, "%u\n", osp->opd_statfs_maxage);
553         return 0;
554 }
555
556 /**
557  * Change interval to update statfs data
558  *
559  * \param[in] file      proc file
560  * \param[in] buffer    string which represents statfs interval (in seconds)
561  * \param[in] count     \a buffer length
562  * \param[in] off       unused for single entry
563  * \retval              \a count on success
564  * \retval              negative number on error
565  */
566 static ssize_t
567 osp_maxage_seq_write(struct file *file, const char __user *buffer,
568                         size_t count, loff_t *off)
569 {
570         struct seq_file         *m = file->private_data;
571         struct obd_device       *dev = m->private;
572         struct osp_device       *osp = lu2osp_dev(dev->obd_lu_dev);
573         int                      val, rc;
574
575         if (osp == NULL)
576                 return -EINVAL;
577
578         rc = lprocfs_write_helper(buffer, count, &val);
579         if (rc)
580                 return rc;
581
582         if (val < 1)
583                 return -ERANGE;
584
585         osp->opd_statfs_maxage = val;
586
587         return count;
588 }
589 LPROC_SEQ_FOPS(osp_maxage);
590
591 /**
592  * Show current precreation status: output 0 means success, otherwise negative
593  * number is printed
594  *
595  * \param[in] m         seq_file handle
596  * \param[in] data      unused for single entry
597  * \retval              0 on success
598  * \retval              negative number on error
599  */
600 static int osp_pre_status_seq_show(struct seq_file *m, void *data)
601 {
602         struct obd_device       *dev = m->private;
603         struct osp_device       *osp = lu2osp_dev(dev->obd_lu_dev);
604
605         if (osp == NULL || osp->opd_pre == NULL)
606                 return -EINVAL;
607
608         seq_printf(m, "%d\n", osp->opd_pre_status);
609         return 0;
610 }
611 LPROC_SEQ_FOPS_RO(osp_pre_status);
612
613 /**
614  * Show the number of RPCs in processing (including uncommitted by OST) plus
615  * changes to sync, i.e. this is the total number of changes OST needs to apply
616  * and commit.
617  *
618  * This counter is used to determine if OST has space returned. A zero value
619  * indicates that OST storage space consumed by destroyed objects has been freed
620  * on disk, the associated llog records have been cleared, and no synchronous
621  * RPC are being processed.
622  *
623  * \param[in] m         seq_file handle
624  * \param[in] data      unused for single entry
625  * \retval              0 on success
626  * \retval              negative number on error
627  */
628 static int osp_destroys_in_flight_seq_show(struct seq_file *m, void *data)
629 {
630         struct obd_device *dev = m->private;
631         struct osp_device *osp = lu2osp_dev(dev->obd_lu_dev);
632
633         if (osp == NULL)
634                 return -EINVAL;
635
636         seq_printf(m, "%lu\n",
637                    osp->opd_syn_rpc_in_progress + osp->opd_syn_changes);
638         return 0;
639 }
640 LPROC_SEQ_FOPS_RO(osp_destroys_in_flight);
641
642 /**
643  * Show changes synced from previous mount
644  *
645  * \param[in] m         seq_file handle
646  * \param[in] data      unused for single entry
647  * \retval              0 on success
648  * \retval              negative number on error
649  */
650 static int osp_old_sync_processed_seq_show(struct seq_file *m, void *data)
651 {
652         struct obd_device       *dev = m->private;
653         struct osp_device       *osp = lu2osp_dev(dev->obd_lu_dev);
654
655         if (osp == NULL)
656                 return -EINVAL;
657
658         seq_printf(m, "%d\n", osp->opd_syn_prev_done);
659         return 0;
660 }
661 LPROC_SEQ_FOPS_RO(osp_old_sync_processed);
662
663 /**
664  * Show maximum number of RPCs in flight
665  *
666  * \param[in] m         seq_file handle
667  * \param[in] data      unused for single entry
668  * \retval              0 on success
669  * \retval              negative number on error
670  */
671 static int
672 osp_lfsck_max_rpcs_in_flight_seq_show(struct seq_file *m, void *data)
673 {
674         struct obd_device *dev = m->private;
675         __u32 max;
676
677         max = obd_get_max_rpcs_in_flight(&dev->u.cli);
678         seq_printf(m, "%u\n", max);
679         return 0;
680 }
681
682 /**
683  * Change maximum number of RPCs in flight
684  *
685  * \param[in] file      proc file
686  * \param[in] buffer    string which represents maximum number of RPCs in flight
687  * \param[in] count     \a buffer length
688  * \param[in] off       unused for single entry
689  * \retval              \a count on success
690  * \retval              negative number on error
691  */
692 static ssize_t
693 osp_lfsck_max_rpcs_in_flight_seq_write(struct file *file,
694                                        const char __user *buffer,
695                                        size_t count, loff_t *off)
696 {
697         struct seq_file   *m = file->private_data;
698         struct obd_device *dev = m->private;
699         int val;
700         int rc;
701
702         rc = lprocfs_write_helper(buffer, count, &val);
703         if (rc == 0)
704                 rc = obd_set_max_rpcs_in_flight(&dev->u.cli, val);
705
706         if (rc != 0)
707                 count = rc;
708
709         return count;
710 }
711 LPROC_SEQ_FOPS(osp_lfsck_max_rpcs_in_flight);
712
713 LPROC_SEQ_FOPS_WO_TYPE(osp, ping);
714 LPROC_SEQ_FOPS_RO_TYPE(osp, uuid);
715 LPROC_SEQ_FOPS_RO_TYPE(osp, connect_flags);
716 LPROC_SEQ_FOPS_RO_TYPE(osp, server_uuid);
717 LPROC_SEQ_FOPS_RO_TYPE(osp, conn_uuid);
718
719 /**
720  * Show maximum pages per bulk RPC
721  *
722  * \param[in] m         seq_file handle
723  * \param[in] data      unused for single entry
724  * \retval              0 on success
725  * \retval              negative number on error
726  */
727 static int osp_max_pages_per_rpc_seq_show(struct seq_file *m, void *v)
728 {
729         return lprocfs_obd_max_pages_per_rpc_seq_show(m, m->private);
730 }
731 LPROC_SEQ_FOPS_RO(osp_max_pages_per_rpc);
732 LPROC_SEQ_FOPS_RO_TYPE(osp, timeouts);
733
734 LPROC_SEQ_FOPS_RW_TYPE(osp, import);
735 LPROC_SEQ_FOPS_RO_TYPE(osp, state);
736
737 static struct lprocfs_vars lprocfs_osp_obd_vars[] = {
738         { .name =       "uuid",
739           .fops =       &osp_uuid_fops                  },
740         { .name =       "ping",
741           .fops =       &osp_ping_fops,
742           .proc_mode =  0222                            },
743         { .name =       "connect_flags",
744           .fops =       &osp_connect_flags_fops         },
745         { .name =       "ost_server_uuid",
746           .fops =       &osp_server_uuid_fops           },
747         { .name =       "ost_conn_uuid",
748           .fops =       &osp_conn_uuid_fops             },
749         { .name =       "active",
750           .fops =       &osp_active_fops                },
751         { .name =       "max_rpcs_in_flight",
752           .fops =       &osp_max_rpcs_in_flight_fops    },
753         { .name =       "max_rpcs_in_progress",
754           .fops =       &osp_max_rpcs_in_prog_fops      },
755         { .name =       "create_count",
756           .fops =       &osp_create_count_fops          },
757         { .name =       "max_create_count",
758           .fops =       &osp_max_create_count_fops      },
759         { .name =       "prealloc_next_id",
760           .fops =       &osp_prealloc_next_id_fops      },
761         { .name =       "prealloc_next_seq",
762           .fops =       &osp_prealloc_next_seq_fops     },
763         { .name =       "prealloc_last_id",
764           .fops =       &osp_prealloc_last_id_fops      },
765         { .name =       "prealloc_last_seq",
766           .fops =       &osp_prealloc_last_seq_fops     },
767         { .name =       "prealloc_reserved",
768           .fops =       &osp_prealloc_reserved_fops     },
769         { .name =       "timeouts",
770           .fops =       &osp_timeouts_fops              },
771         { .name =       "import",
772           .fops =       &osp_import_fops                },
773         { .name =       "state",
774           .fops =       &osp_state_fops                 },
775         { .name =       "maxage",
776           .fops =       &osp_maxage_fops                },
777         { .name =       "prealloc_status",
778           .fops =       &osp_pre_status_fops            },
779         { .name =       "sync_changes",
780           .fops =       &osp_syn_changes_fops           },
781         { .name =       "sync_in_flight",
782           .fops =       &osp_syn_in_flight_fops         },
783         { .name =       "sync_in_progress",
784           .fops =       &osp_syn_in_prog_fops           },
785         { .name =       "old_sync_processed",
786           .fops =       &osp_old_sync_processed_fops    },
787
788         /* for compatibility reasons */
789         { .name =       "destroys_in_flight",
790           .fops =       &osp_destroys_in_flight_fops            },
791         { .name =       "lfsck_max_rpcs_in_flight",
792           .fops =       &osp_lfsck_max_rpcs_in_flight_fops      },
793         { NULL }
794 };
795
796 static struct lprocfs_vars lprocfs_osp_md_vars[] = {
797         { .name =       "uuid",
798           .fops =       &osp_uuid_fops                  },
799         { .name =       "ping",
800           .fops =       &osp_ping_fops,
801           .proc_mode =  0222                            },
802         { .name =       "connect_flags",
803           .fops =       &osp_connect_flags_fops         },
804         { .name =       "mdt_server_uuid",
805           .fops =       &osp_server_uuid_fops           },
806         { .name =       "mdt_conn_uuid",
807           .fops =       &osp_conn_uuid_fops             },
808         { .name =       "active",
809           .fops =       &osp_active_fops                },
810         { .name =       "max_rpcs_in_flight",
811           .fops =       &osp_max_rpcs_in_flight_fops    },
812         { .name =       "max_rpcs_in_progress",
813           .fops =       &osp_max_rpcs_in_prog_fops      },
814         { .name =       "timeouts",
815           .fops =       &osp_timeouts_fops              },
816         { .name =       "import",
817           .fops =       &osp_import_fops                },
818         { .name =       "state",
819           .fops =       &osp_state_fops                 },
820         { .name =       "maxage",
821           .fops =       &osp_maxage_fops                },
822         { .name =       "prealloc_status",
823           .fops =       &osp_pre_status_fops            },
824
825         /* for compatibility reasons */
826         { .name =       "destroys_in_flight",
827           .fops =       &osp_destroys_in_flight_fops            },
828         { .name =       "lfsck_max_rpcs_in_flight",
829           .fops =       &osp_lfsck_max_rpcs_in_flight_fops      },
830         { NULL }
831 };
832
833 LPROC_SEQ_FOPS_RO_TYPE(osp, dt_blksize);
834 LPROC_SEQ_FOPS_RO_TYPE(osp, dt_kbytestotal);
835 LPROC_SEQ_FOPS_RO_TYPE(osp, dt_kbytesfree);
836 LPROC_SEQ_FOPS_RO_TYPE(osp, dt_kbytesavail);
837 LPROC_SEQ_FOPS_RO_TYPE(osp, dt_filestotal);
838 LPROC_SEQ_FOPS_RO_TYPE(osp, dt_filesfree);
839
840 static struct lprocfs_vars lprocfs_osp_osd_vars[] = {
841         { .name =       "blocksize",
842           .fops =       &osp_dt_blksize_fops            },
843         { .name =       "kbytestotal",
844           .fops =       &osp_dt_kbytestotal_fops        },
845         { .name =       "kbytesfree",
846           .fops =       &osp_dt_kbytesfree_fops         },
847         { .name =       "kbytesavail",
848           .fops =       &osp_dt_kbytesavail_fops        },
849         { .name =       "filestotal",
850           .fops =       &osp_dt_filestotal_fops         },
851         { .name =       "filesfree",
852           .fops =       &osp_dt_filesfree_fops          },
853         { NULL }
854 };
855
856 /**
857  * Initialize OSP lprocfs
858  *
859  * param[in] osp        OSP device
860  */
861 void osp_lprocfs_init(struct osp_device *osp)
862 {
863         struct obd_device       *obd = osp->opd_obd;
864         struct proc_dir_entry   *osc_proc_dir = NULL;
865         struct obd_type         *type;
866         int                      rc;
867
868         if (osp->opd_connect_mdt)
869                 obd->obd_vars = lprocfs_osp_md_vars;
870         else
871                 obd->obd_vars = lprocfs_osp_obd_vars;
872         if (lprocfs_obd_setup(obd) != 0)
873                 return;
874
875         rc = lprocfs_add_vars(obd->obd_proc_entry, lprocfs_osp_osd_vars,
876                               &osp->opd_dt_dev);
877         if (rc) {
878                 CERROR("%s: can't register in lprocfs, rc %d\n",
879                        obd->obd_name, rc);
880                 return;
881         }
882
883         sptlrpc_lprocfs_cliobd_attach(obd);
884         ptlrpc_lprocfs_register_obd(obd);
885
886         if (osp->opd_connect_mdt || !strstr(obd->obd_name, "osc"))
887                 return;
888
889         /* If the real OSC is present which is the case for setups
890          * with both server and clients on the same node then use
891          * the OSC's proc root */
892         type = class_search_type(LUSTRE_OSC_NAME);
893         if (type != NULL && type->typ_procroot != NULL)
894                 osc_proc_dir = type->typ_procroot;
895         else
896                 osc_proc_dir = obd->obd_type->typ_procsym;
897
898         if (osc_proc_dir == NULL)
899                 return;
900
901         /* for compatibility we link old procfs's OSC entries to osp ones */
902         osp->opd_symlink = lprocfs_add_symlink(obd->obd_name, osc_proc_dir,
903                                                "../osp/%s", obd->obd_name);
904         if (osp->opd_symlink == NULL)
905                 CERROR("cannot create OSC symlink for /proc/fs/lustre/osp/%s\n",
906                        obd->obd_name);
907 }
908
909 #endif /* CONFIG_PROC_FS */
910