Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

Merge tag 'vfs-6.10.mount' of git://git.kernel.org/pub/scm/linux/kernel/git/vfs/vfs

Pull vfs mount API conversions from Christian Brauner:
"This converts qnx6, minix, debugfs, tracefs, freevxfs, and openpromfs
to the new mount api, further reducing the number of filesystems
relying on the legacy mount api"

* tag 'vfs-6.10.mount' of git://git.kernel.org/pub/scm/linux/kernel/git/vfs/vfs:
minix: convert minix to use the new mount api
vfs: Convert tracefs to use the new mount API
vfs: Convert debugfs to use the new mount API
openpromfs: finish conversion to the new mount API
freevxfs: Convert freevxfs to the new mount API.
qnx6: convert qnx6 to use the new mount api

+325 -307
+91 -103
fs/debugfs/inode.c
··· 14 14 15 15 #include <linux/module.h> 16 16 #include <linux/fs.h> 17 - #include <linux/mount.h> 17 + #include <linux/fs_context.h> 18 + #include <linux/fs_parser.h> 18 19 #include <linux/pagemap.h> 19 20 #include <linux/init.h> 20 21 #include <linux/kobject.h> ··· 24 23 #include <linux/fsnotify.h> 25 24 #include <linux/string.h> 26 25 #include <linux/seq_file.h> 27 - #include <linux/parser.h> 28 26 #include <linux/magic.h> 29 27 #include <linux/slab.h> 30 28 #include <linux/security.h> ··· 77 77 return inode; 78 78 } 79 79 80 - struct debugfs_mount_opts { 80 + struct debugfs_fs_info { 81 81 kuid_t uid; 82 82 kgid_t gid; 83 83 umode_t mode; ··· 89 89 Opt_uid, 90 90 Opt_gid, 91 91 Opt_mode, 92 - Opt_err 93 92 }; 94 93 95 - static const match_table_t tokens = { 96 - {Opt_uid, "uid=%u"}, 97 - {Opt_gid, "gid=%u"}, 98 - {Opt_mode, "mode=%o"}, 99 - {Opt_err, NULL} 94 + static const struct fs_parameter_spec debugfs_param_specs[] = { 95 + fsparam_u32 ("gid", Opt_gid), 96 + fsparam_u32oct ("mode", Opt_mode), 97 + fsparam_u32 ("uid", Opt_uid), 98 + {} 100 99 }; 101 100 102 - struct debugfs_fs_info { 103 - struct debugfs_mount_opts mount_opts; 104 - }; 105 - 106 - static int debugfs_parse_options(char *data, struct debugfs_mount_opts *opts) 101 + static int debugfs_parse_param(struct fs_context *fc, struct fs_parameter *param) 107 102 { 108 - substring_t args[MAX_OPT_ARGS]; 109 - int option; 110 - int token; 103 + struct debugfs_fs_info *opts = fc->s_fs_info; 104 + struct fs_parse_result result; 111 105 kuid_t uid; 112 106 kgid_t gid; 113 - char *p; 107 + int opt; 114 108 115 - opts->opts = 0; 116 - opts->mode = DEBUGFS_DEFAULT_MODE; 109 + opt = fs_parse(fc, debugfs_param_specs, param, &result); 110 + if (opt < 0) 111 + return opt; 117 112 118 - while ((p = strsep(&data, ",")) != NULL) { 119 - if (!*p) 120 - continue; 121 - 122 - token = match_token(p, tokens, args); 123 - switch (token) { 124 - case Opt_uid: 125 - if (match_int(&args[0], &option)) 126 - return -EINVAL; 127 - uid = make_kuid(current_user_ns(), option); 128 - if (!uid_valid(uid)) 129 - return -EINVAL; 130 - opts->uid = uid; 131 - break; 132 - case Opt_gid: 133 - if (match_int(&args[0], &option)) 134 - return -EINVAL; 135 - gid = make_kgid(current_user_ns(), option); 136 - if (!gid_valid(gid)) 137 - return -EINVAL; 138 - opts->gid = gid; 139 - break; 140 - case Opt_mode: 141 - if (match_octal(&args[0], &option)) 142 - return -EINVAL; 143 - opts->mode = option & S_IALLUGO; 144 - break; 145 - /* 146 - * We might like to report bad mount options here; 147 - * but traditionally debugfs has ignored all mount options 148 - */ 149 - } 150 - 151 - opts->opts |= BIT(token); 113 + switch (opt) { 114 + case Opt_uid: 115 + uid = make_kuid(current_user_ns(), result.uint_32); 116 + if (!uid_valid(uid)) 117 + return invalf(fc, "Unknown uid"); 118 + opts->uid = uid; 119 + break; 120 + case Opt_gid: 121 + gid = make_kgid(current_user_ns(), result.uint_32); 122 + if (!gid_valid(gid)) 123 + return invalf(fc, "Unknown gid"); 124 + opts->gid = gid; 125 + break; 126 + case Opt_mode: 127 + opts->mode = result.uint_32 & S_IALLUGO; 128 + break; 129 + /* 130 + * We might like to report bad mount options here; 131 + * but traditionally debugfs has ignored all mount options 132 + */ 152 133 } 134 + 135 + opts->opts |= BIT(opt); 153 136 154 137 return 0; 155 138 } ··· 141 158 { 142 159 struct debugfs_fs_info *fsi = sb->s_fs_info; 143 160 struct inode *inode = d_inode(sb->s_root); 144 - struct debugfs_mount_opts *opts = &fsi->mount_opts; 145 161 146 162 /* 147 163 * On remount, only reset mode/uid/gid if they were provided as mount 148 164 * options. 149 165 */ 150 166 151 - if (!remount || opts->opts & BIT(Opt_mode)) { 167 + if (!remount || fsi->opts & BIT(Opt_mode)) { 152 168 inode->i_mode &= ~S_IALLUGO; 153 - inode->i_mode |= opts->mode; 169 + inode->i_mode |= fsi->mode; 154 170 } 155 171 156 - if (!remount || opts->opts & BIT(Opt_uid)) 157 - inode->i_uid = opts->uid; 172 + if (!remount || fsi->opts & BIT(Opt_uid)) 173 + inode->i_uid = fsi->uid; 158 174 159 - if (!remount || opts->opts & BIT(Opt_gid)) 160 - inode->i_gid = opts->gid; 175 + if (!remount || fsi->opts & BIT(Opt_gid)) 176 + inode->i_gid = fsi->gid; 161 177 } 162 178 163 179 static void debugfs_apply_options(struct super_block *sb) ··· 169 187 _debugfs_apply_options(sb, true); 170 188 } 171 189 172 - static int debugfs_remount(struct super_block *sb, int *flags, char *data) 190 + static int debugfs_reconfigure(struct fs_context *fc) 173 191 { 174 - int err; 175 - struct debugfs_fs_info *fsi = sb->s_fs_info; 192 + struct super_block *sb = fc->root->d_sb; 193 + struct debugfs_fs_info *sb_opts = sb->s_fs_info; 194 + struct debugfs_fs_info *new_opts = fc->s_fs_info; 176 195 177 196 sync_filesystem(sb); 178 - err = debugfs_parse_options(data, &fsi->mount_opts); 179 - if (err) 180 - goto fail; 181 197 198 + /* structure copy of new mount options to sb */ 199 + *sb_opts = *new_opts; 182 200 debugfs_apply_options_remount(sb); 183 201 184 - fail: 185 - return err; 202 + return 0; 186 203 } 187 204 188 205 static int debugfs_show_options(struct seq_file *m, struct dentry *root) 189 206 { 190 207 struct debugfs_fs_info *fsi = root->d_sb->s_fs_info; 191 - struct debugfs_mount_opts *opts = &fsi->mount_opts; 192 208 193 - if (!uid_eq(opts->uid, GLOBAL_ROOT_UID)) 209 + if (!uid_eq(fsi->uid, GLOBAL_ROOT_UID)) 194 210 seq_printf(m, ",uid=%u", 195 - from_kuid_munged(&init_user_ns, opts->uid)); 196 - if (!gid_eq(opts->gid, GLOBAL_ROOT_GID)) 211 + from_kuid_munged(&init_user_ns, fsi->uid)); 212 + if (!gid_eq(fsi->gid, GLOBAL_ROOT_GID)) 197 213 seq_printf(m, ",gid=%u", 198 - from_kgid_munged(&init_user_ns, opts->gid)); 199 - if (opts->mode != DEBUGFS_DEFAULT_MODE) 200 - seq_printf(m, ",mode=%o", opts->mode); 214 + from_kgid_munged(&init_user_ns, fsi->gid)); 215 + if (fsi->mode != DEBUGFS_DEFAULT_MODE) 216 + seq_printf(m, ",mode=%o", fsi->mode); 201 217 202 218 return 0; 203 219 } ··· 209 229 210 230 static const struct super_operations debugfs_super_operations = { 211 231 .statfs = simple_statfs, 212 - .remount_fs = debugfs_remount, 213 232 .show_options = debugfs_show_options, 214 233 .free_inode = debugfs_free_inode, 215 234 }; ··· 242 263 .d_automount = debugfs_automount, 243 264 }; 244 265 245 - static int debug_fill_super(struct super_block *sb, void *data, int silent) 266 + static int debugfs_fill_super(struct super_block *sb, struct fs_context *fc) 246 267 { 247 268 static const struct tree_descr debug_files[] = {{""}}; 248 - struct debugfs_fs_info *fsi; 249 269 int err; 250 270 251 - fsi = kzalloc(sizeof(struct debugfs_fs_info), GFP_KERNEL); 252 - sb->s_fs_info = fsi; 253 - if (!fsi) { 254 - err = -ENOMEM; 255 - goto fail; 256 - } 257 - 258 - err = debugfs_parse_options(data, &fsi->mount_opts); 271 + err = simple_fill_super(sb, DEBUGFS_MAGIC, debug_files); 259 272 if (err) 260 - goto fail; 261 - 262 - err = simple_fill_super(sb, DEBUGFS_MAGIC, debug_files); 263 - if (err) 264 - goto fail; 273 + return err; 265 274 266 275 sb->s_op = &debugfs_super_operations; 267 276 sb->s_d_op = &debugfs_dops; ··· 257 290 debugfs_apply_options(sb); 258 291 259 292 return 0; 260 - 261 - fail: 262 - kfree(fsi); 263 - sb->s_fs_info = NULL; 264 - return err; 265 293 } 266 294 267 - static struct dentry *debug_mount(struct file_system_type *fs_type, 268 - int flags, const char *dev_name, 269 - void *data) 295 + static int debugfs_get_tree(struct fs_context *fc) 270 296 { 271 297 if (!(debugfs_allow & DEBUGFS_ALLOW_API)) 272 - return ERR_PTR(-EPERM); 298 + return -EPERM; 273 299 274 - return mount_single(fs_type, flags, data, debug_fill_super); 300 + return get_tree_single(fc, debugfs_fill_super); 301 + } 302 + 303 + static void debugfs_free_fc(struct fs_context *fc) 304 + { 305 + kfree(fc->s_fs_info); 306 + } 307 + 308 + static const struct fs_context_operations debugfs_context_ops = { 309 + .free = debugfs_free_fc, 310 + .parse_param = debugfs_parse_param, 311 + .get_tree = debugfs_get_tree, 312 + .reconfigure = debugfs_reconfigure, 313 + }; 314 + 315 + static int debugfs_init_fs_context(struct fs_context *fc) 316 + { 317 + struct debugfs_fs_info *fsi; 318 + 319 + fsi = kzalloc(sizeof(struct debugfs_fs_info), GFP_KERNEL); 320 + if (!fsi) 321 + return -ENOMEM; 322 + 323 + fsi->mode = DEBUGFS_DEFAULT_MODE; 324 + 325 + fc->s_fs_info = fsi; 326 + fc->ops = &debugfs_context_ops; 327 + return 0; 275 328 } 276 329 277 330 static struct file_system_type debug_fs_type = { 278 331 .owner = THIS_MODULE, 279 332 .name = "debugfs", 280 - .mount = debug_mount, 333 + .init_fs_context = debugfs_init_fs_context, 334 + .parameters = debugfs_param_specs, 281 335 .kill_sb = kill_litter_super, 282 336 }; 283 337 MODULE_ALIAS_FS("debugfs");
+40 -29
fs/freevxfs/vxfs_super.c
··· 17 17 #include <linux/slab.h> 18 18 #include <linux/stat.h> 19 19 #include <linux/vfs.h> 20 - #include <linux/mount.h> 20 + #include <linux/fs_context.h> 21 21 22 22 #include "vxfs.h" 23 23 #include "vxfs_extern.h" ··· 91 91 return 0; 92 92 } 93 93 94 - static int vxfs_remount(struct super_block *sb, int *flags, char *data) 94 + static int vxfs_reconfigure(struct fs_context *fc) 95 95 { 96 - sync_filesystem(sb); 97 - *flags |= SB_RDONLY; 96 + sync_filesystem(fc->root->d_sb); 97 + fc->sb_flags |= SB_RDONLY; 98 98 return 0; 99 99 } 100 100 ··· 120 120 .evict_inode = vxfs_evict_inode, 121 121 .put_super = vxfs_put_super, 122 122 .statfs = vxfs_statfs, 123 - .remount_fs = vxfs_remount, 124 123 }; 125 124 126 - static int vxfs_try_sb_magic(struct super_block *sbp, int silent, 125 + static int vxfs_try_sb_magic(struct super_block *sbp, struct fs_context *fc, 127 126 unsigned blk, __fs32 magic) 128 127 { 129 128 struct buffer_head *bp; 130 129 struct vxfs_sb *rsbp; 131 130 struct vxfs_sb_info *infp = VXFS_SBI(sbp); 131 + int silent = fc->sb_flags & SB_SILENT; 132 132 int rc = -ENOMEM; 133 133 134 134 bp = sb_bread(sbp, blk); 135 135 do { 136 136 if (!bp || !buffer_mapped(bp)) { 137 137 if (!silent) { 138 - printk(KERN_WARNING 139 - "vxfs: unable to read disk superblock at %u\n", 140 - blk); 138 + warnf(fc, 139 + "vxfs: unable to read disk superblock at %u", 140 + blk); 141 141 } 142 142 break; 143 143 } ··· 146 146 rsbp = (struct vxfs_sb *)bp->b_data; 147 147 if (rsbp->vs_magic != magic) { 148 148 if (!silent) 149 - printk(KERN_NOTICE 150 - "vxfs: WRONG superblock magic %08x at %u\n", 151 - rsbp->vs_magic, blk); 149 + infof(fc, 150 + "vxfs: WRONG superblock magic %08x at %u", 151 + rsbp->vs_magic, blk); 152 152 break; 153 153 } 154 154 ··· 169 169 /** 170 170 * vxfs_fill_super - read superblock into memory and initialize filesystem 171 171 * @sbp: VFS superblock (to fill) 172 - * @dp: fs private mount data 173 - * @silent: do not complain loudly when sth is wrong 172 + * @fc: filesytem context 174 173 * 175 174 * Description: 176 175 * We are called on the first mount of a filesystem to read the ··· 181 182 * Locking: 182 183 * We are under @sbp->s_lock. 183 184 */ 184 - static int vxfs_fill_super(struct super_block *sbp, void *dp, int silent) 185 + static int vxfs_fill_super(struct super_block *sbp, struct fs_context *fc) 185 186 { 186 187 struct vxfs_sb_info *infp; 187 188 struct vxfs_sb *rsbp; 188 189 u_long bsize; 189 190 struct inode *root; 190 191 int ret = -EINVAL; 192 + int silent = fc->sb_flags & SB_SILENT; 191 193 u32 j; 192 194 193 195 sbp->s_flags |= SB_RDONLY; 194 196 195 197 infp = kzalloc(sizeof(*infp), GFP_KERNEL); 196 198 if (!infp) { 197 - printk(KERN_WARNING "vxfs: unable to allocate incore superblock\n"); 199 + warnf(fc, "vxfs: unable to allocate incore superblock"); 198 200 return -ENOMEM; 199 201 } 200 202 201 203 bsize = sb_min_blocksize(sbp, BLOCK_SIZE); 202 204 if (!bsize) { 203 - printk(KERN_WARNING "vxfs: unable to set blocksize\n"); 205 + warnf(fc, "vxfs: unable to set blocksize"); 204 206 goto out; 205 207 } 206 208 ··· 210 210 sbp->s_time_min = 0; 211 211 sbp->s_time_max = U32_MAX; 212 212 213 - if (!vxfs_try_sb_magic(sbp, silent, 1, 213 + if (!vxfs_try_sb_magic(sbp, fc, 1, 214 214 (__force __fs32)cpu_to_le32(VXFS_SUPER_MAGIC))) { 215 215 /* Unixware, x86 */ 216 216 infp->byte_order = VXFS_BO_LE; 217 - } else if (!vxfs_try_sb_magic(sbp, silent, 8, 217 + } else if (!vxfs_try_sb_magic(sbp, fc, 8, 218 218 (__force __fs32)cpu_to_be32(VXFS_SUPER_MAGIC))) { 219 219 /* HP-UX, parisc */ 220 220 infp->byte_order = VXFS_BO_BE; 221 221 } else { 222 222 if (!silent) 223 - printk(KERN_NOTICE "vxfs: can't find superblock.\n"); 223 + infof(fc, "vxfs: can't find superblock."); 224 224 goto out; 225 225 } 226 226 227 227 rsbp = infp->vsi_raw; 228 228 j = fs32_to_cpu(infp, rsbp->vs_version); 229 229 if ((j < 2 || j > 4) && !silent) { 230 - printk(KERN_NOTICE "vxfs: unsupported VxFS version (%d)\n", j); 230 + infof(fc, "vxfs: unsupported VxFS version (%d)", j); 231 231 goto out; 232 232 } 233 233 ··· 244 244 245 245 j = fs32_to_cpu(infp, rsbp->vs_bsize); 246 246 if (!sb_set_blocksize(sbp, j)) { 247 - printk(KERN_WARNING "vxfs: unable to set final block size\n"); 247 + warnf(fc, "vxfs: unable to set final block size"); 248 248 goto out; 249 249 } 250 250 251 251 if (vxfs_read_olt(sbp, bsize)) { 252 - printk(KERN_WARNING "vxfs: unable to read olt\n"); 252 + warnf(fc, "vxfs: unable to read olt"); 253 253 goto out; 254 254 } 255 255 256 256 if (vxfs_read_fshead(sbp)) { 257 - printk(KERN_WARNING "vxfs: unable to read fshead\n"); 257 + warnf(fc, "vxfs: unable to read fshead"); 258 258 goto out; 259 259 } 260 260 ··· 265 265 } 266 266 sbp->s_root = d_make_root(root); 267 267 if (!sbp->s_root) { 268 - printk(KERN_WARNING "vxfs: unable to get root dentry.\n"); 268 + warnf(fc, "vxfs: unable to get root dentry."); 269 269 goto out_free_ilist; 270 270 } 271 271 ··· 284 284 /* 285 285 * The usual module blurb. 286 286 */ 287 - static struct dentry *vxfs_mount(struct file_system_type *fs_type, 288 - int flags, const char *dev_name, void *data) 287 + static int vxfs_get_tree(struct fs_context *fc) 289 288 { 290 - return mount_bdev(fs_type, flags, dev_name, data, vxfs_fill_super); 289 + return get_tree_bdev(fc, vxfs_fill_super); 290 + } 291 + 292 + static const struct fs_context_operations vxfs_context_ops = { 293 + .get_tree = vxfs_get_tree, 294 + .reconfigure = vxfs_reconfigure, 295 + }; 296 + 297 + static int vxfs_init_fs_context(struct fs_context *fc) 298 + { 299 + fc->ops = &vxfs_context_ops; 300 + 301 + return 0; 291 302 } 292 303 293 304 static struct file_system_type vxfs_fs_type = { 294 305 .owner = THIS_MODULE, 295 306 .name = "vxfs", 296 - .mount = vxfs_mount, 297 307 .kill_sb = kill_block_super, 298 308 .fs_flags = FS_REQUIRES_DEV, 309 + .init_fs_context = vxfs_init_fs_context, 299 310 }; 300 311 MODULE_ALIAS_FS("vxfs"); /* makes mount -t vxfs autoload the module */ 301 312 MODULE_ALIAS("vxfs");
+30 -18
fs/minix/inode.c
··· 20 20 #include <linux/mpage.h> 21 21 #include <linux/vfs.h> 22 22 #include <linux/writeback.h> 23 + #include <linux/fs_context.h> 23 24 24 25 static int minix_write_inode(struct inode *inode, 25 26 struct writeback_control *wbc); 26 27 static int minix_statfs(struct dentry *dentry, struct kstatfs *buf); 27 - static int minix_remount (struct super_block * sb, int * flags, char * data); 28 28 29 29 static void minix_evict_inode(struct inode *inode) 30 30 { ··· 111 111 .evict_inode = minix_evict_inode, 112 112 .put_super = minix_put_super, 113 113 .statfs = minix_statfs, 114 - .remount_fs = minix_remount, 115 114 }; 116 115 117 - static int minix_remount (struct super_block * sb, int * flags, char * data) 116 + static int minix_reconfigure(struct fs_context *fc) 118 117 { 119 - struct minix_sb_info * sbi = minix_sb(sb); 120 118 struct minix_super_block * ms; 119 + struct super_block *sb = fc->root->d_sb; 120 + struct minix_sb_info * sbi = sb->s_fs_info; 121 121 122 122 sync_filesystem(sb); 123 123 ms = sbi->s_ms; 124 - if ((bool)(*flags & SB_RDONLY) == sb_rdonly(sb)) 124 + if ((bool)(fc->sb_flags & SB_RDONLY) == sb_rdonly(sb)) 125 125 return 0; 126 - if (*flags & SB_RDONLY) { 126 + if (fc->sb_flags & SB_RDONLY) { 127 127 if (ms->s_state & MINIX_VALID_FS || 128 128 !(sbi->s_mount_state & MINIX_VALID_FS)) 129 129 return 0; ··· 170 170 return true; 171 171 } 172 172 173 - static int minix_fill_super(struct super_block *s, void *data, int silent) 173 + static int minix_fill_super(struct super_block *s, struct fs_context *fc) 174 174 { 175 175 struct buffer_head *bh; 176 176 struct buffer_head **map; ··· 180 180 struct inode *root_inode; 181 181 struct minix_sb_info *sbi; 182 182 int ret = -EINVAL; 183 + int silent = fc->sb_flags & SB_SILENT; 183 184 184 185 sbi = kzalloc(sizeof(struct minix_sb_info), GFP_KERNEL); 185 186 if (!sbi) ··· 370 369 s->s_fs_info = NULL; 371 370 kfree(sbi); 372 371 return ret; 372 + } 373 + 374 + static int minix_get_tree(struct fs_context *fc) 375 + { 376 + return get_tree_bdev(fc, minix_fill_super); 377 + } 378 + 379 + static const struct fs_context_operations minix_context_ops = { 380 + .get_tree = minix_get_tree, 381 + .reconfigure = minix_reconfigure, 382 + }; 383 + 384 + static int minix_init_fs_context(struct fs_context *fc) 385 + { 386 + fc->ops = &minix_context_ops; 387 + 388 + return 0; 373 389 } 374 390 375 391 static int minix_statfs(struct dentry *dentry, struct kstatfs *buf) ··· 698 680 V2_minix_truncate(inode); 699 681 } 700 682 701 - static struct dentry *minix_mount(struct file_system_type *fs_type, 702 - int flags, const char *dev_name, void *data) 703 - { 704 - return mount_bdev(fs_type, flags, dev_name, data, minix_fill_super); 705 - } 706 - 707 683 static struct file_system_type minix_fs_type = { 708 - .owner = THIS_MODULE, 709 - .name = "minix", 710 - .mount = minix_mount, 711 - .kill_sb = kill_block_super, 712 - .fs_flags = FS_REQUIRES_DEV, 684 + .owner = THIS_MODULE, 685 + .name = "minix", 686 + .kill_sb = kill_block_super, 687 + .fs_flags = FS_REQUIRES_DEV, 688 + .init_fs_context = minix_init_fs_context, 713 689 }; 714 690 MODULE_ALIAS_FS("minix"); 715 691
+4 -4
fs/openpromfs/inode.c
··· 355 355 return inode; 356 356 } 357 357 358 - static int openprom_remount(struct super_block *sb, int *flags, char *data) 358 + static int openpromfs_reconfigure(struct fs_context *fc) 359 359 { 360 - sync_filesystem(sb); 361 - *flags |= SB_NOATIME; 360 + sync_filesystem(fc->root->d_sb); 361 + fc->sb_flags |= SB_NOATIME; 362 362 return 0; 363 363 } 364 364 ··· 366 366 .alloc_inode = openprom_alloc_inode, 367 367 .free_inode = openprom_free_inode, 368 368 .statfs = simple_statfs, 369 - .remount_fs = openprom_remount, 370 369 }; 371 370 372 371 static int openprom_fill_super(struct super_block *s, struct fs_context *fc) ··· 414 415 415 416 static const struct fs_context_operations openpromfs_context_ops = { 416 417 .get_tree = openpromfs_get_tree, 418 + .reconfigure = openpromfs_reconfigure, 417 419 }; 418 420 419 421 static int openpromfs_init_fs_context(struct fs_context *fc)
+67 -46
fs/qnx6/inode.c
··· 19 19 #include <linux/buffer_head.h> 20 20 #include <linux/writeback.h> 21 21 #include <linux/statfs.h> 22 - #include <linux/parser.h> 23 22 #include <linux/seq_file.h> 24 - #include <linux/mount.h> 25 23 #include <linux/crc32.h> 26 24 #include <linux/mpage.h> 25 + #include <linux/fs_parser.h> 26 + #include <linux/fs_context.h> 27 27 #include "qnx6.h" 28 28 29 29 static const struct super_operations qnx6_sops; ··· 31 31 static void qnx6_put_super(struct super_block *sb); 32 32 static struct inode *qnx6_alloc_inode(struct super_block *sb); 33 33 static void qnx6_free_inode(struct inode *inode); 34 - static int qnx6_remount(struct super_block *sb, int *flags, char *data); 34 + static int qnx6_reconfigure(struct fs_context *fc); 35 35 static int qnx6_statfs(struct dentry *dentry, struct kstatfs *buf); 36 36 static int qnx6_show_options(struct seq_file *seq, struct dentry *root); 37 37 ··· 40 40 .free_inode = qnx6_free_inode, 41 41 .put_super = qnx6_put_super, 42 42 .statfs = qnx6_statfs, 43 - .remount_fs = qnx6_remount, 44 43 .show_options = qnx6_show_options, 45 44 }; 46 45 ··· 53 54 return 0; 54 55 } 55 56 56 - static int qnx6_remount(struct super_block *sb, int *flags, char *data) 57 + static int qnx6_reconfigure(struct fs_context *fc) 57 58 { 59 + struct super_block *sb = fc->root->d_sb; 60 + 58 61 sync_filesystem(sb); 59 - *flags |= SB_RDONLY; 62 + fc->sb_flags |= SB_RDONLY; 60 63 return 0; 61 64 } 62 65 ··· 219 218 #endif 220 219 221 220 enum { 222 - Opt_mmifs, 223 - Opt_err 221 + Opt_mmifs 224 222 }; 225 223 226 - static const match_table_t tokens = { 227 - {Opt_mmifs, "mmi_fs"}, 228 - {Opt_err, NULL} 224 + struct qnx6_context { 225 + unsigned long s_mount_opts; 229 226 }; 230 227 231 - static int qnx6_parse_options(char *options, struct super_block *sb) 228 + static const struct fs_parameter_spec qnx6_param_spec[] = { 229 + fsparam_flag ("mmi_fs", Opt_mmifs), 230 + {} 231 + }; 232 + 233 + static int qnx6_parse_param(struct fs_context *fc, struct fs_parameter *param) 232 234 { 233 - char *p; 234 - struct qnx6_sb_info *sbi = QNX6_SB(sb); 235 - substring_t args[MAX_OPT_ARGS]; 235 + struct qnx6_context *ctx = fc->fs_private; 236 + struct fs_parse_result result; 237 + int opt; 236 238 237 - if (!options) 238 - return 1; 239 + opt = fs_parse(fc, qnx6_param_spec, param, &result); 240 + if (opt < 0) 241 + return opt; 239 242 240 - while ((p = strsep(&options, ",")) != NULL) { 241 - int token; 242 - if (!*p) 243 - continue; 244 - 245 - token = match_token(p, tokens, args); 246 - switch (token) { 247 - case Opt_mmifs: 248 - set_opt(sbi->s_mount_opt, MMI_FS); 249 - break; 250 - default: 251 - return 0; 252 - } 243 + switch (opt) { 244 + case Opt_mmifs: 245 + ctx->s_mount_opts |= QNX6_MOUNT_MMI_FS; 246 + break; 247 + default: 248 + return -EINVAL; 253 249 } 254 - return 1; 250 + return 0; 255 251 } 256 252 257 253 static struct buffer_head *qnx6_check_first_superblock(struct super_block *s, ··· 291 293 static struct inode *qnx6_private_inode(struct super_block *s, 292 294 struct qnx6_root_node *p); 293 295 294 - static int qnx6_fill_super(struct super_block *s, void *data, int silent) 296 + static int qnx6_fill_super(struct super_block *s, struct fs_context *fc) 295 297 { 296 298 struct buffer_head *bh1 = NULL, *bh2 = NULL; 297 299 struct qnx6_super_block *sb1 = NULL, *sb2 = NULL; 298 300 struct qnx6_sb_info *sbi; 301 + struct qnx6_context *ctx = fc->fs_private; 299 302 struct inode *root; 300 303 const char *errmsg; 301 304 struct qnx6_sb_info *qs; 302 305 int ret = -EINVAL; 303 306 u64 offset; 304 307 int bootblock_offset = QNX6_BOOTBLOCK_SIZE; 308 + int silent = fc->sb_flags & SB_SILENT; 305 309 306 310 qs = kzalloc(sizeof(struct qnx6_sb_info), GFP_KERNEL); 307 311 if (!qs) 308 312 return -ENOMEM; 309 313 s->s_fs_info = qs; 314 + qs->s_mount_opt = ctx->s_mount_opts; 310 315 311 316 /* Superblock always is 512 Byte long */ 312 317 if (!sb_set_blocksize(s, QNX6_SUPERBLOCK_SIZE)) { ··· 317 316 goto outnobh; 318 317 } 319 318 320 - /* parse the mount-options */ 321 - if (!qnx6_parse_options((char *) data, s)) { 322 - pr_err("invalid mount options.\n"); 323 - goto outnobh; 324 - } 325 - if (test_opt(s, MMI_FS)) { 319 + if (qs->s_mount_opt == QNX6_MOUNT_MMI_FS) { 326 320 sb1 = qnx6_mmi_fill_super(s, silent); 327 321 if (sb1) 328 322 goto mmi_success; ··· 628 632 kmem_cache_destroy(qnx6_inode_cachep); 629 633 } 630 634 631 - static struct dentry *qnx6_mount(struct file_system_type *fs_type, 632 - int flags, const char *dev_name, void *data) 635 + static int qnx6_get_tree(struct fs_context *fc) 633 636 { 634 - return mount_bdev(fs_type, flags, dev_name, data, qnx6_fill_super); 637 + return get_tree_bdev(fc, qnx6_fill_super); 638 + } 639 + 640 + static void qnx6_free_fc(struct fs_context *fc) 641 + { 642 + kfree(fc->fs_private); 643 + } 644 + 645 + static const struct fs_context_operations qnx6_context_ops = { 646 + .parse_param = qnx6_parse_param, 647 + .get_tree = qnx6_get_tree, 648 + .reconfigure = qnx6_reconfigure, 649 + .free = qnx6_free_fc, 650 + }; 651 + 652 + static int qnx6_init_fs_context(struct fs_context *fc) 653 + { 654 + struct qnx6_context *ctx; 655 + 656 + ctx = kzalloc(sizeof(struct qnx6_context), GFP_KERNEL); 657 + if (!ctx) 658 + return -ENOMEM; 659 + fc->ops = &qnx6_context_ops; 660 + fc->fs_private = ctx; 661 + 662 + return 0; 635 663 } 636 664 637 665 static struct file_system_type qnx6_fs_type = { 638 - .owner = THIS_MODULE, 639 - .name = "qnx6", 640 - .mount = qnx6_mount, 641 - .kill_sb = kill_block_super, 642 - .fs_flags = FS_REQUIRES_DEV, 666 + .owner = THIS_MODULE, 667 + .name = "qnx6", 668 + .kill_sb = kill_block_super, 669 + .fs_flags = FS_REQUIRES_DEV, 670 + .init_fs_context = qnx6_init_fs_context, 671 + .parameters = qnx6_param_spec, 643 672 }; 644 673 MODULE_ALIAS_FS("qnx6"); 645 674
+93 -107
fs/tracefs/inode.c
··· 11 11 12 12 #include <linux/module.h> 13 13 #include <linux/fs.h> 14 - #include <linux/mount.h> 14 + #include <linux/fs_context.h> 15 + #include <linux/fs_parser.h> 15 16 #include <linux/kobject.h> 16 17 #include <linux/namei.h> 17 18 #include <linux/tracefs.h> 18 19 #include <linux/fsnotify.h> 19 20 #include <linux/security.h> 20 21 #include <linux/seq_file.h> 21 - #include <linux/parser.h> 22 22 #include <linux/magic.h> 23 23 #include <linux/slab.h> 24 24 #include "internal.h" ··· 281 281 return inode; 282 282 } 283 283 284 - struct tracefs_mount_opts { 284 + struct tracefs_fs_info { 285 285 kuid_t uid; 286 286 kgid_t gid; 287 287 umode_t mode; ··· 293 293 Opt_uid, 294 294 Opt_gid, 295 295 Opt_mode, 296 - Opt_err 297 296 }; 298 297 299 - static const match_table_t tokens = { 300 - {Opt_uid, "uid=%u"}, 301 - {Opt_gid, "gid=%u"}, 302 - {Opt_mode, "mode=%o"}, 303 - {Opt_err, NULL} 298 + static const struct fs_parameter_spec tracefs_param_specs[] = { 299 + fsparam_u32 ("gid", Opt_gid), 300 + fsparam_u32oct ("mode", Opt_mode), 301 + fsparam_u32 ("uid", Opt_uid), 302 + {} 304 303 }; 305 304 306 - struct tracefs_fs_info { 307 - struct tracefs_mount_opts mount_opts; 308 - }; 309 - 310 - static int tracefs_parse_options(char *data, struct tracefs_mount_opts *opts) 305 + static int tracefs_parse_param(struct fs_context *fc, struct fs_parameter *param) 311 306 { 312 - substring_t args[MAX_OPT_ARGS]; 313 - int option; 314 - int token; 307 + struct tracefs_fs_info *opts = fc->s_fs_info; 308 + struct fs_parse_result result; 315 309 kuid_t uid; 316 310 kgid_t gid; 317 - char *p; 311 + int opt; 318 312 319 - opts->opts = 0; 320 - opts->mode = TRACEFS_DEFAULT_MODE; 313 + opt = fs_parse(fc, tracefs_param_specs, param, &result); 314 + if (opt < 0) 315 + return opt; 321 316 322 - while ((p = strsep(&data, ",")) != NULL) { 323 - if (!*p) 324 - continue; 325 - 326 - token = match_token(p, tokens, args); 327 - switch (token) { 328 - case Opt_uid: 329 - if (match_int(&args[0], &option)) 330 - return -EINVAL; 331 - uid = make_kuid(current_user_ns(), option); 332 - if (!uid_valid(uid)) 333 - return -EINVAL; 334 - opts->uid = uid; 335 - break; 336 - case Opt_gid: 337 - if (match_int(&args[0], &option)) 338 - return -EINVAL; 339 - gid = make_kgid(current_user_ns(), option); 340 - if (!gid_valid(gid)) 341 - return -EINVAL; 342 - opts->gid = gid; 343 - break; 344 - case Opt_mode: 345 - if (match_octal(&args[0], &option)) 346 - return -EINVAL; 347 - opts->mode = option & S_IALLUGO; 348 - break; 349 - /* 350 - * We might like to report bad mount options here; 351 - * but traditionally tracefs has ignored all mount options 352 - */ 353 - } 354 - 355 - opts->opts |= BIT(token); 317 + switch (opt) { 318 + case Opt_uid: 319 + uid = make_kuid(current_user_ns(), result.uint_32); 320 + if (!uid_valid(uid)) 321 + return invalf(fc, "Unknown uid"); 322 + opts->uid = uid; 323 + break; 324 + case Opt_gid: 325 + gid = make_kgid(current_user_ns(), result.uint_32); 326 + if (!gid_valid(gid)) 327 + return invalf(fc, "Unknown gid"); 328 + opts->gid = gid; 329 + break; 330 + case Opt_mode: 331 + opts->mode = result.uint_32 & S_IALLUGO; 332 + break; 333 + /* 334 + * We might like to report bad mount options here; 335 + * but traditionally tracefs has ignored all mount options 336 + */ 356 337 } 338 + 339 + opts->opts |= BIT(opt); 357 340 358 341 return 0; 359 342 } ··· 345 362 { 346 363 struct tracefs_fs_info *fsi = sb->s_fs_info; 347 364 struct inode *inode = d_inode(sb->s_root); 348 - struct tracefs_mount_opts *opts = &fsi->mount_opts; 349 365 struct tracefs_inode *ti; 350 366 bool update_uid, update_gid; 351 367 umode_t tmp_mode; ··· 354 372 * options. 355 373 */ 356 374 357 - if (!remount || opts->opts & BIT(Opt_mode)) { 375 + if (!remount || fsi->opts & BIT(Opt_mode)) { 358 376 tmp_mode = READ_ONCE(inode->i_mode) & ~S_IALLUGO; 359 - tmp_mode |= opts->mode; 377 + tmp_mode |= fsi->mode; 360 378 WRITE_ONCE(inode->i_mode, tmp_mode); 361 379 } 362 380 363 - if (!remount || opts->opts & BIT(Opt_uid)) 364 - inode->i_uid = opts->uid; 381 + if (!remount || fsi->opts & BIT(Opt_uid)) 382 + inode->i_uid = fsi->uid; 365 383 366 - if (!remount || opts->opts & BIT(Opt_gid)) 367 - inode->i_gid = opts->gid; 384 + if (!remount || fsi->opts & BIT(Opt_gid)) 385 + inode->i_gid = fsi->gid; 368 386 369 - if (remount && (opts->opts & BIT(Opt_uid) || opts->opts & BIT(Opt_gid))) { 387 + if (remount && (fsi->opts & BIT(Opt_uid) || fsi->opts & BIT(Opt_gid))) { 370 388 371 - update_uid = opts->opts & BIT(Opt_uid); 372 - update_gid = opts->opts & BIT(Opt_gid); 389 + update_uid = fsi->opts & BIT(Opt_uid); 390 + update_gid = fsi->opts & BIT(Opt_gid); 373 391 374 392 rcu_read_lock(); 375 393 list_for_each_entry_rcu(ti, &tracefs_inodes, list) { ··· 388 406 return 0; 389 407 } 390 408 391 - static int tracefs_remount(struct super_block *sb, int *flags, char *data) 409 + static int tracefs_reconfigure(struct fs_context *fc) 392 410 { 393 - int err; 394 - struct tracefs_fs_info *fsi = sb->s_fs_info; 411 + struct super_block *sb = fc->root->d_sb; 412 + struct tracefs_fs_info *sb_opts = sb->s_fs_info; 413 + struct tracefs_fs_info *new_opts = fc->s_fs_info; 395 414 396 415 sync_filesystem(sb); 397 - err = tracefs_parse_options(data, &fsi->mount_opts); 398 - if (err) 399 - goto fail; 416 + /* structure copy of new mount options to sb */ 417 + *sb_opts = *new_opts; 400 418 401 - tracefs_apply_options(sb, true); 402 - 403 - fail: 404 - return err; 419 + return tracefs_apply_options(sb, true); 405 420 } 406 421 407 422 static int tracefs_show_options(struct seq_file *m, struct dentry *root) 408 423 { 409 424 struct tracefs_fs_info *fsi = root->d_sb->s_fs_info; 410 - struct tracefs_mount_opts *opts = &fsi->mount_opts; 411 425 412 - if (!uid_eq(opts->uid, GLOBAL_ROOT_UID)) 426 + if (!uid_eq(fsi->uid, GLOBAL_ROOT_UID)) 413 427 seq_printf(m, ",uid=%u", 414 - from_kuid_munged(&init_user_ns, opts->uid)); 415 - if (!gid_eq(opts->gid, GLOBAL_ROOT_GID)) 428 + from_kuid_munged(&init_user_ns, fsi->uid)); 429 + if (!gid_eq(fsi->gid, GLOBAL_ROOT_GID)) 416 430 seq_printf(m, ",gid=%u", 417 - from_kgid_munged(&init_user_ns, opts->gid)); 418 - if (opts->mode != TRACEFS_DEFAULT_MODE) 419 - seq_printf(m, ",mode=%o", opts->mode); 431 + from_kgid_munged(&init_user_ns, fsi->gid)); 432 + if (fsi->mode != TRACEFS_DEFAULT_MODE) 433 + seq_printf(m, ",mode=%o", fsi->mode); 420 434 421 435 return 0; 422 436 } ··· 422 444 .free_inode = tracefs_free_inode, 423 445 .drop_inode = generic_delete_inode, 424 446 .statfs = simple_statfs, 425 - .remount_fs = tracefs_remount, 426 447 .show_options = tracefs_show_options, 427 448 }; 428 449 ··· 466 489 .d_release = tracefs_d_release, 467 490 }; 468 491 469 - static int trace_fill_super(struct super_block *sb, void *data, int silent) 492 + static int tracefs_fill_super(struct super_block *sb, struct fs_context *fc) 470 493 { 471 494 static const struct tree_descr trace_files[] = {{""}}; 472 - struct tracefs_fs_info *fsi; 473 495 int err; 474 496 475 - fsi = kzalloc(sizeof(struct tracefs_fs_info), GFP_KERNEL); 476 - sb->s_fs_info = fsi; 477 - if (!fsi) { 478 - err = -ENOMEM; 479 - goto fail; 480 - } 481 - 482 - err = tracefs_parse_options(data, &fsi->mount_opts); 497 + err = simple_fill_super(sb, TRACEFS_MAGIC, trace_files); 483 498 if (err) 484 - goto fail; 485 - 486 - err = simple_fill_super(sb, TRACEFS_MAGIC, trace_files); 487 - if (err) 488 - goto fail; 499 + return err; 489 500 490 501 sb->s_op = &tracefs_super_operations; 491 502 sb->s_d_op = &tracefs_dentry_operations; ··· 481 516 tracefs_apply_options(sb, false); 482 517 483 518 return 0; 484 - 485 - fail: 486 - kfree(fsi); 487 - sb->s_fs_info = NULL; 488 - return err; 489 519 } 490 520 491 - static struct dentry *trace_mount(struct file_system_type *fs_type, 492 - int flags, const char *dev_name, 493 - void *data) 521 + static int tracefs_get_tree(struct fs_context *fc) 494 522 { 495 - return mount_single(fs_type, flags, data, trace_fill_super); 523 + return get_tree_single(fc, tracefs_fill_super); 524 + } 525 + 526 + static void tracefs_free_fc(struct fs_context *fc) 527 + { 528 + kfree(fc->s_fs_info); 529 + } 530 + 531 + static const struct fs_context_operations tracefs_context_ops = { 532 + .free = tracefs_free_fc, 533 + .parse_param = tracefs_parse_param, 534 + .get_tree = tracefs_get_tree, 535 + .reconfigure = tracefs_reconfigure, 536 + }; 537 + 538 + static int tracefs_init_fs_context(struct fs_context *fc) 539 + { 540 + struct tracefs_fs_info *fsi; 541 + 542 + fsi = kzalloc(sizeof(struct tracefs_fs_info), GFP_KERNEL); 543 + if (!fsi) 544 + return -ENOMEM; 545 + 546 + fsi->mode = TRACEFS_DEFAULT_MODE; 547 + 548 + fc->s_fs_info = fsi; 549 + fc->ops = &tracefs_context_ops; 550 + return 0; 496 551 } 497 552 498 553 static struct file_system_type trace_fs_type = { 499 554 .owner = THIS_MODULE, 500 555 .name = "tracefs", 501 - .mount = trace_mount, 556 + .init_fs_context = tracefs_init_fs_context, 557 + .parameters = tracefs_param_specs, 502 558 .kill_sb = kill_litter_super, 503 559 }; 504 560 MODULE_ALIAS_FS("tracefs");