diff options
Diffstat (limited to 'fs/sysfs/dir.c')
| -rw-r--r-- | fs/sysfs/dir.c | 26 |
1 files changed, 16 insertions, 10 deletions
diff --git a/fs/sysfs/dir.c b/fs/sysfs/dir.c index fe198210bc2d..37d7a6875d86 100644 --- a/fs/sysfs/dir.c +++ b/fs/sysfs/dir.c | |||
| @@ -101,18 +101,19 @@ static int create_dir(struct kobject * k, struct dentry * p, | |||
| 101 | down(&p->d_inode->i_sem); | 101 | down(&p->d_inode->i_sem); |
| 102 | *d = sysfs_get_dentry(p,n); | 102 | *d = sysfs_get_dentry(p,n); |
| 103 | if (!IS_ERR(*d)) { | 103 | if (!IS_ERR(*d)) { |
| 104 | error = sysfs_create(*d, mode, init_dir); | 104 | error = sysfs_make_dirent(p->d_fsdata, *d, k, mode, SYSFS_DIR); |
| 105 | if (!error) { | 105 | if (!error) { |
| 106 | error = sysfs_make_dirent(p->d_fsdata, *d, k, mode, | 106 | error = sysfs_create(*d, mode, init_dir); |
| 107 | SYSFS_DIR); | ||
| 108 | if (!error) { | 107 | if (!error) { |
| 109 | p->d_inode->i_nlink++; | 108 | p->d_inode->i_nlink++; |
| 110 | (*d)->d_op = &sysfs_dentry_ops; | 109 | (*d)->d_op = &sysfs_dentry_ops; |
| 111 | d_rehash(*d); | 110 | d_rehash(*d); |
| 112 | } | 111 | } |
| 113 | } | 112 | } |
| 114 | if (error && (error != -EEXIST)) | 113 | if (error && (error != -EEXIST)) { |
| 114 | sysfs_put((*d)->d_fsdata); | ||
| 115 | d_drop(*d); | 115 | d_drop(*d); |
| 116 | } | ||
| 116 | dput(*d); | 117 | dput(*d); |
| 117 | } else | 118 | } else |
| 118 | error = PTR_ERR(*d); | 119 | error = PTR_ERR(*d); |
| @@ -171,17 +172,19 @@ static int sysfs_attach_attr(struct sysfs_dirent * sd, struct dentry * dentry) | |||
| 171 | init = init_file; | 172 | init = init_file; |
| 172 | } | 173 | } |
| 173 | 174 | ||
| 175 | dentry->d_fsdata = sysfs_get(sd); | ||
| 176 | sd->s_dentry = dentry; | ||
| 174 | error = sysfs_create(dentry, (attr->mode & S_IALLUGO) | S_IFREG, init); | 177 | error = sysfs_create(dentry, (attr->mode & S_IALLUGO) | S_IFREG, init); |
| 175 | if (error) | 178 | if (error) { |
| 179 | sysfs_put(sd); | ||
| 176 | return error; | 180 | return error; |
| 181 | } | ||
| 177 | 182 | ||
| 178 | if (bin_attr) { | 183 | if (bin_attr) { |
| 179 | dentry->d_inode->i_size = bin_attr->size; | 184 | dentry->d_inode->i_size = bin_attr->size; |
| 180 | dentry->d_inode->i_fop = &bin_fops; | 185 | dentry->d_inode->i_fop = &bin_fops; |
| 181 | } | 186 | } |
| 182 | dentry->d_op = &sysfs_dentry_ops; | 187 | dentry->d_op = &sysfs_dentry_ops; |
| 183 | dentry->d_fsdata = sysfs_get(sd); | ||
| 184 | sd->s_dentry = dentry; | ||
| 185 | d_rehash(dentry); | 188 | d_rehash(dentry); |
| 186 | 189 | ||
| 187 | return 0; | 190 | return 0; |
| @@ -191,13 +194,15 @@ static int sysfs_attach_link(struct sysfs_dirent * sd, struct dentry * dentry) | |||
| 191 | { | 194 | { |
| 192 | int err = 0; | 195 | int err = 0; |
| 193 | 196 | ||
| 197 | dentry->d_fsdata = sysfs_get(sd); | ||
| 198 | sd->s_dentry = dentry; | ||
| 194 | err = sysfs_create(dentry, S_IFLNK|S_IRWXUGO, init_symlink); | 199 | err = sysfs_create(dentry, S_IFLNK|S_IRWXUGO, init_symlink); |
| 195 | if (!err) { | 200 | if (!err) { |
| 196 | dentry->d_op = &sysfs_dentry_ops; | 201 | dentry->d_op = &sysfs_dentry_ops; |
| 197 | dentry->d_fsdata = sysfs_get(sd); | ||
| 198 | sd->s_dentry = dentry; | ||
| 199 | d_rehash(dentry); | 202 | d_rehash(dentry); |
| 200 | } | 203 | } else |
| 204 | sysfs_put(sd); | ||
| 205 | |||
| 201 | return err; | 206 | return err; |
| 202 | } | 207 | } |
| 203 | 208 | ||
| @@ -228,6 +233,7 @@ static struct dentry * sysfs_lookup(struct inode *dir, struct dentry *dentry, | |||
| 228 | 233 | ||
| 229 | struct inode_operations sysfs_dir_inode_operations = { | 234 | struct inode_operations sysfs_dir_inode_operations = { |
| 230 | .lookup = sysfs_lookup, | 235 | .lookup = sysfs_lookup, |
| 236 | .setattr = sysfs_setattr, | ||
| 231 | }; | 237 | }; |
| 232 | 238 | ||
| 233 | static void remove_dir(struct dentry * d) | 239 | static void remove_dir(struct dentry * d) |
