diff options
Diffstat (limited to 'fs/proc/inode.c')
-rw-r--r-- | fs/proc/inode.c | 46 |
1 files changed, 26 insertions, 20 deletions
diff --git a/fs/proc/inode.c b/fs/proc/inode.c index 439ae6886507..869116c2afbe 100644 --- a/fs/proc/inode.c +++ b/fs/proc/inode.c | |||
@@ -13,6 +13,7 @@ | |||
13 | #include <linux/stat.h> | 13 | #include <linux/stat.h> |
14 | #include <linux/completion.h> | 14 | #include <linux/completion.h> |
15 | #include <linux/poll.h> | 15 | #include <linux/poll.h> |
16 | #include <linux/printk.h> | ||
16 | #include <linux/file.h> | 17 | #include <linux/file.h> |
17 | #include <linux/limits.h> | 18 | #include <linux/limits.h> |
18 | #include <linux/init.h> | 19 | #include <linux/init.h> |
@@ -144,7 +145,7 @@ void pde_users_dec(struct proc_dir_entry *pde) | |||
144 | 145 | ||
145 | static loff_t proc_reg_llseek(struct file *file, loff_t offset, int whence) | 146 | static loff_t proc_reg_llseek(struct file *file, loff_t offset, int whence) |
146 | { | 147 | { |
147 | struct proc_dir_entry *pde = PDE(file->f_path.dentry->d_inode); | 148 | struct proc_dir_entry *pde = PDE(file_inode(file)); |
148 | loff_t rv = -EINVAL; | 149 | loff_t rv = -EINVAL; |
149 | loff_t (*llseek)(struct file *, loff_t, int); | 150 | loff_t (*llseek)(struct file *, loff_t, int); |
150 | 151 | ||
@@ -179,7 +180,7 @@ static loff_t proc_reg_llseek(struct file *file, loff_t offset, int whence) | |||
179 | 180 | ||
180 | static ssize_t proc_reg_read(struct file *file, char __user *buf, size_t count, loff_t *ppos) | 181 | static ssize_t proc_reg_read(struct file *file, char __user *buf, size_t count, loff_t *ppos) |
181 | { | 182 | { |
182 | struct proc_dir_entry *pde = PDE(file->f_path.dentry->d_inode); | 183 | struct proc_dir_entry *pde = PDE(file_inode(file)); |
183 | ssize_t rv = -EIO; | 184 | ssize_t rv = -EIO; |
184 | ssize_t (*read)(struct file *, char __user *, size_t, loff_t *); | 185 | ssize_t (*read)(struct file *, char __user *, size_t, loff_t *); |
185 | 186 | ||
@@ -201,7 +202,7 @@ static ssize_t proc_reg_read(struct file *file, char __user *buf, size_t count, | |||
201 | 202 | ||
202 | static ssize_t proc_reg_write(struct file *file, const char __user *buf, size_t count, loff_t *ppos) | 203 | static ssize_t proc_reg_write(struct file *file, const char __user *buf, size_t count, loff_t *ppos) |
203 | { | 204 | { |
204 | struct proc_dir_entry *pde = PDE(file->f_path.dentry->d_inode); | 205 | struct proc_dir_entry *pde = PDE(file_inode(file)); |
205 | ssize_t rv = -EIO; | 206 | ssize_t rv = -EIO; |
206 | ssize_t (*write)(struct file *, const char __user *, size_t, loff_t *); | 207 | ssize_t (*write)(struct file *, const char __user *, size_t, loff_t *); |
207 | 208 | ||
@@ -223,7 +224,7 @@ static ssize_t proc_reg_write(struct file *file, const char __user *buf, size_t | |||
223 | 224 | ||
224 | static unsigned int proc_reg_poll(struct file *file, struct poll_table_struct *pts) | 225 | static unsigned int proc_reg_poll(struct file *file, struct poll_table_struct *pts) |
225 | { | 226 | { |
226 | struct proc_dir_entry *pde = PDE(file->f_path.dentry->d_inode); | 227 | struct proc_dir_entry *pde = PDE(file_inode(file)); |
227 | unsigned int rv = DEFAULT_POLLMASK; | 228 | unsigned int rv = DEFAULT_POLLMASK; |
228 | unsigned int (*poll)(struct file *, struct poll_table_struct *); | 229 | unsigned int (*poll)(struct file *, struct poll_table_struct *); |
229 | 230 | ||
@@ -245,7 +246,7 @@ static unsigned int proc_reg_poll(struct file *file, struct poll_table_struct *p | |||
245 | 246 | ||
246 | static long proc_reg_unlocked_ioctl(struct file *file, unsigned int cmd, unsigned long arg) | 247 | static long proc_reg_unlocked_ioctl(struct file *file, unsigned int cmd, unsigned long arg) |
247 | { | 248 | { |
248 | struct proc_dir_entry *pde = PDE(file->f_path.dentry->d_inode); | 249 | struct proc_dir_entry *pde = PDE(file_inode(file)); |
249 | long rv = -ENOTTY; | 250 | long rv = -ENOTTY; |
250 | long (*ioctl)(struct file *, unsigned int, unsigned long); | 251 | long (*ioctl)(struct file *, unsigned int, unsigned long); |
251 | 252 | ||
@@ -268,7 +269,7 @@ static long proc_reg_unlocked_ioctl(struct file *file, unsigned int cmd, unsigne | |||
268 | #ifdef CONFIG_COMPAT | 269 | #ifdef CONFIG_COMPAT |
269 | static long proc_reg_compat_ioctl(struct file *file, unsigned int cmd, unsigned long arg) | 270 | static long proc_reg_compat_ioctl(struct file *file, unsigned int cmd, unsigned long arg) |
270 | { | 271 | { |
271 | struct proc_dir_entry *pde = PDE(file->f_path.dentry->d_inode); | 272 | struct proc_dir_entry *pde = PDE(file_inode(file)); |
272 | long rv = -ENOTTY; | 273 | long rv = -ENOTTY; |
273 | long (*compat_ioctl)(struct file *, unsigned int, unsigned long); | 274 | long (*compat_ioctl)(struct file *, unsigned int, unsigned long); |
274 | 275 | ||
@@ -291,7 +292,7 @@ static long proc_reg_compat_ioctl(struct file *file, unsigned int cmd, unsigned | |||
291 | 292 | ||
292 | static int proc_reg_mmap(struct file *file, struct vm_area_struct *vma) | 293 | static int proc_reg_mmap(struct file *file, struct vm_area_struct *vma) |
293 | { | 294 | { |
294 | struct proc_dir_entry *pde = PDE(file->f_path.dentry->d_inode); | 295 | struct proc_dir_entry *pde = PDE(file_inode(file)); |
295 | int rv = -EIO; | 296 | int rv = -EIO; |
296 | int (*mmap)(struct file *, struct vm_area_struct *); | 297 | int (*mmap)(struct file *, struct vm_area_struct *); |
297 | 298 | ||
@@ -445,12 +446,10 @@ static const struct file_operations proc_reg_file_ops_no_compat = { | |||
445 | 446 | ||
446 | struct inode *proc_get_inode(struct super_block *sb, struct proc_dir_entry *de) | 447 | struct inode *proc_get_inode(struct super_block *sb, struct proc_dir_entry *de) |
447 | { | 448 | { |
448 | struct inode * inode; | 449 | struct inode *inode = new_inode_pseudo(sb); |
449 | 450 | ||
450 | inode = iget_locked(sb, de->low_ino); | 451 | if (inode) { |
451 | if (!inode) | 452 | inode->i_ino = de->low_ino; |
452 | return NULL; | ||
453 | if (inode->i_state & I_NEW) { | ||
454 | inode->i_mtime = inode->i_atime = inode->i_ctime = CURRENT_TIME; | 453 | inode->i_mtime = inode->i_atime = inode->i_ctime = CURRENT_TIME; |
455 | PROC_I(inode)->pde = de; | 454 | PROC_I(inode)->pde = de; |
456 | 455 | ||
@@ -478,14 +477,15 @@ struct inode *proc_get_inode(struct super_block *sb, struct proc_dir_entry *de) | |||
478 | inode->i_fop = de->proc_fops; | 477 | inode->i_fop = de->proc_fops; |
479 | } | 478 | } |
480 | } | 479 | } |
481 | unlock_new_inode(inode); | ||
482 | } else | 480 | } else |
483 | pde_put(de); | 481 | pde_put(de); |
484 | return inode; | 482 | return inode; |
485 | } | 483 | } |
486 | 484 | ||
487 | int proc_fill_super(struct super_block *s) | 485 | int proc_fill_super(struct super_block *s) |
488 | { | 486 | { |
487 | struct inode *root_inode; | ||
488 | |||
489 | s->s_flags |= MS_NODIRATIME | MS_NOSUID | MS_NOEXEC; | 489 | s->s_flags |= MS_NODIRATIME | MS_NOSUID | MS_NOEXEC; |
490 | s->s_blocksize = 1024; | 490 | s->s_blocksize = 1024; |
491 | s->s_blocksize_bits = 10; | 491 | s->s_blocksize_bits = 10; |
@@ -494,11 +494,17 @@ int proc_fill_super(struct super_block *s) | |||
494 | s->s_time_gran = 1; | 494 | s->s_time_gran = 1; |
495 | 495 | ||
496 | pde_get(&proc_root); | 496 | pde_get(&proc_root); |
497 | s->s_root = d_make_root(proc_get_inode(s, &proc_root)); | 497 | root_inode = proc_get_inode(s, &proc_root); |
498 | if (s->s_root) | 498 | if (!root_inode) { |
499 | return 0; | 499 | pr_err("proc_fill_super: get root inode failed\n"); |
500 | return -ENOMEM; | ||
501 | } | ||
500 | 502 | ||
501 | printk("proc_read_super: get root inode failed\n"); | 503 | s->s_root = d_make_root(root_inode); |
502 | pde_put(&proc_root); | 504 | if (!s->s_root) { |
503 | return -ENOMEM; | 505 | pr_err("proc_fill_super: allocate dentry failed\n"); |
506 | return -ENOMEM; | ||
507 | } | ||
508 | |||
509 | return 0; | ||
504 | } | 510 | } |