~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~ [ freetext search ] ~ [ file search ] ~

Linux Cross Reference
Linux/fs/proc/base.c

Version: ~ [ 2.4.0 ] ~
Architecture: ~ [ i386 ] ~ [ alpha ] ~ [ m68k ] ~ [ mips ] ~ [ ppc ] ~ [ sparc ] ~ [ sparc64 ] ~

  1 /*
  2  *  linux/fs/proc/base.c
  3  *
  4  *  Copyright (C) 1991, 1992 Linus Torvalds
  5  *
  6  *  proc base directory handling functions
  7  *
  8  *  1999, Al Viro. Rewritten. Now it covers the whole per-process part.
  9  *  Instead of using magical inumbers to determine the kind of object
 10  *  we allocate and fill in-core inodes upon lookup. They don't even
 11  *  go into icache. We cache the reference to task_struct upon lookup too.
 12  *  Eventually it should become a filesystem in its own. We don't use the
 13  *  rest of procfs anymore.
 14  */
 15 
 16 #include <asm/uaccess.h>
 17 
 18 #include <linux/config.h>
 19 #include <linux/errno.h>
 20 #include <linux/sched.h>
 21 #include <linux/proc_fs.h>
 22 #include <linux/stat.h>
 23 #include <linux/init.h>
 24 #include <linux/file.h>
 25 #include <linux/string.h>
 26 
 27 /*
 28  * For hysterical raisins we keep the same inumbers as in the old procfs.
 29  * Feel free to change the macro below - just keep the range distinct from
 30  * inumbers of the rest of procfs (currently those are in 0x0000--0xffff).
 31  * As soon as we'll get a separate superblock we will be able to forget
 32  * about magical ranges too.
 33  */
 34 
 35 #define fake_ino(pid,ino) (((pid)<<16)|(ino))
 36 
 37 ssize_t proc_pid_read_maps(struct task_struct*,struct file*,char*,size_t,loff_t*);
 38 int proc_pid_stat(struct task_struct*,char*);
 39 int proc_pid_status(struct task_struct*,char*);
 40 int proc_pid_statm(struct task_struct*,char*);
 41 int proc_pid_cpu(struct task_struct*,char*);
 42 
 43 static int proc_fd_link(struct inode *inode, struct dentry **dentry, struct vfsmount **mnt)
 44 {
 45         if (inode->u.proc_i.file) {
 46                 *mnt = mntget(inode->u.proc_i.file->f_vfsmnt);
 47                 *dentry = dget(inode->u.proc_i.file->f_dentry);
 48                 return 0;
 49         }
 50         return -ENOENT;
 51 }
 52 
 53 static int proc_exe_link(struct inode *inode, struct dentry **dentry, struct vfsmount **mnt)
 54 {
 55         struct mm_struct * mm;
 56         struct vm_area_struct * vma;
 57         int result = -ENOENT;
 58         struct task_struct *task = inode->u.proc_i.task;
 59 
 60         task_lock(task);
 61         mm = task->mm;
 62         if (mm)
 63                 atomic_inc(&mm->mm_users);
 64         task_unlock(task);
 65         if (!mm)
 66                 goto out;
 67         down(&mm->mmap_sem);
 68         vma = mm->mmap;
 69         while (vma) {
 70                 if ((vma->vm_flags & VM_EXECUTABLE) && 
 71                     vma->vm_file) {
 72                         *mnt = mntget(vma->vm_file->f_vfsmnt);
 73                         *dentry = dget(vma->vm_file->f_dentry);
 74                         result = 0;
 75                         break;
 76                 }
 77                 vma = vma->vm_next;
 78         }
 79         up(&mm->mmap_sem);
 80         mmput(mm);
 81 out:
 82         return result;
 83 }
 84 
 85 static int proc_cwd_link(struct inode *inode, struct dentry **dentry, struct vfsmount **mnt)
 86 {
 87         struct fs_struct *fs;
 88         int result = -ENOENT;
 89         task_lock(inode->u.proc_i.task);
 90         fs = inode->u.proc_i.task->fs;
 91         if(fs)
 92                 atomic_inc(&fs->count);
 93         task_unlock(inode->u.proc_i.task);
 94         if (fs) {
 95                 read_lock(&fs->lock);
 96                 *mnt = mntget(fs->pwdmnt);
 97                 *dentry = dget(fs->pwd);
 98                 read_unlock(&fs->lock);
 99                 result = 0;
100                 put_fs_struct(fs);
101         }
102         return result;
103 }
104 
105 static int proc_root_link(struct inode *inode, struct dentry **dentry, struct vfsmount **mnt)
106 {
107         struct fs_struct *fs;
108         int result = -ENOENT;
109         task_lock(inode->u.proc_i.task);
110         fs = inode->u.proc_i.task->fs;
111         if(fs)
112                 atomic_inc(&fs->count);
113         task_unlock(inode->u.proc_i.task);
114         if (fs) {
115                 read_lock(&fs->lock);
116                 *mnt = mntget(fs->rootmnt);
117                 *dentry = dget(fs->root);
118                 read_unlock(&fs->lock);
119                 result = 0;
120                 put_fs_struct(fs);
121         }
122         return result;
123 }
124 
125 static int proc_pid_environ(struct task_struct *task, char * buffer)
126 {
127         struct mm_struct *mm;
128         int res = 0;
129         task_lock(task);
130         mm = task->mm;
131         if (mm)
132                 atomic_inc(&mm->mm_users);
133         task_unlock(task);
134         if (mm) {
135                 int len = mm->env_end - mm->env_start;
136                 if (len > PAGE_SIZE)
137                         len = PAGE_SIZE;
138                 res = access_process_vm(task, mm->env_start, buffer, len, 0);
139                 mmput(mm);
140         }
141         return res;
142 }
143 
144 static int proc_pid_cmdline(struct task_struct *task, char * buffer)
145 {
146         struct mm_struct *mm;
147         int res = 0;
148         task_lock(task);
149         mm = task->mm;
150         if (mm)
151                 atomic_inc(&mm->mm_users);
152         task_unlock(task);
153         if (mm) {
154                 int len = mm->arg_end - mm->arg_start;
155                 if (len > PAGE_SIZE)
156                         len = PAGE_SIZE;
157                 res = access_process_vm(task, mm->arg_start, buffer, len, 0);
158                 // If the nul at the end of args has been overwritten, then
159                 // assume application is using setproctitle(3).
160                 if ( res > 0 && buffer[res-1] != '\0' )
161                 {
162                         len = strnlen( buffer, res );
163                         if ( len < res )
164                         {
165                             res = len;
166                         }
167                         else
168                         {
169                                 len = mm->env_end - mm->env_start;
170                                 if (len > PAGE_SIZE - res)
171                                         len = PAGE_SIZE - res;
172                                 res += access_process_vm(task, mm->env_start, buffer+res, len, 0);
173                                 res = strnlen( buffer, res );
174                         }
175                 }
176                 mmput(mm);
177         }
178         return res;
179 }
180 
181 /************************************************************************/
182 /*                       Here the fs part begins                        */
183 /************************************************************************/
184 
185 /* permission checks */
186 
187 static int standard_permission(struct inode *inode, int mask)
188 {
189         int mode = inode->i_mode;
190 
191         if ((mask & S_IWOTH) && IS_RDONLY(inode) &&
192             (S_ISREG(mode) || S_ISDIR(mode) || S_ISLNK(mode)))
193                 return -EROFS; /* Nobody gets write access to a read-only fs */
194         else if ((mask & S_IWOTH) && IS_IMMUTABLE(inode))
195                 return -EACCES; /* Nobody gets write access to an immutable file */
196         else if (current->fsuid == inode->i_uid)
197                 mode >>= 6;
198         else if (in_group_p(inode->i_gid))
199                 mode >>= 3;
200         if (((mode & mask & S_IRWXO) == mask) || capable(CAP_DAC_OVERRIDE))
201                 return 0;
202         /* read and search access */
203         if ((mask == S_IROTH) ||
204             (S_ISDIR(mode)  && !(mask & ~(S_IROTH | S_IXOTH))))
205                 if (capable(CAP_DAC_READ_SEARCH))
206                         return 0;
207         return -EACCES;
208 }
209 
210 static int proc_check_root(struct inode *inode)
211 {
212         struct dentry *de, *base, *root;
213         struct vfsmount *our_vfsmnt, *vfsmnt, *mnt;
214         int res = 0;
215 
216         if (proc_root_link(inode, &root, &vfsmnt)) /* Ewww... */
217                 return -ENOENT;
218         read_lock(&current->fs->lock);
219         our_vfsmnt = mntget(current->fs->rootmnt);
220         base = dget(current->fs->root);
221         read_unlock(&current->fs->lock);
222 
223         spin_lock(&dcache_lock);
224         de = root;
225         mnt = vfsmnt;
226 
227         while (vfsmnt != our_vfsmnt) {
228                 if (vfsmnt == vfsmnt->mnt_parent)
229                         goto out;
230                 de = vfsmnt->mnt_mountpoint;
231                 vfsmnt = vfsmnt->mnt_parent;
232         }
233 
234         if (!is_subdir(de, base))
235                 goto out;
236         spin_unlock(&dcache_lock);
237 
238 exit:
239         dput(base);
240         mntput(our_vfsmnt);
241         dput(root);
242         mntput(mnt);
243         return res;
244 out:
245         spin_unlock(&dcache_lock);
246         res = -EACCES;
247         goto exit;
248 }
249 
250 static int proc_permission(struct inode *inode, int mask)
251 {
252         if (standard_permission(inode, mask) != 0)
253                 return -EACCES;
254         return proc_check_root(inode);
255 }
256 
257 static ssize_t pid_maps_read(struct file * file, char * buf,
258                               size_t count, loff_t *ppos)
259 {
260         struct inode * inode = file->f_dentry->d_inode;
261         struct task_struct *task = inode->u.proc_i.task;
262         ssize_t res;
263 
264         res = proc_pid_read_maps(task, file, buf, count, ppos);
265         return res;
266 }
267 
268 static struct file_operations proc_maps_operations = {
269         read:           pid_maps_read,
270 };
271 
272 #define PROC_BLOCK_SIZE (3*1024)                /* 4K page size but our output routines use some slack for overruns */
273 
274 static ssize_t proc_info_read(struct file * file, char * buf,
275                           size_t count, loff_t *ppos)
276 {
277         struct inode * inode = file->f_dentry->d_inode;
278         unsigned long page;
279         ssize_t length;
280         ssize_t end;
281         struct task_struct *task = inode->u.proc_i.task;
282 
283         if (count > PROC_BLOCK_SIZE)
284                 count = PROC_BLOCK_SIZE;
285         if (!(page = __get_free_page(GFP_KERNEL)))
286                 return -ENOMEM;
287 
288         length = inode->u.proc_i.op.proc_read(task, (char*)page);
289 
290         if (length < 0) {
291                 free_page(page);
292                 return length;
293         }
294         /* Static 4kB (or whatever) block capacity */
295         if (*ppos >= length) {
296                 free_page(page);
297                 return 0;
298         }
299         if (count + *ppos > length)
300                 count = length - *ppos;
301         end = count + *ppos;
302         copy_to_user(buf, (char *) page + *ppos, count);
303         *ppos = end;
304         free_page(page);
305         return count;
306 }
307 
308 static struct file_operations proc_info_file_operations = {
309         read:           proc_info_read,
310 };
311 
312 #define MAY_PTRACE(p) \
313 (p==current||(p->p_pptr==current&&(p->ptrace & PT_PTRACED)&&p->state==TASK_STOPPED))
314 
315 static ssize_t mem_read(struct file * file, char * buf,
316                         size_t count, loff_t *ppos)
317 {
318         struct task_struct *task = file->f_dentry->d_inode->u.proc_i.task;
319         char *page;
320         unsigned long src = *ppos;
321         int copied = 0;
322 
323         if (!MAY_PTRACE(task))
324                 return -ESRCH;
325 
326         page = (char *)__get_free_page(GFP_USER);
327         if (!page)
328                 return -ENOMEM;
329 
330         while (count > 0) {
331                 int this_len, retval;
332 
333                 this_len = (count > PAGE_SIZE) ? PAGE_SIZE : count;
334                 retval = access_process_vm(task, src, page, this_len, 0);
335                 if (!retval) {
336                         if (!copied)
337                                 copied = -EIO;
338                         break;
339                 }
340                 if (copy_to_user(buf, page, retval)) {
341                         copied = -EFAULT;
342                         break;
343                 }
344                 copied += retval;
345                 src += retval;
346                 buf += retval;
347                 count -= retval;
348         }
349         *ppos = src;
350         free_page((unsigned long) page);
351         return copied;
352 }
353 
354 #define mem_write NULL
355 
356 #ifndef mem_write
357 /* This is a security hazard */
358 static ssize_t mem_write(struct file * file, const char * buf,
359                          size_t count, loff_t *ppos)
360 {
361         int copied = 0;
362         char *page;
363         struct task_struct *task = file->f_dentry->d_inode->u.proc_i.task;
364         unsigned long dst = *ppos;
365 
366         if (!MAY_PTRACE(task))
367                 return -ESRCH;
368 
369         page = (char *)__get_free_page(GFP_USER);
370         if (!page)
371                 return -ENOMEM;
372 
373         while (count > 0) {
374                 int this_len, retval;
375 
376                 this_len = (count > PAGE_SIZE) ? PAGE_SIZE : count;
377                 if (copy_from_user(page, buf, this_len)) {
378                         copied = -EFAULT;
379                         break;
380                 }
381                 retval = access_process_vm(task, dst, page, this_len, 1);
382                 if (!retval) {
383                         if (!copied)
384                                 copied = -EIO;
385                         break;
386                 }
387                 copied += retval;
388                 buf += retval;
389                 dst += retval;
390                 count -= retval;                        
391         }
392         *ppos = dst;
393         free_page((unsigned long) page);
394         return copied;
395 }
396 #endif
397 
398 static struct file_operations proc_mem_operations = {
399         read:           mem_read,
400         write:          mem_write,
401 };
402 
403 static struct inode_operations proc_mem_inode_operations = {
404         permission:     proc_permission,
405 };
406 
407 static int proc_pid_follow_link(struct dentry *dentry, struct nameidata *nd)
408 {
409         struct inode *inode = dentry->d_inode;
410         int error = -EACCES;
411 
412         /* We don't need a base pointer in the /proc filesystem */
413         path_release(nd);
414 
415         if (current->fsuid != inode->i_uid && !capable(CAP_DAC_OVERRIDE))
416                 goto out;
417         error = proc_check_root(inode);
418         if (error)
419                 goto out;
420 
421         error = inode->u.proc_i.op.proc_get_link(inode, &nd->dentry, &nd->mnt);
422         nd->last_type = LAST_BIND;
423 out:
424         return error;
425 }
426 
427 static int do_proc_readlink(struct dentry *dentry, struct vfsmount *mnt,
428                             char * buffer, int buflen)
429 {
430         struct inode * inode;
431         char * tmp = (char*)__get_free_page(GFP_KERNEL), *path;
432         int len;
433 
434         if (!tmp)
435                 return -ENOMEM;
436                 
437         inode = dentry->d_inode;
438         path = d_path(dentry, mnt, tmp, PAGE_SIZE);
439         len = tmp + PAGE_SIZE - 1 - path;
440 
441         if (len < buflen)
442                 buflen = len;
443         copy_to_user(buffer, path, buflen);
444         free_page((unsigned long)tmp);
445         return buflen;
446 }
447 
448 static int proc_pid_readlink(struct dentry * dentry, char * buffer, int buflen)
449 {
450         int error = -EACCES;
451         struct inode *inode = dentry->d_inode;
452         struct dentry *de;
453         struct vfsmount *mnt = NULL;
454 
455         if (current->fsuid != inode->i_uid && !capable(CAP_DAC_OVERRIDE))
456                 goto out;
457         error = proc_check_root(inode);
458         if (error)
459                 goto out;
460 
461         error = inode->u.proc_i.op.proc_get_link(inode, &de, &mnt);
462         if (error)
463                 goto out;
464 
465         error = do_proc_readlink(de, mnt, buffer, buflen);
466         dput(de);
467         mntput(mnt);
468 out:
469         return error;
470 }
471 
472 static struct inode_operations proc_pid_link_inode_operations = {
473         readlink:       proc_pid_readlink,
474         follow_link:    proc_pid_follow_link
475 };
476 
477 struct pid_entry {
478         int type;
479         int len;
480         char *name;
481         mode_t mode;
482 };
483 
484 enum pid_directory_inos {
485         PROC_PID_INO = 2,
486         PROC_PID_STATUS,
487         PROC_PID_MEM,
488         PROC_PID_CWD,
489         PROC_PID_ROOT,
490         PROC_PID_EXE,
491         PROC_PID_FD,
492         PROC_PID_ENVIRON,
493         PROC_PID_CMDLINE,
494         PROC_PID_STAT,
495         PROC_PID_STATM,
496         PROC_PID_MAPS,
497         PROC_PID_CPU,
498         PROC_PID_FD_DIR = 0x8000,       /* 0x8000-0xffff */
499 };
500 
501 #define E(type,name,mode) {(type),sizeof(name)-1,(name),(mode)}
502 static struct pid_entry base_stuff[] = {
503   E(PROC_PID_FD,        "fd",           S_IFDIR|S_IRUSR|S_IXUSR),
504   E(PROC_PID_ENVIRON,   "environ",      S_IFREG|S_IRUSR),
505   E(PROC_PID_STATUS,    "status",       S_IFREG|S_IRUGO),
506   E(PROC_PID_CMDLINE,   "cmdline",      S_IFREG|S_IRUGO),
507   E(PROC_PID_STAT,      "stat",         S_IFREG|S_IRUGO),
508   E(PROC_PID_STATM,     "statm",        S_IFREG|S_IRUGO),
509 #ifdef CONFIG_SMP
510   E(PROC_PID_CPU,       "cpu",          S_IFREG|S_IRUGO),
511 #endif
512   E(PROC_PID_MAPS,      "maps",         S_IFREG|S_IRUGO),
513   E(PROC_PID_MEM,       "mem",          S_IFREG|S_IRUSR|S_IWUSR),
514   E(PROC_PID_CWD,       "cwd",          S_IFLNK|S_IRWXUGO),
515   E(PROC_PID_ROOT,      "root",         S_IFLNK|S_IRWXUGO),
516   E(PROC_PID_EXE,       "exe",          S_IFLNK|S_IRWXUGO),
517   {0,0,NULL,0}
518 };
519 #undef E
520 
521 #define NUMBUF 10
522 
523 static int proc_readfd(struct file * filp, void * dirent, filldir_t filldir)
524 {
525         struct inode *inode = filp->f_dentry->d_inode;
526         struct task_struct *p = inode->u.proc_i.task;
527         unsigned int fd, pid, ino;
528         int retval;
529         char buf[NUMBUF];
530         struct files_struct * files;
531 
532         retval = 0;
533         pid = p->pid;
534 
535         fd = filp->f_pos;
536         switch (fd) {
537                 case 0:
538                         if (filldir(dirent, ".", 1, 0, inode->i_ino, DT_DIR) < 0)
539                                 goto out;
540                         filp->f_pos++;
541                 case 1:
542                         ino = fake_ino(pid, PROC_PID_INO);
543                         if (filldir(dirent, "..", 2, 1, ino, DT_DIR) < 0)
544                                 goto out;
545                         filp->f_pos++;
546                 default:
547                         task_lock(p);
548                         files = p->files;
549                         if (files)
550                                 atomic_inc(&files->count);
551                         task_unlock(p);
552                         if (!files)
553                                 goto out;
554                         for (fd = filp->f_pos-2;
555                              fd < files->max_fds;
556                              fd++, filp->f_pos++) {
557                                 unsigned int i,j;
558 
559                                 if (!fcheck_files(files, fd))
560                                         continue;
561 
562                                 j = NUMBUF;
563                                 i = fd;
564                                 do {
565                                         j--;
566                                         buf[j] = '' + (i % 10);
567                                         i /= 10;
568                                 } while (i);
569 
570                                 ino = fake_ino(pid, PROC_PID_FD_DIR + fd);
571                                 if (filldir(dirent, buf+j, NUMBUF-j, fd+2, ino, DT_LNK) < 0)
572                                         break;
573                         }
574                         put_files_struct(files);
575         }
576 out:
577         return retval;
578 }
579 
580 static int proc_base_readdir(struct file * filp,
581         void * dirent, filldir_t filldir)
582 {
583         int i;
584         int pid;
585         struct inode *inode = filp->f_dentry->d_inode;
586         struct pid_entry *p;
587 
588         pid = inode->u.proc_i.task->pid;
589         if (!inode->u.proc_i.task->p_pptr)
590                 return -ENOENT;
591         i = filp->f_pos;
592         switch (i) {
593                 case 0:
594                         if (filldir(dirent, ".", 1, i, inode->i_ino, DT_DIR) < 0)
595                                 return 0;
596                         i++;
597                         filp->f_pos++;
598                         /* fall through */
599                 case 1:
600                         if (filldir(dirent, "..", 2, i, PROC_ROOT_INO, DT_DIR) < 0)
601                                 return 0;
602                         i++;
603                         filp->f_pos++;
604                         /* fall through */
605                 default:
606                         i -= 2;
607                         if (i>=sizeof(base_stuff)/sizeof(base_stuff[0]))
608                                 return 1;
609                         p = base_stuff + i;
610                         while (p->name) {
611                                 if (filldir(dirent, p->name, p->len, filp->f_pos,
612                                             fake_ino(pid, p->type), p->mode >> 12) < 0)
613                                         return 0;
614                                 filp->f_pos++;
615                                 p++;
616                         }
617         }
618         return 1;
619 }
620 
621 /* building an inode */
622 
623 static struct inode *proc_pid_make_inode(struct super_block * sb, struct task_struct *task, int ino)
624 {
625         struct inode * inode;
626 
627         /* We need a new inode */
628         
629         inode = new_inode(sb);
630         if (!inode)
631                 goto out;
632 
633         /* Common stuff */
634 
635         inode->i_mtime = inode->i_atime = inode->i_ctime = CURRENT_TIME;
636         inode->i_ino = fake_ino(task->pid, ino);
637 
638         inode->u.proc_i.file = NULL;
639         /*
640          * grab the reference to task.
641          */
642         inode->u.proc_i.task = task;
643         get_task_struct(task);
644         if (!task->p_pptr)
645                 goto out_unlock;
646 
647         inode->i_uid = 0;
648         inode->i_gid = 0;
649         if (ino == PROC_PID_INO || task->dumpable) {
650                 inode->i_uid = task->euid;
651                 inode->i_gid = task->egid;
652         }
653 
654 out:
655         return inode;
656 
657 out_unlock:
658         iput(inode);
659         return NULL;
660 }
661 
662 /* dentry stuff */
663 
664 static int pid_fd_revalidate(struct dentry * dentry, int flags)
665 {
666         return 0;
667 }
668 
669 /*
670  *      Exceptional case: normally we are not allowed to unhash a busy
671  * directory. In this case, however, we can do it - no aliasing problems
672  * due to the way we treat inodes.
673  */
674 static int pid_base_revalidate(struct dentry * dentry, int flags)
675 {
676         if (dentry->d_inode->u.proc_i.task->p_pptr)
677                 return 1;
678         d_drop(dentry);
679         return 0;
680 }
681 
682 static int pid_delete_dentry(struct dentry * dentry)
683 {
684         return 1;
685 }
686 
687 static struct dentry_operations pid_fd_dentry_operations =
688 {
689         d_revalidate:   pid_fd_revalidate,
690         d_delete:       pid_delete_dentry,
691 };
692 
693 static struct dentry_operations pid_dentry_operations =
694 {
695         d_delete:       pid_delete_dentry,
696 };
697 
698 static struct dentry_operations pid_base_dentry_operations =
699 {
700         d_revalidate:   pid_base_revalidate,
701         d_delete:       pid_delete_dentry,
702 };
703 
704 /* Lookups */
705 #define MAX_MULBY10     ((~0U-9)/10)
706 
707 static struct dentry *proc_lookupfd(struct inode * dir, struct dentry * dentry)
708 {
709         unsigned int fd, c;
710         struct task_struct *task = dir->u.proc_i.task;
711         struct file * file;
712         struct files_struct * files;
713         struct inode *inode;
714         const char *name;
715         int len;
716 
717         fd = 0;
718         len = dentry->d_name.len;
719         name = dentry->d_name.name;
720         if (len > 1 && *name == '') goto out;
721         while (len-- > 0) {
722                 c = *name - '';
723                 name++;
724                 if (c > 9)
725                         goto out;
726                 if (fd >= MAX_MULBY10)
727                         goto out;
728                 fd *= 10;
729                 fd += c;
730         }
731 
732         inode = proc_pid_make_inode(dir->i_sb, task, PROC_PID_FD_DIR+fd);
733         if (!inode)
734                 goto out;
735         task_lock(task);
736         files = task->files;
737         if (files)
738                 atomic_inc(&files->count);
739         task_unlock(task);
740         if (!files)
741                 goto out_unlock;
742         read_lock(&files->file_lock);
743         file = inode->u.proc_i.file = fcheck_files(files, fd);
744         if (!file)
745                 goto out_unlock2;
746         get_file(file);
747         read_unlock(&files->file_lock);
748         put_files_struct(files);
749         inode->i_op = &proc_pid_link_inode_operations;
750         inode->i_size = 64;
751         inode->i_mode = S_IFLNK;
752         inode->u.proc_i.op.proc_get_link = proc_fd_link;
753         if (file->f_mode & 1)
754                 inode->i_mode |= S_IRUSR | S_IXUSR;
755         if (file->f_mode & 2)
756                 inode->i_mode |= S_IWUSR | S_IXUSR;
757         dentry->d_op = &pid_fd_dentry_operations;
758         d_add(dentry, inode);
759         return NULL;
760 
761 out_unlock2:
762         put_files_struct(files);
763         read_unlock(&files->file_lock);
764 out_unlock:
765         iput(inode);
766 out:
767         return ERR_PTR(-ENOENT);
768 }
769 
770 static struct file_operations proc_fd_operations = {
771         read:           generic_read_dir,
772         readdir:        proc_readfd,
773 };
774 
775 /*
776  * proc directories can do almost nothing..
777  */
778 static struct inode_operations proc_fd_inode_operations = {
779         lookup:         proc_lookupfd,
780         permission:     proc_permission,
781 };
782 
783 static struct dentry *proc_base_lookup(struct inode *dir, struct dentry *dentry)
784 {
785         struct inode *inode;
786         int error;
787         struct task_struct *task = dir->u.proc_i.task;
788         struct pid_entry *p;
789 
790         error = -ENOENT;
791         inode = NULL;
792 
793         for (p = base_stuff; p->name; p++) {
794                 if (p->len != dentry->d_name.len)
795                         continue;
796                 if (!memcmp(dentry->d_name.name, p->name, p->len))
797                         break;
798         }
799         if (!p->name)
800                 goto out;
801 
802         error = -EINVAL;
803         inode = proc_pid_make_inode(dir->i_sb, task, p->type);
804         if (!inode)
805                 goto out;
806 
807         inode->i_mode = p->mode;
808         /*
809          * Yes, it does not scale. And it should not. Don't add
810          * new entries into /proc/<pid>/ without very good reasons.
811          */
812         switch(p->type) {
813                 case PROC_PID_FD:
814                         inode->i_nlink = 2;
815                         inode->i_op = &proc_fd_inode_operations;
816                         inode->i_fop = &proc_fd_operations;
817                         break;
818                 case PROC_PID_EXE:
819                         inode->i_op = &proc_pid_link_inode_operations;
820                         inode->u.proc_i.op.proc_get_link = proc_exe_link;
821                         break;
822                 case PROC_PID_CWD:
823                         inode->i_op = &proc_pid_link_inode_operations;
824                         inode->u.proc_i.op.proc_get_link = proc_cwd_link;
825                         break;
826                 case PROC_PID_ROOT:
827                         inode->i_op = &proc_pid_link_inode_operations;
828                         inode->u.proc_i.op.proc_get_link = proc_root_link;
829                         break;
830                 case PROC_PID_ENVIRON:
831                         inode->i_fop = &proc_info_file_operations;
832                         inode->u.proc_i.op.proc_read = proc_pid_environ;
833                         break;
834                 case PROC_PID_STATUS:
835                         inode->i_fop = &proc_info_file_operations;
836                         inode->u.proc_i.op.proc_read = proc_pid_status;
837                         break;
838                 case PROC_PID_STAT:
839                         inode->i_fop = &proc_info_file_operations;
840                         inode->u.proc_i.op.proc_read = proc_pid_stat;
841                         break;
842                 case PROC_PID_CMDLINE:
843                         inode->i_fop = &proc_info_file_operations;
844                         inode->u.proc_i.op.proc_read = proc_pid_cmdline;
845                         break;
846                 case PROC_PID_STATM:
847                         inode->i_fop = &proc_info_file_operations;
848                         inode->u.proc_i.op.proc_read = proc_pid_statm;
849                         break;
850                 case PROC_PID_MAPS:
851                         inode->i_fop = &proc_maps_operations;
852                         break;
853 #ifdef CONFIG_SMP
854                 case PROC_PID_CPU:
855                         inode->i_fop = &proc_info_file_operations;
856                         inode->u.proc_i.op.proc_read = proc_pid_cpu;
857                         break;
858 #endif
859                 case PROC_PID_MEM:
860                         inode->i_op = &proc_mem_inode_operations;
861                         inode->i_fop = &proc_mem_operations;
862                         break;
863                 default:
864                         printk("procfs: impossible type (%d)",p->type);
865                         iput(inode);
866                         return ERR_PTR(-EINVAL);
867         }
868         dentry->d_op = &pid_dentry_operations;
869         d_add(dentry, inode);
870         return NULL;
871 
872 out:
873         return ERR_PTR(error);
874 }
875 
876 static struct file_operations proc_base_operations = {
877         read:           generic_read_dir,
878         readdir:        proc_base_readdir,
879 };
880 
881 static struct inode_operations proc_base_inode_operations = {
882         lookup:         proc_base_lookup,
883 };
884 
885 /*
886  * /proc/self:
887  */
888 static int proc_self_readlink(struct dentry *dentry, char *buffer, int buflen)
889 {
890         char tmp[30];
891         sprintf(tmp, "%d", current->pid);
892         return vfs_readlink(dentry,buffer,buflen,tmp);
893 }
894 
895 static int proc_self_follow_link(struct dentry *dentry, struct nameidata *nd)
896 {
897         char tmp[30];
898         sprintf(tmp, "%d", current->pid);
899         return vfs_follow_link(nd,tmp);
900 }       
901 
902 static struct inode_operations proc_self_inode_operations = {
903         readlink:       proc_self_readlink,
904         follow_link:    proc_self_follow_link,
905 };
906 
907 struct dentry *proc_pid_lookup(struct inode *dir, struct dentry * dentry)
908 {
909         unsigned int pid, c;
910         struct task_struct *task;
911         const char *name;
912         struct inode *inode;
913         int len;
914 
915         pid = 0;
916         name = dentry->d_name.name;
917         len = dentry->d_name.len;
918         if (len == 4 && !memcmp(name, "self", 4)) {
919                 inode = new_inode(dir->i_sb);
920                 if (!inode)
921                         return ERR_PTR(-ENOMEM);
922                 inode->i_mtime = inode->i_atime = inode->i_ctime = CURRENT_TIME;
923                 inode->i_ino = fake_ino(0, PROC_PID_INO);
924                 inode->u.proc_i.file = NULL;
925                 inode->u.proc_i.task = NULL;
926                 inode->i_mode = S_IFLNK|S_IRWXUGO;
927                 inode->i_uid = inode->i_gid = 0;
928                 inode->i_size = 64;
929                 inode->i_op = &proc_self_inode_operations;
930                 d_add(dentry, inode);
931                 return NULL;
932         }
933         while (len-- > 0) {
934                 c = *name - '';
935                 name++;
936                 if (c > 9)
937                         goto out;
938                 if (pid >= MAX_MULBY10)
939                         goto out;
940                 pid *= 10;
941                 pid += c;
942                 if (!pid)
943                         goto out;
944         }
945 
946         read_lock(&tasklist_lock);
947         task = find_task_by_pid(pid);
948         if (task)
949                 get_task_struct(task);
950         read_unlock(&tasklist_lock);
951         if (!task)
952                 goto out;
953 
954         inode = proc_pid_make_inode(dir->i_sb, task, PROC_PID_INO);
955 
956         free_task_struct(task);
957 
958         if (!inode)
959                 goto out;
960         inode->i_mode = S_IFDIR|S_IRUGO|S_IXUGO;
961         inode->i_op = &proc_base_inode_operations;
962         inode->i_fop = &proc_base_operations;
963         inode->i_nlink = 3;
964         inode->i_flags|=S_IMMUTABLE;
965 
966         dentry->d_op = &pid_base_dentry_operations;
967         d_add(dentry, inode);
968         return NULL;
969 out:
970         return ERR_PTR(-ENOENT);
971 }
972 
973 void proc_pid_delete_inode(struct inode *inode)
974 {
975         if (inode->u.proc_i.file)
976                 fput(inode->u.proc_i.file);
977         if (inode->u.proc_i.task)
978                 free_task_struct(inode->u.proc_i.task);
979 }
980 
981 #define PROC_NUMBUF 10
982 #define PROC_MAXPIDS 20
983 
984 /*
985  * Get a few pid's to return for filldir - we need to hold the
986  * tasklist lock while doing this, and we must release it before
987  * we actually do the filldir itself, so we use a temp buffer..
988  */
989 static int get_pid_list(int index, unsigned int *pids)
990 {
991         struct task_struct *p;
992         int nr_pids = 0;
993 
994         index--;
995         read_lock(&tasklist_lock);
996         for_each_task(p) {
997                 int pid = p->pid;
998                 if (!pid)
999                         continue;
1000                 if (--index >= 0)
1001                         continue;
1002                 pids[nr_pids] = pid;
1003                 nr_pids++;
1004                 if (nr_pids >= PROC_MAXPIDS)
1005                         break;
1006         }
1007         read_unlock(&tasklist_lock);
1008         return nr_pids;
1009 }
1010 
1011 int proc_pid_readdir(struct file * filp, void * dirent, filldir_t filldir)
1012 {
1013         unsigned int pid_array[PROC_MAXPIDS];
1014         char buf[PROC_NUMBUF];
1015         unsigned int nr = filp->f_pos - FIRST_PROCESS_ENTRY;
1016         unsigned int nr_pids, i;
1017 
1018         if (!nr) {
1019                 ino_t ino = fake_ino(0,PROC_PID_INO);
1020                 if (filldir(dirent, "self", 4, filp->f_pos, ino, DT_LNK) < 0)
1021                         return 0;
1022                 filp->f_pos++;
1023                 nr++;
1024         }
1025 
1026         nr_pids = get_pid_list(nr, pid_array);
1027 
1028         for (i = 0; i < nr_pids; i++) {
1029                 int pid = pid_array[i];
1030                 ino_t ino = fake_ino(pid,PROC_PID_INO);
1031                 unsigned long j = PROC_NUMBUF;
1032 
1033                 do buf[--j] = '' + (pid % 10); while (pid/=10);
1034 
1035                 if (filldir(dirent, buf+j, PROC_NUMBUF-j, filp->f_pos, ino, DT_DIR) < 0)
1036                         break;
1037                 filp->f_pos++;
1038         }
1039         return 0;
1040 }
1041 

~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~ [ freetext search ] ~ [ file search ] ~

This page was automatically generated by the LXR engine.
Visit the LXR main site for more information.