···754754static int ext3_mark_dquot_dirty(struct dquot *dquot);755755static int ext3_write_info(struct super_block *sb, int type);756756static int ext3_quota_on(struct super_block *sb, int type, int format_id,757757- char *path);757757+ struct path *path);758758static int ext3_quota_on_mount(struct super_block *sb, int type);759759static ssize_t ext3_quota_read(struct super_block *sb, int type, char *data,760760 size_t len, loff_t off);···28772877 * Standard function to be called on quota_on28782878 */28792879static int ext3_quota_on(struct super_block *sb, int type, int format_id,28802880- char *name)28802880+ struct path *path)28812881{28822882 int err;28832883- struct path path;2884288328852884 if (!test_opt(sb, QUOTA))28862885 return -EINVAL;2887288628882888- err = kern_path(name, LOOKUP_FOLLOW, &path);28892889- if (err)28902890- return err;28912891-28922887 /* Quotafile not on the same filesystem? */28932893- if (path.mnt->mnt_sb != sb) {28942894- path_put(&path);28882888+ if (path->mnt->mnt_sb != sb)28952889 return -EXDEV;28962896- }28972890 /* Journaling quota? */28982891 if (EXT3_SB(sb)->s_qf_names[type]) {28992892 /* Quotafile not of fs root? */29002900- if (path.dentry->d_parent != sb->s_root)28932893+ if (path->dentry->d_parent != sb->s_root)29012894 ext3_msg(sb, KERN_WARNING,29022895 "warning: Quota file not on filesystem root. "29032896 "Journaled quota will not work.");···29002907 * When we journal data on quota file, we have to flush journal to see29012908 * all updates to the file when we bypass pagecache...29022909 */29032903- if (ext3_should_journal_data(path.dentry->d_inode)) {29102910+ if (ext3_should_journal_data(path->dentry->d_inode)) {29042911 /*29052912 * We don't need to lock updates but journal_flush() could29062913 * otherwise be livelocked...···29082915 journal_lock_updates(EXT3_SB(sb)->s_journal);29092916 err = journal_flush(EXT3_SB(sb)->s_journal);29102917 journal_unlock_updates(EXT3_SB(sb)->s_journal);29112911- if (err) {29122912- path_put(&path);29182918+ if (err)29132919 return err;29142914- }29152920 }2916292129172917- err = dquot_quota_on_path(sb, type, format_id, &path);29182918- path_put(&path);29192919- return err;29222922+ return dquot_quota_on(sb, type, format_id, path);29202923}2921292429222925/* Read data from quotafile - avoid pagecache and such because we cannot afford
+7-18
fs/ext4/super.c
···11611161static int ext4_mark_dquot_dirty(struct dquot *dquot);11621162static int ext4_write_info(struct super_block *sb, int type);11631163static int ext4_quota_on(struct super_block *sb, int type, int format_id,11641164- char *path);11641164+ struct path *path);11651165static int ext4_quota_off(struct super_block *sb, int type);11661166static int ext4_quota_on_mount(struct super_block *sb, int type);11671167static ssize_t ext4_quota_read(struct super_block *sb, int type, char *data,···45584558 * Standard function to be called on quota_on45594559 */45604560static int ext4_quota_on(struct super_block *sb, int type, int format_id,45614561- char *name)45614561+ struct path *path)45624562{45634563 int err;45644564- struct path path;4565456445664565 if (!test_opt(sb, QUOTA))45674566 return -EINVAL;4568456745694569- err = kern_path(name, LOOKUP_FOLLOW, &path);45704570- if (err)45714571- return err;45724572-45734568 /* Quotafile not on the same filesystem? */45744574- if (path.mnt->mnt_sb != sb) {45754575- path_put(&path);45694569+ if (path->mnt->mnt_sb != sb)45764570 return -EXDEV;45774577- }45784571 /* Journaling quota? */45794572 if (EXT4_SB(sb)->s_qf_names[type]) {45804573 /* Quotafile not in fs root? */45814581- if (path.dentry->d_parent != sb->s_root)45744574+ if (path->dentry->d_parent != sb->s_root)45824575 ext4_msg(sb, KERN_WARNING,45834576 "Quota file not on filesystem root. "45844577 "Journaled quota will not work");···45824589 * all updates to the file when we bypass pagecache...45834590 */45844591 if (EXT4_SB(sb)->s_journal &&45854585- ext4_should_journal_data(path.dentry->d_inode)) {45924592+ ext4_should_journal_data(path->dentry->d_inode)) {45864593 /*45874594 * We don't need to lock updates but journal_flush() could45884595 * otherwise be livelocked...···45904597 jbd2_journal_lock_updates(EXT4_SB(sb)->s_journal);45914598 err = jbd2_journal_flush(EXT4_SB(sb)->s_journal);45924599 jbd2_journal_unlock_updates(EXT4_SB(sb)->s_journal);45934593- if (err) {45944594- path_put(&path);46004600+ if (err)45954601 return err;45964596- }45974602 }4598460345994599- err = dquot_quota_on_path(sb, type, format_id, &path);46004600- path_put(&path);46014601- return err;46044604+ return dquot_quota_on(sb, type, format_id, path);46024605}4603460646044607static int ext4_quota_off(struct super_block *sb, int type)
+2-3
fs/ocfs2/super.c
···993993}994994995995/* Handle quota on quotactl */996996-static int ocfs2_quota_on(struct super_block *sb, int type, int format_id,997997- char *path)996996+static int ocfs2_quota_on(struct super_block *sb, int type, int format_id)998997{999998 unsigned int feature[MAXQUOTAS] = { OCFS2_FEATURE_RO_COMPAT_USRQUOTA,1000999 OCFS2_FEATURE_RO_COMPAT_GRPQUOTA};···10121013}1013101410141015static const struct quotactl_ops ocfs2_quotactl_ops = {10151015- .quota_on = ocfs2_quota_on,10161016+ .quota_on_meta = ocfs2_quota_on,10161017 .quota_off = ocfs2_quota_off,10171018 .quota_sync = dquot_quota_sync,10181019 .get_info = dquot_get_dqinfo,
+2-16
fs/quota/dquot.c
···21892189}21902190EXPORT_SYMBOL(dquot_resume);2191219121922192-int dquot_quota_on_path(struct super_block *sb, int type, int format_id,21932193- struct path *path)21922192+int dquot_quota_on(struct super_block *sb, int type, int format_id,21932193+ struct path *path)21942194{21952195 int error = security_quota_on(path->dentry);21962196 if (error)···22022202 error = vfs_load_quota_inode(path->dentry->d_inode, type,22032203 format_id, DQUOT_USAGE_ENABLED |22042204 DQUOT_LIMITS_ENABLED);22052205- return error;22062206-}22072207-EXPORT_SYMBOL(dquot_quota_on_path);22082208-22092209-int dquot_quota_on(struct super_block *sb, int type, int format_id, char *name)22102210-{22112211- struct path path;22122212- int error;22132213-22142214- error = kern_path(name, LOOKUP_FOLLOW, &path);22152215- if (!error) {22162216- error = dquot_quota_on_path(sb, type, format_id, &path);22172217- path_put(&path);22182218- }22192205 return error;22202206}22212207EXPORT_SYMBOL(dquot_quota_on);
+27-14
fs/quota/quota.c
···6464}65656666static int quota_quotaon(struct super_block *sb, int type, int cmd, qid_t id,6767- void __user *addr)6767+ struct path *path)6868{6969- char *pathname;7070- int ret = -ENOSYS;7171-7272- pathname = getname(addr);7373- if (IS_ERR(pathname))7474- return PTR_ERR(pathname);7575- if (sb->s_qcop->quota_on)7676- ret = sb->s_qcop->quota_on(sb, type, id, pathname);7777- putname(pathname);7878- return ret;6969+ if (!sb->s_qcop->quota_on && !sb->s_qcop->quota_on_meta)7070+ return -ENOSYS;7171+ if (sb->s_qcop->quota_on_meta)7272+ return sb->s_qcop->quota_on_meta(sb, type, id);7373+ if (IS_ERR(path))7474+ return PTR_ERR(path);7575+ return sb->s_qcop->quota_on(sb, type, id, path);7976}80778178static int quota_getfmt(struct super_block *sb, int type, void __user *addr)···238241239242/* Copy parameters and call proper function */240243static int do_quotactl(struct super_block *sb, int type, int cmd, qid_t id,241241- void __user *addr)244244+ void __user *addr, struct path *path)242245{243246 int ret;244247···253256254257 switch (cmd) {255258 case Q_QUOTAON:256256- return quota_quotaon(sb, type, cmd, id, addr);259259+ return quota_quotaon(sb, type, cmd, id, path);257260 case Q_QUOTAOFF:258261 if (!sb->s_qcop->quota_off)259262 return -ENOSYS;···332335{333336 uint cmds, type;334337 struct super_block *sb = NULL;338338+ struct path path, *pathp = NULL;335339 int ret;336340337341 cmds = cmd >> SUBCMDSHIFT;···349351 return -ENODEV;350352 }351353354354+ /*355355+ * Path for quotaon has to be resolved before grabbing superblock356356+ * because that gets s_umount sem which is also possibly needed by path357357+ * resolution (think about autofs) and thus deadlocks could arise.358358+ */359359+ if (cmds == Q_QUOTAON) {360360+ ret = user_path_at(AT_FDCWD, addr, LOOKUP_FOLLOW, &path);361361+ if (ret)362362+ pathp = ERR_PTR(ret);363363+ else364364+ pathp = &path;365365+ }366366+352367 sb = quotactl_block(special);353368 if (IS_ERR(sb))354369 return PTR_ERR(sb);355370356356- ret = do_quotactl(sb, type, cmds, id, addr);371371+ ret = do_quotactl(sb, type, cmds, id, addr, pathp);357372358373 drop_super(sb);374374+ if (pathp && !IS_ERR(pathp))375375+ path_put(pathp);359376 return ret;360377}
+6-11
fs/reiserfs/super.c
···632632static int reiserfs_release_dquot(struct dquot *);633633static int reiserfs_mark_dquot_dirty(struct dquot *);634634static int reiserfs_write_info(struct super_block *, int);635635-static int reiserfs_quota_on(struct super_block *, int, int, char *);635635+static int reiserfs_quota_on(struct super_block *, int, int, struct path *);636636637637static const struct dquot_operations reiserfs_quota_operations = {638638 .write_dquot = reiserfs_write_dquot,···20482048 * Standard function to be called on quota_on20492049 */20502050static int reiserfs_quota_on(struct super_block *sb, int type, int format_id,20512051- char *name)20512051+ struct path *path)20522052{20532053 int err;20542054- struct path path;20552054 struct inode *inode;20562055 struct reiserfs_transaction_handle th;2057205620582057 if (!(REISERFS_SB(sb)->s_mount_opt & (1 << REISERFS_QUOTA)))20592058 return -EINVAL;2060205920612061- err = kern_path(name, LOOKUP_FOLLOW, &path);20622062- if (err)20632063- return err;20642060 /* Quotafile not on the same filesystem? */20652065- if (path.mnt->mnt_sb != sb) {20612061+ if (path->mnt->mnt_sb != sb) {20662062 err = -EXDEV;20672063 goto out;20682064 }20692069- inode = path.dentry->d_inode;20652065+ inode = path->dentry->d_inode;20702066 /* We must not pack tails for quota files on reiserfs for quota IO to work */20712067 if (!(REISERFS_I(inode)->i_flags & i_nopack_mask)) {20722068 err = reiserfs_unpack(inode, NULL);···20782082 /* Journaling quota? */20792083 if (REISERFS_SB(sb)->s_qf_names[type]) {20802084 /* Quotafile not of fs root? */20812081- if (path.dentry->d_parent != sb->s_root)20852085+ if (path->dentry->d_parent != sb->s_root)20822086 reiserfs_warning(sb, "super-6521",20832087 "Quota file not on filesystem root. "20842088 "Journalled quota will not work.");···20972101 if (err)20982102 goto out;20992103 }21002100- err = dquot_quota_on_path(sb, type, format_id, &path);21042104+ err = dquot_quota_on(sb, type, format_id, path);21012105out:21022102- path_put(&path);21032106 return err;21042107}21052108
+4-1
include/linux/quota.h
···322322 qsize_t *(*get_reserved_space) (struct inode *);323323};324324325325+struct path;326326+325327/* Operations handling requests from userspace */326328struct quotactl_ops {327327- int (*quota_on)(struct super_block *, int, int, char *);329329+ int (*quota_on)(struct super_block *, int, int, struct path *);330330+ int (*quota_on_meta)(struct super_block *, int, int);328331 int (*quota_off)(struct super_block *, int);329332 int (*quota_sync)(struct super_block *, int, int);330333 int (*get_info)(struct super_block *, int, struct if_dqinfo *);
+1-3
include/linux/quotaops.h
···76767777int dquot_file_open(struct inode *inode, struct file *file);78787979-int dquot_quota_on(struct super_block *sb, int type, int format_id,8080- char *path);8179int dquot_enable(struct inode *inode, int type, int format_id,8280 unsigned int flags);8383-int dquot_quota_on_path(struct super_block *sb, int type, int format_id,8181+int dquot_quota_on(struct super_block *sb, int type, int format_id,8482 struct path *path);8583int dquot_quota_on_mount(struct super_block *sb, char *qf_name,8684 int format_id, int type);