| inode.c (b8441ed279bff09a0a5ddeacf8f4087d2fb424ca) | inode.c (ffed24e22845a3da0ae01095ae3f11c8d16e889d) |
|---|---|
| 1/* 2 * fs/kernfs/inode.c - kernfs inode implementation 3 * 4 * Copyright (c) 2001-3 Patrick Mochel 5 * Copyright (c) 2007 SUSE Linux Products GmbH 6 * Copyright (c) 2007, 2013 Tejun Heo <tj@kernel.org> 7 * 8 * This file is released under the GPLv2. 9 */ | 1/* 2 * fs/kernfs/inode.c - kernfs inode implementation 3 * 4 * Copyright (c) 2001-3 Patrick Mochel 5 * Copyright (c) 2007 SUSE Linux Products GmbH 6 * Copyright (c) 2007, 2013 Tejun Heo <tj@kernel.org> 7 * 8 * This file is released under the GPLv2. 9 */ |
| 10 11#include <linux/pagemap.h> 12#include <linux/backing-dev.h> 13#include <linux/capability.h> 14#include <linux/errno.h> 15#include <linux/slab.h> 16#include <linux/xattr.h> 17#include <linux/security.h> 18 19#include "kernfs-internal.h" 20 21static const struct address_space_operations sysfs_aops = { 22 .readpage = simple_readpage, 23 .write_begin = simple_write_begin, 24 .write_end = simple_write_end, 25}; 26 27static struct backing_dev_info sysfs_backing_dev_info = { 28 .name = "sysfs", 29 .ra_pages = 0, /* No readahead */ 30 .capabilities = BDI_CAP_NO_ACCT_AND_WRITEBACK, 31}; 32 33static const struct inode_operations sysfs_inode_operations = { 34 .permission = sysfs_permission, 35 .setattr = sysfs_setattr, 36 .getattr = sysfs_getattr, 37 .setxattr = sysfs_setxattr, 38}; 39 40int __init sysfs_inode_init(void) 41{ 42 return bdi_init(&sysfs_backing_dev_info); 43} 44 45static struct sysfs_inode_attrs *sysfs_init_inode_attrs(struct sysfs_dirent *sd) 46{ 47 struct sysfs_inode_attrs *attrs; 48 struct iattr *iattrs; 49 50 attrs = kzalloc(sizeof(struct sysfs_inode_attrs), GFP_KERNEL); 51 if (!attrs) 52 return NULL; 53 iattrs = &attrs->ia_iattr; 54 55 /* assign default attributes */ 56 iattrs->ia_mode = sd->s_mode; 57 iattrs->ia_uid = GLOBAL_ROOT_UID; 58 iattrs->ia_gid = GLOBAL_ROOT_GID; 59 iattrs->ia_atime = iattrs->ia_mtime = iattrs->ia_ctime = CURRENT_TIME; 60 61 return attrs; 62} 63 64static int __kernfs_setattr(struct sysfs_dirent *sd, const struct iattr *iattr) 65{ 66 struct sysfs_inode_attrs *sd_attrs; 67 struct iattr *iattrs; 68 unsigned int ia_valid = iattr->ia_valid; 69 70 sd_attrs = sd->s_iattr; 71 72 if (!sd_attrs) { 73 /* setting attributes for the first time, allocate now */ 74 sd_attrs = sysfs_init_inode_attrs(sd); 75 if (!sd_attrs) 76 return -ENOMEM; 77 sd->s_iattr = sd_attrs; 78 } 79 /* attributes were changed at least once in past */ 80 iattrs = &sd_attrs->ia_iattr; 81 82 if (ia_valid & ATTR_UID) 83 iattrs->ia_uid = iattr->ia_uid; 84 if (ia_valid & ATTR_GID) 85 iattrs->ia_gid = iattr->ia_gid; 86 if (ia_valid & ATTR_ATIME) 87 iattrs->ia_atime = iattr->ia_atime; 88 if (ia_valid & ATTR_MTIME) 89 iattrs->ia_mtime = iattr->ia_mtime; 90 if (ia_valid & ATTR_CTIME) 91 iattrs->ia_ctime = iattr->ia_ctime; 92 if (ia_valid & ATTR_MODE) { 93 umode_t mode = iattr->ia_mode; 94 iattrs->ia_mode = sd->s_mode = mode; 95 } 96 return 0; 97} 98 99/** 100 * kernfs_setattr - set iattr on a node 101 * @sd: target node 102 * @iattr: iattr to set 103 * 104 * Returns 0 on success, -errno on failure. 105 */ 106int kernfs_setattr(struct sysfs_dirent *sd, const struct iattr *iattr) 107{ 108 int ret; 109 110 mutex_lock(&sysfs_mutex); 111 ret = __kernfs_setattr(sd, iattr); 112 mutex_unlock(&sysfs_mutex); 113 return ret; 114} 115 116int sysfs_setattr(struct dentry *dentry, struct iattr *iattr) 117{ 118 struct inode *inode = dentry->d_inode; 119 struct sysfs_dirent *sd = dentry->d_fsdata; 120 int error; 121 122 if (!sd) 123 return -EINVAL; 124 125 mutex_lock(&sysfs_mutex); 126 error = inode_change_ok(inode, iattr); 127 if (error) 128 goto out; 129 130 error = __kernfs_setattr(sd, iattr); 131 if (error) 132 goto out; 133 134 /* this ignores size changes */ 135 setattr_copy(inode, iattr); 136 137out: 138 mutex_unlock(&sysfs_mutex); 139 return error; 140} 141 142static int sysfs_sd_setsecdata(struct sysfs_dirent *sd, void **secdata, 143 u32 *secdata_len) 144{ 145 struct sysfs_inode_attrs *iattrs; 146 void *old_secdata; 147 size_t old_secdata_len; 148 149 if (!sd->s_iattr) { 150 sd->s_iattr = sysfs_init_inode_attrs(sd); 151 if (!sd->s_iattr) 152 return -ENOMEM; 153 } 154 155 iattrs = sd->s_iattr; 156 old_secdata = iattrs->ia_secdata; 157 old_secdata_len = iattrs->ia_secdata_len; 158 159 iattrs->ia_secdata = *secdata; 160 iattrs->ia_secdata_len = *secdata_len; 161 162 *secdata = old_secdata; 163 *secdata_len = old_secdata_len; 164 return 0; 165} 166 167int sysfs_setxattr(struct dentry *dentry, const char *name, const void *value, 168 size_t size, int flags) 169{ 170 struct sysfs_dirent *sd = dentry->d_fsdata; 171 void *secdata; 172 int error; 173 u32 secdata_len = 0; 174 175 if (!sd) 176 return -EINVAL; 177 178 if (!strncmp(name, XATTR_SECURITY_PREFIX, XATTR_SECURITY_PREFIX_LEN)) { 179 const char *suffix = name + XATTR_SECURITY_PREFIX_LEN; 180 error = security_inode_setsecurity(dentry->d_inode, suffix, 181 value, size, flags); 182 if (error) 183 goto out; 184 error = security_inode_getsecctx(dentry->d_inode, 185 &secdata, &secdata_len); 186 if (error) 187 goto out; 188 189 mutex_lock(&sysfs_mutex); 190 error = sysfs_sd_setsecdata(sd, &secdata, &secdata_len); 191 mutex_unlock(&sysfs_mutex); 192 193 if (secdata) 194 security_release_secctx(secdata, secdata_len); 195 } else 196 return -EINVAL; 197out: 198 return error; 199} 200 201static inline void set_default_inode_attr(struct inode *inode, umode_t mode) 202{ 203 inode->i_mode = mode; 204 inode->i_atime = inode->i_mtime = inode->i_ctime = CURRENT_TIME; 205} 206 207static inline void set_inode_attr(struct inode *inode, struct iattr *iattr) 208{ 209 inode->i_uid = iattr->ia_uid; 210 inode->i_gid = iattr->ia_gid; 211 inode->i_atime = iattr->ia_atime; 212 inode->i_mtime = iattr->ia_mtime; 213 inode->i_ctime = iattr->ia_ctime; 214} 215 216static void sysfs_refresh_inode(struct sysfs_dirent *sd, struct inode *inode) 217{ 218 struct sysfs_inode_attrs *iattrs = sd->s_iattr; 219 220 inode->i_mode = sd->s_mode; 221 if (iattrs) { 222 /* sysfs_dirent has non-default attributes 223 * get them from persistent copy in sysfs_dirent 224 */ 225 set_inode_attr(inode, &iattrs->ia_iattr); 226 security_inode_notifysecctx(inode, 227 iattrs->ia_secdata, 228 iattrs->ia_secdata_len); 229 } 230 231 if (sysfs_type(sd) == SYSFS_DIR) 232 set_nlink(inode, sd->s_dir.subdirs + 2); 233} 234 235int sysfs_getattr(struct vfsmount *mnt, struct dentry *dentry, 236 struct kstat *stat) 237{ 238 struct sysfs_dirent *sd = dentry->d_fsdata; 239 struct inode *inode = dentry->d_inode; 240 241 mutex_lock(&sysfs_mutex); 242 sysfs_refresh_inode(sd, inode); 243 mutex_unlock(&sysfs_mutex); 244 245 generic_fillattr(inode, stat); 246 return 0; 247} 248 249static void sysfs_init_inode(struct sysfs_dirent *sd, struct inode *inode) 250{ 251 kernfs_get(sd); 252 inode->i_private = sd; 253 inode->i_mapping->a_ops = &sysfs_aops; 254 inode->i_mapping->backing_dev_info = &sysfs_backing_dev_info; 255 inode->i_op = &sysfs_inode_operations; 256 257 set_default_inode_attr(inode, sd->s_mode); 258 sysfs_refresh_inode(sd, inode); 259 260 /* initialize inode according to type */ 261 switch (sysfs_type(sd)) { 262 case SYSFS_DIR: 263 inode->i_op = &sysfs_dir_inode_operations; 264 inode->i_fop = &sysfs_dir_operations; 265 break; 266 case SYSFS_KOBJ_ATTR: 267 inode->i_size = sd->s_attr.size; 268 inode->i_fop = &kernfs_file_operations; 269 break; 270 case SYSFS_KOBJ_LINK: 271 inode->i_op = &sysfs_symlink_inode_operations; 272 break; 273 default: 274 BUG(); 275 } 276 277 unlock_new_inode(inode); 278} 279 280/** 281 * sysfs_get_inode - get inode for sysfs_dirent 282 * @sb: super block 283 * @sd: sysfs_dirent to allocate inode for 284 * 285 * Get inode for @sd. If such inode doesn't exist, a new inode 286 * is allocated and basics are initialized. New inode is 287 * returned locked. 288 * 289 * LOCKING: 290 * Kernel thread context (may sleep). 291 * 292 * RETURNS: 293 * Pointer to allocated inode on success, NULL on failure. 294 */ 295struct inode *sysfs_get_inode(struct super_block *sb, struct sysfs_dirent *sd) 296{ 297 struct inode *inode; 298 299 inode = iget_locked(sb, sd->s_ino); 300 if (inode && (inode->i_state & I_NEW)) 301 sysfs_init_inode(sd, inode); 302 303 return inode; 304} 305 306/* 307 * The sysfs_dirent serves as both an inode and a directory entry for sysfs. 308 * To prevent the sysfs inode numbers from being freed prematurely we take a 309 * reference to sysfs_dirent from the sysfs inode. A 310 * super_operations.evict_inode() implementation is needed to drop that 311 * reference upon inode destruction. 312 */ 313void sysfs_evict_inode(struct inode *inode) 314{ 315 struct sysfs_dirent *sd = inode->i_private; 316 317 truncate_inode_pages(&inode->i_data, 0); 318 clear_inode(inode); 319 kernfs_put(sd); 320} 321 322int sysfs_permission(struct inode *inode, int mask) 323{ 324 struct sysfs_dirent *sd; 325 326 if (mask & MAY_NOT_BLOCK) 327 return -ECHILD; 328 329 sd = inode->i_private; 330 331 mutex_lock(&sysfs_mutex); 332 sysfs_refresh_inode(sd, inode); 333 mutex_unlock(&sysfs_mutex); 334 335 return generic_permission(inode, mask); 336} |
|