Commit 1ba106818615faddb63ba782f85f3498b9eb61c6

Authored by Al Viro
1 parent dae6ad8f37

switch do_spufs_create() to user_path_create(), fix double-unlock

Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>

Showing 3 changed files with 21 additions and 32 deletions Side-by-side Diff

arch/powerpc/platforms/cell/spufs/inode.c
... ... @@ -611,15 +611,14 @@
611 611  
612 612 static struct file_system_type spufs_type;
613 613  
614   -long spufs_create(struct nameidata *nd, unsigned int flags, mode_t mode,
615   - struct file *filp)
  614 +long spufs_create(struct path *path, struct dentry *dentry,
  615 + unsigned int flags, mode_t mode, struct file *filp)
616 616 {
617   - struct dentry *dentry;
618 617 int ret;
619 618  
620 619 ret = -EINVAL;
621 620 /* check if we are on spufs */
622   - if (nd->path.dentry->d_sb->s_type != &spufs_type)
  621 + if (path->dentry->d_sb->s_type != &spufs_type)
623 622 goto out;
624 623  
625 624 /* don't accept undefined flags */
626 625  
627 626  
628 627  
629 628  
630 629  
631 630  
632 631  
... ... @@ -627,33 +626,27 @@
627 626 goto out;
628 627  
629 628 /* only threads can be underneath a gang */
630   - if (nd->path.dentry != nd->path.dentry->d_sb->s_root) {
  629 + if (path->dentry != path->dentry->d_sb->s_root) {
631 630 if ((flags & SPU_CREATE_GANG) ||
632   - !SPUFS_I(nd->path.dentry->d_inode)->i_gang)
  631 + !SPUFS_I(path->dentry->d_inode)->i_gang)
633 632 goto out;
634 633 }
635 634  
636   - dentry = lookup_create(nd, 1);
637   - ret = PTR_ERR(dentry);
638   - if (IS_ERR(dentry))
639   - goto out_dir;
640   -
641 635 mode &= ~current_umask();
642 636  
643 637 if (flags & SPU_CREATE_GANG)
644   - ret = spufs_create_gang(nd->path.dentry->d_inode,
645   - dentry, nd->path.mnt, mode);
  638 + ret = spufs_create_gang(path->dentry->d_inode,
  639 + dentry, path->mnt, mode);
646 640 else
647   - ret = spufs_create_context(nd->path.dentry->d_inode,
648   - dentry, nd->path.mnt, flags, mode,
  641 + ret = spufs_create_context(path->dentry->d_inode,
  642 + dentry, path->mnt, flags, mode,
649 643 filp);
650 644 if (ret >= 0)
651   - fsnotify_mkdir(nd->path.dentry->d_inode, dentry);
  645 + fsnotify_mkdir(path->dentry->d_inode, dentry);
652 646 return ret;
653 647  
654   -out_dir:
655   - mutex_unlock(&nd->path.dentry->d_inode->i_mutex);
656 648 out:
  649 + mutex_unlock(&path->dentry->d_inode->i_mutex);
657 650 return ret;
658 651 }
659 652  
arch/powerpc/platforms/cell/spufs/spufs.h
... ... @@ -248,7 +248,7 @@
248 248 /* system call implementation */
249 249 extern struct spufs_calls spufs_calls;
250 250 long spufs_run_spu(struct spu_context *ctx, u32 *npc, u32 *status);
251   -long spufs_create(struct nameidata *nd, unsigned int flags,
  251 +long spufs_create(struct path *nd, struct dentry *dentry, unsigned int flags,
252 252 mode_t mode, struct file *filp);
253 253 /* ELF coredump callbacks for writing SPU ELF notes */
254 254 extern int spufs_coredump_extra_notes_size(void);
arch/powerpc/platforms/cell/spufs/syscalls.c
... ... @@ -62,21 +62,17 @@
62 62 static long do_spu_create(const char __user *pathname, unsigned int flags,
63 63 mode_t mode, struct file *neighbor)
64 64 {
65   - char *tmp;
  65 + struct path path;
  66 + struct dentry *dentry;
66 67 int ret;
67 68  
68   - tmp = getname(pathname);
69   - ret = PTR_ERR(tmp);
70   - if (!IS_ERR(tmp)) {
71   - struct nameidata nd;
72   -
73   - ret = kern_path_parent(tmp, &nd);
74   - if (!ret) {
75   - nd.flags |= LOOKUP_OPEN | LOOKUP_CREATE;
76   - ret = spufs_create(&nd, flags, mode, neighbor);
77   - path_put(&nd.path);
78   - }
79   - putname(tmp);
  69 + dentry = user_path_create(AT_FDCWD, pathname, &path, 1);
  70 + ret = PTR_ERR(dentry);
  71 + if (!IS_ERR(dentry)) {
  72 + ret = spufs_create(&path, dentry, flags, mode, neighbor);
  73 + mutex_unlock(&path.dentry->d_inode->i_mutex);
  74 + dput(dentry);
  75 + path_put(&path);
80 76 }
81 77  
82 78 return ret;