diff options
author | Linus Torvalds <torvalds@linux-foundation.org> | 2018-06-04 13:00:01 -0400 |
---|---|---|
committer | Linus Torvalds <torvalds@linux-foundation.org> | 2018-06-04 13:00:01 -0400 |
commit | cf626b0da78df6669c6b5f51ddd9a70a0702e579 (patch) | |
tree | 45d29a4cb7574aed7f140814ed22088ded21c291 /fs/proc | |
parent | 9c50eafc32ddbd166c8a2bbaecd4ad201c452b14 (diff) | |
parent | 5ef03dbd91855544cd4c7c1910c3ef5226ee87e8 (diff) |
Merge branch 'hch.procfs' of git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs
Pull procfs updates from Al Viro:
"Christoph's proc_create_... cleanups series"
* 'hch.procfs' of git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs: (44 commits)
xfs, proc: hide unused xfs procfs helpers
isdn/gigaset: add back gigaset_procinfo assignment
proc: update SIZEOF_PDE_INLINE_NAME for the new pde fields
tty: replace ->proc_fops with ->proc_show
ide: replace ->proc_fops with ->proc_show
ide: remove ide_driver_proc_write
isdn: replace ->proc_fops with ->proc_show
atm: switch to proc_create_seq_private
atm: simplify procfs code
bluetooth: switch to proc_create_seq_data
netfilter/x_tables: switch to proc_create_seq_private
netfilter/xt_hashlimit: switch to proc_create_{seq,single}_data
neigh: switch to proc_create_seq_data
hostap: switch to proc_create_{seq,single}_data
bonding: switch to proc_create_seq_data
rtc/proc: switch to proc_create_single_data
drbd: switch to proc_create_single
resource: switch to proc_create_seq_data
staging/rtl8192u: simplify procfs code
jfs: simplify procfs code
...
Diffstat (limited to 'fs/proc')
-rw-r--r-- | fs/proc/array.c | 23 | ||||
-rw-r--r-- | fs/proc/base.c | 18 | ||||
-rw-r--r-- | fs/proc/cmdline.c | 14 | ||||
-rw-r--r-- | fs/proc/consoles.c | 14 | ||||
-rw-r--r-- | fs/proc/devices.c | 14 | ||||
-rw-r--r-- | fs/proc/generic.c | 148 | ||||
-rw-r--r-- | fs/proc/internal.h | 13 | ||||
-rw-r--r-- | fs/proc/interrupts.c | 14 | ||||
-rw-r--r-- | fs/proc/loadavg.c | 14 | ||||
-rw-r--r-- | fs/proc/meminfo.c | 14 | ||||
-rw-r--r-- | fs/proc/nommu.c | 14 | ||||
-rw-r--r-- | fs/proc/proc_net.c | 104 | ||||
-rw-r--r-- | fs/proc/proc_tty.c | 22 | ||||
-rw-r--r-- | fs/proc/self.c | 4 | ||||
-rw-r--r-- | fs/proc/softirqs.c | 14 | ||||
-rw-r--r-- | fs/proc/thread_self.c | 4 | ||||
-rw-r--r-- | fs/proc/uptime.c | 14 | ||||
-rw-r--r-- | fs/proc/version.c | 14 |
18 files changed, 215 insertions, 261 deletions
diff --git a/fs/proc/array.c b/fs/proc/array.c index 72391b3f6927..e6d7f41b6684 100644 --- a/fs/proc/array.c +++ b/fs/proc/array.c | |||
@@ -702,25 +702,22 @@ out: | |||
702 | 702 | ||
703 | static int children_seq_show(struct seq_file *seq, void *v) | 703 | static int children_seq_show(struct seq_file *seq, void *v) |
704 | { | 704 | { |
705 | struct inode *inode = seq->private; | 705 | struct inode *inode = file_inode(seq->file); |
706 | pid_t pid; | ||
707 | |||
708 | pid = pid_nr_ns(v, inode->i_sb->s_fs_info); | ||
709 | seq_printf(seq, "%d ", pid); | ||
710 | 706 | ||
707 | seq_printf(seq, "%d ", pid_nr_ns(v, proc_pid_ns(inode))); | ||
711 | return 0; | 708 | return 0; |
712 | } | 709 | } |
713 | 710 | ||
714 | static void *children_seq_start(struct seq_file *seq, loff_t *pos) | 711 | static void *children_seq_start(struct seq_file *seq, loff_t *pos) |
715 | { | 712 | { |
716 | return get_children_pid(seq->private, NULL, *pos); | 713 | return get_children_pid(file_inode(seq->file), NULL, *pos); |
717 | } | 714 | } |
718 | 715 | ||
719 | static void *children_seq_next(struct seq_file *seq, void *v, loff_t *pos) | 716 | static void *children_seq_next(struct seq_file *seq, void *v, loff_t *pos) |
720 | { | 717 | { |
721 | struct pid *pid; | 718 | struct pid *pid; |
722 | 719 | ||
723 | pid = get_children_pid(seq->private, v, *pos + 1); | 720 | pid = get_children_pid(file_inode(seq->file), v, *pos + 1); |
724 | put_pid(v); | 721 | put_pid(v); |
725 | 722 | ||
726 | ++*pos; | 723 | ++*pos; |
@@ -741,17 +738,7 @@ static const struct seq_operations children_seq_ops = { | |||
741 | 738 | ||
742 | static int children_seq_open(struct inode *inode, struct file *file) | 739 | static int children_seq_open(struct inode *inode, struct file *file) |
743 | { | 740 | { |
744 | struct seq_file *m; | 741 | return seq_open(file, &children_seq_ops); |
745 | int ret; | ||
746 | |||
747 | ret = seq_open(file, &children_seq_ops); | ||
748 | if (ret) | ||
749 | return ret; | ||
750 | |||
751 | m = file->private_data; | ||
752 | m->private = inode; | ||
753 | |||
754 | return ret; | ||
755 | } | 742 | } |
756 | 743 | ||
757 | const struct file_operations proc_tid_children_operations = { | 744 | const struct file_operations proc_tid_children_operations = { |
diff --git a/fs/proc/base.c b/fs/proc/base.c index 1a76d751cf3c..4e35593546b1 100644 --- a/fs/proc/base.c +++ b/fs/proc/base.c | |||
@@ -698,7 +698,7 @@ static bool has_pid_permissions(struct pid_namespace *pid, | |||
698 | 698 | ||
699 | static int proc_pid_permission(struct inode *inode, int mask) | 699 | static int proc_pid_permission(struct inode *inode, int mask) |
700 | { | 700 | { |
701 | struct pid_namespace *pid = inode->i_sb->s_fs_info; | 701 | struct pid_namespace *pid = proc_pid_ns(inode); |
702 | struct task_struct *task; | 702 | struct task_struct *task; |
703 | bool has_perms; | 703 | bool has_perms; |
704 | 704 | ||
@@ -733,13 +733,11 @@ static const struct inode_operations proc_def_inode_operations = { | |||
733 | static int proc_single_show(struct seq_file *m, void *v) | 733 | static int proc_single_show(struct seq_file *m, void *v) |
734 | { | 734 | { |
735 | struct inode *inode = m->private; | 735 | struct inode *inode = m->private; |
736 | struct pid_namespace *ns; | 736 | struct pid_namespace *ns = proc_pid_ns(inode); |
737 | struct pid *pid; | 737 | struct pid *pid = proc_pid(inode); |
738 | struct task_struct *task; | 738 | struct task_struct *task; |
739 | int ret; | 739 | int ret; |
740 | 740 | ||
741 | ns = inode->i_sb->s_fs_info; | ||
742 | pid = proc_pid(inode); | ||
743 | task = get_pid_task(pid, PIDTYPE_PID); | 741 | task = get_pid_task(pid, PIDTYPE_PID); |
744 | if (!task) | 742 | if (!task) |
745 | return -ESRCH; | 743 | return -ESRCH; |
@@ -1410,7 +1408,7 @@ static const struct file_operations proc_fail_nth_operations = { | |||
1410 | static int sched_show(struct seq_file *m, void *v) | 1408 | static int sched_show(struct seq_file *m, void *v) |
1411 | { | 1409 | { |
1412 | struct inode *inode = m->private; | 1410 | struct inode *inode = m->private; |
1413 | struct pid_namespace *ns = inode->i_sb->s_fs_info; | 1411 | struct pid_namespace *ns = proc_pid_ns(inode); |
1414 | struct task_struct *p; | 1412 | struct task_struct *p; |
1415 | 1413 | ||
1416 | p = get_proc_task(inode); | 1414 | p = get_proc_task(inode); |
@@ -1782,8 +1780,8 @@ int pid_getattr(const struct path *path, struct kstat *stat, | |||
1782 | u32 request_mask, unsigned int query_flags) | 1780 | u32 request_mask, unsigned int query_flags) |
1783 | { | 1781 | { |
1784 | struct inode *inode = d_inode(path->dentry); | 1782 | struct inode *inode = d_inode(path->dentry); |
1783 | struct pid_namespace *pid = proc_pid_ns(inode); | ||
1785 | struct task_struct *task; | 1784 | struct task_struct *task; |
1786 | struct pid_namespace *pid = path->dentry->d_sb->s_fs_info; | ||
1787 | 1785 | ||
1788 | generic_fillattr(inode, stat); | 1786 | generic_fillattr(inode, stat); |
1789 | 1787 | ||
@@ -2337,7 +2335,7 @@ static int proc_timers_open(struct inode *inode, struct file *file) | |||
2337 | return -ENOMEM; | 2335 | return -ENOMEM; |
2338 | 2336 | ||
2339 | tp->pid = proc_pid(inode); | 2337 | tp->pid = proc_pid(inode); |
2340 | tp->ns = inode->i_sb->s_fs_info; | 2338 | tp->ns = proc_pid_ns(inode); |
2341 | return 0; | 2339 | return 0; |
2342 | } | 2340 | } |
2343 | 2341 | ||
@@ -3239,7 +3237,7 @@ retry: | |||
3239 | int proc_pid_readdir(struct file *file, struct dir_context *ctx) | 3237 | int proc_pid_readdir(struct file *file, struct dir_context *ctx) |
3240 | { | 3238 | { |
3241 | struct tgid_iter iter; | 3239 | struct tgid_iter iter; |
3242 | struct pid_namespace *ns = file_inode(file)->i_sb->s_fs_info; | 3240 | struct pid_namespace *ns = proc_pid_ns(file_inode(file)); |
3243 | loff_t pos = ctx->pos; | 3241 | loff_t pos = ctx->pos; |
3244 | 3242 | ||
3245 | if (pos >= PID_MAX_LIMIT + TGID_OFFSET) | 3243 | if (pos >= PID_MAX_LIMIT + TGID_OFFSET) |
@@ -3588,7 +3586,7 @@ static int proc_task_readdir(struct file *file, struct dir_context *ctx) | |||
3588 | /* f_version caches the tgid value that the last readdir call couldn't | 3586 | /* f_version caches the tgid value that the last readdir call couldn't |
3589 | * return. lseek aka telldir automagically resets f_version to 0. | 3587 | * return. lseek aka telldir automagically resets f_version to 0. |
3590 | */ | 3588 | */ |
3591 | ns = inode->i_sb->s_fs_info; | 3589 | ns = proc_pid_ns(inode); |
3592 | tid = (int)file->f_version; | 3590 | tid = (int)file->f_version; |
3593 | file->f_version = 0; | 3591 | file->f_version = 0; |
3594 | for (task = first_tid(proc_pid(inode), tid, ctx->pos - 2, ns); | 3592 | for (task = first_tid(proc_pid(inode), tid, ctx->pos - 2, ns); |
diff --git a/fs/proc/cmdline.c b/fs/proc/cmdline.c index 8233e7af9389..fa762c5fbcb2 100644 --- a/fs/proc/cmdline.c +++ b/fs/proc/cmdline.c | |||
@@ -11,21 +11,9 @@ static int cmdline_proc_show(struct seq_file *m, void *v) | |||
11 | return 0; | 11 | return 0; |
12 | } | 12 | } |
13 | 13 | ||
14 | static int cmdline_proc_open(struct inode *inode, struct file *file) | ||
15 | { | ||
16 | return single_open(file, cmdline_proc_show, NULL); | ||
17 | } | ||
18 | |||
19 | static const struct file_operations cmdline_proc_fops = { | ||
20 | .open = cmdline_proc_open, | ||
21 | .read = seq_read, | ||
22 | .llseek = seq_lseek, | ||
23 | .release = single_release, | ||
24 | }; | ||
25 | |||
26 | static int __init proc_cmdline_init(void) | 14 | static int __init proc_cmdline_init(void) |
27 | { | 15 | { |
28 | proc_create("cmdline", 0, NULL, &cmdline_proc_fops); | 16 | proc_create_single("cmdline", 0, NULL, cmdline_proc_show); |
29 | return 0; | 17 | return 0; |
30 | } | 18 | } |
31 | fs_initcall(proc_cmdline_init); | 19 | fs_initcall(proc_cmdline_init); |
diff --git a/fs/proc/consoles.c b/fs/proc/consoles.c index a8ac48aebd59..954caf0b7fee 100644 --- a/fs/proc/consoles.c +++ b/fs/proc/consoles.c | |||
@@ -91,21 +91,9 @@ static const struct seq_operations consoles_op = { | |||
91 | .show = show_console_dev | 91 | .show = show_console_dev |
92 | }; | 92 | }; |
93 | 93 | ||
94 | static int consoles_open(struct inode *inode, struct file *file) | ||
95 | { | ||
96 | return seq_open(file, &consoles_op); | ||
97 | } | ||
98 | |||
99 | static const struct file_operations proc_consoles_operations = { | ||
100 | .open = consoles_open, | ||
101 | .read = seq_read, | ||
102 | .llseek = seq_lseek, | ||
103 | .release = seq_release, | ||
104 | }; | ||
105 | |||
106 | static int __init proc_consoles_init(void) | 94 | static int __init proc_consoles_init(void) |
107 | { | 95 | { |
108 | proc_create("consoles", 0, NULL, &proc_consoles_operations); | 96 | proc_create_seq("consoles", 0, NULL, &consoles_op); |
109 | return 0; | 97 | return 0; |
110 | } | 98 | } |
111 | fs_initcall(proc_consoles_init); | 99 | fs_initcall(proc_consoles_init); |
diff --git a/fs/proc/devices.c b/fs/proc/devices.c index 2c7f22b14489..37d38697eaf8 100644 --- a/fs/proc/devices.c +++ b/fs/proc/devices.c | |||
@@ -51,21 +51,9 @@ static const struct seq_operations devinfo_ops = { | |||
51 | .show = devinfo_show | 51 | .show = devinfo_show |
52 | }; | 52 | }; |
53 | 53 | ||
54 | static int devinfo_open(struct inode *inode, struct file *filp) | ||
55 | { | ||
56 | return seq_open(filp, &devinfo_ops); | ||
57 | } | ||
58 | |||
59 | static const struct file_operations proc_devinfo_operations = { | ||
60 | .open = devinfo_open, | ||
61 | .read = seq_read, | ||
62 | .llseek = seq_lseek, | ||
63 | .release = seq_release, | ||
64 | }; | ||
65 | |||
66 | static int __init proc_devices_init(void) | 54 | static int __init proc_devices_init(void) |
67 | { | 55 | { |
68 | proc_create("devices", 0, NULL, &proc_devinfo_operations); | 56 | proc_create_seq("devices", 0, NULL, &devinfo_ops); |
69 | return 0; | 57 | return 0; |
70 | } | 58 | } |
71 | fs_initcall(proc_devices_init); | 59 | fs_initcall(proc_devices_init); |
diff --git a/fs/proc/generic.c b/fs/proc/generic.c index 2078e70e1595..02bb1914f5f7 100644 --- a/fs/proc/generic.c +++ b/fs/proc/generic.c | |||
@@ -25,6 +25,7 @@ | |||
25 | #include <linux/spinlock.h> | 25 | #include <linux/spinlock.h> |
26 | #include <linux/completion.h> | 26 | #include <linux/completion.h> |
27 | #include <linux/uaccess.h> | 27 | #include <linux/uaccess.h> |
28 | #include <linux/seq_file.h> | ||
28 | 29 | ||
29 | #include "internal.h" | 30 | #include "internal.h" |
30 | 31 | ||
@@ -346,13 +347,12 @@ static const struct inode_operations proc_dir_inode_operations = { | |||
346 | .setattr = proc_notify_change, | 347 | .setattr = proc_notify_change, |
347 | }; | 348 | }; |
348 | 349 | ||
349 | static int proc_register(struct proc_dir_entry * dir, struct proc_dir_entry * dp) | 350 | /* returns the registered entry, or frees dp and returns NULL on failure */ |
351 | struct proc_dir_entry *proc_register(struct proc_dir_entry *dir, | ||
352 | struct proc_dir_entry *dp) | ||
350 | { | 353 | { |
351 | int ret; | 354 | if (proc_alloc_inum(&dp->low_ino)) |
352 | 355 | goto out_free_entry; | |
353 | ret = proc_alloc_inum(&dp->low_ino); | ||
354 | if (ret) | ||
355 | return ret; | ||
356 | 356 | ||
357 | write_lock(&proc_subdir_lock); | 357 | write_lock(&proc_subdir_lock); |
358 | dp->parent = dir; | 358 | dp->parent = dir; |
@@ -360,12 +360,16 @@ static int proc_register(struct proc_dir_entry * dir, struct proc_dir_entry * dp | |||
360 | WARN(1, "proc_dir_entry '%s/%s' already registered\n", | 360 | WARN(1, "proc_dir_entry '%s/%s' already registered\n", |
361 | dir->name, dp->name); | 361 | dir->name, dp->name); |
362 | write_unlock(&proc_subdir_lock); | 362 | write_unlock(&proc_subdir_lock); |
363 | proc_free_inum(dp->low_ino); | 363 | goto out_free_inum; |
364 | return -EEXIST; | ||
365 | } | 364 | } |
366 | write_unlock(&proc_subdir_lock); | 365 | write_unlock(&proc_subdir_lock); |
367 | 366 | ||
368 | return 0; | 367 | return dp; |
368 | out_free_inum: | ||
369 | proc_free_inum(dp->low_ino); | ||
370 | out_free_entry: | ||
371 | pde_free(dp); | ||
372 | return NULL; | ||
369 | } | 373 | } |
370 | 374 | ||
371 | static struct proc_dir_entry *__proc_create(struct proc_dir_entry **parent, | 375 | static struct proc_dir_entry *__proc_create(struct proc_dir_entry **parent, |
@@ -443,10 +447,7 @@ struct proc_dir_entry *proc_symlink(const char *name, | |||
443 | if (ent->data) { | 447 | if (ent->data) { |
444 | strcpy((char*)ent->data,dest); | 448 | strcpy((char*)ent->data,dest); |
445 | ent->proc_iops = &proc_link_inode_operations; | 449 | ent->proc_iops = &proc_link_inode_operations; |
446 | if (proc_register(parent, ent) < 0) { | 450 | ent = proc_register(parent, ent); |
447 | pde_free(ent); | ||
448 | ent = NULL; | ||
449 | } | ||
450 | } else { | 451 | } else { |
451 | pde_free(ent); | 452 | pde_free(ent); |
452 | ent = NULL; | 453 | ent = NULL; |
@@ -470,11 +471,9 @@ struct proc_dir_entry *proc_mkdir_data(const char *name, umode_t mode, | |||
470 | ent->proc_fops = &proc_dir_operations; | 471 | ent->proc_fops = &proc_dir_operations; |
471 | ent->proc_iops = &proc_dir_inode_operations; | 472 | ent->proc_iops = &proc_dir_inode_operations; |
472 | parent->nlink++; | 473 | parent->nlink++; |
473 | if (proc_register(parent, ent) < 0) { | 474 | ent = proc_register(parent, ent); |
474 | pde_free(ent); | 475 | if (!ent) |
475 | parent->nlink--; | 476 | parent->nlink--; |
476 | ent = NULL; | ||
477 | } | ||
478 | } | 477 | } |
479 | return ent; | 478 | return ent; |
480 | } | 479 | } |
@@ -505,47 +504,47 @@ struct proc_dir_entry *proc_create_mount_point(const char *name) | |||
505 | ent->proc_fops = NULL; | 504 | ent->proc_fops = NULL; |
506 | ent->proc_iops = NULL; | 505 | ent->proc_iops = NULL; |
507 | parent->nlink++; | 506 | parent->nlink++; |
508 | if (proc_register(parent, ent) < 0) { | 507 | ent = proc_register(parent, ent); |
509 | pde_free(ent); | 508 | if (!ent) |
510 | parent->nlink--; | 509 | parent->nlink--; |
511 | ent = NULL; | ||
512 | } | ||
513 | } | 510 | } |
514 | return ent; | 511 | return ent; |
515 | } | 512 | } |
516 | EXPORT_SYMBOL(proc_create_mount_point); | 513 | EXPORT_SYMBOL(proc_create_mount_point); |
517 | 514 | ||
518 | struct proc_dir_entry *proc_create_data(const char *name, umode_t mode, | 515 | struct proc_dir_entry *proc_create_reg(const char *name, umode_t mode, |
519 | struct proc_dir_entry *parent, | 516 | struct proc_dir_entry **parent, void *data) |
520 | const struct file_operations *proc_fops, | ||
521 | void *data) | ||
522 | { | 517 | { |
523 | struct proc_dir_entry *pde; | 518 | struct proc_dir_entry *p; |
519 | |||
524 | if ((mode & S_IFMT) == 0) | 520 | if ((mode & S_IFMT) == 0) |
525 | mode |= S_IFREG; | 521 | mode |= S_IFREG; |
526 | 522 | if ((mode & S_IALLUGO) == 0) | |
527 | if (!S_ISREG(mode)) { | 523 | mode |= S_IRUGO; |
528 | WARN_ON(1); /* use proc_mkdir() */ | 524 | if (WARN_ON_ONCE(!S_ISREG(mode))) |
529 | return NULL; | 525 | return NULL; |
526 | |||
527 | p = __proc_create(parent, name, mode, 1); | ||
528 | if (p) { | ||
529 | p->proc_iops = &proc_file_inode_operations; | ||
530 | p->data = data; | ||
530 | } | 531 | } |
532 | return p; | ||
533 | } | ||
534 | |||
535 | struct proc_dir_entry *proc_create_data(const char *name, umode_t mode, | ||
536 | struct proc_dir_entry *parent, | ||
537 | const struct file_operations *proc_fops, void *data) | ||
538 | { | ||
539 | struct proc_dir_entry *p; | ||
531 | 540 | ||
532 | BUG_ON(proc_fops == NULL); | 541 | BUG_ON(proc_fops == NULL); |
533 | 542 | ||
534 | if ((mode & S_IALLUGO) == 0) | 543 | p = proc_create_reg(name, mode, &parent, data); |
535 | mode |= S_IRUGO; | 544 | if (!p) |
536 | pde = __proc_create(&parent, name, mode, 1); | 545 | return NULL; |
537 | if (!pde) | 546 | p->proc_fops = proc_fops; |
538 | goto out; | 547 | return proc_register(parent, p); |
539 | pde->proc_fops = proc_fops; | ||
540 | pde->data = data; | ||
541 | pde->proc_iops = &proc_file_inode_operations; | ||
542 | if (proc_register(parent, pde) < 0) | ||
543 | goto out_free; | ||
544 | return pde; | ||
545 | out_free: | ||
546 | pde_free(pde); | ||
547 | out: | ||
548 | return NULL; | ||
549 | } | 548 | } |
550 | EXPORT_SYMBOL(proc_create_data); | 549 | EXPORT_SYMBOL(proc_create_data); |
551 | 550 | ||
@@ -557,6 +556,67 @@ struct proc_dir_entry *proc_create(const char *name, umode_t mode, | |||
557 | } | 556 | } |
558 | EXPORT_SYMBOL(proc_create); | 557 | EXPORT_SYMBOL(proc_create); |
559 | 558 | ||
559 | static int proc_seq_open(struct inode *inode, struct file *file) | ||
560 | { | ||
561 | struct proc_dir_entry *de = PDE(inode); | ||
562 | |||
563 | if (de->state_size) | ||
564 | return seq_open_private(file, de->seq_ops, de->state_size); | ||
565 | return seq_open(file, de->seq_ops); | ||
566 | } | ||
567 | |||
568 | static const struct file_operations proc_seq_fops = { | ||
569 | .open = proc_seq_open, | ||
570 | .read = seq_read, | ||
571 | .llseek = seq_lseek, | ||
572 | .release = seq_release, | ||
573 | }; | ||
574 | |||
575 | struct proc_dir_entry *proc_create_seq_private(const char *name, umode_t mode, | ||
576 | struct proc_dir_entry *parent, const struct seq_operations *ops, | ||
577 | unsigned int state_size, void *data) | ||
578 | { | ||
579 | struct proc_dir_entry *p; | ||
580 | |||
581 | p = proc_create_reg(name, mode, &parent, data); | ||
582 | if (!p) | ||
583 | return NULL; | ||
584 | p->proc_fops = &proc_seq_fops; | ||
585 | p->seq_ops = ops; | ||
586 | p->state_size = state_size; | ||
587 | return proc_register(parent, p); | ||
588 | } | ||
589 | EXPORT_SYMBOL(proc_create_seq_private); | ||
590 | |||
591 | static int proc_single_open(struct inode *inode, struct file *file) | ||
592 | { | ||
593 | struct proc_dir_entry *de = PDE(inode); | ||
594 | |||
595 | return single_open(file, de->single_show, de->data); | ||
596 | } | ||
597 | |||
598 | static const struct file_operations proc_single_fops = { | ||
599 | .open = proc_single_open, | ||
600 | .read = seq_read, | ||
601 | .llseek = seq_lseek, | ||
602 | .release = single_release, | ||
603 | }; | ||
604 | |||
605 | struct proc_dir_entry *proc_create_single_data(const char *name, umode_t mode, | ||
606 | struct proc_dir_entry *parent, | ||
607 | int (*show)(struct seq_file *, void *), void *data) | ||
608 | { | ||
609 | struct proc_dir_entry *p; | ||
610 | |||
611 | p = proc_create_reg(name, mode, &parent, data); | ||
612 | if (!p) | ||
613 | return NULL; | ||
614 | p->proc_fops = &proc_single_fops; | ||
615 | p->single_show = show; | ||
616 | return proc_register(parent, p); | ||
617 | } | ||
618 | EXPORT_SYMBOL(proc_create_single_data); | ||
619 | |||
560 | void proc_set_size(struct proc_dir_entry *de, loff_t size) | 620 | void proc_set_size(struct proc_dir_entry *de, loff_t size) |
561 | { | 621 | { |
562 | de->size = size; | 622 | de->size = size; |
diff --git a/fs/proc/internal.h b/fs/proc/internal.h index 0f1692e63cb6..a318ae5b36b4 100644 --- a/fs/proc/internal.h +++ b/fs/proc/internal.h | |||
@@ -44,7 +44,12 @@ struct proc_dir_entry { | |||
44 | struct completion *pde_unload_completion; | 44 | struct completion *pde_unload_completion; |
45 | const struct inode_operations *proc_iops; | 45 | const struct inode_operations *proc_iops; |
46 | const struct file_operations *proc_fops; | 46 | const struct file_operations *proc_fops; |
47 | union { | ||
48 | const struct seq_operations *seq_ops; | ||
49 | int (*single_show)(struct seq_file *, void *); | ||
50 | }; | ||
47 | void *data; | 51 | void *data; |
52 | unsigned int state_size; | ||
48 | unsigned int low_ino; | 53 | unsigned int low_ino; |
49 | nlink_t nlink; | 54 | nlink_t nlink; |
50 | kuid_t uid; | 55 | kuid_t uid; |
@@ -57,9 +62,9 @@ struct proc_dir_entry { | |||
57 | umode_t mode; | 62 | umode_t mode; |
58 | u8 namelen; | 63 | u8 namelen; |
59 | #ifdef CONFIG_64BIT | 64 | #ifdef CONFIG_64BIT |
60 | #define SIZEOF_PDE_INLINE_NAME (192-139) | 65 | #define SIZEOF_PDE_INLINE_NAME (192-155) |
61 | #else | 66 | #else |
62 | #define SIZEOF_PDE_INLINE_NAME (128-87) | 67 | #define SIZEOF_PDE_INLINE_NAME (128-95) |
63 | #endif | 68 | #endif |
64 | char inline_name[SIZEOF_PDE_INLINE_NAME]; | 69 | char inline_name[SIZEOF_PDE_INLINE_NAME]; |
65 | } __randomize_layout; | 70 | } __randomize_layout; |
@@ -162,6 +167,10 @@ extern bool proc_fill_cache(struct file *, struct dir_context *, const char *, i | |||
162 | /* | 167 | /* |
163 | * generic.c | 168 | * generic.c |
164 | */ | 169 | */ |
170 | struct proc_dir_entry *proc_create_reg(const char *name, umode_t mode, | ||
171 | struct proc_dir_entry **parent, void *data); | ||
172 | struct proc_dir_entry *proc_register(struct proc_dir_entry *dir, | ||
173 | struct proc_dir_entry *dp); | ||
165 | extern struct dentry *proc_lookup(struct inode *, struct dentry *, unsigned int); | 174 | extern struct dentry *proc_lookup(struct inode *, struct dentry *, unsigned int); |
166 | struct dentry *proc_lookup_de(struct inode *, struct dentry *, struct proc_dir_entry *); | 175 | struct dentry *proc_lookup_de(struct inode *, struct dentry *, struct proc_dir_entry *); |
167 | extern int proc_readdir(struct file *, struct dir_context *); | 176 | extern int proc_readdir(struct file *, struct dir_context *); |
diff --git a/fs/proc/interrupts.c b/fs/proc/interrupts.c index 6a6bee9c603c..cb0edc7cbf09 100644 --- a/fs/proc/interrupts.c +++ b/fs/proc/interrupts.c | |||
@@ -34,21 +34,9 @@ static const struct seq_operations int_seq_ops = { | |||
34 | .show = show_interrupts | 34 | .show = show_interrupts |
35 | }; | 35 | }; |
36 | 36 | ||
37 | static int interrupts_open(struct inode *inode, struct file *filp) | ||
38 | { | ||
39 | return seq_open(filp, &int_seq_ops); | ||
40 | } | ||
41 | |||
42 | static const struct file_operations proc_interrupts_operations = { | ||
43 | .open = interrupts_open, | ||
44 | .read = seq_read, | ||
45 | .llseek = seq_lseek, | ||
46 | .release = seq_release, | ||
47 | }; | ||
48 | |||
49 | static int __init proc_interrupts_init(void) | 37 | static int __init proc_interrupts_init(void) |
50 | { | 38 | { |
51 | proc_create("interrupts", 0, NULL, &proc_interrupts_operations); | 39 | proc_create_seq("interrupts", 0, NULL, &int_seq_ops); |
52 | return 0; | 40 | return 0; |
53 | } | 41 | } |
54 | fs_initcall(proc_interrupts_init); | 42 | fs_initcall(proc_interrupts_init); |
diff --git a/fs/proc/loadavg.c b/fs/proc/loadavg.c index b572cc865b92..d06694757201 100644 --- a/fs/proc/loadavg.c +++ b/fs/proc/loadavg.c | |||
@@ -28,21 +28,9 @@ static int loadavg_proc_show(struct seq_file *m, void *v) | |||
28 | return 0; | 28 | return 0; |
29 | } | 29 | } |
30 | 30 | ||
31 | static int loadavg_proc_open(struct inode *inode, struct file *file) | ||
32 | { | ||
33 | return single_open(file, loadavg_proc_show, NULL); | ||
34 | } | ||
35 | |||
36 | static const struct file_operations loadavg_proc_fops = { | ||
37 | .open = loadavg_proc_open, | ||
38 | .read = seq_read, | ||
39 | .llseek = seq_lseek, | ||
40 | .release = single_release, | ||
41 | }; | ||
42 | |||
43 | static int __init proc_loadavg_init(void) | 31 | static int __init proc_loadavg_init(void) |
44 | { | 32 | { |
45 | proc_create("loadavg", 0, NULL, &loadavg_proc_fops); | 33 | proc_create_single("loadavg", 0, NULL, loadavg_proc_show); |
46 | return 0; | 34 | return 0; |
47 | } | 35 | } |
48 | fs_initcall(proc_loadavg_init); | 36 | fs_initcall(proc_loadavg_init); |
diff --git a/fs/proc/meminfo.c b/fs/proc/meminfo.c index 65a72ab57471..2fb04846ed11 100644 --- a/fs/proc/meminfo.c +++ b/fs/proc/meminfo.c | |||
@@ -149,21 +149,9 @@ static int meminfo_proc_show(struct seq_file *m, void *v) | |||
149 | return 0; | 149 | return 0; |
150 | } | 150 | } |
151 | 151 | ||
152 | static int meminfo_proc_open(struct inode *inode, struct file *file) | ||
153 | { | ||
154 | return single_open(file, meminfo_proc_show, NULL); | ||
155 | } | ||
156 | |||
157 | static const struct file_operations meminfo_proc_fops = { | ||
158 | .open = meminfo_proc_open, | ||
159 | .read = seq_read, | ||
160 | .llseek = seq_lseek, | ||
161 | .release = single_release, | ||
162 | }; | ||
163 | |||
164 | static int __init proc_meminfo_init(void) | 152 | static int __init proc_meminfo_init(void) |
165 | { | 153 | { |
166 | proc_create("meminfo", 0, NULL, &meminfo_proc_fops); | 154 | proc_create_single("meminfo", 0, NULL, meminfo_proc_show); |
167 | return 0; | 155 | return 0; |
168 | } | 156 | } |
169 | fs_initcall(proc_meminfo_init); | 157 | fs_initcall(proc_meminfo_init); |
diff --git a/fs/proc/nommu.c b/fs/proc/nommu.c index 75634379f82e..3b63be64e436 100644 --- a/fs/proc/nommu.c +++ b/fs/proc/nommu.c | |||
@@ -113,21 +113,9 @@ static const struct seq_operations proc_nommu_region_list_seqop = { | |||
113 | .show = nommu_region_list_show | 113 | .show = nommu_region_list_show |
114 | }; | 114 | }; |
115 | 115 | ||
116 | static int proc_nommu_region_list_open(struct inode *inode, struct file *file) | ||
117 | { | ||
118 | return seq_open(file, &proc_nommu_region_list_seqop); | ||
119 | } | ||
120 | |||
121 | static const struct file_operations proc_nommu_region_list_operations = { | ||
122 | .open = proc_nommu_region_list_open, | ||
123 | .read = seq_read, | ||
124 | .llseek = seq_lseek, | ||
125 | .release = seq_release, | ||
126 | }; | ||
127 | |||
128 | static int __init proc_nommu_init(void) | 116 | static int __init proc_nommu_init(void) |
129 | { | 117 | { |
130 | proc_create("maps", S_IRUGO, NULL, &proc_nommu_region_list_operations); | 118 | proc_create_seq("maps", S_IRUGO, NULL, &proc_nommu_region_list_seqop); |
131 | return 0; | 119 | return 0; |
132 | } | 120 | } |
133 | 121 | ||
diff --git a/fs/proc/proc_net.c b/fs/proc/proc_net.c index 1763f370489d..7d94fa005b0d 100644 --- a/fs/proc/proc_net.c +++ b/fs/proc/proc_net.c | |||
@@ -38,20 +38,20 @@ static struct net *get_proc_net(const struct inode *inode) | |||
38 | return maybe_get_net(PDE_NET(PDE(inode))); | 38 | return maybe_get_net(PDE_NET(PDE(inode))); |
39 | } | 39 | } |
40 | 40 | ||
41 | int seq_open_net(struct inode *ino, struct file *f, | 41 | static int seq_open_net(struct inode *inode, struct file *file) |
42 | const struct seq_operations *ops, int size) | ||
43 | { | 42 | { |
44 | struct net *net; | 43 | unsigned int state_size = PDE(inode)->state_size; |
45 | struct seq_net_private *p; | 44 | struct seq_net_private *p; |
45 | struct net *net; | ||
46 | 46 | ||
47 | BUG_ON(size < sizeof(*p)); | 47 | WARN_ON_ONCE(state_size < sizeof(*p)); |
48 | 48 | ||
49 | net = get_proc_net(ino); | 49 | net = get_proc_net(inode); |
50 | if (net == NULL) | 50 | if (!net) |
51 | return -ENXIO; | 51 | return -ENXIO; |
52 | 52 | ||
53 | p = __seq_open_private(f, ops, size); | 53 | p = __seq_open_private(file, PDE(inode)->seq_ops, state_size); |
54 | if (p == NULL) { | 54 | if (!p) { |
55 | put_net(net); | 55 | put_net(net); |
56 | return -ENOMEM; | 56 | return -ENOMEM; |
57 | } | 57 | } |
@@ -60,51 +60,83 @@ int seq_open_net(struct inode *ino, struct file *f, | |||
60 | #endif | 60 | #endif |
61 | return 0; | 61 | return 0; |
62 | } | 62 | } |
63 | EXPORT_SYMBOL_GPL(seq_open_net); | ||
64 | 63 | ||
65 | int single_open_net(struct inode *inode, struct file *file, | 64 | static int seq_release_net(struct inode *ino, struct file *f) |
66 | int (*show)(struct seq_file *, void *)) | ||
67 | { | 65 | { |
68 | int err; | 66 | struct seq_file *seq = f->private_data; |
69 | struct net *net; | ||
70 | |||
71 | err = -ENXIO; | ||
72 | net = get_proc_net(inode); | ||
73 | if (net == NULL) | ||
74 | goto err_net; | ||
75 | |||
76 | err = single_open(file, show, net); | ||
77 | if (err < 0) | ||
78 | goto err_open; | ||
79 | 67 | ||
68 | put_net(seq_file_net(seq)); | ||
69 | seq_release_private(ino, f); | ||
80 | return 0; | 70 | return 0; |
71 | } | ||
81 | 72 | ||
82 | err_open: | 73 | static const struct file_operations proc_net_seq_fops = { |
83 | put_net(net); | 74 | .open = seq_open_net, |
84 | err_net: | 75 | .read = seq_read, |
85 | return err; | 76 | .llseek = seq_lseek, |
77 | .release = seq_release_net, | ||
78 | }; | ||
79 | |||
80 | struct proc_dir_entry *proc_create_net_data(const char *name, umode_t mode, | ||
81 | struct proc_dir_entry *parent, const struct seq_operations *ops, | ||
82 | unsigned int state_size, void *data) | ||
83 | { | ||
84 | struct proc_dir_entry *p; | ||
85 | |||
86 | p = proc_create_reg(name, mode, &parent, data); | ||
87 | if (!p) | ||
88 | return NULL; | ||
89 | p->proc_fops = &proc_net_seq_fops; | ||
90 | p->seq_ops = ops; | ||
91 | p->state_size = state_size; | ||
92 | return proc_register(parent, p); | ||
86 | } | 93 | } |
87 | EXPORT_SYMBOL_GPL(single_open_net); | 94 | EXPORT_SYMBOL_GPL(proc_create_net_data); |
88 | 95 | ||
89 | int seq_release_net(struct inode *ino, struct file *f) | 96 | static int single_open_net(struct inode *inode, struct file *file) |
90 | { | 97 | { |
91 | struct seq_file *seq; | 98 | struct proc_dir_entry *de = PDE(inode); |
99 | struct net *net; | ||
100 | int err; | ||
92 | 101 | ||
93 | seq = f->private_data; | 102 | net = get_proc_net(inode); |
103 | if (!net) | ||
104 | return -ENXIO; | ||
94 | 105 | ||
95 | put_net(seq_file_net(seq)); | 106 | err = single_open(file, de->single_show, net); |
96 | seq_release_private(ino, f); | 107 | if (err) |
97 | return 0; | 108 | put_net(net); |
109 | return err; | ||
98 | } | 110 | } |
99 | EXPORT_SYMBOL_GPL(seq_release_net); | ||
100 | 111 | ||
101 | int single_release_net(struct inode *ino, struct file *f) | 112 | static int single_release_net(struct inode *ino, struct file *f) |
102 | { | 113 | { |
103 | struct seq_file *seq = f->private_data; | 114 | struct seq_file *seq = f->private_data; |
104 | put_net(seq->private); | 115 | put_net(seq->private); |
105 | return single_release(ino, f); | 116 | return single_release(ino, f); |
106 | } | 117 | } |
107 | EXPORT_SYMBOL_GPL(single_release_net); | 118 | |
119 | static const struct file_operations proc_net_single_fops = { | ||
120 | .open = single_open_net, | ||
121 | .read = seq_read, | ||
122 | .llseek = seq_lseek, | ||
123 | .release = single_release_net, | ||
124 | }; | ||
125 | |||
126 | struct proc_dir_entry *proc_create_net_single(const char *name, umode_t mode, | ||
127 | struct proc_dir_entry *parent, | ||
128 | int (*show)(struct seq_file *, void *), void *data) | ||
129 | { | ||
130 | struct proc_dir_entry *p; | ||
131 | |||
132 | p = proc_create_reg(name, mode, &parent, data); | ||
133 | if (!p) | ||
134 | return NULL; | ||
135 | p->proc_fops = &proc_net_single_fops; | ||
136 | p->single_show = show; | ||
137 | return proc_register(parent, p); | ||
138 | } | ||
139 | EXPORT_SYMBOL_GPL(proc_create_net_single); | ||
108 | 140 | ||
109 | static struct net *get_proc_task_net(struct inode *dir) | 141 | static struct net *get_proc_task_net(struct inode *dir) |
110 | { | 142 | { |
diff --git a/fs/proc/proc_tty.c b/fs/proc/proc_tty.c index d0cf1c50bb6c..c69ff191e5d8 100644 --- a/fs/proc/proc_tty.c +++ b/fs/proc/proc_tty.c | |||
@@ -126,18 +126,6 @@ static const struct seq_operations tty_drivers_op = { | |||
126 | .show = show_tty_driver | 126 | .show = show_tty_driver |
127 | }; | 127 | }; |
128 | 128 | ||
129 | static int tty_drivers_open(struct inode *inode, struct file *file) | ||
130 | { | ||
131 | return seq_open(file, &tty_drivers_op); | ||
132 | } | ||
133 | |||
134 | static const struct file_operations proc_tty_drivers_operations = { | ||
135 | .open = tty_drivers_open, | ||
136 | .read = seq_read, | ||
137 | .llseek = seq_lseek, | ||
138 | .release = seq_release, | ||
139 | }; | ||
140 | |||
141 | /* | 129 | /* |
142 | * This function is called by tty_register_driver() to handle | 130 | * This function is called by tty_register_driver() to handle |
143 | * registering the driver's /proc handler into /proc/tty/driver/<foo> | 131 | * registering the driver's /proc handler into /proc/tty/driver/<foo> |
@@ -147,11 +135,11 @@ void proc_tty_register_driver(struct tty_driver *driver) | |||
147 | struct proc_dir_entry *ent; | 135 | struct proc_dir_entry *ent; |
148 | 136 | ||
149 | if (!driver->driver_name || driver->proc_entry || | 137 | if (!driver->driver_name || driver->proc_entry || |
150 | !driver->ops->proc_fops) | 138 | !driver->ops->proc_show) |
151 | return; | 139 | return; |
152 | 140 | ||
153 | ent = proc_create_data(driver->driver_name, 0, proc_tty_driver, | 141 | ent = proc_create_single_data(driver->driver_name, 0, proc_tty_driver, |
154 | driver->ops->proc_fops, driver); | 142 | driver->ops->proc_show, driver); |
155 | driver->proc_entry = ent; | 143 | driver->proc_entry = ent; |
156 | } | 144 | } |
157 | 145 | ||
@@ -186,6 +174,6 @@ void __init proc_tty_init(void) | |||
186 | * entry. | 174 | * entry. |
187 | */ | 175 | */ |
188 | proc_tty_driver = proc_mkdir_mode("tty/driver", S_IRUSR|S_IXUSR, NULL); | 176 | proc_tty_driver = proc_mkdir_mode("tty/driver", S_IRUSR|S_IXUSR, NULL); |
189 | proc_create("tty/ldiscs", 0, NULL, &tty_ldiscs_proc_fops); | 177 | proc_create_seq("tty/ldiscs", 0, NULL, &tty_ldiscs_seq_ops); |
190 | proc_create("tty/drivers", 0, NULL, &proc_tty_drivers_operations); | 178 | proc_create_seq("tty/drivers", 0, NULL, &tty_drivers_op); |
191 | } | 179 | } |
diff --git a/fs/proc/self.c b/fs/proc/self.c index 4d7d061696b3..127265e5c55f 100644 --- a/fs/proc/self.c +++ b/fs/proc/self.c | |||
@@ -12,7 +12,7 @@ static const char *proc_self_get_link(struct dentry *dentry, | |||
12 | struct inode *inode, | 12 | struct inode *inode, |
13 | struct delayed_call *done) | 13 | struct delayed_call *done) |
14 | { | 14 | { |
15 | struct pid_namespace *ns = inode->i_sb->s_fs_info; | 15 | struct pid_namespace *ns = proc_pid_ns(inode); |
16 | pid_t tgid = task_tgid_nr_ns(current, ns); | 16 | pid_t tgid = task_tgid_nr_ns(current, ns); |
17 | char *name; | 17 | char *name; |
18 | 18 | ||
@@ -36,7 +36,7 @@ static unsigned self_inum __ro_after_init; | |||
36 | int proc_setup_self(struct super_block *s) | 36 | int proc_setup_self(struct super_block *s) |
37 | { | 37 | { |
38 | struct inode *root_inode = d_inode(s->s_root); | 38 | struct inode *root_inode = d_inode(s->s_root); |
39 | struct pid_namespace *ns = s->s_fs_info; | 39 | struct pid_namespace *ns = proc_pid_ns(root_inode); |
40 | struct dentry *self; | 40 | struct dentry *self; |
41 | 41 | ||
42 | inode_lock(root_inode); | 42 | inode_lock(root_inode); |
diff --git a/fs/proc/softirqs.c b/fs/proc/softirqs.c index 24072cc06e65..12901dcf57e2 100644 --- a/fs/proc/softirqs.c +++ b/fs/proc/softirqs.c | |||
@@ -25,21 +25,9 @@ static int show_softirqs(struct seq_file *p, void *v) | |||
25 | return 0; | 25 | return 0; |
26 | } | 26 | } |
27 | 27 | ||
28 | static int softirqs_open(struct inode *inode, struct file *file) | ||
29 | { | ||
30 | return single_open(file, show_softirqs, NULL); | ||
31 | } | ||
32 | |||
33 | static const struct file_operations proc_softirqs_operations = { | ||
34 | .open = softirqs_open, | ||
35 | .read = seq_read, | ||
36 | .llseek = seq_lseek, | ||
37 | .release = single_release, | ||
38 | }; | ||
39 | |||
40 | static int __init proc_softirqs_init(void) | 28 | static int __init proc_softirqs_init(void) |
41 | { | 29 | { |
42 | proc_create("softirqs", 0, NULL, &proc_softirqs_operations); | 30 | proc_create_single("softirqs", 0, NULL, show_softirqs); |
43 | return 0; | 31 | return 0; |
44 | } | 32 | } |
45 | fs_initcall(proc_softirqs_init); | 33 | fs_initcall(proc_softirqs_init); |
diff --git a/fs/proc/thread_self.c b/fs/proc/thread_self.c index 9d2efaca499f..b905010ca9eb 100644 --- a/fs/proc/thread_self.c +++ b/fs/proc/thread_self.c | |||
@@ -12,7 +12,7 @@ static const char *proc_thread_self_get_link(struct dentry *dentry, | |||
12 | struct inode *inode, | 12 | struct inode *inode, |
13 | struct delayed_call *done) | 13 | struct delayed_call *done) |
14 | { | 14 | { |
15 | struct pid_namespace *ns = inode->i_sb->s_fs_info; | 15 | struct pid_namespace *ns = proc_pid_ns(inode); |
16 | pid_t tgid = task_tgid_nr_ns(current, ns); | 16 | pid_t tgid = task_tgid_nr_ns(current, ns); |
17 | pid_t pid = task_pid_nr_ns(current, ns); | 17 | pid_t pid = task_pid_nr_ns(current, ns); |
18 | char *name; | 18 | char *name; |
@@ -36,7 +36,7 @@ static unsigned thread_self_inum __ro_after_init; | |||
36 | int proc_setup_thread_self(struct super_block *s) | 36 | int proc_setup_thread_self(struct super_block *s) |
37 | { | 37 | { |
38 | struct inode *root_inode = d_inode(s->s_root); | 38 | struct inode *root_inode = d_inode(s->s_root); |
39 | struct pid_namespace *ns = s->s_fs_info; | 39 | struct pid_namespace *ns = proc_pid_ns(root_inode); |
40 | struct dentry *thread_self; | 40 | struct dentry *thread_self; |
41 | 41 | ||
42 | inode_lock(root_inode); | 42 | inode_lock(root_inode); |
diff --git a/fs/proc/uptime.c b/fs/proc/uptime.c index 95a708d83721..3bd12f955867 100644 --- a/fs/proc/uptime.c +++ b/fs/proc/uptime.c | |||
@@ -30,21 +30,9 @@ static int uptime_proc_show(struct seq_file *m, void *v) | |||
30 | return 0; | 30 | return 0; |
31 | } | 31 | } |
32 | 32 | ||
33 | static int uptime_proc_open(struct inode *inode, struct file *file) | ||
34 | { | ||
35 | return single_open(file, uptime_proc_show, NULL); | ||
36 | } | ||
37 | |||
38 | static const struct file_operations uptime_proc_fops = { | ||
39 | .open = uptime_proc_open, | ||
40 | .read = seq_read, | ||
41 | .llseek = seq_lseek, | ||
42 | .release = single_release, | ||
43 | }; | ||
44 | |||
45 | static int __init proc_uptime_init(void) | 33 | static int __init proc_uptime_init(void) |
46 | { | 34 | { |
47 | proc_create("uptime", 0, NULL, &uptime_proc_fops); | 35 | proc_create_single("uptime", 0, NULL, uptime_proc_show); |
48 | return 0; | 36 | return 0; |
49 | } | 37 | } |
50 | fs_initcall(proc_uptime_init); | 38 | fs_initcall(proc_uptime_init); |
diff --git a/fs/proc/version.c b/fs/proc/version.c index 94901e8e700d..b449f186577f 100644 --- a/fs/proc/version.c +++ b/fs/proc/version.c | |||
@@ -15,21 +15,9 @@ static int version_proc_show(struct seq_file *m, void *v) | |||
15 | return 0; | 15 | return 0; |
16 | } | 16 | } |
17 | 17 | ||
18 | static int version_proc_open(struct inode *inode, struct file *file) | ||
19 | { | ||
20 | return single_open(file, version_proc_show, NULL); | ||
21 | } | ||
22 | |||
23 | static const struct file_operations version_proc_fops = { | ||
24 | .open = version_proc_open, | ||
25 | .read = seq_read, | ||
26 | .llseek = seq_lseek, | ||
27 | .release = single_release, | ||
28 | }; | ||
29 | |||
30 | static int __init proc_version_init(void) | 18 | static int __init proc_version_init(void) |
31 | { | 19 | { |
32 | proc_create("version", 0, NULL, &version_proc_fops); | 20 | proc_create_single("version", 0, NULL, version_proc_show); |
33 | return 0; | 21 | return 0; |
34 | } | 22 | } |
35 | fs_initcall(proc_version_init); | 23 | fs_initcall(proc_version_init); |