Linux Kernel  3.7.1
 All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros Groups Pages
sys.c
Go to the documentation of this file.
1 /*
2  * Copyright (C) Sistina Software, Inc. 1997-2003 All rights reserved.
3  * Copyright (C) 2004-2006 Red Hat, Inc. All rights reserved.
4  *
5  * This copyrighted material is made available to anyone wishing to use,
6  * modify, copy, or redistribute it subject to the terms and conditions
7  * of the GNU General Public License version 2.
8  */
9 
10 #include <linux/sched.h>
11 #include <linux/spinlock.h>
12 #include <linux/completion.h>
13 #include <linux/buffer_head.h>
14 #include <linux/module.h>
15 #include <linux/kobject.h>
16 #include <asm/uaccess.h>
17 #include <linux/gfs2_ondisk.h>
18 #include <linux/genhd.h>
19 
20 #include "gfs2.h"
21 #include "incore.h"
22 #include "sys.h"
23 #include "super.h"
24 #include "glock.h"
25 #include "quota.h"
26 #include "util.h"
27 #include "glops.h"
28 #include "recovery.h"
29 
30 struct gfs2_attr {
31  struct attribute attr;
32  ssize_t (*show)(struct gfs2_sbd *, char *);
33  ssize_t (*store)(struct gfs2_sbd *, const char *, size_t);
34 };
35 
36 static ssize_t gfs2_attr_show(struct kobject *kobj, struct attribute *attr,
37  char *buf)
38 {
39  struct gfs2_sbd *sdp = container_of(kobj, struct gfs2_sbd, sd_kobj);
40  struct gfs2_attr *a = container_of(attr, struct gfs2_attr, attr);
41  return a->show ? a->show(sdp, buf) : 0;
42 }
43 
44 static ssize_t gfs2_attr_store(struct kobject *kobj, struct attribute *attr,
45  const char *buf, size_t len)
46 {
47  struct gfs2_sbd *sdp = container_of(kobj, struct gfs2_sbd, sd_kobj);
48  struct gfs2_attr *a = container_of(attr, struct gfs2_attr, attr);
49  return a->store ? a->store(sdp, buf, len) : len;
50 }
51 
52 static const struct sysfs_ops gfs2_attr_ops = {
53  .show = gfs2_attr_show,
54  .store = gfs2_attr_store,
55 };
56 
57 
58 static struct kset *gfs2_kset;
59 
60 static ssize_t id_show(struct gfs2_sbd *sdp, char *buf)
61 {
62  return snprintf(buf, PAGE_SIZE, "%u:%u\n",
63  MAJOR(sdp->sd_vfs->s_dev), MINOR(sdp->sd_vfs->s_dev));
64 }
65 
66 static ssize_t fsname_show(struct gfs2_sbd *sdp, char *buf)
67 {
68  return snprintf(buf, PAGE_SIZE, "%s\n", sdp->sd_fsname);
69 }
70 
71 static int gfs2_uuid_valid(const u8 *uuid)
72 {
73  int i;
74 
75  for (i = 0; i < 16; i++) {
76  if (uuid[i])
77  return 1;
78  }
79  return 0;
80 }
81 
82 static ssize_t uuid_show(struct gfs2_sbd *sdp, char *buf)
83 {
84  struct super_block *s = sdp->sd_vfs;
85  const u8 *uuid = s->s_uuid;
86  buf[0] = '\0';
87  if (!gfs2_uuid_valid(uuid))
88  return 0;
89  return snprintf(buf, PAGE_SIZE, "%pUB\n", uuid);
90 }
91 
92 static ssize_t freeze_show(struct gfs2_sbd *sdp, char *buf)
93 {
94  unsigned int count;
95 
97  count = sdp->sd_freeze_count;
99 
100  return snprintf(buf, PAGE_SIZE, "%u\n", count);
101 }
102 
103 static ssize_t freeze_store(struct gfs2_sbd *sdp, const char *buf, size_t len)
104 {
105  ssize_t ret = len;
106  int error = 0;
107  int n = simple_strtol(buf, NULL, 0);
108 
109  if (!capable(CAP_SYS_ADMIN))
110  return -EACCES;
111 
112  switch (n) {
113  case 0:
114  gfs2_unfreeze_fs(sdp);
115  break;
116  case 1:
117  error = gfs2_freeze_fs(sdp);
118  break;
119  default:
120  ret = -EINVAL;
121  }
122 
123  if (error)
124  fs_warn(sdp, "freeze %d error %d", n, error);
125 
126  return ret;
127 }
128 
129 static ssize_t withdraw_show(struct gfs2_sbd *sdp, char *buf)
130 {
131  unsigned int b = test_bit(SDF_SHUTDOWN, &sdp->sd_flags);
132  return snprintf(buf, PAGE_SIZE, "%u\n", b);
133 }
134 
135 static ssize_t withdraw_store(struct gfs2_sbd *sdp, const char *buf, size_t len)
136 {
137  if (!capable(CAP_SYS_ADMIN))
138  return -EACCES;
139 
140  if (simple_strtol(buf, NULL, 0) != 1)
141  return -EINVAL;
142 
143  gfs2_lm_withdraw(sdp,
144  "GFS2: fsid=%s: withdrawing from cluster at user's request\n",
145  sdp->sd_fsname);
146  return len;
147 }
148 
149 static ssize_t statfs_sync_store(struct gfs2_sbd *sdp, const char *buf,
150  size_t len)
151 {
152  if (!capable(CAP_SYS_ADMIN))
153  return -EACCES;
154 
155  if (simple_strtol(buf, NULL, 0) != 1)
156  return -EINVAL;
157 
158  gfs2_statfs_sync(sdp->sd_vfs, 0);
159  return len;
160 }
161 
162 static ssize_t quota_sync_store(struct gfs2_sbd *sdp, const char *buf,
163  size_t len)
164 {
165  if (!capable(CAP_SYS_ADMIN))
166  return -EACCES;
167 
168  if (simple_strtol(buf, NULL, 0) != 1)
169  return -EINVAL;
170 
171  gfs2_quota_sync(sdp->sd_vfs, 0);
172  return len;
173 }
174 
175 static ssize_t quota_refresh_user_store(struct gfs2_sbd *sdp, const char *buf,
176  size_t len)
177 {
178  int error;
179  u32 id;
180 
181  if (!capable(CAP_SYS_ADMIN))
182  return -EACCES;
183 
184  id = simple_strtoul(buf, NULL, 0);
185 
186  error = gfs2_quota_refresh(sdp, 1, id);
187  return error ? error : len;
188 }
189 
190 static ssize_t quota_refresh_group_store(struct gfs2_sbd *sdp, const char *buf,
191  size_t len)
192 {
193  int error;
194  u32 id;
195 
196  if (!capable(CAP_SYS_ADMIN))
197  return -EACCES;
198 
199  id = simple_strtoul(buf, NULL, 0);
200 
201  error = gfs2_quota_refresh(sdp, 0, id);
202  return error ? error : len;
203 }
204 
205 static ssize_t demote_rq_store(struct gfs2_sbd *sdp, const char *buf, size_t len)
206 {
207  struct gfs2_glock *gl;
208  const struct gfs2_glock_operations *glops;
209  unsigned int glmode;
210  unsigned int gltype;
211  unsigned long long glnum;
212  char mode[16];
213  int rv;
214 
215  if (!capable(CAP_SYS_ADMIN))
216  return -EACCES;
217 
218  rv = sscanf(buf, "%u:%llu %15s", &gltype, &glnum,
219  mode);
220  if (rv != 3)
221  return -EINVAL;
222 
223  if (strcmp(mode, "EX") == 0)
224  glmode = LM_ST_UNLOCKED;
225  else if ((strcmp(mode, "CW") == 0) || (strcmp(mode, "DF") == 0))
226  glmode = LM_ST_DEFERRED;
227  else if ((strcmp(mode, "PR") == 0) || (strcmp(mode, "SH") == 0))
228  glmode = LM_ST_SHARED;
229  else
230  return -EINVAL;
231 
232  if (gltype > LM_TYPE_JOURNAL)
233  return -EINVAL;
234  if (gltype == LM_TYPE_NONDISK && glnum == GFS2_TRANS_LOCK)
235  glops = &gfs2_trans_glops;
236  else
237  glops = gfs2_glops_list[gltype];
238  if (glops == NULL)
239  return -EINVAL;
240  if (!test_and_set_bit(SDF_DEMOTE, &sdp->sd_flags))
241  fs_info(sdp, "demote interface used\n");
242  rv = gfs2_glock_get(sdp, glnum, glops, 0, &gl);
243  if (rv)
244  return rv;
245  gfs2_glock_cb(gl, glmode);
246  gfs2_glock_put(gl);
247  return len;
248 }
249 
250 
251 #define GFS2_ATTR(name, mode, show, store) \
252 static struct gfs2_attr gfs2_attr_##name = __ATTR(name, mode, show, store)
253 
254 GFS2_ATTR(id, 0444, id_show, NULL);
255 GFS2_ATTR(fsname, 0444, fsname_show, NULL);
256 GFS2_ATTR(uuid, 0444, uuid_show, NULL);
257 GFS2_ATTR(freeze, 0644, freeze_show, freeze_store);
258 GFS2_ATTR(withdraw, 0644, withdraw_show, withdraw_store);
259 GFS2_ATTR(statfs_sync, 0200, NULL, statfs_sync_store);
260 GFS2_ATTR(quota_sync, 0200, NULL, quota_sync_store);
261 GFS2_ATTR(quota_refresh_user, 0200, NULL, quota_refresh_user_store);
262 GFS2_ATTR(quota_refresh_group, 0200, NULL, quota_refresh_group_store);
263 GFS2_ATTR(demote_rq, 0200, NULL, demote_rq_store);
264 
265 static struct attribute *gfs2_attrs[] = {
266  &gfs2_attr_id.attr,
267  &gfs2_attr_fsname.attr,
268  &gfs2_attr_uuid.attr,
269  &gfs2_attr_freeze.attr,
270  &gfs2_attr_withdraw.attr,
271  &gfs2_attr_statfs_sync.attr,
272  &gfs2_attr_quota_sync.attr,
273  &gfs2_attr_quota_refresh_user.attr,
274  &gfs2_attr_quota_refresh_group.attr,
275  &gfs2_attr_demote_rq.attr,
276  NULL,
277 };
278 
279 static void gfs2_sbd_release(struct kobject *kobj)
280 {
281  struct gfs2_sbd *sdp = container_of(kobj, struct gfs2_sbd, sd_kobj);
282 
283  kfree(sdp);
284 }
285 
286 static struct kobj_type gfs2_ktype = {
287  .release = gfs2_sbd_release,
288  .default_attrs = gfs2_attrs,
289  .sysfs_ops = &gfs2_attr_ops,
290 };
291 
292 
293 /*
294  * lock_module. Originally from lock_dlm
295  */
296 
297 static ssize_t proto_name_show(struct gfs2_sbd *sdp, char *buf)
298 {
299  const struct lm_lockops *ops = sdp->sd_lockstruct.ls_ops;
300  return sprintf(buf, "%s\n", ops->lm_proto_name);
301 }
302 
303 static ssize_t block_show(struct gfs2_sbd *sdp, char *buf)
304 {
305  struct lm_lockstruct *ls = &sdp->sd_lockstruct;
306  ssize_t ret;
307  int val = 0;
308 
310  val = 1;
311  ret = sprintf(buf, "%d\n", val);
312  return ret;
313 }
314 
315 static ssize_t block_store(struct gfs2_sbd *sdp, const char *buf, size_t len)
316 {
317  struct lm_lockstruct *ls = &sdp->sd_lockstruct;
318  ssize_t ret = len;
319  int val;
320 
321  val = simple_strtol(buf, NULL, 0);
322 
323  if (val == 1)
325  else if (val == 0) {
328  gfs2_glock_thaw(sdp);
329  } else {
330  ret = -EINVAL;
331  }
332  return ret;
333 }
334 
335 static ssize_t lkfirst_show(struct gfs2_sbd *sdp, char *buf)
336 {
337  struct lm_lockstruct *ls = &sdp->sd_lockstruct;
338  return sprintf(buf, "%d\n", ls->ls_first);
339 }
340 
341 static ssize_t lkfirst_store(struct gfs2_sbd *sdp, const char *buf, size_t len)
342 {
343  unsigned first;
344  int rv;
345 
346  rv = sscanf(buf, "%u", &first);
347  if (rv != 1 || first > 1)
348  return -EINVAL;
350  if (rv)
351  return rv;
352  spin_lock(&sdp->sd_jindex_spin);
353  rv = -EBUSY;
354  if (test_bit(SDF_NOJOURNALID, &sdp->sd_flags) == 0)
355  goto out;
356  rv = -EINVAL;
357  if (sdp->sd_args.ar_spectator)
358  goto out;
359  if (sdp->sd_lockstruct.ls_ops->lm_mount == NULL)
360  goto out;
361  sdp->sd_lockstruct.ls_first = first;
362  rv = 0;
363 out:
364  spin_unlock(&sdp->sd_jindex_spin);
365  return rv ? rv : len;
366 }
367 
368 static ssize_t first_done_show(struct gfs2_sbd *sdp, char *buf)
369 {
370  struct lm_lockstruct *ls = &sdp->sd_lockstruct;
371  return sprintf(buf, "%d\n", !!test_bit(DFL_FIRST_MOUNT_DONE, &ls->ls_recover_flags));
372 }
373 
374 int gfs2_recover_set(struct gfs2_sbd *sdp, unsigned jid)
375 {
376  struct gfs2_jdesc *jd;
377  int rv;
378 
379  spin_lock(&sdp->sd_jindex_spin);
380  rv = -EBUSY;
381  if (sdp->sd_jdesc->jd_jid == jid)
382  goto out;
383  rv = -ENOENT;
385  if (jd->jd_jid != jid)
386  continue;
387  rv = gfs2_recover_journal(jd, false);
388  break;
389  }
390 out:
391  spin_unlock(&sdp->sd_jindex_spin);
392  return rv;
393 }
394 
395 static ssize_t recover_store(struct gfs2_sbd *sdp, const char *buf, size_t len)
396 {
397  unsigned jid;
398  int rv;
399 
400  rv = sscanf(buf, "%u", &jid);
401  if (rv != 1)
402  return -EINVAL;
403 
404  if (test_bit(SDF_NORECOVERY, &sdp->sd_flags)) {
405  rv = -ESHUTDOWN;
406  goto out;
407  }
408 
409  rv = gfs2_recover_set(sdp, jid);
410 out:
411  return rv ? rv : len;
412 }
413 
414 static ssize_t recover_done_show(struct gfs2_sbd *sdp, char *buf)
415 {
416  struct lm_lockstruct *ls = &sdp->sd_lockstruct;
417  return sprintf(buf, "%d\n", ls->ls_recover_jid_done);
418 }
419 
420 static ssize_t recover_status_show(struct gfs2_sbd *sdp, char *buf)
421 {
422  struct lm_lockstruct *ls = &sdp->sd_lockstruct;
423  return sprintf(buf, "%d\n", ls->ls_recover_jid_status);
424 }
425 
426 static ssize_t jid_show(struct gfs2_sbd *sdp, char *buf)
427 {
428  return sprintf(buf, "%d\n", sdp->sd_lockstruct.ls_jid);
429 }
430 
431 static ssize_t jid_store(struct gfs2_sbd *sdp, const char *buf, size_t len)
432 {
433  int jid;
434  int rv;
435 
436  rv = sscanf(buf, "%d", &jid);
437  if (rv != 1)
438  return -EINVAL;
440  if (rv)
441  return rv;
442  spin_lock(&sdp->sd_jindex_spin);
443  rv = -EINVAL;
444  if (sdp->sd_lockstruct.ls_ops->lm_mount == NULL)
445  goto out;
446  rv = -EBUSY;
447  if (test_bit(SDF_NOJOURNALID, &sdp->sd_flags) == 0)
448  goto out;
449  rv = 0;
450  if (sdp->sd_args.ar_spectator && jid > 0)
451  rv = jid = -EINVAL;
452  sdp->sd_lockstruct.ls_jid = jid;
456 out:
457  spin_unlock(&sdp->sd_jindex_spin);
458  return rv ? rv : len;
459 }
460 
461 #define GDLM_ATTR(_name,_mode,_show,_store) \
462 static struct gfs2_attr gdlm_attr_##_name = __ATTR(_name,_mode,_show,_store)
463 
464 GDLM_ATTR(proto_name, 0444, proto_name_show, NULL);
465 GDLM_ATTR(block, 0644, block_show, block_store);
466 GDLM_ATTR(withdraw, 0644, withdraw_show, withdraw_store);
467 GDLM_ATTR(jid, 0644, jid_show, jid_store);
468 GDLM_ATTR(first, 0644, lkfirst_show, lkfirst_store);
469 GDLM_ATTR(first_done, 0444, first_done_show, NULL);
470 GDLM_ATTR(recover, 0600, NULL, recover_store);
471 GDLM_ATTR(recover_done, 0444, recover_done_show, NULL);
472 GDLM_ATTR(recover_status, 0444, recover_status_show, NULL);
473 
474 static struct attribute *lock_module_attrs[] = {
475  &gdlm_attr_proto_name.attr,
476  &gdlm_attr_block.attr,
477  &gdlm_attr_withdraw.attr,
478  &gdlm_attr_jid.attr,
479  &gdlm_attr_first.attr,
480  &gdlm_attr_first_done.attr,
481  &gdlm_attr_recover.attr,
482  &gdlm_attr_recover_done.attr,
483  &gdlm_attr_recover_status.attr,
484  NULL,
485 };
486 
487 /*
488  * get and set struct gfs2_tune fields
489  */
490 
491 static ssize_t quota_scale_show(struct gfs2_sbd *sdp, char *buf)
492 {
493  return snprintf(buf, PAGE_SIZE, "%u %u\n",
494  sdp->sd_tune.gt_quota_scale_num,
495  sdp->sd_tune.gt_quota_scale_den);
496 }
497 
498 static ssize_t quota_scale_store(struct gfs2_sbd *sdp, const char *buf,
499  size_t len)
500 {
501  struct gfs2_tune *gt = &sdp->sd_tune;
502  unsigned int x, y;
503 
504  if (!capable(CAP_SYS_ADMIN))
505  return -EACCES;
506 
507  if (sscanf(buf, "%u %u", &x, &y) != 2 || !y)
508  return -EINVAL;
509 
510  spin_lock(&gt->gt_spin);
511  gt->gt_quota_scale_num = x;
512  gt->gt_quota_scale_den = y;
513  spin_unlock(&gt->gt_spin);
514  return len;
515 }
516 
517 static ssize_t tune_set(struct gfs2_sbd *sdp, unsigned int *field,
518  int check_zero, const char *buf, size_t len)
519 {
520  struct gfs2_tune *gt = &sdp->sd_tune;
521  unsigned int x;
522 
523  if (!capable(CAP_SYS_ADMIN))
524  return -EACCES;
525 
526  x = simple_strtoul(buf, NULL, 0);
527 
528  if (check_zero && !x)
529  return -EINVAL;
530 
531  spin_lock(&gt->gt_spin);
532  *field = x;
533  spin_unlock(&gt->gt_spin);
534  return len;
535 }
536 
537 #define TUNE_ATTR_3(name, show, store) \
538 static struct gfs2_attr tune_attr_##name = __ATTR(name, 0644, show, store)
539 
540 #define TUNE_ATTR_2(name, store) \
541 static ssize_t name##_show(struct gfs2_sbd *sdp, char *buf) \
542 { \
543  return snprintf(buf, PAGE_SIZE, "%u\n", sdp->sd_tune.gt_##name); \
544 } \
545 TUNE_ATTR_3(name, name##_show, store)
546 
547 #define TUNE_ATTR(name, check_zero) \
548 static ssize_t name##_store(struct gfs2_sbd *sdp, const char *buf, size_t len)\
549 { \
550  return tune_set(sdp, &sdp->sd_tune.gt_##name, check_zero, buf, len); \
551 } \
552 TUNE_ATTR_2(name, name##_store)
553 
554 TUNE_ATTR(quota_warn_period, 0);
555 TUNE_ATTR(quota_quantum, 0);
556 TUNE_ATTR(max_readahead, 0);
557 TUNE_ATTR(complain_secs, 0);
558 TUNE_ATTR(statfs_slow, 0);
559 TUNE_ATTR(new_files_jdata, 0);
560 TUNE_ATTR(quota_simul_sync, 1);
561 TUNE_ATTR(statfs_quantum, 1);
562 TUNE_ATTR_3(quota_scale, quota_scale_show, quota_scale_store);
563 
564 static struct attribute *tune_attrs[] = {
565  &tune_attr_quota_warn_period.attr,
566  &tune_attr_quota_quantum.attr,
567  &tune_attr_max_readahead.attr,
568  &tune_attr_complain_secs.attr,
569  &tune_attr_statfs_slow.attr,
570  &tune_attr_quota_simul_sync.attr,
571  &tune_attr_statfs_quantum.attr,
572  &tune_attr_quota_scale.attr,
573  &tune_attr_new_files_jdata.attr,
574  NULL,
575 };
576 
577 static struct attribute_group tune_group = {
578  .name = "tune",
579  .attrs = tune_attrs,
580 };
581 
582 static struct attribute_group lock_module_group = {
583  .name = "lock_module",
584  .attrs = lock_module_attrs,
585 };
586 
587 int gfs2_sys_fs_add(struct gfs2_sbd *sdp)
588 {
589  struct super_block *sb = sdp->sd_vfs;
590  int error;
591  char ro[20];
592  char spectator[20];
593  char *envp[] = { ro, spectator, NULL };
594  int sysfs_frees_sdp = 0;
595 
596  sprintf(ro, "RDONLY=%d", (sb->s_flags & MS_RDONLY) ? 1 : 0);
597  sprintf(spectator, "SPECTATOR=%d", sdp->sd_args.ar_spectator ? 1 : 0);
598 
599  sdp->sd_kobj.kset = gfs2_kset;
600  error = kobject_init_and_add(&sdp->sd_kobj, &gfs2_ktype, NULL,
601  "%s", sdp->sd_table_name);
602  if (error)
603  goto fail_reg;
604 
605  sysfs_frees_sdp = 1; /* Freeing sdp is now done by sysfs calling
606  function gfs2_sbd_release. */
607  error = sysfs_create_group(&sdp->sd_kobj, &tune_group);
608  if (error)
609  goto fail_reg;
610 
611  error = sysfs_create_group(&sdp->sd_kobj, &lock_module_group);
612  if (error)
613  goto fail_tune;
614 
615  error = sysfs_create_link(&sdp->sd_kobj,
616  &disk_to_dev(sb->s_bdev->bd_disk)->kobj,
617  "device");
618  if (error)
619  goto fail_lock_module;
620 
621  kobject_uevent_env(&sdp->sd_kobj, KOBJ_ADD, envp);
622  return 0;
623 
624 fail_lock_module:
625  sysfs_remove_group(&sdp->sd_kobj, &lock_module_group);
626 fail_tune:
627  sysfs_remove_group(&sdp->sd_kobj, &tune_group);
628 fail_reg:
629  free_percpu(sdp->sd_lkstats);
630  fs_err(sdp, "error %d adding sysfs files", error);
631  if (sysfs_frees_sdp)
632  kobject_put(&sdp->sd_kobj);
633  else
634  kfree(sdp);
635  sb->s_fs_info = NULL;
636  return error;
637 }
638 
639 void gfs2_sys_fs_del(struct gfs2_sbd *sdp)
640 {
641  sysfs_remove_link(&sdp->sd_kobj, "device");
642  sysfs_remove_group(&sdp->sd_kobj, &tune_group);
643  sysfs_remove_group(&sdp->sd_kobj, &lock_module_group);
644  kobject_put(&sdp->sd_kobj);
645 }
646 
647 static int gfs2_uevent(struct kset *kset, struct kobject *kobj,
648  struct kobj_uevent_env *env)
649 {
650  struct gfs2_sbd *sdp = container_of(kobj, struct gfs2_sbd, sd_kobj);
651  struct super_block *s = sdp->sd_vfs;
652  const u8 *uuid = s->s_uuid;
653 
654  add_uevent_var(env, "LOCKTABLE=%s", sdp->sd_table_name);
655  add_uevent_var(env, "LOCKPROTO=%s", sdp->sd_proto_name);
656  if (!test_bit(SDF_NOJOURNALID, &sdp->sd_flags))
657  add_uevent_var(env, "JOURNALID=%d", sdp->sd_lockstruct.ls_jid);
658  if (gfs2_uuid_valid(uuid))
659  add_uevent_var(env, "UUID=%pUB", uuid);
660  return 0;
661 }
662 
663 static const struct kset_uevent_ops gfs2_uevent_ops = {
664  .uevent = gfs2_uevent,
665 };
666 
667 int gfs2_sys_init(void)
668 {
669  gfs2_kset = kset_create_and_add("gfs2", &gfs2_uevent_ops, fs_kobj);
670  if (!gfs2_kset)
671  return -ENOMEM;
672  return 0;
673 }
674 
675 void gfs2_sys_uninit(void)
676 {
677  kset_unregister(gfs2_kset);
678 }
679