Import 2.1.81
[davej-history.git] / fs / proc / root.c
blobae9ccce2e6bd88df3a0bd1f233ae5a33eddb070c
1 /*
2 * linux/fs/proc/root.c
4 * Copyright (C) 1991, 1992 Linus Torvalds
6 * proc root directory handling functions
7 */
9 #include <asm/uaccess.h>
11 #include <linux/errno.h>
12 #include <linux/sched.h>
13 #include <linux/proc_fs.h>
14 #include <linux/stat.h>
15 #include <linux/config.h>
16 #include <asm/bitops.h>
17 #ifdef CONFIG_KERNELD
18 #include <linux/kerneld.h>
19 #endif
22 * Offset of the first process in the /proc root directory..
24 #define FIRST_PROCESS_ENTRY 256
26 static int proc_root_readdir(struct file *, void *, filldir_t);
27 static int proc_root_lookup(struct inode *,struct dentry *);
28 static int proc_unlink(struct inode *, struct dentry *);
30 static unsigned char proc_alloc_map[PROC_NDYNAMIC / 8] = {0};
33 * These are the generic /proc directory operations. They
34 * use the in-memory "struct proc_dir_entry" tree to parse
35 * the /proc directory.
37 * NOTE! The /proc/scsi directory currently does not correctly
38 * build up the proc_dir_entry tree, and will show up empty.
40 static struct file_operations proc_dir_operations = {
41 NULL, /* lseek - default */
42 NULL, /* read - bad */
43 NULL, /* write - bad */
44 proc_readdir, /* readdir */
45 NULL, /* poll - default */
46 NULL, /* ioctl - default */
47 NULL, /* mmap */
48 NULL, /* no special open code */
49 NULL, /* no special release code */
50 NULL /* can't fsync */
53 int proc_readlink(struct dentry * dentry, char * buffer, int buflen);
54 struct dentry * proc_follow_link(struct dentry *dentry, struct dentry *base);
57 * proc directories can do almost nothing..
59 struct inode_operations proc_dir_inode_operations = {
60 &proc_dir_operations, /* default net directory file-ops */
61 NULL, /* create */
62 proc_lookup, /* lookup */
63 NULL, /* link */
64 NULL, /* unlink */
65 NULL, /* symlink */
66 NULL, /* mkdir */
67 NULL, /* rmdir */
68 NULL, /* mknod */
69 NULL, /* rename */
70 NULL, /* readlink */
71 NULL, /* follow_link */
72 NULL, /* readpage */
73 NULL, /* writepage */
74 NULL, /* bmap */
75 NULL, /* truncate */
76 NULL /* permission */
80 * /proc dynamic directories now support unlinking
82 struct inode_operations proc_dyna_dir_inode_operations = {
83 &proc_dir_operations, /* default proc dir ops */
84 NULL, /* create */
85 proc_lookup, /* lookup */
86 NULL, /* link */
87 proc_unlink, /* unlink(struct inode *, struct dentry *) */
88 NULL, /* symlink */
89 NULL, /* mkdir */
90 NULL, /* rmdir */
91 NULL, /* mknod */
92 NULL, /* rename */
93 NULL, /* readlink */
94 NULL, /* follow_link */
95 NULL, /* readpage */
96 NULL, /* writepage */
97 NULL, /* bmap */
98 NULL, /* truncate */
99 NULL /* permission */
103 * The root /proc directory is special, as it has the
104 * <pid> directories. Thus we don't use the generic
105 * directory handling functions for that..
107 static struct file_operations proc_root_operations = {
108 NULL, /* lseek - default */
109 NULL, /* read - bad */
110 NULL, /* write - bad */
111 proc_root_readdir, /* readdir */
112 NULL, /* poll - default */
113 NULL, /* ioctl - default */
114 NULL, /* mmap */
115 NULL, /* no special open code */
116 NULL, /* no special release code */
117 NULL /* no fsync */
121 * proc root can do almost nothing..
123 static struct inode_operations proc_root_inode_operations = {
124 &proc_root_operations, /* default base directory file-ops */
125 NULL, /* create */
126 proc_root_lookup, /* lookup */
127 NULL, /* link */
128 NULL, /* unlink */
129 NULL, /* symlink */
130 NULL, /* mkdir */
131 NULL, /* rmdir */
132 NULL, /* mknod */
133 NULL, /* rename */
134 NULL, /* readlink */
135 NULL, /* follow_link */
136 NULL, /* readpage */
137 NULL, /* writepage */
138 NULL, /* bmap */
139 NULL, /* truncate */
140 NULL /* permission */
144 * This is the root "inode" in the /proc tree..
146 struct proc_dir_entry proc_root = {
147 PROC_ROOT_INO, 5, "/proc",
148 S_IFDIR | S_IRUGO | S_IXUGO, 2, 0, 0,
149 0, &proc_root_inode_operations,
150 NULL, NULL,
151 NULL,
152 &proc_root, NULL
155 struct proc_dir_entry *proc_net, *proc_scsi;
157 #ifdef CONFIG_MCA
158 struct proc_dir_entry proc_mca = {
159 PROC_MCA, 3, "mca",
160 S_IFDIR | S_IRUGO | S_IXUGO, 2, 0, 0,
161 0, &proc_dir_inode_operations,
162 NULL, NULL,
163 NULL, &proc_root, NULL
165 #endif
167 #ifdef CONFIG_SYSCTL
168 struct proc_dir_entry proc_sys_root = {
169 PROC_SYS, 3, "sys", /* inode, name */
170 S_IFDIR | S_IRUGO | S_IXUGO, 2, 0, 0, /* mode, nlink, uid, gid */
171 0, &proc_dir_inode_operations, /* size, ops */
172 NULL, NULL, /* get_info, fill_inode */
173 NULL, /* next */
174 NULL, NULL /* parent, subdir */
176 #endif
178 #if defined(CONFIG_SUN_OPENPROMFS) || defined(CONFIG_SUN_OPENPROMFS_MODULE)
180 static int (*proc_openprom_defreaddir_ptr)(struct inode *, struct file *, void *, filldir_t);
181 static int (*proc_openprom_deflookup_ptr)(struct inode *, struct dentry *);
182 void (*proc_openprom_use)(struct inode *, int) = 0;
183 static struct openpromfs_dev *proc_openprom_devices = NULL;
184 static ino_t proc_openpromdev_ino = PROC_OPENPROMD_FIRST;
186 struct inode_operations *
187 proc_openprom_register(int (*readdir)(struct inode *, struct file *, void *, filldir_t),
188 int (*lookup)(struct inode *, struct dentry *),
189 void (*use)(struct inode *, int),
190 struct openpromfs_dev ***devices)
192 proc_openprom_defreaddir_ptr = (proc_openprom_inode_operations.default_file_ops)->readdir;
193 proc_openprom_deflookup_ptr = proc_openprom_inode_operations.lookup;
194 (proc_openprom_inode_operations.default_file_ops)->readdir = readdir;
195 proc_openprom_inode_operations.lookup = lookup;
196 proc_openprom_use = use;
197 *devices = &proc_openprom_devices;
198 return &proc_openprom_inode_operations;
201 int proc_openprom_regdev(struct openpromfs_dev *d)
203 if (proc_openpromdev_ino == PROC_OPENPROMD_FIRST + PROC_NOPENPROMD)
204 return -1;
205 d->next = proc_openprom_devices;
206 d->inode = proc_openpromdev_ino++;
207 proc_openprom_devices = d;
208 return 0;
211 int proc_openprom_unregdev(struct openpromfs_dev *d)
213 if (d == proc_openprom_devices) {
214 proc_openprom_devices = d->next;
215 } else if (!proc_openprom_devices)
216 return -1;
217 else {
218 struct openpromfs_dev *p;
220 for (p = proc_openprom_devices; p->next != d && p->next; p = p->next);
221 if (!p->next) return -1;
222 p->next = d->next;
224 return 0;
227 #ifdef CONFIG_SUN_OPENPROMFS_MODULE
228 void
229 proc_openprom_deregister(void)
231 (proc_openprom_inode_operations.default_file_ops)->readdir = proc_openprom_defreaddir_ptr;
232 proc_openprom_inode_operations.lookup = proc_openprom_deflookup_ptr;
233 proc_openprom_use = 0;
235 #endif
237 #if defined(CONFIG_SUN_OPENPROMFS_MODULE) && defined(CONFIG_KERNELD)
238 static int
239 proc_openprom_defreaddir(struct inode * inode, struct file * filp,
240 void * dirent, filldir_t filldir)
242 request_module("openpromfs");
243 if ((proc_openprom_inode_operations.default_file_ops)->readdir !=
244 proc_openprom_defreaddir)
245 return (proc_openprom_inode_operations.default_file_ops)->readdir
246 (inode, filp, dirent, filldir);
247 return -EINVAL;
249 #define OPENPROM_DEFREADDIR proc_openprom_defreaddir
251 static int
252 proc_openprom_deflookup(struct inode * dir, struct dentry *dentry)
254 request_module("openpromfs");
255 if (proc_openprom_inode_operations.lookup !=
256 proc_openprom_deflookup)
257 return proc_openprom_inode_operations.lookup
258 (dir, dentry);
259 return -ENOENT;
261 #define OPENPROM_DEFLOOKUP proc_openprom_deflookup
262 #else
263 #define OPENPROM_DEFREADDIR NULL
264 #define OPENPROM_DEFLOOKUP NULL
265 #endif
267 static struct file_operations proc_openprom_operations = {
268 NULL, /* lseek - default */
269 NULL, /* read - bad */
270 NULL, /* write - bad */
271 OPENPROM_DEFREADDIR, /* readdir */
272 NULL, /* poll - default */
273 NULL, /* ioctl - default */
274 NULL, /* mmap */
275 NULL, /* no special open code */
276 NULL, /* no special release code */
277 NULL /* can't fsync */
280 struct inode_operations proc_openprom_inode_operations = {
281 &proc_openprom_operations,/* default net directory file-ops */
282 NULL, /* create */
283 OPENPROM_DEFLOOKUP, /* lookup */
284 NULL, /* link */
285 NULL, /* unlink */
286 NULL, /* symlink */
287 NULL, /* mkdir */
288 NULL, /* rmdir */
289 NULL, /* mknod */
290 NULL, /* rename */
291 NULL, /* readlink */
292 NULL, /* follow_link */
293 NULL, /* readpage */
294 NULL, /* writepage */
295 NULL, /* bmap */
296 NULL, /* truncate */
297 NULL /* permission */
300 struct proc_dir_entry proc_openprom = {
301 PROC_OPENPROM, 8, "openprom",
302 S_IFDIR | S_IRUGO | S_IXUGO, 2, 0, 0,
303 0, &proc_openprom_inode_operations,
304 NULL, NULL,
305 NULL,
306 &proc_root, NULL
309 extern void openpromfs_init (void);
310 #endif /* CONFIG_SUN_OPENPROMFS */
312 static int make_inode_number(void)
314 int i = find_first_zero_bit((void *) proc_alloc_map, PROC_NDYNAMIC);
315 if (i<0 || i>=PROC_NDYNAMIC)
316 return -1;
317 set_bit(i, (void *) proc_alloc_map);
318 return PROC_DYNAMIC_FIRST + i;
321 int proc_register(struct proc_dir_entry * dir, struct proc_dir_entry * dp)
323 int i;
325 if (dp->low_ino == 0) {
326 i = make_inode_number();
327 if (i < 0)
328 return -EAGAIN;
329 dp->low_ino = i;
331 dp->next = dir->subdir;
332 dp->parent = dir;
333 dir->subdir = dp;
334 if (S_ISDIR(dp->mode)) {
335 if (dp->ops == NULL)
336 dp->ops = &proc_dir_inode_operations;
337 dir->nlink++;
338 } else if (S_ISLNK(dp->mode)) {
339 if (dp->ops == NULL)
340 dp->ops = &proc_link_inode_operations;
341 } else {
342 if (dp->ops == NULL)
343 dp->ops = &proc_file_inode_operations;
345 return 0;
348 int proc_unregister(struct proc_dir_entry * dir, int ino)
350 struct proc_dir_entry **p = &dir->subdir, *dp;
352 while ((dp = *p) != NULL) {
353 if (dp->low_ino == ino) {
354 *p = dp->next;
355 dp->next = NULL;
356 if (S_ISDIR(dp->mode))
357 dir->nlink--;
358 if (ino >= PROC_DYNAMIC_FIRST &&
359 ino < PROC_DYNAMIC_FIRST+PROC_NDYNAMIC)
360 clear_bit(ino-PROC_DYNAMIC_FIRST,
361 (void *) proc_alloc_map);
362 return 0;
364 p = &dp->next;
366 return -EINVAL;
370 * /proc/self:
372 static int proc_self_readlink(struct dentry *dentry, char *buffer, int buflen)
374 int len;
375 char tmp[30];
377 len = sprintf(tmp, "%d", current->pid);
378 if (buflen < len)
379 len = buflen;
380 copy_to_user(buffer, tmp, len);
381 return len;
384 static struct dentry * proc_self_follow_link(struct dentry *dentry,
385 struct dentry *base)
387 char tmp[30];
389 sprintf(tmp, "%d", current->pid);
390 return lookup_dentry(tmp, base, 1);
393 int proc_readlink(struct dentry * dentry, char * buffer, int buflen)
395 struct inode *inode = dentry->d_inode;
396 struct proc_dir_entry * de;
397 char *page;
398 int len = 0;
400 de = (struct proc_dir_entry *) inode->u.generic_ip;
401 if (!de)
402 return -ENOENT;
403 if (!(page = (char*) __get_free_page(GFP_KERNEL)))
404 return -ENOMEM;
406 if (de->readlink_proc)
407 len = de->readlink_proc(de, page);
409 if (len > buflen)
410 len = buflen;
412 copy_to_user(buffer, page, len);
413 free_page((unsigned long) page);
414 return len;
417 struct dentry * proc_follow_link(struct dentry * dentry, struct dentry *base)
419 struct inode *inode = dentry->d_inode;
420 struct proc_dir_entry * de;
421 char *page;
422 struct dentry *d;
423 int len = 0;
425 de = (struct proc_dir_entry *) inode->u.generic_ip;
426 if (!(page = (char*) __get_free_page(GFP_KERNEL)))
427 return NULL;
429 if (de->readlink_proc)
430 len = de->readlink_proc(de, page);
432 d = lookup_dentry(page, base, 1);
433 free_page((unsigned long) page);
434 return d;
437 static struct inode_operations proc_self_inode_operations = {
438 NULL, /* no file-ops */
439 NULL, /* create */
440 NULL, /* lookup */
441 NULL, /* link */
442 NULL, /* unlink */
443 NULL, /* symlink */
444 NULL, /* mkdir */
445 NULL, /* rmdir */
446 NULL, /* mknod */
447 NULL, /* rename */
448 proc_self_readlink, /* readlink */
449 proc_self_follow_link, /* follow_link */
450 NULL, /* readpage */
451 NULL, /* writepage */
452 NULL, /* bmap */
453 NULL, /* truncate */
454 NULL /* permission */
457 static struct inode_operations proc_link_inode_operations = {
458 NULL, /* no file-ops */
459 NULL, /* create */
460 NULL, /* lookup */
461 NULL, /* link */
462 NULL, /* unlink */
463 NULL, /* symlink */
464 NULL, /* mkdir */
465 NULL, /* rmdir */
466 NULL, /* mknod */
467 NULL, /* rename */
468 proc_readlink, /* readlink */
469 proc_follow_link, /* follow_link */
470 NULL, /* readpage */
471 NULL, /* writepage */
472 NULL, /* bmap */
473 NULL, /* truncate */
474 NULL /* permission */
477 static struct proc_dir_entry proc_root_loadavg = {
478 PROC_LOADAVG, 7, "loadavg",
479 S_IFREG | S_IRUGO, 1, 0, 0,
480 0, &proc_array_inode_operations
482 static struct proc_dir_entry proc_root_uptime = {
483 PROC_UPTIME, 6, "uptime",
484 S_IFREG | S_IRUGO, 1, 0, 0,
485 0, &proc_array_inode_operations
487 static struct proc_dir_entry proc_root_meminfo = {
488 PROC_MEMINFO, 7, "meminfo",
489 S_IFREG | S_IRUGO, 1, 0, 0,
490 0, &proc_array_inode_operations
492 static struct proc_dir_entry proc_root_kmsg = {
493 PROC_KMSG, 4, "kmsg",
494 S_IFREG | S_IRUSR, 1, 0, 0,
495 0, &proc_kmsg_inode_operations
497 static struct proc_dir_entry proc_root_version = {
498 PROC_VERSION, 7, "version",
499 S_IFREG | S_IRUGO, 1, 0, 0,
500 0, &proc_array_inode_operations
502 #ifdef CONFIG_PCI
503 static struct proc_dir_entry proc_root_pci = {
504 PROC_PCI, 3, "pci",
505 S_IFREG | S_IRUGO, 1, 0, 0,
506 0, &proc_array_inode_operations
508 #endif
509 #ifdef CONFIG_ZORRO
510 static struct proc_dir_entry proc_root_zorro = {
511 PROC_ZORRO, 5, "zorro",
512 S_IFREG | S_IRUGO, 1, 0, 0,
513 0, &proc_array_inode_operations
515 #endif
516 static struct proc_dir_entry proc_root_cpuinfo = {
517 PROC_CPUINFO, 7, "cpuinfo",
518 S_IFREG | S_IRUGO, 1, 0, 0,
519 0, &proc_array_inode_operations
521 #if defined (CONFIG_AMIGA) || defined (CONFIG_ATARI)
522 static struct proc_dir_entry proc_root_hardware = {
523 PROC_HARDWARE, 8, "hardware",
524 S_IFREG | S_IRUGO, 1, 0, 0,
525 0, &proc_array_inode_operations
527 #endif
528 static struct proc_dir_entry proc_root_self = {
529 PROC_SELF, 4, "self",
530 S_IFLNK | S_IRUGO | S_IWUGO | S_IXUGO, 1, 0, 0,
531 64, &proc_self_inode_operations,
533 #ifdef CONFIG_DEBUG_MALLOC
534 static struct proc_dir_entry proc_root_malloc = {
535 PROC_MALLOC, 6, "malloc",
536 S_IFREG | S_IRUGO, 1, 0, 0,
537 0, &proc_array_inode_operations
539 #endif
540 static struct proc_dir_entry proc_root_kcore = {
541 PROC_KCORE, 5, "kcore",
542 S_IFREG | S_IRUSR, 1, 0, 0,
543 0, &proc_kcore_inode_operations
545 #ifdef CONFIG_MODULES
546 static struct proc_dir_entry proc_root_modules = {
547 PROC_MODULES, 7, "modules",
548 S_IFREG | S_IRUGO, 1, 0, 0,
549 0, &proc_array_inode_operations
551 static struct proc_dir_entry proc_root_ksyms = {
552 PROC_KSYMS, 5, "ksyms",
553 S_IFREG | S_IRUGO, 1, 0, 0,
554 0, &proc_array_inode_operations
556 #endif
557 static struct proc_dir_entry proc_root_stat = {
558 PROC_STAT, 4, "stat",
559 S_IFREG | S_IRUGO, 1, 0, 0,
560 0, &proc_array_inode_operations
562 static struct proc_dir_entry proc_root_devices = {
563 PROC_DEVICES, 7, "devices",
564 S_IFREG | S_IRUGO, 1, 0, 0,
565 0, &proc_array_inode_operations
567 static struct proc_dir_entry proc_root_interrupts = {
568 PROC_INTERRUPTS, 10,"interrupts",
569 S_IFREG | S_IRUGO, 1, 0, 0,
570 0, &proc_array_inode_operations
572 static struct proc_dir_entry proc_root_filesystems = {
573 PROC_FILESYSTEMS, 11,"filesystems",
574 S_IFREG | S_IRUGO, 1, 0, 0,
575 0, &proc_array_inode_operations
577 static struct proc_dir_entry proc_root_dma = {
578 PROC_DMA, 3, "dma",
579 S_IFREG | S_IRUGO, 1, 0, 0,
580 0, &proc_array_inode_operations
582 static struct proc_dir_entry proc_root_ioports = {
583 PROC_IOPORTS, 7, "ioports",
584 S_IFREG | S_IRUGO, 1, 0, 0,
585 0, &proc_array_inode_operations
587 static struct proc_dir_entry proc_root_cmdline = {
588 PROC_CMDLINE, 7, "cmdline",
589 S_IFREG | S_IRUGO, 1, 0, 0,
590 0, &proc_array_inode_operations
592 #ifdef CONFIG_RTC
593 static struct proc_dir_entry proc_root_rtc = {
594 PROC_RTC, 3, "rtc",
595 S_IFREG | S_IRUGO, 1, 0, 0,
596 0, &proc_array_inode_operations
598 #endif
599 static struct proc_dir_entry proc_root_locks = {
600 PROC_LOCKS, 5, "locks",
601 S_IFREG | S_IRUGO, 1, 0, 0,
602 0, &proc_array_inode_operations
604 static struct proc_dir_entry proc_root_mounts = {
605 PROC_MTAB, 6, "mounts",
606 S_IFREG | S_IRUGO, 1, 0, 0,
607 0, &proc_array_inode_operations
609 static struct proc_dir_entry proc_root_swaps = {
610 PROC_SWAP, 5, "swaps",
611 S_IFREG | S_IRUGO, 1, 0, 0,
612 0, &proc_array_inode_operations
614 static struct proc_dir_entry proc_root_profile = {
615 PROC_PROFILE, 7, "profile",
616 S_IFREG | S_IRUGO | S_IWUSR, 1, 0, 0,
617 0, &proc_profile_inode_operations
619 static struct proc_dir_entry proc_root_slab = {
620 PROC_SLABINFO, 8, "slabinfo",
621 S_IFREG | S_IRUGO, 1, 0, 0,
622 0, &proc_array_inode_operations
624 #ifdef CONFIG_OMIRR
625 static struct proc_dir_entry proc_root_omirr = {
626 PROC_OMIRR, 5, "omirr",
627 S_IFREG | S_IRUSR, 1, 0, 0,
628 0, &proc_omirr_inode_operations
630 #endif
631 #ifdef __powerpc__
632 static struct proc_dir_entry proc_root_ppc_htab = {
633 PROC_PPC_HTAB, 8, "ppc_htab",
634 S_IFREG | S_IRUSR|S_IWUSR|S_IRGRP|S_IROTH, 1, 0, 0,
635 0, &proc_ppc_htab_inode_operations,
636 NULL, NULL, /* get_info, fill_inode */
637 NULL, /* next */
638 NULL, NULL /* parent, subdir */
641 #endif
643 void proc_root_init(void)
645 proc_base_init();
646 proc_register(&proc_root, &proc_root_loadavg);
647 proc_register(&proc_root, &proc_root_uptime);
648 proc_register(&proc_root, &proc_root_meminfo);
649 proc_register(&proc_root, &proc_root_kmsg);
650 proc_register(&proc_root, &proc_root_version);
651 #ifdef CONFIG_PCI
652 proc_register(&proc_root, &proc_root_pci);
653 #endif
654 #ifdef CONFIG_ZORRO
655 proc_register(&proc_root, &proc_root_zorro);
656 #endif
657 proc_register(&proc_root, &proc_root_cpuinfo);
658 proc_register(&proc_root, &proc_root_self);
659 proc_net = create_proc_entry("net", S_IFDIR, 0);
660 proc_scsi = create_proc_entry("scsi", S_IFDIR, 0);
661 #ifdef CONFIG_SYSCTL
662 proc_register(&proc_root, &proc_sys_root);
663 #endif
664 #ifdef CONFIG_MCA
665 proc_register(&proc_root, &proc_mca);
666 #endif
668 #ifdef CONFIG_DEBUG_MALLOC
669 proc_register(&proc_root, &proc_root_malloc);
670 #endif
671 proc_register(&proc_root, &proc_root_kcore);
672 proc_root_kcore.size = (MAP_NR(high_memory) << PAGE_SHIFT) + PAGE_SIZE;
674 #ifdef CONFIG_MODULES
675 proc_register(&proc_root, &proc_root_modules);
676 proc_register(&proc_root, &proc_root_ksyms);
677 #endif
678 proc_register(&proc_root, &proc_root_stat);
679 proc_register(&proc_root, &proc_root_devices);
680 proc_register(&proc_root, &proc_root_interrupts);
681 proc_register(&proc_root, &proc_root_filesystems);
682 proc_register(&proc_root, &proc_root_dma);
683 proc_register(&proc_root, &proc_root_ioports);
684 proc_register(&proc_root, &proc_root_cmdline);
685 #ifdef CONFIG_RTC
686 proc_register(&proc_root, &proc_root_rtc);
687 #endif
688 proc_register(&proc_root, &proc_root_locks);
690 proc_register(&proc_root, &proc_root_mounts);
691 proc_register(&proc_root, &proc_root_swaps);
693 #if defined(CONFIG_SUN_OPENPROMFS) || defined(CONFIG_SUN_OPENPROMFS_MODULE)
694 #ifdef CONFIG_SUN_OPENPROMFS
695 openpromfs_init ();
696 #endif
697 proc_register(&proc_root, &proc_openprom);
698 #endif
699 #if defined (CONFIG_AMIGA) || defined (CONFIG_ATARI)
700 proc_register(&proc_root, &proc_root_hardware);
701 #endif
702 proc_register(&proc_root, &proc_root_slab);
704 if (prof_shift) {
705 proc_register(&proc_root, &proc_root_profile);
706 proc_root_profile.size = (1+prof_len) * sizeof(unsigned long);
709 proc_tty_init();
710 #ifdef __powerpc__
711 proc_register(&proc_root, &proc_root_ppc_htab);
712 #endif
713 #ifdef CONFIG_PROC_DEVICETREE
714 proc_device_tree_init();
715 #endif
719 * As some entries in /proc are volatile, we want to
720 * get rid of unused dentries. This could be made
721 * smarter: we could keep a "volatile" flag in the
722 * inode to indicate which ones to keep.
724 static void
725 proc_delete_dentry(struct dentry * dentry)
727 d_drop(dentry);
730 static struct dentry_operations proc_dentry_operations =
732 NULL, /* revalidate */
733 NULL, /* d_hash */
734 NULL, /* d_compare */
735 proc_delete_dentry /* d_delete(struct dentry *) */
739 * Don't create negative dentries here, return -ENOENT by hand
740 * instead.
742 int proc_lookup(struct inode * dir, struct dentry *dentry)
744 struct inode *inode;
745 struct proc_dir_entry * de;
746 int error;
748 error = -ENOTDIR;
749 if (!dir || !S_ISDIR(dir->i_mode))
750 goto out;
752 error = -ENOENT;
753 inode = NULL;
754 de = (struct proc_dir_entry *) dir->u.generic_ip;
755 if (de) {
756 for (de = de->subdir; de ; de = de->next) {
757 if (!de || !de->low_ino)
758 continue;
759 if (de->namelen != dentry->d_name.len)
760 continue;
761 if (!memcmp(dentry->d_name.name, de->name, de->namelen)) {
762 int ino = de->low_ino | (dir->i_ino & ~(0xffff));
763 error = -EINVAL;
764 inode = proc_get_inode(dir->i_sb, ino, de);
765 break;
770 if (inode) {
771 dentry->d_op = &proc_dentry_operations;
772 d_add(dentry, inode);
773 error = 0;
775 out:
776 return error;
779 static int proc_root_lookup(struct inode * dir, struct dentry * dentry)
781 unsigned int pid, c;
782 struct task_struct *p;
783 const char *name;
784 struct inode *inode;
785 int len;
787 if (dir->i_ino == PROC_ROOT_INO) { /* check for safety... */
788 dir->i_nlink = proc_root.nlink;
790 read_lock(&tasklist_lock);
791 for_each_task(p) {
792 if (p->pid)
793 dir->i_nlink++;
795 read_unlock(&tasklist_lock);
798 if (!proc_lookup(dir, dentry))
799 return 0;
801 pid = 0;
802 name = dentry->d_name.name;
803 len = dentry->d_name.len;
804 while (len-- > 0) {
805 c = *name - '0';
806 name++;
807 if (c > 9) {
808 pid = 0;
809 break;
811 pid *= 10;
812 pid += c;
813 if (pid & 0xffff0000) {
814 pid = 0;
815 break;
818 p = find_task_by_pid(pid);
819 inode = NULL;
820 if (pid && p) {
821 unsigned long ino = (pid << 16) + PROC_PID_INO;
822 inode = proc_get_inode(dir->i_sb, ino, &proc_pid);
823 if (!inode)
824 return -EINVAL;
827 dentry->d_op = &proc_dentry_operations;
828 d_add(dentry, inode);
829 return 0;
833 * This returns non-zero if at EOF, so that the /proc
834 * root directory can use this and check if it should
835 * continue with the <pid> entries..
837 * Note that the VFS-layer doesn't care about the return
838 * value of the readdir() call, as long as it's non-negative
839 * for success..
841 int proc_readdir(struct file * filp,
842 void * dirent, filldir_t filldir)
844 struct proc_dir_entry * de;
845 unsigned int ino;
846 int i;
847 struct inode *inode = filp->f_dentry->d_inode;
849 if (!inode || !S_ISDIR(inode->i_mode))
850 return -ENOTDIR;
851 ino = inode->i_ino;
852 de = (struct proc_dir_entry *) inode->u.generic_ip;
853 if (!de)
854 return -EINVAL;
855 i = filp->f_pos;
856 switch (i) {
857 case 0:
858 if (filldir(dirent, ".", 1, i, ino) < 0)
859 return 0;
860 i++;
861 filp->f_pos++;
862 /* fall through */
863 case 1:
864 if (filldir(dirent, "..", 2, i, de->parent->low_ino) < 0)
865 return 0;
866 i++;
867 filp->f_pos++;
868 /* fall through */
869 default:
870 ino &= ~0xffff;
871 de = de->subdir;
872 i -= 2;
873 for (;;) {
874 if (!de)
875 return 1;
876 if (!i)
877 break;
878 de = de->next;
879 i--;
882 do {
883 if (filldir(dirent, de->name, de->namelen, filp->f_pos, ino | de->low_ino) < 0)
884 return 0;
885 filp->f_pos++;
886 de = de->next;
887 } while (de);
889 return 1;
892 #define NUMBUF 10
894 static int proc_root_readdir(struct file * filp,
895 void * dirent, filldir_t filldir)
897 struct task_struct *p;
898 char buf[NUMBUF];
899 unsigned int nr = filp->f_pos;
901 if (nr < FIRST_PROCESS_ENTRY) {
902 int error = proc_readdir(filp, dirent, filldir);
903 if (error <= 0)
904 return error;
905 filp->f_pos = FIRST_PROCESS_ENTRY;
907 nr = FIRST_PROCESS_ENTRY;
909 read_lock(&tasklist_lock);
910 for_each_task(p) {
911 unsigned int pid;
913 if(nr++ < filp->f_pos)
914 continue;
916 if((pid = p->pid) != 0) {
917 unsigned long j = NUMBUF, i = pid;
919 do {
920 j--;
921 buf[j] = '0' + (i % 10);
922 i /= 10;
923 } while (i);
925 if (filldir(dirent, buf+j, NUMBUF-j,
926 filp->f_pos, (pid << 16) + PROC_PID_INO) < 0)
927 break;
929 filp->f_pos++;
931 read_unlock(&tasklist_lock);
932 return 0;
935 static int proc_unlink(struct inode *dir, struct dentry *dentry)
937 struct proc_dir_entry * dp = dir->u.generic_ip;
939 printk("proc_file_unlink: deleting %s/%s\n", dp->name, dentry->d_name.name);
941 remove_proc_entry(dentry->d_name.name, dp);
942 dentry->d_inode->i_nlink = 0;
943 d_delete(dentry);
944 return 0;