📄 devps.patch.9_25_2000
字号:
+ return -ENOMEM;++ /* Check for special dentries.. */+ pattern = NULL;+ inode = dentry->d_inode;+ if (inode && dentry->d_parent == dentry) {+ if (S_ISSOCK (inode->i_mode))+ pattern = "socket:[%lu]";+ if (S_ISFIFO (inode->i_mode))+ pattern = "pipe:[%lu]";+ }++ if (pattern) {+ len = sprintf (tmp, pattern, inode->i_ino);+ path = tmp;+ } else {+ path = d_path (dentry, tmp, PAGE_SIZE);+ len = tmp + PAGE_SIZE - 1 - path;+ }++ if (len < buflen)+ buflen = len;+ dput (dentry);+ strncpy (buffer, path, buflen);+ free_page ((unsigned long) tmp);+ return buflen;+}++static unsigned long get_phys_addr (struct task_struct *p,+ unsigned long ptr)+{+ pgd_t *page_dir;+ pmd_t *page_middle;+ pte_t pte;++ if (!p || !p->mm || ptr >= TASK_SIZE)+ return 0;+ /* Check for NULL pgd .. shouldn't happen! */+ if (!p->mm->pgd) {+ printk ("get_phys_addr: pid %d has NULL pgd!\n", p->pid);+ return 0;+ }++ page_dir = pgd_offset (p->mm, ptr);+ if (pgd_none (*page_dir))+ return 0;+ if (pgd_bad (*page_dir)) {+ printk ("bad page directory entry %08lx\n",+ pgd_val (*page_dir));+ pgd_clear (page_dir);+ return 0;+ }+ page_middle = pmd_offset (page_dir, ptr);+ if (pmd_none (*page_middle))+ return 0;+ if (pmd_bad (*page_middle)) {+ printk ("bad page middle entry %08lx\n",+ pmd_val (*page_middle));+ pmd_clear (page_middle);+ return 0;+ }+ pte = *pte_offset (page_middle, ptr);+ if (!pte_present (pte))+ return 0;+ return pte_page (pte) + (ptr & ~PAGE_MASK);+}++static int get_array (struct task_struct *p, unsigned long start,+ unsigned long end, char *buffer)+{+ unsigned long addr;+ int size = 0, result = 0;+ char c;++ if (start >= end)+ return result;+ for (;;) {+ addr = get_phys_addr (p, start);+ if (!addr)+ return result;+ do {+ c = *(char *) addr;+ if (!c)+ result = size;+ if (size < PAGE_SIZE)+ buffer[size++] = c;+ else+ return result;+ addr++;+ start++;+ if (!c && start >= end)+ return result;+ } while (addr & ~PAGE_MASK);+ }+ return result;+}++static int+devps_ioctl (struct inode *ip, struct file *fp,+ unsigned int cmd, unsigned long arg)+{+ switch (cmd) {++ /* Count up the total number of processes, + * and then return that total */+ case DEVPS_GET_NUM_PIDS:{+ struct task_struct *p;+ pid_t num_pids = 0;++ read_lock (&tasklist_lock);+ for_each_task (p) {+ if (!p->pid)+ continue;+ num_pids++;+ }+ read_unlock (&tasklist_lock);++ copy_to_user_ret ((pid_t *) arg, &num_pids,+ sizeof (num_pids), -EFAULT);+ return 0;+ }++ /* Returns an array containing all current pids, where+ pidlist[0]=number of PIDs in the array. pidlist[0] also+ specifies the size of the array for the kernel to+ fill... */+ case DEVPS_GET_PID_LIST:{+ struct task_struct *p;+ pid_t *pid_array = NULL;+ pid_t num_pids;+ int stat;++ /* Grab the first element to see how many * entries+ they want us to fill */+ stat = verify_area (VERIFY_READ, (char *) arg,+ sizeof (pid_t));+ if (stat) {+ printk (KERN_INFO+ "devps: can't tell how many "+ "to pid's to write.\n");+ return stat;+ }++ copy_from_user (&num_pids, (void *) arg,+ sizeof (num_pids));++ /* Now make sure we can write the specified amount+ of stuff into the array. If we can't we might + as well quit now and save ourselves the bother. */+ stat = verify_area (VERIFY_WRITE, (char *) arg,+ sizeof (pid_t) * num_pids);+ if (stat) {+ printk (KERN_INFO+ "devps: Insufficient space was "+ "provided to write %d pid's.\n",+ num_pids);+ return stat;+ }++ /* Allocate some memory to hold this stuff in before+ * we copy it out to user-space */+ pid_array = (pid_t *) kmalloc (num_pids *+ sizeof (pid_t),+ GFP_KERNEL);+ if (pid_array == NULL)+ return -ENOMEM;++ /* Now march through the PID list */+ pid_array[0] = 0;+ read_lock (&tasklist_lock);+ for_each_task (p) {+ if (!p->pid)+ continue;+ (pid_array[0])++;+ if (pid_array[0] >= (num_pids - 1))+ continue;+ pid_array[pid_array[0]] = p->pid;+ }+ read_unlock (&tasklist_lock);++ /* Copy out to the user the number we actually filled + */+ copy_to_user_ret ((void *) arg, pid_array,+ sizeof (pid_t) * pid_array[0],+ -EFAULT);+ kfree (pid_array);++ return 0;+ }++ /* Find the details on a particular pid, and fill out a+ struct with all the gory details. */+ case DEVPS_GET_PID_INFO:{+ struct task_struct *p;+ struct pid_info mypidinfo;+ unsigned int state;+ /* 'R' running */+ /* 'S' sleeping */+ /* 'D' disk sleep */+ /* 'Z' zombie */+ /* 'T' stopped */+ /* 'W' paging */+ const char *state_string = "RSDZTW";++ copy_from_user_ret (&mypidinfo,+ (struct pid_info *) arg,+ sizeof (mypidinfo), -EFAULT);++ read_lock (&tasklist_lock);+ p = find_task_by_pid (mypidinfo.pid);+ read_unlock (&tasklist_lock);++ /* Now copy all this crap so we can tell user space + all about it. ick. */+ memset (mypidinfo.name, 0,+ sizeof (mypidinfo.name));+ strcpy (mypidinfo.name, p->comm);+ mypidinfo.flags = p->flags;+ mypidinfo.pgrp = p->pgrp;+ mypidinfo.tms_cutime = p->times.tms_cutime;+ mypidinfo.tms_cstime = p->times.tms_cstime;+ mypidinfo.tms_utime = p->times.tms_utime;+ mypidinfo.tms_stime = p->times.tms_stime;+ mypidinfo.min_flt = p->min_flt;+ mypidinfo.cmin_flt = p->cmin_flt;+ mypidinfo.maj_flt = p->maj_flt;+ mypidinfo.cmaj_flt = p->cmaj_flt;+ mypidinfo.session = p->session;+ mypidinfo.pid = p->pid;+ mypidinfo.ppid = p->p_pptr->pid;+ mypidinfo.tty =+ p->tty ? kdev_t_to_nr (p->tty->device) : 0;+ mypidinfo.start_time = p->start_time;+ mypidinfo.uid = p->uid;+ mypidinfo.euid = p->euid;+ mypidinfo.suid = p->suid;+ mypidinfo.fsuid = p->fsuid;+ mypidinfo.gid = p->gid;+ mypidinfo.egid = p->egid;+ mypidinfo.sgid = p->sgid;+ mypidinfo.fsgid = p->fsgid;+ mypidinfo.priority = 20 - (p->counter * 10 + + DEF_PRIORITY / 2) / DEF_PRIORITY;+ mypidinfo.nice = 20 - (mypidinfo.priority * 20 ++ DEF_PRIORITY / 2) / DEF_PRIORITY;+ state = p-> state & (TASK_RUNNING | TASK_INTERRUPTIBLE+ | TASK_UNINTERRUPTIBLE |+ TASK_ZOMBIE | TASK_STOPPED |+ TASK_SWAPPING);+ while (state) {+ state_string++;+ state >>= 1;+ }+ mypidinfo.state = *state_string;+ mypidinfo.processor = p->processor;+ mypidinfo.nswap = p->nswap;+ mypidinfo.cnswap = p->cnswap;+ if (p && p->mm) {+ char *page = NULL;++ /* Look for some elbow room */+ if (!(page = (char*)get_free_page (GFP_KERNEL)))+ return -ENOMEM;+ /* Grab the command line */+ get_array (p, p->mm->arg_start,+ p->mm->arg_end, page);+ memcpy( mypidinfo.command_line, page, sizeof( mypidinfo.command_line));+ mypidinfo.command_line[sizeof( mypidinfo.command_line)-1]='\0';++ /* Grab the environment */+ memset (page, 0, PAGE_SIZE);+ get_array (p, p->mm->env_start,+ p->mm->env_end, page);+ memcpy( mypidinfo.environment, page, sizeof( mypidinfo.environment));+ mypidinfo.command_line[sizeof( mypidinfo.environment)-1]='\0';+ free_page ((unsigned long) page);+ }+ memset (mypidinfo.cwd, 0, sizeof (mypidinfo.cwd));+ get_name_from_dentry (dget (p->fs->pwd), mypidinfo.cwd,+ sizeof (mypidinfo.cwd));+ memset (mypidinfo.root, 0, sizeof (mypidinfo.root));+ get_name_from_dentry (dget (p->fs->root),+ mypidinfo.root,+ sizeof (mypidinfo.root));++ copy_to_user_ret ((struct pid_info *) arg,+ &mypidinfo, sizeof (mypidinfo),+ -EFAULT);++ return 0;+ }++ /* Return the PID of the current process */+ case DEVPS_GET_CURRENT_PID:{+ return current->pid;+ }++ default:+ return -EINVAL;++ }+ return 0;+}++++/****************************************************************************+ * Set up the file operations devps will support+ */+static struct file_operations devps_fops = {+ NULL, /* No lseek */+ NULL, /* No read */+ NULL, /* No write */+ NULL, /* No readdir */+ NULL, /* No poll */+ devps_ioctl,+ NULL, /* No mmap */+ devps_open,+ NULL, /* flush */+ devps_release,+ NULL, /* fsync */+ NULL, /* fasync */+ NULL, /* check_media_change */+ NULL /* revalidate */+};++static struct miscdevice devps_misc_dev = {+ DEVPS_MINOR,+ "devps",+ &devps_fops+};++/* The real driver initialization function */+extern int devps_init (void)+{+ printk (KERN_INFO "devps driver %s loaded\n", DEVPS_VERSION);++ if (misc_register (&devps_misc_dev)) {+ printk ("devps: unable to get misc device %d\n",+ DEVPS_MINOR);+ return -EIO;+ }++ return 0;+}++#ifdef MODULE++MODULE_AUTHOR ("Erik Andersen <andersee@debian.org>");+MODULE_DESCRIPTION+ ("devps driver -- exports kernel process information to user space");+++/* Stub driver initialization function */+int init_module (void)+{+ return (devps_init ());+}++void cleanup_module (void)+{+ printk (KERN_INFO "devps driver unloaded\n");+ misc_deregister (&devps_misc_dev);+}++#endif /* endif MODULE */diff -urN --exclude=.version --exclude=.config* --exclude=.*depend linux-2.2.18-9.virgin/drivers/char/makedevps.sh linux/drivers/char/makedevps.sh--- linux-2.2.18-9.virgin/drivers/char/makedevps.sh Wed Dec 31 17:00:00 1969+++ linux/drivers/char/makedevps.sh Mon Sep 25 17:00:57 2000@@ -0,0 +1,5 @@+#!/bin/sh -x++gcc -Wall -g -I /usr/src/linux/include ps-devps.c -o ps-devps+gcc -Wall -g -I /usr/src/linux/include mounts.c -o mounts+diff -urN --exclude=.version --exclude=.config* --exclude=.*depend linux-2.2.18-9.virgin/drivers/char/misc.c linux/drivers/char/misc.c--- linux-2.2.18-9.virgin/drivers/char/misc.c Mon Sep 18 15:02:31 2000+++ linux/drivers/char/misc.c Mon Sep 25 17:00:57 2000@@ -85,6 +85,8 @@ extern int pmu_device_init(void); extern int tosh_init(void); extern int rng_init(void);+extern int devps_init(void);+extern int devmtab_init(void); static int misc_read_proc(char *buf, char **start, off_t offset, int len, int *eof, void *private)@@ -268,6 +270,12 @@ #endif #ifdef CONFIG_PMAC_PBOOK pmu_device_init();+#endif+#ifdef CONFIG_DEVPS+ devps_init();+#endif+#ifdef CONFIG_DEVMTAB+ devmtab_init(); #endif #ifdef CONFIG_SGI_NEWPORT_GFX gfx_register ();diff -urN --exclude=.version --exclude=.config* --exclude=.*depend linux-2.2.18-9.virgin/drivers/char/mounts.c linux/drivers/char/mounts.c--- linux-2.2.18-9.virgin/drivers/char/mounts.c Wed Dec 31 17:00:00 1969+++ linux/drivers/char/mounts.c Mon Sep 25 17:00:57 2000@@ -0,0 +1,116 @@+/* vi: set sw=4 ts=4: */+/*+ * devmtab tester+ *+ *+ * Copyright (C) 2000 by Erik Andersen <andersee@debian.org>+ *+ * This program is free software; you can redistribute it and/or modify+ * it under the terms of the GNU General Public License as published by+ * the Free Software Foundation; either version 2 of the License, or+ * (at your option) any later version.+ *+ * This program is distributed in the hope that it will be useful,+ * but WITHOUT ANY WARRANTY; without even the implied warranty of+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU+ * General Public License for more details.+ *+ * You should have received a copy of the GNU General Public License+ * along with this program; if not, write to the Free Software+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA+ *+ */++#include <stdio.h>+#include <stdlib.h>+#include <errno.h>+#include <string.h>+#include <unistd.h>+#include <time.h>+#include <fcntl.h>+#include <sys/ioctl.h>+#include <sys/types.h>+#include <linux/devmtab.h>+++int main (int argc, char **argv)+{+ char device[80] = "/dev/mtab";+ int fd; /* file descriptor for devmtab device */+ int i, numfilesystems;+ struct k_fstype *fslist;+ struct k_mntent *mntentlist;++ if (argc > 1 && **(argv + 1) == '-') {+ fprintf(stderr, "Usage: mounts\n\nReport mounted stuff\n\nThis version of mounts accepts no options.\n\n");+ exit(1);+ }++ /* open device */ + if ((fd = open(device, O_RDONLY)) < 0) {+ fprintf (stderr, "open failed for `%s': %s\n",+ device, strerror (errno));+ exit (1);+ }++ /* How many filesystems? We need to know to allocate + * enough space for later... */+ numfilesystems = ioctl (fd, DEVMTAB_COUNT_FILESYSTEMS);+ if (numfilesystems<0) {+ fprintf (stderr, "\nDEVMTAB_COUNT_FILESYSTEMS: %s\n", + strerror (errno));+ exit (1);+ } + fslist = (struct k_fstype *) calloc ( numfilesystems, sizeof(struct k_fstype));++ /* Grab the list of available filesystems */+ if (ioctl (fd, DEVMTAB_GET_FILESYSTEMS, fslist)<0) {+ fprintf (stderr, "\nDEVMTAB_GET_FILESYSTEMS: %s\n", + strerror (errno));+ exit (1);+ } + fprintf( stdout, "\nEquivalent of /proc/filesystems:\n");+ for( i = 0 ; i < numfilesystems ; i++) {+ fprintf( stdout, "%s%s\n", fslist[i].mnt_type, + (fslist[i].mnt_nodev)? " nodev" : "");+ }+++ /* How many mounted filesystems? We need to know to + * allocate enough space for later... */+ numfilesystems = ioctl (fd, DEVMTAB_COUNT_MOUNTS);+ if (numfilesystems<0) {+ fprintf (stderr, "\nDEVMTAB_COUNT_MOUNTS: %s\n", + strerror (errno));+ exit (1);+ } + mntentlist = (struct k_mntent *) calloc ( numfilesystems, sizeof(struct k_mntent));+ + /* Grab the list of mounted filesystems */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -