procfs switched to alloc_inode/destroy_inode.
static int comx_rmdir(struct inode *dir, struct dentry *dentry)
{
- struct proc_dir_entry *entry = dentry->d_inode->u.generic_ip;
+ struct proc_dir_entry *entry = PDE(dentry->d_inode);
struct net_device *dev = entry->data;
struct comx_channel *ch = dev->priv;
int ret;
struct proc_dir_entry *de;
struct inode *inode = NULL;
- if ((de = (struct proc_dir_entry *) dir->u.generic_ip) != NULL) {
+ if ((de = PDE(dir)) != NULL) {
for (de = de->subdir ; de ; de = de->next) {
if ((de && de->low_ino) &&
(de->namelen == dentry->d_name.len) &&
static int proc_status_open( struct inode *inode, struct file *file ) {
struct proc_data *data;
- struct proc_dir_entry *dp = inode->u.generic_ip;
+ struct proc_dir_entry *dp = PDE(inode);
struct net_device *dev = dp->data;
struct airo_info *apriv = (struct airo_info *)dev->priv;
CapabilityRid cap_rid;
MOD_INC_USE_COUNT;
- dp = inode->u.generic_ip;
-
if ((file->private_data = kmalloc(sizeof(struct proc_data ), GFP_KERNEL)) == NULL)
return -ENOMEM;
memset(file->private_data, 0, sizeof(struct proc_data));
struct file *file,
u16 rid ) {
struct proc_data *data;
- struct proc_dir_entry *dp = inode->u.generic_ip;
+ struct proc_dir_entry *dp = PDE(inode);
struct net_device *dev = dp->data;
struct airo_info *apriv = (struct airo_info *)dev->priv;
StatsRid stats;
int *vals = stats.vals;
MOD_INC_USE_COUNT;
-
- dp = inode->u.generic_ip;
-
if ((file->private_data = kmalloc(sizeof(struct proc_data ), GFP_KERNEL)) == NULL)
return -ENOMEM;
memset(file->private_data, 0, sizeof(struct proc_data));
static void proc_config_on_close( struct inode *inode, struct file *file ) {
struct proc_data *data = file->private_data;
- struct proc_dir_entry *dp = inode->u.generic_ip;
+ struct proc_dir_entry *dp = PDE(inode);
struct net_device *dev = dp->data;
struct airo_info *ai = (struct airo_info*)dev->priv;
ConfigRid config;
int need_reset = 0;
if ( !data->writelen ) return;
- dp = (struct proc_dir_entry *) inode->u.generic_ip;
disable_MAC(ai);
readConfigRid(ai, &config);
static int proc_config_open( struct inode *inode, struct file *file ) {
struct proc_data *data;
- struct proc_dir_entry *dp = inode->u.generic_ip;
+ struct proc_dir_entry *dp = PDE(inode);
struct net_device *dev = dp->data;
struct airo_info *ai = (struct airo_info*)dev->priv;
ConfigRid config;
MOD_INC_USE_COUNT;
- dp = (struct proc_dir_entry *) inode->u.generic_ip;
-
if ((file->private_data = kmalloc(sizeof(struct proc_data ), GFP_KERNEL)) == NULL)
return -ENOMEM;
memset(file->private_data, 0, sizeof(struct proc_data));
static void proc_SSID_on_close( struct inode *inode, struct file *file ) {
struct proc_data *data = (struct proc_data *)file->private_data;
- struct proc_dir_entry *dp = inode->u.generic_ip;
+ struct proc_dir_entry *dp = PDE(inode);
struct net_device *dev = dp->data;
struct airo_info *ai = (struct airo_info*)dev->priv;
SsidRid SSID_rid;
static void proc_APList_on_close( struct inode *inode, struct file *file ) {
struct proc_data *data = (struct proc_data *)file->private_data;
- struct proc_dir_entry *dp = inode->u.generic_ip;
+ struct proc_dir_entry *dp = PDE(inode);
struct net_device *dev = dp->data;
struct airo_info *ai = (struct airo_info*)dev->priv;
APListRid APList_rid;
static void proc_wepkey_on_close( struct inode *inode, struct file *file ) {
struct proc_data *data;
- struct proc_dir_entry *dp = inode->u.generic_ip;
+ struct proc_dir_entry *dp = PDE(inode);
struct net_device *dev = dp->data;
struct airo_info *ai = (struct airo_info*)dev->priv;
int i;
memset(key, 0, sizeof(key));
- dp = (struct proc_dir_entry *) inode->u.generic_ip;
data = (struct proc_data *)file->private_data;
if ( !data->writelen ) return;
static int proc_wepkey_open( struct inode *inode, struct file *file ) {
struct proc_data *data;
- struct proc_dir_entry *dp = inode->u.generic_ip;
+ struct proc_dir_entry *dp = PDE(inode);
struct net_device *dev = dp->data;
struct airo_info *ai = (struct airo_info*)dev->priv;
char *ptr;
MOD_INC_USE_COUNT;
- dp = (struct proc_dir_entry *) inode->u.generic_ip;
-
if ((file->private_data = kmalloc(sizeof(struct proc_data ), GFP_KERNEL)) == NULL)
return -ENOMEM;
memset(file->private_data, 0, sizeof(struct proc_data));
static int proc_SSID_open( struct inode *inode, struct file *file ) {
struct proc_data *data;
- struct proc_dir_entry *dp = inode->u.generic_ip;
+ struct proc_dir_entry *dp = PDE(inode);
struct net_device *dev = dp->data;
struct airo_info *ai = (struct airo_info*)dev->priv;
int i;
MOD_INC_USE_COUNT;
- dp = (struct proc_dir_entry *) inode->u.generic_ip;
-
if ((file->private_data = kmalloc(sizeof(struct proc_data ), GFP_KERNEL)) == NULL)
return -ENOMEM;
memset(file->private_data, 0, sizeof(struct proc_data));
static int proc_APList_open( struct inode *inode, struct file *file ) {
struct proc_data *data;
- struct proc_dir_entry *dp = inode->u.generic_ip;
+ struct proc_dir_entry *dp = PDE(inode);
struct net_device *dev = dp->data;
struct airo_info *ai = (struct airo_info*)dev->priv;
int i;
MOD_INC_USE_COUNT;
- dp = (struct proc_dir_entry *) inode->u.generic_ip;
-
if ((file->private_data = kmalloc(sizeof(struct proc_data ), GFP_KERNEL)) == NULL)
return -ENOMEM;
memset(file->private_data, 0, sizeof(struct proc_data));
static int proc_BSSList_open( struct inode *inode, struct file *file ) {
struct proc_data *data;
- struct proc_dir_entry *dp = inode->u.generic_ip;
+ struct proc_dir_entry *dp = PDE(inode);
struct net_device *dev = dp->data;
struct airo_info *ai = (struct airo_info*)dev->priv;
char *ptr;
MOD_INC_USE_COUNT;
- dp = (struct proc_dir_entry *) inode->u.generic_ip;
-
if ((file->private_data = kmalloc(sizeof(struct proc_data ), GFP_KERNEL)) == NULL)
return -ENOMEM;
memset(file->private_data, 0, sizeof(struct proc_data));
proc_bus_pci_read(struct file *file, char *buf, size_t nbytes, loff_t *ppos)
{
const struct inode *ino = file->f_dentry->d_inode;
- const struct proc_dir_entry *dp = ino->u.generic_ip;
+ const struct proc_dir_entry *dp = PDE(ino);
struct pci_dev *dev = dp->data;
unsigned int pos = *ppos;
unsigned int cnt, size;
proc_bus_pci_write(struct file *file, const char *buf, size_t nbytes, loff_t *ppos)
{
const struct inode *ino = file->f_dentry->d_inode;
- const struct proc_dir_entry *dp = ino->u.generic_ip;
+ const struct proc_dir_entry *dp = PDE(ino);
struct pci_dev *dev = dp->data;
int pos = *ppos;
int cnt;
static int proc_bus_pci_ioctl(struct inode *inode, struct file *file, unsigned int cmd, unsigned long arg)
{
- const struct proc_dir_entry *dp = inode->u.generic_ip;
+ const struct proc_dir_entry *dp = PDE(inode);
struct pci_dev *dev = dp->data;
#ifdef HAVE_PCI_MMAP
struct pci_filp_private *fpriv = file->private_data;
static int proc_bus_pci_mmap(struct file *file, struct vm_area_struct *vma)
{
struct inode *inode = file->f_dentry->d_inode;
- const struct proc_dir_entry *dp = inode->u.generic_ip;
+ const struct proc_dir_entry *dp = PDE(inode);
struct pci_dev *dev = dp->data;
struct pci_filp_private *fpriv = file->private_data;
int ret;
static ssize_t isapnp_proc_bus_read(struct file *file, char *buf, size_t nbytes, loff_t *ppos)
{
struct inode *ino = file->f_dentry->d_inode;
- struct proc_dir_entry *dp = ino->u.generic_ip;
+ struct proc_dir_entry *dp = PDE(ino);
struct pci_dev *dev = dp->data;
int pos = *ppos;
int cnt, size = 256;
void *arg = (void *) ularg;
int rc;
- pde = (struct proc_dir_entry *) inode->u.generic_ip;
+ pde = PDE(inode);
if (!pde)
return -ENOENT;
static int uhci_proc_open(struct inode *inode, struct file *file)
{
- const struct proc_dir_entry *dp = inode->u.generic_ip;
+ const struct proc_dir_entry *dp = PDE(inode);
struct uhci *uhci = dp->data;
struct uhci_proc *up;
unsigned long flags;
proc_bus_zorro_read(struct file *file, char *buf, size_t nbytes, loff_t *ppos)
{
struct inode *ino = file->f_dentry->d_inode;
- struct proc_dir_entry *dp = ino->u.generic_ip;
+ struct proc_dir_entry *dp = PDE(ino);
struct zorro_dev *dev = dp->data;
struct ConfigDev cd;
int pos = *ppos;
#define fake_ino(pid,ino) (((pid)<<16)|(ino))
+static inline struct task_struct *proc_task(struct inode *inode)
+{
+ return PROC_I(inode)->task;
+}
+
ssize_t proc_pid_read_maps(struct task_struct*,struct file*,char*,size_t,loff_t*);
int proc_pid_stat(struct task_struct*,char*);
int proc_pid_status(struct task_struct*,char*);
static int proc_fd_link(struct inode *inode, struct dentry **dentry, struct vfsmount **mnt)
{
- if (inode->u.proc_i.file) {
- *mnt = mntget(inode->u.proc_i.file->f_vfsmnt);
- *dentry = dget(inode->u.proc_i.file->f_dentry);
+ struct file *file = PROC_I(inode)->file;
+ if (file) {
+ *mnt = mntget(file->f_vfsmnt);
+ *dentry = dget(file->f_dentry);
return 0;
}
return -ENOENT;
struct mm_struct * mm;
struct vm_area_struct * vma;
int result = -ENOENT;
- struct task_struct *task = inode->u.proc_i.task;
+ struct task_struct *task = proc_task(inode);
task_lock(task);
mm = task->mm;
{
struct fs_struct *fs;
int result = -ENOENT;
- task_lock(inode->u.proc_i.task);
- fs = inode->u.proc_i.task->fs;
+ task_lock(proc_task(inode));
+ fs = proc_task(inode)->fs;
if(fs)
atomic_inc(&fs->count);
- task_unlock(inode->u.proc_i.task);
+ task_unlock(proc_task(inode));
if (fs) {
read_lock(&fs->lock);
*mnt = mntget(fs->pwdmnt);
{
struct fs_struct *fs;
int result = -ENOENT;
- task_lock(inode->u.proc_i.task);
- fs = inode->u.proc_i.task->fs;
+ task_lock(proc_task(inode));
+ fs = proc_task(inode)->fs;
if(fs)
atomic_inc(&fs->count);
- task_unlock(inode->u.proc_i.task);
+ task_unlock(proc_task(inode));
if (fs) {
read_lock(&fs->lock);
*mnt = mntget(fs->rootmnt);
size_t count, loff_t *ppos)
{
struct inode * inode = file->f_dentry->d_inode;
- struct task_struct *task = inode->u.proc_i.task;
+ struct task_struct *task = proc_task(inode);
ssize_t res;
res = proc_pid_read_maps(task, file, buf, count, ppos);
extern struct seq_operations mounts_op;
static int mounts_open(struct inode *inode, struct file *file)
{
- struct task_struct *task = inode->u.proc_i.task;
+ struct task_struct *task = proc_task(inode);
int ret = seq_open(file, &mounts_op);
if (!ret) {
unsigned long page;
ssize_t length;
ssize_t end;
- struct task_struct *task = inode->u.proc_i.task;
+ struct task_struct *task = proc_task(inode);
if (count > PROC_BLOCK_SIZE)
count = PROC_BLOCK_SIZE;
if (!(page = __get_free_page(GFP_KERNEL)))
return -ENOMEM;
- length = inode->u.proc_i.op.proc_read(task, (char*)page);
+ length = PROC_I(inode)->op.proc_read(task, (char*)page);
if (length < 0) {
free_page(page);
static ssize_t mem_read(struct file * file, char * buf,
size_t count, loff_t *ppos)
{
- struct task_struct *task = file->f_dentry->d_inode->u.proc_i.task;
+ struct task_struct *task = proc_task(file->f_dentry->d_inode);
char *page;
unsigned long src = *ppos;
int copied = 0;
{
int copied = 0;
char *page;
- struct task_struct *task = file->f_dentry->d_inode->u.proc_i.task;
+ struct task_struct *task = proc_task(file->f_dentry->d_inode);
unsigned long dst = *ppos;
if (!MAY_PTRACE(task))
if (error)
goto out;
- error = inode->u.proc_i.op.proc_get_link(inode, &nd->dentry, &nd->mnt);
+ error = PROC_I(inode)->op.proc_get_link(inode, &nd->dentry, &nd->mnt);
nd->last_type = LAST_BIND;
out:
return error;
if (error)
goto out;
- error = inode->u.proc_i.op.proc_get_link(inode, &de, &mnt);
+ error = PROC_I(inode)->op.proc_get_link(inode, &de, &mnt);
if (error)
goto out;
static int proc_readfd(struct file * filp, void * dirent, filldir_t filldir)
{
struct inode *inode = filp->f_dentry->d_inode;
- struct task_struct *p = inode->u.proc_i.task;
+ struct task_struct *p = proc_task(inode);
unsigned int fd, pid, ino;
int retval;
char buf[NUMBUF];
task_unlock(p);
if (!files)
goto out;
+ read_lock(&files->file_lock);
for (fd = filp->f_pos-2;
fd < files->max_fds;
fd++, filp->f_pos++) {
if (!fcheck_files(files, fd))
continue;
+ read_unlock(&files->file_lock);
j = NUMBUF;
i = fd;
ino = fake_ino(pid, PROC_PID_FD_DIR + fd);
if (filldir(dirent, buf+j, NUMBUF-j, fd+2, ino, DT_LNK) < 0)
break;
+ read_lock(&files->file_lock);
}
+ read_unlock(&files->file_lock);
put_files_struct(files);
}
out:
struct inode *inode = filp->f_dentry->d_inode;
struct pid_entry *p;
- pid = inode->u.proc_i.task->pid;
+ pid = proc_task(inode)->pid;
if (!pid)
return -ENOENT;
i = filp->f_pos;
static struct inode *proc_pid_make_inode(struct super_block * sb, struct task_struct *task, int ino)
{
struct inode * inode;
+ struct proc_inode *ei;
/* We need a new inode */
goto out;
/* Common stuff */
-
+ ei = PROC_I(inode);
+ ei->task = NULL;
+ ei->file = NULL;
inode->i_mtime = inode->i_atime = inode->i_ctime = CURRENT_TIME;
inode->i_ino = fake_ino(task->pid, ino);
* grab the reference to task.
*/
get_task_struct(task);
- inode->u.proc_i.task = task;
+ ei->task = task;
inode->i_uid = 0;
inode->i_gid = 0;
if (ino == PROC_PID_INO || task_dumpable(task)) {
*/
static int pid_base_revalidate(struct dentry * dentry, int flags)
{
- if (dentry->d_inode->u.proc_i.task->pid)
+ if (proc_task(dentry->d_inode)->pid)
return 1;
d_drop(dentry);
return 0;
static struct dentry *proc_lookupfd(struct inode * dir, struct dentry * dentry)
{
unsigned int fd, c;
- struct task_struct *task = dir->u.proc_i.task;
+ struct task_struct *task = proc_task(dir);
struct file * file;
struct files_struct * files;
struct inode *inode;
+ struct proc_inode *ei;
const char *name;
int len;
inode = proc_pid_make_inode(dir->i_sb, task, PROC_PID_FD_DIR+fd);
if (!inode)
goto out;
+ ei = PROC_I(inode);
task_lock(task);
files = task->files;
if (files)
if (!files)
goto out_unlock;
read_lock(&files->file_lock);
- file = inode->u.proc_i.file = fcheck_files(files, fd);
+ file = ei->file = fcheck_files(files, fd);
if (!file)
goto out_unlock2;
get_file(file);
inode->i_op = &proc_pid_link_inode_operations;
inode->i_size = 64;
inode->i_mode = S_IFLNK;
- inode->u.proc_i.op.proc_get_link = proc_fd_link;
+ ei->op.proc_get_link = proc_fd_link;
if (file->f_mode & 1)
inode->i_mode |= S_IRUSR | S_IXUSR;
if (file->f_mode & 2)
{
struct inode *inode;
int error;
- struct task_struct *task = dir->u.proc_i.task;
+ struct task_struct *task = proc_task(dir);
struct pid_entry *p;
+ struct proc_inode *ei;
error = -ENOENT;
inode = NULL;
if (!inode)
goto out;
+ ei = PROC_I(inode);
inode->i_mode = p->mode;
/*
* Yes, it does not scale. And it should not. Don't add
break;
case PROC_PID_EXE:
inode->i_op = &proc_pid_link_inode_operations;
- inode->u.proc_i.op.proc_get_link = proc_exe_link;
+ ei->op.proc_get_link = proc_exe_link;
break;
case PROC_PID_CWD:
inode->i_op = &proc_pid_link_inode_operations;
- inode->u.proc_i.op.proc_get_link = proc_cwd_link;
+ ei->op.proc_get_link = proc_cwd_link;
break;
case PROC_PID_ROOT:
inode->i_op = &proc_pid_link_inode_operations;
- inode->u.proc_i.op.proc_get_link = proc_root_link;
+ ei->op.proc_get_link = proc_root_link;
break;
case PROC_PID_ENVIRON:
inode->i_fop = &proc_info_file_operations;
- inode->u.proc_i.op.proc_read = proc_pid_environ;
+ ei->op.proc_read = proc_pid_environ;
break;
case PROC_PID_STATUS:
inode->i_fop = &proc_info_file_operations;
- inode->u.proc_i.op.proc_read = proc_pid_status;
+ ei->op.proc_read = proc_pid_status;
break;
case PROC_PID_STAT:
inode->i_fop = &proc_info_file_operations;
- inode->u.proc_i.op.proc_read = proc_pid_stat;
+ ei->op.proc_read = proc_pid_stat;
break;
case PROC_PID_CMDLINE:
inode->i_fop = &proc_info_file_operations;
- inode->u.proc_i.op.proc_read = proc_pid_cmdline;
+ ei->op.proc_read = proc_pid_cmdline;
break;
case PROC_PID_STATM:
inode->i_fop = &proc_info_file_operations;
- inode->u.proc_i.op.proc_read = proc_pid_statm;
+ ei->op.proc_read = proc_pid_statm;
break;
case PROC_PID_MAPS:
inode->i_fop = &proc_maps_operations;
#ifdef CONFIG_SMP
case PROC_PID_CPU:
inode->i_fop = &proc_info_file_operations;
- inode->u.proc_i.op.proc_read = proc_pid_cpu;
+ ei->op.proc_read = proc_pid_cpu;
break;
#endif
case PROC_PID_MEM:
struct task_struct *task;
const char *name;
struct inode *inode;
+ struct proc_inode *ei;
int len;
pid = 0;
inode = new_inode(dir->i_sb);
if (!inode)
return ERR_PTR(-ENOMEM);
+ ei = PROC_I(inode);
inode->i_mtime = inode->i_atime = inode->i_ctime = CURRENT_TIME;
inode->i_ino = fake_ino(0, PROC_PID_INO);
- inode->u.proc_i.file = NULL;
- inode->u.proc_i.task = NULL;
+ ei->file = NULL;
+ ei->task = NULL;
inode->i_mode = S_IFLNK|S_IRWXUGO;
inode->i_uid = inode->i_gid = 0;
inode->i_size = 64;
void proc_pid_delete_inode(struct inode *inode)
{
- if (inode->u.proc_i.file)
- fput(inode->u.proc_i.file);
- if (inode->u.proc_i.task)
- free_task_struct(inode->u.proc_i.task);
+ if (PROC_I(inode)->file)
+ fput(PROC_I(inode)->file);
+ if (proc_task(inode))
+ free_task_struct(proc_task(inode));
}
#define PROC_NUMBUF 10
char *start;
struct proc_dir_entry * dp;
- dp = (struct proc_dir_entry *) inode->u.generic_ip;
+ dp = PDE(inode);
if (!(page = (char*) __get_free_page(GFP_KERNEL)))
return -ENOMEM;
struct inode *inode = file->f_dentry->d_inode;
struct proc_dir_entry * dp;
- dp = (struct proc_dir_entry *) inode->u.generic_ip;
+ dp = PDE(inode);
if (!dp->write_proc)
return -EIO;
static int proc_readlink(struct dentry *dentry, char *buffer, int buflen)
{
- char *s=((struct proc_dir_entry *)dentry->d_inode->u.generic_ip)->data;
+ char *s=PDE(dentry->d_inode)->data;
return vfs_readlink(dentry, buffer, buflen, s);
}
static int proc_follow_link(struct dentry *dentry, struct nameidata *nd)
{
- char *s=((struct proc_dir_entry *)dentry->d_inode->u.generic_ip)->data;
+ char *s=PDE(dentry->d_inode)->data;
return vfs_follow_link(nd, s);
}
error = -ENOENT;
inode = NULL;
- de = (struct proc_dir_entry *) dir->u.generic_ip;
+ de = PDE(dir);
if (de) {
for (de = de->subdir; de ; de = de->next) {
if (!de || !de->low_ino)
struct inode *inode = filp->f_dentry->d_inode;
ino = inode->i_ino;
- de = (struct proc_dir_entry *) inode->u.generic_ip;
+ de = PDE(inode);
if (!de)
return -EINVAL;
i = filp->f_pos;
if (dentry->d_op != &proc_dentry_operations)
continue;
inode = dentry->d_inode;
- if (inode->u.generic_ip != de)
+ if (PDE(inode) != de)
continue;
fops = filp->f_op;
filp->f_op = NULL;
*/
static void proc_delete_inode(struct inode *inode)
{
- struct proc_dir_entry *de = inode->u.generic_ip;
+ struct proc_dir_entry *de = PDE(inode);
inode->i_state = I_CLEAR;
return 0;
}
+static kmem_cache_t * proc_inode_cachep;
+
+static struct inode *proc_alloc_inode(struct super_block *sb)
+{
+ struct proc_inode *ei;
+ ei = (struct proc_inode *)kmem_cache_alloc(proc_inode_cachep, SLAB_KERNEL);
+ if (!ei)
+ return NULL;
+ return &ei->vfs_inode;
+}
+
+static void proc_destroy_inode(struct inode *inode)
+{
+ kmem_cache_free(proc_inode_cachep, PROC_I(inode));
+}
+
+static void init_once(void * foo, kmem_cache_t * cachep, unsigned long flags)
+{
+ struct proc_inode *ei = (struct proc_inode *) foo;
+
+ if ((flags & (SLAB_CTOR_VERIFY|SLAB_CTOR_CONSTRUCTOR)) ==
+ SLAB_CTOR_CONSTRUCTOR)
+ inode_init_once(&ei->vfs_inode);
+}
+
+int __init proc_init_inodecache(void)
+{
+ proc_inode_cachep = kmem_cache_create("proc_inode_cache",
+ sizeof(struct proc_inode),
+ 0, SLAB_HWCACHE_ALIGN,
+ init_once, NULL);
+ if (proc_inode_cachep == NULL)
+ return -ENOMEM;
+ return 0;
+}
+
static struct super_operations proc_sops = {
+ alloc_inode: proc_alloc_inode,
+ destroy_inode: proc_destroy_inode,
read_inode: proc_read_inode,
put_inode: force_delete,
delete_inode: proc_delete_inode,
statfs: proc_statfs,
};
-
static int parse_options(char *options,uid_t *uid,gid_t *gid)
{
char *this_char,*value;
if (!inode)
goto out_fail;
- inode->u.generic_ip = (void *) de;
+ PROC_I(inode)->pde = de;
if (de) {
if (de->mode) {
inode->i_mode = de->mode;
static DECLARE_FSTYPE(proc_fs_type, "proc", proc_read_super, FS_SINGLE);
+extern int __init proc_init_inodecache(void);
void __init proc_root_init(void)
{
- int err = register_filesystem(&proc_fs_type);
+ int err = proc_init_inodecache();
+ if (err)
+ return;
+ err = register_filesystem(&proc_fs_type);
if (err)
return;
proc_mnt = kern_mount(&proc_fs_type);
#include <linux/pipe_fs_i.h>
/* #include <linux/umsdos_fs_i.h> */
#include <linux/romfs_fs_i.h>
-#include <linux/proc_fs_i.h>
#include <linux/cramfs_fs_sb.h>
/*
union {
/* struct umsdos_inode_info umsdos_i; */
struct romfs_inode_info romfs_i;
- struct proc_inode_info proc_i;
void *generic_ip;
} u;
};
#endif /* CONFIG_PROC_FS */
+struct proc_inode {
+ struct task_struct *task;
+ int type;
+ union {
+ int (*proc_get_link)(struct inode *, struct dentry **, struct vfsmount **);
+ int (*proc_read)(struct task_struct *task, char *page);
+ } op;
+ struct file *file;
+ struct proc_dir_entry *pde;
+ struct inode vfs_inode;
+};
+
+static inline struct proc_inode *PROC_I(struct inode *inode)
+{
+ return list_entry(inode, struct proc_inode, vfs_inode);
+}
+
+static inline struct proc_dir_entry *PDE(struct inode *inode)
+{
+ return PROC_I(inode)->pde;
+}
+
#endif /* _LINUX_PROC_FS_H */
size_t res;
ssize_t error;
- de = (struct proc_dir_entry*) file->f_dentry->d_inode->u.generic_ip;
+ de = PDE(file->f_dentry->d_inode);
if (!de || !de->data)
return -ENOTDIR;
table = (struct ctl_table *) de->data;
if (count <= 0)
return 0;
- dent = inode->u.generic_ip;
+ dent = PDE(inode);
if ((dent == NULL) || (dent->get_info == NULL))
return 0;
if (count == 0) return 0;
page = get_free_page(GFP_KERNEL);
if (!page) return -ENOMEM;
- dev = ((struct proc_dir_entry *) file->f_dentry->d_inode->u.generic_ip)
- ->data;
+ dev = PDE(file->f_dentry->d_inode)->data;
if (!dev->ops->proc_read)
length = -EINVAL;
else {
unsigned long page;
int length;
int (*info)(loff_t,char *);
- info = ((struct proc_dir_entry *) file->f_dentry->d_inode->u.generic_ip)
- ->data;
+ info = PDE(file->f_dentry->d_inode)->data;
if (count == 0) return 0;
page = get_free_page(GFP_KERNEL);
if ((cmd >> 8) != ROUTER_IOCTL)
return -EINVAL;
- dent = inode->u.generic_ip;
+ dent = PDE(inode);
if ((dent == NULL) || (dent->data == NULL))
return -EINVAL;
if (count <= 0)
return 0;
- dent = inode->u.generic_ip;
+ dent = PDE(inode);
if ((dent == NULL) || (dent->get_info == NULL))
return 0;
if (count <= 0)
return 0;
- dent = inode->u.generic_ip;
+ dent = PDE(inode);
if ((dent == NULL) || (dent->get_info == NULL))
return 0;
if (count <= 0)
return 0;
- dent = inode->u.generic_ip;
+ dent = PDE(inode);
if ((dent == NULL) || (dent->get_info == NULL))
return -ENODATA;
err = verify_area(VERIFY_WRITE, buf, count);
if (err) return err;
- dent = inode->u.generic_ip;
+ dent = PDE(inode);
if ((dent == NULL) || (dent->data == NULL))
return -ENODATA;