Merge branch 'drm-patches' of master.kernel.org:/pub/scm/linux/kernel/git/airlied...
[linux-drm-fsl-dcu.git] / arch / powerpc / platforms / cell / spufs / inode.c
index e3af9112c02620a794ce051a685417b9086cf1f5..a93f328a73178fa6e21a194d74667c2353289d19 100644 (file)
@@ -36,6 +36,7 @@
 #include <asm/prom.h>
 #include <asm/semaphore.h>
 #include <asm/spu.h>
+#include <asm/spu_priv1.h>
 #include <asm/uaccess.h>
 
 #include "spufs.h"
@@ -54,6 +55,7 @@ spufs_alloc_inode(struct super_block *sb)
 
        ei->i_gang = NULL;
        ei->i_ctx = NULL;
+       ei->i_openers = 0;
 
        return &ei->vfs_inode;
 }
@@ -69,8 +71,7 @@ spufs_init_once(void *p, struct kmem_cache * cachep, unsigned long flags)
 {
        struct spufs_inode_info *ei = p;
 
-       if ((flags & (SLAB_CTOR_VERIFY|SLAB_CTOR_CONSTRUCTOR)) ==
-           SLAB_CTOR_CONSTRUCTOR) {
+       if (flags & SLAB_CTOR_CONSTRUCTOR) {
                inode_init_once(&ei->vfs_inode);
        }
 }
@@ -205,7 +206,7 @@ static int spufs_dir_close(struct inode *inode, struct file *file)
        struct dentry *dir;
        int ret;
 
-       dir = file->f_dentry;
+       dir = file->f_path.dentry;
        parent = dir->d_parent->d_inode;
        ctx = SPUFS_I(dir->d_inode)->i_ctx;
 
@@ -220,11 +221,11 @@ static int spufs_dir_close(struct inode *inode, struct file *file)
        return dcache_dir_close(inode, file);
 }
 
-struct inode_operations spufs_dir_inode_operations = {
+const struct inode_operations spufs_dir_inode_operations = {
        .lookup = simple_lookup,
 };
 
-struct file_operations spufs_context_fops = {
+const struct file_operations spufs_context_fops = {
        .open           = dcache_dir_open,
        .release        = spufs_dir_close,
        .llseek         = dcache_dir_lseek,
@@ -363,7 +364,7 @@ static int spufs_gang_close(struct inode *inode, struct file *file)
        struct dentry *dir;
        int ret;
 
-       dir = file->f_dentry;
+       dir = file->f_path.dentry;
        parent = dir->d_parent->d_inode;
 
        ret = spufs_rmgang(parent, dir);
@@ -372,7 +373,7 @@ static int spufs_gang_close(struct inode *inode, struct file *file)
        return dcache_dir_close(inode, file);
 }
 
-struct file_operations spufs_gang_fops = {
+const struct file_operations spufs_gang_fops = {
        .open           = dcache_dir_open,
        .release        = spufs_gang_close,
        .llseek         = dcache_dir_lseek,
@@ -520,13 +521,14 @@ out:
 
 /* File system initialization */
 enum {
-       Opt_uid, Opt_gid, Opt_err,
+       Opt_uid, Opt_gid, Opt_mode, Opt_err,
 };
 
 static match_table_t spufs_tokens = {
-       { Opt_uid, "uid=%d" },
-       { Opt_gid, "gid=%d" },
-       { Opt_err, NULL  },
+       { Opt_uid,  "uid=%d" },
+       { Opt_gid,  "gid=%d" },
+       { Opt_mode, "mode=%o" },
+       { Opt_err,   NULL  },
 };
 
 static int
@@ -553,6 +555,11 @@ spufs_parse_options(char *options, struct inode *root)
                                return 0;
                        root->i_gid = option;
                        break;
+               case Opt_mode:
+                       if (match_octal(&args[0], &option))
+                               return 0;
+                       root->i_mode = option | S_IFDIR;
+                       break;
                default:
                        return 0;
                }
@@ -560,6 +567,11 @@ spufs_parse_options(char *options, struct inode *root)
        return 1;
 }
 
+static void spufs_exit_isolated_loader(void)
+{
+       kfree(isolated_loader);
+}
+
 static void
 spufs_init_isolated_loader(void)
 {
@@ -571,7 +583,7 @@ spufs_init_isolated_loader(void)
        if (!dn)
                return;
 
-       loader = get_property(dn, "loader", &size);
+       loader = of_get_property(dn, "loader", &size);
        if (!loader)
                return;
 
@@ -653,6 +665,10 @@ static int __init spufs_init(void)
 {
        int ret;
 
+       ret = -ENODEV;
+       if (!spu_management_ops)
+               goto out;
+
        ret = -ENOMEM;
        spufs_inode_cache = kmem_cache_create("spufs_inode_cache",
                        sizeof(struct spufs_inode_info), 0,
@@ -660,25 +676,29 @@ static int __init spufs_init(void)
 
        if (!spufs_inode_cache)
                goto out;
-       if (spu_sched_init() != 0) {
-               kmem_cache_destroy(spufs_inode_cache);
-               goto out;
-       }
-       ret = register_filesystem(&spufs_type);
+       ret = spu_sched_init();
        if (ret)
                goto out_cache;
+       ret = register_filesystem(&spufs_type);
+       if (ret)
+               goto out_sched;
        ret = register_spu_syscalls(&spufs_calls);
        if (ret)
                goto out_fs;
        ret = register_arch_coredump_calls(&spufs_coredump_calls);
        if (ret)
-               goto out_fs;
+               goto out_syscalls;
 
        spufs_init_isolated_loader();
 
        return 0;
+
+out_syscalls:
+       unregister_spu_syscalls(&spufs_calls);
 out_fs:
        unregister_filesystem(&spufs_type);
+out_sched:
+       spu_sched_exit();
 out_cache:
        kmem_cache_destroy(spufs_inode_cache);
 out:
@@ -689,6 +709,7 @@ module_init(spufs_init);
 static void __exit spufs_exit(void)
 {
        spu_sched_exit();
+       spufs_exit_isolated_loader();
        unregister_arch_coredump_calls(&spufs_coredump_calls);
        unregister_spu_syscalls(&spufs_calls);
        unregister_filesystem(&spufs_type);