remove inode_setattr
[linux-2.6.git] / arch / powerpc / platforms / cell / spufs / inode.c
1
2 /*
3  * SPU file system
4  *
5  * (C) Copyright IBM Deutschland Entwicklung GmbH 2005
6  *
7  * Author: Arnd Bergmann <arndb@de.ibm.com>
8  *
9  * This program is free software; you can redistribute it and/or modify
10  * it under the terms of the GNU General Public License as published by
11  * the Free Software Foundation; either version 2, or (at your option)
12  * any later version.
13  *
14  * This program is distributed in the hope that it will be useful,
15  * but WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17  * GNU General Public License for more details.
18  *
19  * You should have received a copy of the GNU General Public License
20  * along with this program; if not, write to the Free Software
21  * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
22  */
23
24 #include <linux/file.h>
25 #include <linux/fs.h>
26 #include <linux/fsnotify.h>
27 #include <linux/backing-dev.h>
28 #include <linux/init.h>
29 #include <linux/ioctl.h>
30 #include <linux/module.h>
31 #include <linux/mount.h>
32 #include <linux/namei.h>
33 #include <linux/pagemap.h>
34 #include <linux/poll.h>
35 #include <linux/slab.h>
36 #include <linux/parser.h>
37
38 #include <asm/prom.h>
39 #include <asm/spu.h>
40 #include <asm/spu_priv1.h>
41 #include <asm/uaccess.h>
42
43 #include "spufs.h"
44
45 struct spufs_sb_info {
46         int debug;
47 };
48
49 static struct kmem_cache *spufs_inode_cache;
50 char *isolated_loader;
51 static int isolated_loader_size;
52
53 static struct spufs_sb_info *spufs_get_sb_info(struct super_block *sb)
54 {
55         return sb->s_fs_info;
56 }
57
58 static struct inode *
59 spufs_alloc_inode(struct super_block *sb)
60 {
61         struct spufs_inode_info *ei;
62
63         ei = kmem_cache_alloc(spufs_inode_cache, GFP_KERNEL);
64         if (!ei)
65                 return NULL;
66
67         ei->i_gang = NULL;
68         ei->i_ctx = NULL;
69         ei->i_openers = 0;
70
71         return &ei->vfs_inode;
72 }
73
74 static void
75 spufs_destroy_inode(struct inode *inode)
76 {
77         kmem_cache_free(spufs_inode_cache, SPUFS_I(inode));
78 }
79
80 static void
81 spufs_init_once(void *p)
82 {
83         struct spufs_inode_info *ei = p;
84
85         inode_init_once(&ei->vfs_inode);
86 }
87
88 static struct inode *
89 spufs_new_inode(struct super_block *sb, int mode)
90 {
91         struct inode *inode;
92
93         inode = new_inode(sb);
94         if (!inode)
95                 goto out;
96
97         inode->i_mode = mode;
98         inode->i_uid = current_fsuid();
99         inode->i_gid = current_fsgid();
100         inode->i_atime = inode->i_mtime = inode->i_ctime = CURRENT_TIME;
101 out:
102         return inode;
103 }
104
105 static int
106 spufs_setattr(struct dentry *dentry, struct iattr *attr)
107 {
108         struct inode *inode = dentry->d_inode;
109
110         if ((attr->ia_valid & ATTR_SIZE) &&
111             (attr->ia_size != inode->i_size))
112                 return -EINVAL;
113         setattr_copy(inode, attr);
114         mark_inode_dirty(inode);
115         return 0;
116 }
117
118
119 static int
120 spufs_new_file(struct super_block *sb, struct dentry *dentry,
121                 const struct file_operations *fops, int mode,
122                 size_t size, struct spu_context *ctx)
123 {
124         static const struct inode_operations spufs_file_iops = {
125                 .setattr = spufs_setattr,
126         };
127         struct inode *inode;
128         int ret;
129
130         ret = -ENOSPC;
131         inode = spufs_new_inode(sb, S_IFREG | mode);
132         if (!inode)
133                 goto out;
134
135         ret = 0;
136         inode->i_op = &spufs_file_iops;
137         inode->i_fop = fops;
138         inode->i_size = size;
139         inode->i_private = SPUFS_I(inode)->i_ctx = get_spu_context(ctx);
140         d_add(dentry, inode);
141 out:
142         return ret;
143 }
144
145 static void
146 spufs_delete_inode(struct inode *inode)
147 {
148         struct spufs_inode_info *ei = SPUFS_I(inode);
149
150         if (ei->i_ctx)
151                 put_spu_context(ei->i_ctx);
152         if (ei->i_gang)
153                 put_spu_gang(ei->i_gang);
154         clear_inode(inode);
155 }
156
157 static void spufs_prune_dir(struct dentry *dir)
158 {
159         struct dentry *dentry, *tmp;
160
161         mutex_lock(&dir->d_inode->i_mutex);
162         list_for_each_entry_safe(dentry, tmp, &dir->d_subdirs, d_u.d_child) {
163                 spin_lock(&dcache_lock);
164                 spin_lock(&dentry->d_lock);
165                 if (!(d_unhashed(dentry)) && dentry->d_inode) {
166                         dget_locked(dentry);
167                         __d_drop(dentry);
168                         spin_unlock(&dentry->d_lock);
169                         simple_unlink(dir->d_inode, dentry);
170                         spin_unlock(&dcache_lock);
171                         dput(dentry);
172                 } else {
173                         spin_unlock(&dentry->d_lock);
174                         spin_unlock(&dcache_lock);
175                 }
176         }
177         shrink_dcache_parent(dir);
178         mutex_unlock(&dir->d_inode->i_mutex);
179 }
180
181 /* Caller must hold parent->i_mutex */
182 static int spufs_rmdir(struct inode *parent, struct dentry *dir)
183 {
184         /* remove all entries */
185         spufs_prune_dir(dir);
186         d_drop(dir);
187
188         return simple_rmdir(parent, dir);
189 }
190
191 static int spufs_fill_dir(struct dentry *dir,
192                 const struct spufs_tree_descr *files, int mode,
193                 struct spu_context *ctx)
194 {
195         struct dentry *dentry, *tmp;
196         int ret;
197
198         while (files->name && files->name[0]) {
199                 ret = -ENOMEM;
200                 dentry = d_alloc_name(dir, files->name);
201                 if (!dentry)
202                         goto out;
203                 ret = spufs_new_file(dir->d_sb, dentry, files->ops,
204                                         files->mode & mode, files->size, ctx);
205                 if (ret)
206                         goto out;
207                 files++;
208         }
209         return 0;
210 out:
211         /*
212          * remove all children from dir. dir->inode is not set so don't
213          * just simply use spufs_prune_dir() and panic afterwards :)
214          * dput() looks like it will do the right thing:
215          * - dec parent's ref counter
216          * - remove child from parent's child list
217          * - free child's inode if possible
218          * - free child
219          */
220         list_for_each_entry_safe(dentry, tmp, &dir->d_subdirs, d_u.d_child) {
221                 dput(dentry);
222         }
223
224         shrink_dcache_parent(dir);
225         return ret;
226 }
227
228 static int spufs_dir_close(struct inode *inode, struct file *file)
229 {
230         struct spu_context *ctx;
231         struct inode *parent;
232         struct dentry *dir;
233         int ret;
234
235         dir = file->f_path.dentry;
236         parent = dir->d_parent->d_inode;
237         ctx = SPUFS_I(dir->d_inode)->i_ctx;
238
239         mutex_lock_nested(&parent->i_mutex, I_MUTEX_PARENT);
240         ret = spufs_rmdir(parent, dir);
241         mutex_unlock(&parent->i_mutex);
242         WARN_ON(ret);
243
244         /* We have to give up the mm_struct */
245         spu_forget(ctx);
246
247         return dcache_dir_close(inode, file);
248 }
249
250 const struct file_operations spufs_context_fops = {
251         .open           = dcache_dir_open,
252         .release        = spufs_dir_close,
253         .llseek         = dcache_dir_lseek,
254         .read           = generic_read_dir,
255         .readdir        = dcache_readdir,
256         .fsync          = noop_fsync,
257 };
258 EXPORT_SYMBOL_GPL(spufs_context_fops);
259
260 static int
261 spufs_mkdir(struct inode *dir, struct dentry *dentry, unsigned int flags,
262                 int mode)
263 {
264         int ret;
265         struct inode *inode;
266         struct spu_context *ctx;
267
268         ret = -ENOSPC;
269         inode = spufs_new_inode(dir->i_sb, mode | S_IFDIR);
270         if (!inode)
271                 goto out;
272
273         if (dir->i_mode & S_ISGID) {
274                 inode->i_gid = dir->i_gid;
275                 inode->i_mode &= S_ISGID;
276         }
277         ctx = alloc_spu_context(SPUFS_I(dir)->i_gang); /* XXX gang */
278         SPUFS_I(inode)->i_ctx = ctx;
279         if (!ctx)
280                 goto out_iput;
281
282         ctx->flags = flags;
283         inode->i_op = &simple_dir_inode_operations;
284         inode->i_fop = &simple_dir_operations;
285         if (flags & SPU_CREATE_NOSCHED)
286                 ret = spufs_fill_dir(dentry, spufs_dir_nosched_contents,
287                                          mode, ctx);
288         else
289                 ret = spufs_fill_dir(dentry, spufs_dir_contents, mode, ctx);
290
291         if (ret)
292                 goto out_free_ctx;
293
294         if (spufs_get_sb_info(dir->i_sb)->debug)
295                 ret = spufs_fill_dir(dentry, spufs_dir_debug_contents,
296                                 mode, ctx);
297
298         if (ret)
299                 goto out_free_ctx;
300
301         d_instantiate(dentry, inode);
302         dget(dentry);
303         inc_nlink(dir);
304         inc_nlink(dentry->d_inode);
305         goto out;
306
307 out_free_ctx:
308         spu_forget(ctx);
309         put_spu_context(ctx);
310 out_iput:
311         iput(inode);
312 out:
313         return ret;
314 }
315
316 static int spufs_context_open(struct dentry *dentry, struct vfsmount *mnt)
317 {
318         int ret;
319         struct file *filp;
320
321         ret = get_unused_fd();
322         if (ret < 0) {
323                 dput(dentry);
324                 mntput(mnt);
325                 goto out;
326         }
327
328         filp = dentry_open(dentry, mnt, O_RDONLY, current_cred());
329         if (IS_ERR(filp)) {
330                 put_unused_fd(ret);
331                 ret = PTR_ERR(filp);
332                 goto out;
333         }
334
335         filp->f_op = &spufs_context_fops;
336         fd_install(ret, filp);
337 out:
338         return ret;
339 }
340
341 static struct spu_context *
342 spufs_assert_affinity(unsigned int flags, struct spu_gang *gang,
343                                                 struct file *filp)
344 {
345         struct spu_context *tmp, *neighbor, *err;
346         int count, node;
347         int aff_supp;
348
349         aff_supp = !list_empty(&(list_entry(cbe_spu_info[0].spus.next,
350                                         struct spu, cbe_list))->aff_list);
351
352         if (!aff_supp)
353                 return ERR_PTR(-EINVAL);
354
355         if (flags & SPU_CREATE_GANG)
356                 return ERR_PTR(-EINVAL);
357
358         if (flags & SPU_CREATE_AFFINITY_MEM &&
359             gang->aff_ref_ctx &&
360             gang->aff_ref_ctx->flags & SPU_CREATE_AFFINITY_MEM)
361                 return ERR_PTR(-EEXIST);
362
363         if (gang->aff_flags & AFF_MERGED)
364                 return ERR_PTR(-EBUSY);
365
366         neighbor = NULL;
367         if (flags & SPU_CREATE_AFFINITY_SPU) {
368                 if (!filp || filp->f_op != &spufs_context_fops)
369                         return ERR_PTR(-EINVAL);
370
371                 neighbor = get_spu_context(
372                                 SPUFS_I(filp->f_dentry->d_inode)->i_ctx);
373
374                 if (!list_empty(&neighbor->aff_list) && !(neighbor->aff_head) &&
375                     !list_is_last(&neighbor->aff_list, &gang->aff_list_head) &&
376                     !list_entry(neighbor->aff_list.next, struct spu_context,
377                     aff_list)->aff_head) {
378                         err = ERR_PTR(-EEXIST);
379                         goto out_put_neighbor;
380                 }
381
382                 if (gang != neighbor->gang) {
383                         err = ERR_PTR(-EINVAL);
384                         goto out_put_neighbor;
385                 }
386
387                 count = 1;
388                 list_for_each_entry(tmp, &gang->aff_list_head, aff_list)
389                         count++;
390                 if (list_empty(&neighbor->aff_list))
391                         count++;
392
393                 for (node = 0; node < MAX_NUMNODES; node++) {
394                         if ((cbe_spu_info[node].n_spus - atomic_read(
395                                 &cbe_spu_info[node].reserved_spus)) >= count)
396                                 break;
397                 }
398
399                 if (node == MAX_NUMNODES) {
400                         err = ERR_PTR(-EEXIST);
401                         goto out_put_neighbor;
402                 }
403         }
404
405         return neighbor;
406
407 out_put_neighbor:
408         put_spu_context(neighbor);
409         return err;
410 }
411
412 static void
413 spufs_set_affinity(unsigned int flags, struct spu_context *ctx,
414                                         struct spu_context *neighbor)
415 {
416         if (flags & SPU_CREATE_AFFINITY_MEM)
417                 ctx->gang->aff_ref_ctx = ctx;
418
419         if (flags & SPU_CREATE_AFFINITY_SPU) {
420                 if (list_empty(&neighbor->aff_list)) {
421                         list_add_tail(&neighbor->aff_list,
422                                 &ctx->gang->aff_list_head);
423                         neighbor->aff_head = 1;
424                 }
425
426                 if (list_is_last(&neighbor->aff_list, &ctx->gang->aff_list_head)
427                     || list_entry(neighbor->aff_list.next, struct spu_context,
428                                                         aff_list)->aff_head) {
429                         list_add(&ctx->aff_list, &neighbor->aff_list);
430                 } else  {
431                         list_add_tail(&ctx->aff_list, &neighbor->aff_list);
432                         if (neighbor->aff_head) {
433                                 neighbor->aff_head = 0;
434                                 ctx->aff_head = 1;
435                         }
436                 }
437
438                 if (!ctx->gang->aff_ref_ctx)
439                         ctx->gang->aff_ref_ctx = ctx;
440         }
441 }
442
443 static int
444 spufs_create_context(struct inode *inode, struct dentry *dentry,
445                         struct vfsmount *mnt, int flags, int mode,
446                         struct file *aff_filp)
447 {
448         int ret;
449         int affinity;
450         struct spu_gang *gang;
451         struct spu_context *neighbor;
452
453         ret = -EPERM;
454         if ((flags & SPU_CREATE_NOSCHED) &&
455             !capable(CAP_SYS_NICE))
456                 goto out_unlock;
457
458         ret = -EINVAL;
459         if ((flags & (SPU_CREATE_NOSCHED | SPU_CREATE_ISOLATE))
460             == SPU_CREATE_ISOLATE)
461                 goto out_unlock;
462
463         ret = -ENODEV;
464         if ((flags & SPU_CREATE_ISOLATE) && !isolated_loader)
465                 goto out_unlock;
466
467         gang = NULL;
468         neighbor = NULL;
469         affinity = flags & (SPU_CREATE_AFFINITY_MEM | SPU_CREATE_AFFINITY_SPU);
470         if (affinity) {
471                 gang = SPUFS_I(inode)->i_gang;
472                 ret = -EINVAL;
473                 if (!gang)
474                         goto out_unlock;
475                 mutex_lock(&gang->aff_mutex);
476                 neighbor = spufs_assert_affinity(flags, gang, aff_filp);
477                 if (IS_ERR(neighbor)) {
478                         ret = PTR_ERR(neighbor);
479                         goto out_aff_unlock;
480                 }
481         }
482
483         ret = spufs_mkdir(inode, dentry, flags, mode & S_IRWXUGO);
484         if (ret)
485                 goto out_aff_unlock;
486
487         if (affinity) {
488                 spufs_set_affinity(flags, SPUFS_I(dentry->d_inode)->i_ctx,
489                                                                 neighbor);
490                 if (neighbor)
491                         put_spu_context(neighbor);
492         }
493
494         /*
495          * get references for dget and mntget, will be released
496          * in error path of *_open().
497          */
498         ret = spufs_context_open(dget(dentry), mntget(mnt));
499         if (ret < 0) {
500                 WARN_ON(spufs_rmdir(inode, dentry));
501                 if (affinity)
502                         mutex_unlock(&gang->aff_mutex);
503                 mutex_unlock(&inode->i_mutex);
504                 spu_forget(SPUFS_I(dentry->d_inode)->i_ctx);
505                 goto out;
506         }
507
508 out_aff_unlock:
509         if (affinity)
510                 mutex_unlock(&gang->aff_mutex);
511 out_unlock:
512         mutex_unlock(&inode->i_mutex);
513 out:
514         dput(dentry);
515         return ret;
516 }
517
518 static int
519 spufs_mkgang(struct inode *dir, struct dentry *dentry, int mode)
520 {
521         int ret;
522         struct inode *inode;
523         struct spu_gang *gang;
524
525         ret = -ENOSPC;
526         inode = spufs_new_inode(dir->i_sb, mode | S_IFDIR);
527         if (!inode)
528                 goto out;
529
530         ret = 0;
531         if (dir->i_mode & S_ISGID) {
532                 inode->i_gid = dir->i_gid;
533                 inode->i_mode &= S_ISGID;
534         }
535         gang = alloc_spu_gang();
536         SPUFS_I(inode)->i_ctx = NULL;
537         SPUFS_I(inode)->i_gang = gang;
538         if (!gang)
539                 goto out_iput;
540
541         inode->i_op = &simple_dir_inode_operations;
542         inode->i_fop = &simple_dir_operations;
543
544         d_instantiate(dentry, inode);
545         inc_nlink(dir);
546         inc_nlink(dentry->d_inode);
547         return ret;
548
549 out_iput:
550         iput(inode);
551 out:
552         return ret;
553 }
554
555 static int spufs_gang_open(struct dentry *dentry, struct vfsmount *mnt)
556 {
557         int ret;
558         struct file *filp;
559
560         ret = get_unused_fd();
561         if (ret < 0) {
562                 dput(dentry);
563                 mntput(mnt);
564                 goto out;
565         }
566
567         filp = dentry_open(dentry, mnt, O_RDONLY, current_cred());
568         if (IS_ERR(filp)) {
569                 put_unused_fd(ret);
570                 ret = PTR_ERR(filp);
571                 goto out;
572         }
573
574         filp->f_op = &simple_dir_operations;
575         fd_install(ret, filp);
576 out:
577         return ret;
578 }
579
580 static int spufs_create_gang(struct inode *inode,
581                         struct dentry *dentry,
582                         struct vfsmount *mnt, int mode)
583 {
584         int ret;
585
586         ret = spufs_mkgang(inode, dentry, mode & S_IRWXUGO);
587         if (ret)
588                 goto out;
589
590         /*
591          * get references for dget and mntget, will be released
592          * in error path of *_open().
593          */
594         ret = spufs_gang_open(dget(dentry), mntget(mnt));
595         if (ret < 0) {
596                 int err = simple_rmdir(inode, dentry);
597                 WARN_ON(err);
598         }
599
600 out:
601         mutex_unlock(&inode->i_mutex);
602         dput(dentry);
603         return ret;
604 }
605
606
607 static struct file_system_type spufs_type;
608
609 long spufs_create(struct nameidata *nd, unsigned int flags, mode_t mode,
610                                                         struct file *filp)
611 {
612         struct dentry *dentry;
613         int ret;
614
615         ret = -EINVAL;
616         /* check if we are on spufs */
617         if (nd->path.dentry->d_sb->s_type != &spufs_type)
618                 goto out;
619
620         /* don't accept undefined flags */
621         if (flags & (~SPU_CREATE_FLAG_ALL))
622                 goto out;
623
624         /* only threads can be underneath a gang */
625         if (nd->path.dentry != nd->path.dentry->d_sb->s_root) {
626                 if ((flags & SPU_CREATE_GANG) ||
627                     !SPUFS_I(nd->path.dentry->d_inode)->i_gang)
628                         goto out;
629         }
630
631         dentry = lookup_create(nd, 1);
632         ret = PTR_ERR(dentry);
633         if (IS_ERR(dentry))
634                 goto out_dir;
635
636         mode &= ~current_umask();
637
638         if (flags & SPU_CREATE_GANG)
639                 ret = spufs_create_gang(nd->path.dentry->d_inode,
640                                          dentry, nd->path.mnt, mode);
641         else
642                 ret = spufs_create_context(nd->path.dentry->d_inode,
643                                             dentry, nd->path.mnt, flags, mode,
644                                             filp);
645         if (ret >= 0)
646                 fsnotify_mkdir(nd->path.dentry->d_inode, dentry);
647         return ret;
648
649 out_dir:
650         mutex_unlock(&nd->path.dentry->d_inode->i_mutex);
651 out:
652         return ret;
653 }
654
655 /* File system initialization */
656 enum {
657         Opt_uid, Opt_gid, Opt_mode, Opt_debug, Opt_err,
658 };
659
660 static const match_table_t spufs_tokens = {
661         { Opt_uid,   "uid=%d" },
662         { Opt_gid,   "gid=%d" },
663         { Opt_mode,  "mode=%o" },
664         { Opt_debug, "debug" },
665         { Opt_err,    NULL  },
666 };
667
668 static int
669 spufs_parse_options(struct super_block *sb, char *options, struct inode *root)
670 {
671         char *p;
672         substring_t args[MAX_OPT_ARGS];
673
674         while ((p = strsep(&options, ",")) != NULL) {
675                 int token, option;
676
677                 if (!*p)
678                         continue;
679
680                 token = match_token(p, spufs_tokens, args);
681                 switch (token) {
682                 case Opt_uid:
683                         if (match_int(&args[0], &option))
684                                 return 0;
685                         root->i_uid = option;
686                         break;
687                 case Opt_gid:
688                         if (match_int(&args[0], &option))
689                                 return 0;
690                         root->i_gid = option;
691                         break;
692                 case Opt_mode:
693                         if (match_octal(&args[0], &option))
694                                 return 0;
695                         root->i_mode = option | S_IFDIR;
696                         break;
697                 case Opt_debug:
698                         spufs_get_sb_info(sb)->debug = 1;
699                         break;
700                 default:
701                         return 0;
702                 }
703         }
704         return 1;
705 }
706
707 static void spufs_exit_isolated_loader(void)
708 {
709         free_pages((unsigned long) isolated_loader,
710                         get_order(isolated_loader_size));
711 }
712
713 static void
714 spufs_init_isolated_loader(void)
715 {
716         struct device_node *dn;
717         const char *loader;
718         int size;
719
720         dn = of_find_node_by_path("/spu-isolation");
721         if (!dn)
722                 return;
723
724         loader = of_get_property(dn, "loader", &size);
725         if (!loader)
726                 return;
727
728         /* the loader must be align on a 16 byte boundary */
729         isolated_loader = (char *)__get_free_pages(GFP_KERNEL, get_order(size));
730         if (!isolated_loader)
731                 return;
732
733         isolated_loader_size = size;
734         memcpy(isolated_loader, loader, size);
735         printk(KERN_INFO "spufs: SPU isolation mode enabled\n");
736 }
737
738 static int
739 spufs_create_root(struct super_block *sb, void *data)
740 {
741         struct inode *inode;
742         int ret;
743
744         ret = -ENODEV;
745         if (!spu_management_ops)
746                 goto out;
747
748         ret = -ENOMEM;
749         inode = spufs_new_inode(sb, S_IFDIR | 0775);
750         if (!inode)
751                 goto out;
752
753         inode->i_op = &simple_dir_inode_operations;
754         inode->i_fop = &simple_dir_operations;
755         SPUFS_I(inode)->i_ctx = NULL;
756         inc_nlink(inode);
757
758         ret = -EINVAL;
759         if (!spufs_parse_options(sb, data, inode))
760                 goto out_iput;
761
762         ret = -ENOMEM;
763         sb->s_root = d_alloc_root(inode);
764         if (!sb->s_root)
765                 goto out_iput;
766
767         return 0;
768 out_iput:
769         iput(inode);
770 out:
771         return ret;
772 }
773
774 static int
775 spufs_fill_super(struct super_block *sb, void *data, int silent)
776 {
777         struct spufs_sb_info *info;
778         static const struct super_operations s_ops = {
779                 .alloc_inode = spufs_alloc_inode,
780                 .destroy_inode = spufs_destroy_inode,
781                 .statfs = simple_statfs,
782                 .delete_inode = spufs_delete_inode,
783                 .drop_inode = generic_delete_inode,
784                 .show_options = generic_show_options,
785         };
786
787         save_mount_options(sb, data);
788
789         info = kzalloc(sizeof(*info), GFP_KERNEL);
790         if (!info)
791                 return -ENOMEM;
792
793         sb->s_maxbytes = MAX_LFS_FILESIZE;
794         sb->s_blocksize = PAGE_CACHE_SIZE;
795         sb->s_blocksize_bits = PAGE_CACHE_SHIFT;
796         sb->s_magic = SPUFS_MAGIC;
797         sb->s_op = &s_ops;
798         sb->s_fs_info = info;
799
800         return spufs_create_root(sb, data);
801 }
802
803 static int
804 spufs_get_sb(struct file_system_type *fstype, int flags,
805                 const char *name, void *data, struct vfsmount *mnt)
806 {
807         return get_sb_single(fstype, flags, data, spufs_fill_super, mnt);
808 }
809
810 static struct file_system_type spufs_type = {
811         .owner = THIS_MODULE,
812         .name = "spufs",
813         .get_sb = spufs_get_sb,
814         .kill_sb = kill_litter_super,
815 };
816
817 static int __init spufs_init(void)
818 {
819         int ret;
820
821         ret = -ENODEV;
822         if (!spu_management_ops)
823                 goto out;
824
825         ret = -ENOMEM;
826         spufs_inode_cache = kmem_cache_create("spufs_inode_cache",
827                         sizeof(struct spufs_inode_info), 0,
828                         SLAB_HWCACHE_ALIGN, spufs_init_once);
829
830         if (!spufs_inode_cache)
831                 goto out;
832         ret = spu_sched_init();
833         if (ret)
834                 goto out_cache;
835         ret = register_filesystem(&spufs_type);
836         if (ret)
837                 goto out_sched;
838         ret = register_spu_syscalls(&spufs_calls);
839         if (ret)
840                 goto out_fs;
841
842         spufs_init_isolated_loader();
843
844         return 0;
845
846 out_fs:
847         unregister_filesystem(&spufs_type);
848 out_sched:
849         spu_sched_exit();
850 out_cache:
851         kmem_cache_destroy(spufs_inode_cache);
852 out:
853         return ret;
854 }
855 module_init(spufs_init);
856
857 static void __exit spufs_exit(void)
858 {
859         spu_sched_exit();
860         spufs_exit_isolated_loader();
861         unregister_spu_syscalls(&spufs_calls);
862         unregister_filesystem(&spufs_type);
863         kmem_cache_destroy(spufs_inode_cache);
864 }
865 module_exit(spufs_exit);
866
867 MODULE_LICENSE("GPL");
868 MODULE_AUTHOR("Arnd Bergmann <arndb@de.ibm.com>");
869