Commit 7dbb30bf authored by Patrick Mochel's avatar Patrick Mochel Committed by Linus Torvalds

[PATCH] sysfs dput crash fix

This is a new patch that includes Martin's, and makes create_dir() return
an int. That matches sysfs_create_file(), and saves a couple of
conversions back and forth between pointer and error.
parent 55b6936d
...@@ -21,32 +21,32 @@ static int init_dir(struct inode * inode) ...@@ -21,32 +21,32 @@ static int init_dir(struct inode * inode)
} }
static struct dentry * static int create_dir(struct kobject * k, struct dentry * p,
create_dir(struct kobject * k, struct dentry * p, const char * n) const char * n, struct dentry ** d)
{ {
struct dentry * dentry; int error;
down(&p->d_inode->i_sem); down(&p->d_inode->i_sem);
dentry = sysfs_get_dentry(p,n); *d = sysfs_get_dentry(p,n);
if (!IS_ERR(dentry)) { if (!IS_ERR(*d)) {
int error = sysfs_create(dentry, error = sysfs_create(*d,
S_IFDIR| S_IRWXU | S_IRUGO | S_IXUGO, S_IFDIR| S_IRWXU | S_IRUGO | S_IXUGO,
init_dir); init_dir);
if (!error) { if (!error) {
dentry->d_fsdata = k; (*d)->d_fsdata = k;
p->d_inode->i_nlink++; p->d_inode->i_nlink++;
} else
dentry = ERR_PTR(error);
dput(dentry);
} }
dput(*d);
} else
error = PTR_ERR(*d);
up(&p->d_inode->i_sem); up(&p->d_inode->i_sem);
return dentry; return error;
} }
struct dentry * sysfs_create_subdir(struct kobject * k, const char * n) int sysfs_create_subdir(struct kobject * k, const char * n, struct dentry ** d)
{ {
return create_dir(k,k->dentry,n); return create_dir(k,k->dentry,n,d);
} }
/** /**
...@@ -71,11 +71,9 @@ int sysfs_create_dir(struct kobject * kobj) ...@@ -71,11 +71,9 @@ int sysfs_create_dir(struct kobject * kobj)
else else
return -EFAULT; return -EFAULT;
dentry = create_dir(kobj,parent,kobject_name(kobj)); error = create_dir(kobj,parent,kobject_name(kobj),&dentry);
if (!IS_ERR(dentry)) if (!error)
kobj->dentry = dentry; kobj->dentry = dentry;
else
error = PTR_ERR(dentry);
return error; return error;
} }
......
...@@ -353,11 +353,11 @@ int sysfs_add_file(struct dentry * dir, const struct attribute * attr) ...@@ -353,11 +353,11 @@ int sysfs_add_file(struct dentry * dir, const struct attribute * attr)
down(&dir->d_inode->i_sem); down(&dir->d_inode->i_sem);
dentry = sysfs_get_dentry(dir,attr->name); dentry = sysfs_get_dentry(dir,attr->name);
if (!IS_ERR(dentry)) { if (!IS_ERR(dentry)) {
error = sysfs_create(dentry,(attr->mode & S_IALLUGO) | S_IFREG,init_file); error = sysfs_create(dentry,
(attr->mode & S_IALLUGO) | S_IFREG,
init_file);
if (!error) if (!error)
dentry->d_fsdata = (void *)attr; dentry->d_fsdata = (void *)attr;
else
dentry = ERR_PTR(error);
dput(dentry); dput(dentry);
} else } else
error = PTR_ERR(dentry); error = PTR_ERR(dentry);
......
...@@ -46,9 +46,9 @@ int sysfs_create_group(struct kobject * kobj, ...@@ -46,9 +46,9 @@ int sysfs_create_group(struct kobject * kobj,
int error; int error;
if (grp->name) { if (grp->name) {
dir = sysfs_create_subdir(kobj,grp->name); error = sysfs_create_subdir(kobj,grp->name,&dir);
if (IS_ERR(dir)) if (error)
return PTR_ERR(dir); return error;
} else } else
dir = kobj->dentry; dir = kobj->dentry;
dir = dget(dir); dir = dget(dir);
......
...@@ -9,5 +9,5 @@ extern struct dentry * sysfs_get_dentry(struct dentry *, const char *); ...@@ -9,5 +9,5 @@ extern struct dentry * sysfs_get_dentry(struct dentry *, const char *);
extern int sysfs_add_file(struct dentry * dir, const struct attribute * attr); extern int sysfs_add_file(struct dentry * dir, const struct attribute * attr);
extern void sysfs_hash_and_remove(struct dentry * dir, const char * name); extern void sysfs_hash_and_remove(struct dentry * dir, const char * name);
extern struct dentry * sysfs_create_subdir(struct kobject *, const char *); extern int sysfs_create_subdir(struct kobject *, const char *, struct dentry **);
extern void sysfs_remove_subdir(struct dentry *); extern void sysfs_remove_subdir(struct dentry *);
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment