aboutsummaryrefslogtreecommitdiffstats
path: root/arch
diff options
context:
space:
mode:
authorAlexey Dobriyan <adobriyan@openvz.org>2007-02-10 04:46:11 -0500
committerLinus Torvalds <torvalds@woody.linux-foundation.org>2007-02-11 13:51:34 -0500
commit85cc9b11446fb8e2762269cfbc28676bfe2eaa4b (patch)
tree4795d357c9239d2e965dfa2d3183a918d6cb04c0 /arch
parent38584c14bbba02d8aedace335073b30e49de66a0 (diff)
[PATCH] sn2: use static ->proc_fops
fix-rmmod-read-write-races-in-proc-entries.patch doesn't want dynamically allocated ->proc_fops, because it will set it to NULL at module unload time. Regardless of module status, switch to statically allocated ->proc_fops which leads to simpler code without wrappers. AFAICS, also fix the following bug: "sn_force_interrupt" proc entry set ->write for itself, but was created with 0444 permissions. Change to 0644. Signed-off-by: Alexey Dobriyan <adobriyan@openvz.org> Cc: Al Viro <viro@zeniv.linux.org.uk> Cc: "Eric W. Biederman" <ebiederm@xmission.com> Cc: "Luck, Tony" <tony.luck@intel.com> Signed-off-by: Andrew Morton <akpm@linux-foundation.org> Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Diffstat (limited to 'arch')
-rw-r--r--arch/ia64/sn/kernel/sn2/sn_proc_fs.c105
1 files changed, 62 insertions, 43 deletions
diff --git a/arch/ia64/sn/kernel/sn2/sn_proc_fs.c b/arch/ia64/sn/kernel/sn2/sn_proc_fs.c
index 43ddc2eccb96..62b3e9a496ac 100644
--- a/arch/ia64/sn/kernel/sn2/sn_proc_fs.c
+++ b/arch/ia64/sn/kernel/sn2/sn_proc_fs.c
@@ -89,61 +89,80 @@ static int coherence_id_open(struct inode *inode, struct file *file)
89 return single_open(file, coherence_id_show, NULL); 89 return single_open(file, coherence_id_show, NULL);
90} 90}
91 91
92static struct proc_dir_entry
93*sn_procfs_create_entry(const char *name, struct proc_dir_entry *parent,
94 int (*openfunc)(struct inode *, struct file *),
95 int (*releasefunc)(struct inode *, struct file *),
96 ssize_t (*write) (struct file *, const char __user *, size_t, loff_t *))
97{
98 struct proc_dir_entry *e = create_proc_entry(name, 0444, parent);
99
100 if (e) {
101 struct file_operations *f;
102
103 f = kzalloc(sizeof(*f), GFP_KERNEL);
104 if (f) {
105 f->open = openfunc;
106 f->read = seq_read;
107 f->llseek = seq_lseek;
108 f->release = releasefunc;
109 f->write = write;
110 e->proc_fops = f;
111 }
112 }
113
114 return e;
115}
116
117/* /proc/sgi_sn/sn_topology uses seq_file, see sn_hwperf.c */ 92/* /proc/sgi_sn/sn_topology uses seq_file, see sn_hwperf.c */
118extern int sn_topology_open(struct inode *, struct file *); 93extern int sn_topology_open(struct inode *, struct file *);
119extern int sn_topology_release(struct inode *, struct file *); 94extern int sn_topology_release(struct inode *, struct file *);
120 95
96static const struct file_operations proc_partition_id_fops = {
97 .open = partition_id_open,
98 .read = seq_read,
99 .llseek = seq_lseek,
100 .release = single_release,
101};
102
103static const struct file_operations proc_system_sn_fops = {
104 .open = system_serial_number_open,
105 .read = seq_read,
106 .llseek = seq_lseek,
107 .release = single_release,
108};
109
110static const struct file_operations proc_license_id_fops = {
111 .open = licenseID_open,
112 .read = seq_read,
113 .llseek = seq_lseek,
114 .release = single_release,
115};
116
117static const struct file_operations proc_sn_force_intr_fops = {
118 .open = sn_force_interrupt_open,
119 .read = seq_read,
120 .write = sn_force_interrupt_write_proc,
121 .llseek = seq_lseek,
122 .release = single_release,
123};
124
125static const struct file_operations proc_coherence_id_fops = {
126 .open = coherence_id_open,
127 .read = seq_read,
128 .llseek = seq_lseek,
129 .release = single_release,
130};
131
132static const struct file_operations proc_sn_topo_fops = {
133 .open = sn_topology_open,
134 .read = seq_read,
135 .llseek = seq_lseek,
136 .release = sn_topology_release,
137};
138
121void register_sn_procfs(void) 139void register_sn_procfs(void)
122{ 140{
123 static struct proc_dir_entry *sgi_proc_dir = NULL; 141 static struct proc_dir_entry *sgi_proc_dir = NULL;
142 struct proc_dir_entry *pde;
124 143
125 BUG_ON(sgi_proc_dir != NULL); 144 BUG_ON(sgi_proc_dir != NULL);
126 if (!(sgi_proc_dir = proc_mkdir("sgi_sn", NULL))) 145 if (!(sgi_proc_dir = proc_mkdir("sgi_sn", NULL)))
127 return; 146 return;
128 147
129 sn_procfs_create_entry("partition_id", sgi_proc_dir, 148 pde = create_proc_entry("partition_id", 0444, sgi_proc_dir);
130 partition_id_open, single_release, NULL); 149 if (pde)
131 150 pde->proc_fops = &proc_partition_id_fops;
132 sn_procfs_create_entry("system_serial_number", sgi_proc_dir, 151 pde = create_proc_entry("system_serial_number", 0444, sgi_proc_dir);
133 system_serial_number_open, single_release, NULL); 152 if (pde)
134 153 pde->proc_fops = &proc_system_sn_fops;
135 sn_procfs_create_entry("licenseID", sgi_proc_dir, 154 pde = create_proc_entry("licenseID", 0444, sgi_proc_dir);
136 licenseID_open, single_release, NULL); 155 if (pde)
137 156 pde->proc_fops = &proc_license_id_fops;
138 sn_procfs_create_entry("sn_force_interrupt", sgi_proc_dir, 157 pde = create_proc_entry("sn_force_interrupt", 0644, sgi_proc_dir);
139 sn_force_interrupt_open, single_release, 158 if (pde)
140 sn_force_interrupt_write_proc); 159 pde->proc_fops = &proc_sn_force_intr_fops;
141 160 pde = create_proc_entry("coherence_id", 0444, sgi_proc_dir);
142 sn_procfs_create_entry("coherence_id", sgi_proc_dir, 161 if (pde)
143 coherence_id_open, single_release, NULL); 162 pde->proc_fops = &proc_coherence_id_fops;
144 163 pde = create_proc_entry("sn_topology", 0444, sgi_proc_dir);
145 sn_procfs_create_entry("sn_topology", sgi_proc_dir, 164 if (pde)
146 sn_topology_open, sn_topology_release, NULL); 165 pde->proc_fops = &proc_sn_topo_fops;
147} 166}
148 167
149#endif /* CONFIG_PROC_FS */ 168#endif /* CONFIG_PROC_FS */