[PATCH] FUSE: tighten check for processes allowed access
[safe/jmp/linux-2.6] / fs / fuse / dir.c
1 /*
2   FUSE: Filesystem in Userspace
3   Copyright (C) 2001-2005  Miklos Szeredi <miklos@szeredi.hu>
4
5   This program can be distributed under the terms of the GNU GPL.
6   See the file COPYING.
7 */
8
9 #include "fuse_i.h"
10
11 #include <linux/pagemap.h>
12 #include <linux/file.h>
13 #include <linux/gfp.h>
14 #include <linux/sched.h>
15 #include <linux/namei.h>
16
17 static inline unsigned long time_to_jiffies(unsigned long sec,
18                                             unsigned long nsec)
19 {
20         struct timespec ts = {sec, nsec};
21         return jiffies + timespec_to_jiffies(&ts);
22 }
23
24 static void fuse_lookup_init(struct fuse_req *req, struct inode *dir,
25                              struct dentry *entry,
26                              struct fuse_entry_out *outarg)
27 {
28         req->in.h.opcode = FUSE_LOOKUP;
29         req->in.h.nodeid = get_node_id(dir);
30         req->inode = dir;
31         req->in.numargs = 1;
32         req->in.args[0].size = entry->d_name.len + 1;
33         req->in.args[0].value = entry->d_name.name;
34         req->out.numargs = 1;
35         req->out.args[0].size = sizeof(struct fuse_entry_out);
36         req->out.args[0].value = outarg;
37 }
38
39 static int fuse_dentry_revalidate(struct dentry *entry, struct nameidata *nd)
40 {
41         if (!entry->d_inode || is_bad_inode(entry->d_inode))
42                 return 0;
43         else if (time_after(jiffies, entry->d_time)) {
44                 int err;
45                 struct fuse_entry_out outarg;
46                 struct inode *inode = entry->d_inode;
47                 struct fuse_inode *fi = get_fuse_inode(inode);
48                 struct fuse_conn *fc = get_fuse_conn(inode);
49                 struct fuse_req *req = fuse_get_request_nonint(fc);
50                 if (!req)
51                         return 0;
52
53                 fuse_lookup_init(req, entry->d_parent->d_inode, entry, &outarg);
54                 request_send_nonint(fc, req);
55                 err = req->out.h.error;
56                 if (!err) {
57                         if (outarg.nodeid != get_node_id(inode)) {
58                                 fuse_send_forget(fc, req, outarg.nodeid, 1);
59                                 return 0;
60                         }
61                         fi->nlookup ++;
62                 }
63                 fuse_put_request(fc, req);
64                 if (err || (outarg.attr.mode ^ inode->i_mode) & S_IFMT)
65                         return 0;
66
67                 fuse_change_attributes(inode, &outarg.attr);
68                 entry->d_time = time_to_jiffies(outarg.entry_valid,
69                                                 outarg.entry_valid_nsec);
70                 fi->i_time = time_to_jiffies(outarg.attr_valid,
71                                              outarg.attr_valid_nsec);
72         }
73         return 1;
74 }
75
76 static struct dentry_operations fuse_dentry_operations = {
77         .d_revalidate   = fuse_dentry_revalidate,
78 };
79
80 static int fuse_lookup_iget(struct inode *dir, struct dentry *entry,
81                             struct inode **inodep)
82 {
83         int err;
84         struct fuse_entry_out outarg;
85         struct inode *inode = NULL;
86         struct fuse_conn *fc = get_fuse_conn(dir);
87         struct fuse_req *req;
88
89         if (entry->d_name.len > FUSE_NAME_MAX)
90                 return -ENAMETOOLONG;
91
92         req = fuse_get_request(fc);
93         if (!req)
94                 return -ERESTARTNOINTR;
95
96         fuse_lookup_init(req, dir, entry, &outarg);
97         request_send(fc, req);
98         err = req->out.h.error;
99         if (!err) {
100                 inode = fuse_iget(dir->i_sb, outarg.nodeid, outarg.generation,
101                                   &outarg.attr);
102                 if (!inode) {
103                         fuse_send_forget(fc, req, outarg.nodeid, 1);
104                         return -ENOMEM;
105                 }
106         }
107         fuse_put_request(fc, req);
108         if (err && err != -ENOENT)
109                 return err;
110
111         if (inode) {
112                 struct fuse_inode *fi = get_fuse_inode(inode);
113                 entry->d_time = time_to_jiffies(outarg.entry_valid,
114                                                 outarg.entry_valid_nsec);
115                 fi->i_time = time_to_jiffies(outarg.attr_valid,
116                                              outarg.attr_valid_nsec);
117         }
118
119         entry->d_op = &fuse_dentry_operations;
120         *inodep = inode;
121         return 0;
122 }
123
124 void fuse_invalidate_attr(struct inode *inode)
125 {
126         get_fuse_inode(inode)->i_time = jiffies - 1;
127 }
128
129 static void fuse_invalidate_entry(struct dentry *entry)
130 {
131         d_invalidate(entry);
132         entry->d_time = jiffies - 1;
133 }
134
135 static int create_new_entry(struct fuse_conn *fc, struct fuse_req *req,
136                             struct inode *dir, struct dentry *entry,
137                             int mode)
138 {
139         struct fuse_entry_out outarg;
140         struct inode *inode;
141         struct fuse_inode *fi;
142         int err;
143
144         req->in.h.nodeid = get_node_id(dir);
145         req->inode = dir;
146         req->out.numargs = 1;
147         req->out.args[0].size = sizeof(outarg);
148         req->out.args[0].value = &outarg;
149         request_send(fc, req);
150         err = req->out.h.error;
151         if (err) {
152                 fuse_put_request(fc, req);
153                 return err;
154         }
155         inode = fuse_iget(dir->i_sb, outarg.nodeid, outarg.generation,
156                           &outarg.attr);
157         if (!inode) {
158                 fuse_send_forget(fc, req, outarg.nodeid, 1);
159                 return -ENOMEM;
160         }
161         fuse_put_request(fc, req);
162
163         /* Don't allow userspace to do really stupid things... */
164         if ((inode->i_mode ^ mode) & S_IFMT) {
165                 iput(inode);
166                 return -EIO;
167         }
168
169         entry->d_time = time_to_jiffies(outarg.entry_valid,
170                                         outarg.entry_valid_nsec);
171
172         fi = get_fuse_inode(inode);
173         fi->i_time = time_to_jiffies(outarg.attr_valid,
174                                      outarg.attr_valid_nsec);
175
176         d_instantiate(entry, inode);
177         fuse_invalidate_attr(dir);
178         return 0;
179 }
180
181 static int fuse_mknod(struct inode *dir, struct dentry *entry, int mode,
182                       dev_t rdev)
183 {
184         struct fuse_mknod_in inarg;
185         struct fuse_conn *fc = get_fuse_conn(dir);
186         struct fuse_req *req = fuse_get_request(fc);
187         if (!req)
188                 return -ERESTARTNOINTR;
189
190         memset(&inarg, 0, sizeof(inarg));
191         inarg.mode = mode;
192         inarg.rdev = new_encode_dev(rdev);
193         req->in.h.opcode = FUSE_MKNOD;
194         req->in.numargs = 2;
195         req->in.args[0].size = sizeof(inarg);
196         req->in.args[0].value = &inarg;
197         req->in.args[1].size = entry->d_name.len + 1;
198         req->in.args[1].value = entry->d_name.name;
199         return create_new_entry(fc, req, dir, entry, mode);
200 }
201
202 static int fuse_create(struct inode *dir, struct dentry *entry, int mode,
203                        struct nameidata *nd)
204 {
205         return fuse_mknod(dir, entry, mode, 0);
206 }
207
208 static int fuse_mkdir(struct inode *dir, struct dentry *entry, int mode)
209 {
210         struct fuse_mkdir_in inarg;
211         struct fuse_conn *fc = get_fuse_conn(dir);
212         struct fuse_req *req = fuse_get_request(fc);
213         if (!req)
214                 return -ERESTARTNOINTR;
215
216         memset(&inarg, 0, sizeof(inarg));
217         inarg.mode = mode;
218         req->in.h.opcode = FUSE_MKDIR;
219         req->in.numargs = 2;
220         req->in.args[0].size = sizeof(inarg);
221         req->in.args[0].value = &inarg;
222         req->in.args[1].size = entry->d_name.len + 1;
223         req->in.args[1].value = entry->d_name.name;
224         return create_new_entry(fc, req, dir, entry, S_IFDIR);
225 }
226
227 static int fuse_symlink(struct inode *dir, struct dentry *entry,
228                         const char *link)
229 {
230         struct fuse_conn *fc = get_fuse_conn(dir);
231         unsigned len = strlen(link) + 1;
232         struct fuse_req *req;
233
234         if (len > FUSE_SYMLINK_MAX)
235                 return -ENAMETOOLONG;
236
237         req = fuse_get_request(fc);
238         if (!req)
239                 return -ERESTARTNOINTR;
240
241         req->in.h.opcode = FUSE_SYMLINK;
242         req->in.numargs = 2;
243         req->in.args[0].size = entry->d_name.len + 1;
244         req->in.args[0].value = entry->d_name.name;
245         req->in.args[1].size = len;
246         req->in.args[1].value = link;
247         return create_new_entry(fc, req, dir, entry, S_IFLNK);
248 }
249
250 static int fuse_unlink(struct inode *dir, struct dentry *entry)
251 {
252         int err;
253         struct fuse_conn *fc = get_fuse_conn(dir);
254         struct fuse_req *req = fuse_get_request(fc);
255         if (!req)
256                 return -ERESTARTNOINTR;
257
258         req->in.h.opcode = FUSE_UNLINK;
259         req->in.h.nodeid = get_node_id(dir);
260         req->inode = dir;
261         req->in.numargs = 1;
262         req->in.args[0].size = entry->d_name.len + 1;
263         req->in.args[0].value = entry->d_name.name;
264         request_send(fc, req);
265         err = req->out.h.error;
266         fuse_put_request(fc, req);
267         if (!err) {
268                 struct inode *inode = entry->d_inode;
269
270                 /* Set nlink to zero so the inode can be cleared, if
271                    the inode does have more links this will be
272                    discovered at the next lookup/getattr */
273                 inode->i_nlink = 0;
274                 fuse_invalidate_attr(inode);
275                 fuse_invalidate_attr(dir);
276         } else if (err == -EINTR)
277                 fuse_invalidate_entry(entry);
278         return err;
279 }
280
281 static int fuse_rmdir(struct inode *dir, struct dentry *entry)
282 {
283         int err;
284         struct fuse_conn *fc = get_fuse_conn(dir);
285         struct fuse_req *req = fuse_get_request(fc);
286         if (!req)
287                 return -ERESTARTNOINTR;
288
289         req->in.h.opcode = FUSE_RMDIR;
290         req->in.h.nodeid = get_node_id(dir);
291         req->inode = dir;
292         req->in.numargs = 1;
293         req->in.args[0].size = entry->d_name.len + 1;
294         req->in.args[0].value = entry->d_name.name;
295         request_send(fc, req);
296         err = req->out.h.error;
297         fuse_put_request(fc, req);
298         if (!err) {
299                 entry->d_inode->i_nlink = 0;
300                 fuse_invalidate_attr(dir);
301         } else if (err == -EINTR)
302                 fuse_invalidate_entry(entry);
303         return err;
304 }
305
306 static int fuse_rename(struct inode *olddir, struct dentry *oldent,
307                        struct inode *newdir, struct dentry *newent)
308 {
309         int err;
310         struct fuse_rename_in inarg;
311         struct fuse_conn *fc = get_fuse_conn(olddir);
312         struct fuse_req *req = fuse_get_request(fc);
313         if (!req)
314                 return -ERESTARTNOINTR;
315
316         memset(&inarg, 0, sizeof(inarg));
317         inarg.newdir = get_node_id(newdir);
318         req->in.h.opcode = FUSE_RENAME;
319         req->in.h.nodeid = get_node_id(olddir);
320         req->inode = olddir;
321         req->inode2 = newdir;
322         req->in.numargs = 3;
323         req->in.args[0].size = sizeof(inarg);
324         req->in.args[0].value = &inarg;
325         req->in.args[1].size = oldent->d_name.len + 1;
326         req->in.args[1].value = oldent->d_name.name;
327         req->in.args[2].size = newent->d_name.len + 1;
328         req->in.args[2].value = newent->d_name.name;
329         request_send(fc, req);
330         err = req->out.h.error;
331         fuse_put_request(fc, req);
332         if (!err) {
333                 fuse_invalidate_attr(olddir);
334                 if (olddir != newdir)
335                         fuse_invalidate_attr(newdir);
336         } else if (err == -EINTR) {
337                 /* If request was interrupted, DEITY only knows if the
338                    rename actually took place.  If the invalidation
339                    fails (e.g. some process has CWD under the renamed
340                    directory), then there can be inconsistency between
341                    the dcache and the real filesystem.  Tough luck. */
342                 fuse_invalidate_entry(oldent);
343                 if (newent->d_inode)
344                         fuse_invalidate_entry(newent);
345         }
346
347         return err;
348 }
349
350 static int fuse_link(struct dentry *entry, struct inode *newdir,
351                      struct dentry *newent)
352 {
353         int err;
354         struct fuse_link_in inarg;
355         struct inode *inode = entry->d_inode;
356         struct fuse_conn *fc = get_fuse_conn(inode);
357         struct fuse_req *req = fuse_get_request(fc);
358         if (!req)
359                 return -ERESTARTNOINTR;
360
361         memset(&inarg, 0, sizeof(inarg));
362         inarg.oldnodeid = get_node_id(inode);
363         req->in.h.opcode = FUSE_LINK;
364         req->inode2 = inode;
365         req->in.numargs = 2;
366         req->in.args[0].size = sizeof(inarg);
367         req->in.args[0].value = &inarg;
368         req->in.args[1].size = newent->d_name.len + 1;
369         req->in.args[1].value = newent->d_name.name;
370         err = create_new_entry(fc, req, newdir, newent, inode->i_mode);
371         /* Contrary to "normal" filesystems it can happen that link
372            makes two "logical" inodes point to the same "physical"
373            inode.  We invalidate the attributes of the old one, so it
374            will reflect changes in the backing inode (link count,
375            etc.)
376         */
377         if (!err || err == -EINTR)
378                 fuse_invalidate_attr(inode);
379         return err;
380 }
381
382 int fuse_do_getattr(struct inode *inode)
383 {
384         int err;
385         struct fuse_attr_out arg;
386         struct fuse_conn *fc = get_fuse_conn(inode);
387         struct fuse_req *req = fuse_get_request(fc);
388         if (!req)
389                 return -ERESTARTNOINTR;
390
391         req->in.h.opcode = FUSE_GETATTR;
392         req->in.h.nodeid = get_node_id(inode);
393         req->inode = inode;
394         req->out.numargs = 1;
395         req->out.args[0].size = sizeof(arg);
396         req->out.args[0].value = &arg;
397         request_send(fc, req);
398         err = req->out.h.error;
399         fuse_put_request(fc, req);
400         if (!err) {
401                 if ((inode->i_mode ^ arg.attr.mode) & S_IFMT) {
402                         make_bad_inode(inode);
403                         err = -EIO;
404                 } else {
405                         struct fuse_inode *fi = get_fuse_inode(inode);
406                         fuse_change_attributes(inode, &arg.attr);
407                         fi->i_time = time_to_jiffies(arg.attr_valid,
408                                                      arg.attr_valid_nsec);
409                 }
410         }
411         return err;
412 }
413
414 /*
415  * Calling into a user-controlled filesystem gives the filesystem
416  * daemon ptrace-like capabilities over the requester process.  This
417  * means, that the filesystem daemon is able to record the exact
418  * filesystem operations performed, and can also control the behavior
419  * of the requester process in otherwise impossible ways.  For example
420  * it can delay the operation for arbitrary length of time allowing
421  * DoS against the requester.
422  *
423  * For this reason only those processes can call into the filesystem,
424  * for which the owner of the mount has ptrace privilege.  This
425  * excludes processes started by other users, suid or sgid processes.
426  */
427 static int fuse_allow_task(struct fuse_conn *fc, struct task_struct *task)
428 {
429         if (fc->flags & FUSE_ALLOW_OTHER)
430                 return 1;
431
432         if (task->euid == fc->user_id &&
433             task->suid == fc->user_id &&
434             task->uid == fc->user_id &&
435             task->egid == fc->group_id &&
436             task->sgid == fc->group_id &&
437             task->gid == fc->group_id)
438                 return 1;
439
440         return 0;
441 }
442
443 static int fuse_revalidate(struct dentry *entry)
444 {
445         struct inode *inode = entry->d_inode;
446         struct fuse_inode *fi = get_fuse_inode(inode);
447         struct fuse_conn *fc = get_fuse_conn(inode);
448
449         if (!fuse_allow_task(fc, current))
450                 return -EACCES;
451         if (get_node_id(inode) != FUSE_ROOT_ID &&
452             time_before_eq(jiffies, fi->i_time))
453                 return 0;
454
455         return fuse_do_getattr(inode);
456 }
457
458 static int fuse_permission(struct inode *inode, int mask, struct nameidata *nd)
459 {
460         struct fuse_conn *fc = get_fuse_conn(inode);
461
462         if (!fuse_allow_task(fc, current))
463                 return -EACCES;
464         else if (fc->flags & FUSE_DEFAULT_PERMISSIONS) {
465                 int err = generic_permission(inode, mask, NULL);
466
467                 /* If permission is denied, try to refresh file
468                    attributes.  This is also needed, because the root
469                    node will at first have no permissions */
470                 if (err == -EACCES) {
471                         err = fuse_do_getattr(inode);
472                         if (!err)
473                                 err = generic_permission(inode, mask, NULL);
474                 }
475
476                 /* FIXME: Need some mechanism to revoke permissions:
477                    currently if the filesystem suddenly changes the
478                    file mode, we will not be informed about it, and
479                    continue to allow access to the file/directory.
480
481                    This is actually not so grave, since the user can
482                    simply keep access to the file/directory anyway by
483                    keeping it open... */
484
485                 return err;
486         } else {
487                 int mode = inode->i_mode;
488                 if ((mask & MAY_WRITE) && IS_RDONLY(inode) &&
489                     (S_ISREG(mode) || S_ISDIR(mode) || S_ISLNK(mode)))
490                         return -EROFS;
491                 if ((mask & MAY_EXEC) && !S_ISDIR(mode) && !(mode & S_IXUGO))
492                         return -EACCES;
493                 return 0;
494         }
495 }
496
497 static int parse_dirfile(char *buf, size_t nbytes, struct file *file,
498                          void *dstbuf, filldir_t filldir)
499 {
500         while (nbytes >= FUSE_NAME_OFFSET) {
501                 struct fuse_dirent *dirent = (struct fuse_dirent *) buf;
502                 size_t reclen = FUSE_DIRENT_SIZE(dirent);
503                 int over;
504                 if (!dirent->namelen || dirent->namelen > FUSE_NAME_MAX)
505                         return -EIO;
506                 if (reclen > nbytes)
507                         break;
508
509                 over = filldir(dstbuf, dirent->name, dirent->namelen,
510                                file->f_pos, dirent->ino, dirent->type);
511                 if (over)
512                         break;
513
514                 buf += reclen;
515                 nbytes -= reclen;
516                 file->f_pos = dirent->off;
517         }
518
519         return 0;
520 }
521
522 static int fuse_checkdir(struct file *cfile, struct file *file)
523 {
524         struct inode *inode;
525         if (!cfile)
526                 return -EIO;
527         inode = cfile->f_dentry->d_inode;
528         if (!S_ISREG(inode->i_mode)) {
529                 fput(cfile);
530                 return -EIO;
531         }
532
533         file->private_data = cfile;
534         return 0;
535 }
536
537 static int fuse_getdir(struct file *file)
538 {
539         struct inode *inode = file->f_dentry->d_inode;
540         struct fuse_conn *fc = get_fuse_conn(inode);
541         struct fuse_req *req = fuse_get_request(fc);
542         struct fuse_getdir_out_i outarg;
543         int err;
544
545         if (!req)
546                 return -ERESTARTNOINTR;
547
548         req->in.h.opcode = FUSE_GETDIR;
549         req->in.h.nodeid = get_node_id(inode);
550         req->inode = inode;
551         req->out.numargs = 1;
552         req->out.args[0].size = sizeof(struct fuse_getdir_out);
553         req->out.args[0].value = &outarg;
554         request_send(fc, req);
555         err = req->out.h.error;
556         fuse_put_request(fc, req);
557         if (!err)
558                 err = fuse_checkdir(outarg.file, file);
559         return err;
560 }
561
562 static int fuse_readdir(struct file *file, void *dstbuf, filldir_t filldir)
563 {
564         struct file *cfile = file->private_data;
565         char *buf;
566         int ret;
567
568         if (!cfile) {
569                 ret = fuse_getdir(file);
570                 if (ret)
571                         return ret;
572
573                 cfile = file->private_data;
574         }
575
576         buf = (char *) __get_free_page(GFP_KERNEL);
577         if (!buf)
578                 return -ENOMEM;
579
580         ret = kernel_read(cfile, file->f_pos, buf, PAGE_SIZE);
581         if (ret > 0)
582                 ret = parse_dirfile(buf, ret, file, dstbuf, filldir);
583
584         free_page((unsigned long) buf);
585         return ret;
586 }
587
588 static char *read_link(struct dentry *dentry)
589 {
590         struct inode *inode = dentry->d_inode;
591         struct fuse_conn *fc = get_fuse_conn(inode);
592         struct fuse_req *req = fuse_get_request(fc);
593         char *link;
594
595         if (!req)
596                 return ERR_PTR(-ERESTARTNOINTR);
597
598         link = (char *) __get_free_page(GFP_KERNEL);
599         if (!link) {
600                 link = ERR_PTR(-ENOMEM);
601                 goto out;
602         }
603         req->in.h.opcode = FUSE_READLINK;
604         req->in.h.nodeid = get_node_id(inode);
605         req->inode = inode;
606         req->out.argvar = 1;
607         req->out.numargs = 1;
608         req->out.args[0].size = PAGE_SIZE - 1;
609         req->out.args[0].value = link;
610         request_send(fc, req);
611         if (req->out.h.error) {
612                 free_page((unsigned long) link);
613                 link = ERR_PTR(req->out.h.error);
614         } else
615                 link[req->out.args[0].size] = '\0';
616  out:
617         fuse_put_request(fc, req);
618         return link;
619 }
620
621 static void free_link(char *link)
622 {
623         if (!IS_ERR(link))
624                 free_page((unsigned long) link);
625 }
626
627 static void *fuse_follow_link(struct dentry *dentry, struct nameidata *nd)
628 {
629         nd_set_link(nd, read_link(dentry));
630         return NULL;
631 }
632
633 static void fuse_put_link(struct dentry *dentry, struct nameidata *nd, void *c)
634 {
635         free_link(nd_get_link(nd));
636 }
637
638 static int fuse_dir_open(struct inode *inode, struct file *file)
639 {
640         file->private_data = NULL;
641         return 0;
642 }
643
644 static int fuse_dir_release(struct inode *inode, struct file *file)
645 {
646         struct file *cfile = file->private_data;
647
648         if (cfile)
649                 fput(cfile);
650
651         return 0;
652 }
653
654 static unsigned iattr_to_fattr(struct iattr *iattr, struct fuse_attr *fattr)
655 {
656         unsigned ivalid = iattr->ia_valid;
657         unsigned fvalid = 0;
658
659         memset(fattr, 0, sizeof(*fattr));
660
661         if (ivalid & ATTR_MODE)
662                 fvalid |= FATTR_MODE,   fattr->mode = iattr->ia_mode;
663         if (ivalid & ATTR_UID)
664                 fvalid |= FATTR_UID,    fattr->uid = iattr->ia_uid;
665         if (ivalid & ATTR_GID)
666                 fvalid |= FATTR_GID,    fattr->gid = iattr->ia_gid;
667         if (ivalid & ATTR_SIZE)
668                 fvalid |= FATTR_SIZE,   fattr->size = iattr->ia_size;
669         /* You can only _set_ these together (they may change by themselves) */
670         if ((ivalid & (ATTR_ATIME | ATTR_MTIME)) == (ATTR_ATIME | ATTR_MTIME)) {
671                 fvalid |= FATTR_ATIME | FATTR_MTIME;
672                 fattr->atime = iattr->ia_atime.tv_sec;
673                 fattr->mtime = iattr->ia_mtime.tv_sec;
674         }
675
676         return fvalid;
677 }
678
679 static int fuse_setattr(struct dentry *entry, struct iattr *attr)
680 {
681         struct inode *inode = entry->d_inode;
682         struct fuse_conn *fc = get_fuse_conn(inode);
683         struct fuse_inode *fi = get_fuse_inode(inode);
684         struct fuse_req *req;
685         struct fuse_setattr_in inarg;
686         struct fuse_attr_out outarg;
687         int err;
688         int is_truncate = 0;
689
690         if (fc->flags & FUSE_DEFAULT_PERMISSIONS) {
691                 err = inode_change_ok(inode, attr);
692                 if (err)
693                         return err;
694         }
695
696         if (attr->ia_valid & ATTR_SIZE) {
697                 unsigned long limit;
698                 is_truncate = 1;
699                 limit = current->signal->rlim[RLIMIT_FSIZE].rlim_cur;
700                 if (limit != RLIM_INFINITY && attr->ia_size > (loff_t) limit) {
701                         send_sig(SIGXFSZ, current, 0);
702                         return -EFBIG;
703                 }
704         }
705
706         req = fuse_get_request(fc);
707         if (!req)
708                 return -ERESTARTNOINTR;
709
710         memset(&inarg, 0, sizeof(inarg));
711         inarg.valid = iattr_to_fattr(attr, &inarg.attr);
712         req->in.h.opcode = FUSE_SETATTR;
713         req->in.h.nodeid = get_node_id(inode);
714         req->inode = inode;
715         req->in.numargs = 1;
716         req->in.args[0].size = sizeof(inarg);
717         req->in.args[0].value = &inarg;
718         req->out.numargs = 1;
719         req->out.args[0].size = sizeof(outarg);
720         req->out.args[0].value = &outarg;
721         request_send(fc, req);
722         err = req->out.h.error;
723         fuse_put_request(fc, req);
724         if (!err) {
725                 if ((inode->i_mode ^ outarg.attr.mode) & S_IFMT) {
726                         make_bad_inode(inode);
727                         err = -EIO;
728                 } else {
729                         if (is_truncate) {
730                                 loff_t origsize = i_size_read(inode);
731                                 i_size_write(inode, outarg.attr.size);
732                                 if (origsize > outarg.attr.size)
733                                         vmtruncate(inode, outarg.attr.size);
734                         }
735                         fuse_change_attributes(inode, &outarg.attr);
736                         fi->i_time = time_to_jiffies(outarg.attr_valid,
737                                                      outarg.attr_valid_nsec);
738                 }
739         } else if (err == -EINTR)
740                 fuse_invalidate_attr(inode);
741
742         return err;
743 }
744
745 static int fuse_getattr(struct vfsmount *mnt, struct dentry *entry,
746                         struct kstat *stat)
747 {
748         struct inode *inode = entry->d_inode;
749         int err = fuse_revalidate(entry);
750         if (!err)
751                 generic_fillattr(inode, stat);
752
753         return err;
754 }
755
756 static struct dentry *fuse_lookup(struct inode *dir, struct dentry *entry,
757                                   struct nameidata *nd)
758 {
759         struct inode *inode;
760         int err = fuse_lookup_iget(dir, entry, &inode);
761         if (err)
762                 return ERR_PTR(err);
763         if (inode && S_ISDIR(inode->i_mode)) {
764                 /* Don't allow creating an alias to a directory  */
765                 struct dentry *alias = d_find_alias(inode);
766                 if (alias && !(alias->d_flags & DCACHE_DISCONNECTED)) {
767                         dput(alias);
768                         iput(inode);
769                         return ERR_PTR(-EIO);
770                 }
771         }
772         return d_splice_alias(inode, entry);
773 }
774
775 static int fuse_setxattr(struct dentry *entry, const char *name,
776                          const void *value, size_t size, int flags)
777 {
778         struct inode *inode = entry->d_inode;
779         struct fuse_conn *fc = get_fuse_conn(inode);
780         struct fuse_req *req;
781         struct fuse_setxattr_in inarg;
782         int err;
783
784         if (size > FUSE_XATTR_SIZE_MAX)
785                 return -E2BIG;
786
787         if (fc->no_setxattr)
788                 return -EOPNOTSUPP;
789
790         req = fuse_get_request(fc);
791         if (!req)
792                 return -ERESTARTNOINTR;
793
794         memset(&inarg, 0, sizeof(inarg));
795         inarg.size = size;
796         inarg.flags = flags;
797         req->in.h.opcode = FUSE_SETXATTR;
798         req->in.h.nodeid = get_node_id(inode);
799         req->inode = inode;
800         req->in.numargs = 3;
801         req->in.args[0].size = sizeof(inarg);
802         req->in.args[0].value = &inarg;
803         req->in.args[1].size = strlen(name) + 1;
804         req->in.args[1].value = name;
805         req->in.args[2].size = size;
806         req->in.args[2].value = value;
807         request_send(fc, req);
808         err = req->out.h.error;
809         fuse_put_request(fc, req);
810         if (err == -ENOSYS) {
811                 fc->no_setxattr = 1;
812                 err = -EOPNOTSUPP;
813         }
814         return err;
815 }
816
817 static ssize_t fuse_getxattr(struct dentry *entry, const char *name,
818                              void *value, size_t size)
819 {
820         struct inode *inode = entry->d_inode;
821         struct fuse_conn *fc = get_fuse_conn(inode);
822         struct fuse_req *req;
823         struct fuse_getxattr_in inarg;
824         struct fuse_getxattr_out outarg;
825         ssize_t ret;
826
827         if (fc->no_getxattr)
828                 return -EOPNOTSUPP;
829
830         req = fuse_get_request(fc);
831         if (!req)
832                 return -ERESTARTNOINTR;
833
834         memset(&inarg, 0, sizeof(inarg));
835         inarg.size = size;
836         req->in.h.opcode = FUSE_GETXATTR;
837         req->in.h.nodeid = get_node_id(inode);
838         req->inode = inode;
839         req->in.numargs = 2;
840         req->in.args[0].size = sizeof(inarg);
841         req->in.args[0].value = &inarg;
842         req->in.args[1].size = strlen(name) + 1;
843         req->in.args[1].value = name;
844         /* This is really two different operations rolled into one */
845         req->out.numargs = 1;
846         if (size) {
847                 req->out.argvar = 1;
848                 req->out.args[0].size = size;
849                 req->out.args[0].value = value;
850         } else {
851                 req->out.args[0].size = sizeof(outarg);
852                 req->out.args[0].value = &outarg;
853         }
854         request_send(fc, req);
855         ret = req->out.h.error;
856         if (!ret)
857                 ret = size ? req->out.args[0].size : outarg.size;
858         else {
859                 if (ret == -ENOSYS) {
860                         fc->no_getxattr = 1;
861                         ret = -EOPNOTSUPP;
862                 }
863         }
864         fuse_put_request(fc, req);
865         return ret;
866 }
867
868 static ssize_t fuse_listxattr(struct dentry *entry, char *list, size_t size)
869 {
870         struct inode *inode = entry->d_inode;
871         struct fuse_conn *fc = get_fuse_conn(inode);
872         struct fuse_req *req;
873         struct fuse_getxattr_in inarg;
874         struct fuse_getxattr_out outarg;
875         ssize_t ret;
876
877         if (fc->no_listxattr)
878                 return -EOPNOTSUPP;
879
880         req = fuse_get_request(fc);
881         if (!req)
882                 return -ERESTARTNOINTR;
883
884         memset(&inarg, 0, sizeof(inarg));
885         inarg.size = size;
886         req->in.h.opcode = FUSE_LISTXATTR;
887         req->in.h.nodeid = get_node_id(inode);
888         req->inode = inode;
889         req->in.numargs = 1;
890         req->in.args[0].size = sizeof(inarg);
891         req->in.args[0].value = &inarg;
892         /* This is really two different operations rolled into one */
893         req->out.numargs = 1;
894         if (size) {
895                 req->out.argvar = 1;
896                 req->out.args[0].size = size;
897                 req->out.args[0].value = list;
898         } else {
899                 req->out.args[0].size = sizeof(outarg);
900                 req->out.args[0].value = &outarg;
901         }
902         request_send(fc, req);
903         ret = req->out.h.error;
904         if (!ret)
905                 ret = size ? req->out.args[0].size : outarg.size;
906         else {
907                 if (ret == -ENOSYS) {
908                         fc->no_listxattr = 1;
909                         ret = -EOPNOTSUPP;
910                 }
911         }
912         fuse_put_request(fc, req);
913         return ret;
914 }
915
916 static int fuse_removexattr(struct dentry *entry, const char *name)
917 {
918         struct inode *inode = entry->d_inode;
919         struct fuse_conn *fc = get_fuse_conn(inode);
920         struct fuse_req *req;
921         int err;
922
923         if (fc->no_removexattr)
924                 return -EOPNOTSUPP;
925
926         req = fuse_get_request(fc);
927         if (!req)
928                 return -ERESTARTNOINTR;
929
930         req->in.h.opcode = FUSE_REMOVEXATTR;
931         req->in.h.nodeid = get_node_id(inode);
932         req->inode = inode;
933         req->in.numargs = 1;
934         req->in.args[0].size = strlen(name) + 1;
935         req->in.args[0].value = name;
936         request_send(fc, req);
937         err = req->out.h.error;
938         fuse_put_request(fc, req);
939         if (err == -ENOSYS) {
940                 fc->no_removexattr = 1;
941                 err = -EOPNOTSUPP;
942         }
943         return err;
944 }
945
946 static struct inode_operations fuse_dir_inode_operations = {
947         .lookup         = fuse_lookup,
948         .mkdir          = fuse_mkdir,
949         .symlink        = fuse_symlink,
950         .unlink         = fuse_unlink,
951         .rmdir          = fuse_rmdir,
952         .rename         = fuse_rename,
953         .link           = fuse_link,
954         .setattr        = fuse_setattr,
955         .create         = fuse_create,
956         .mknod          = fuse_mknod,
957         .permission     = fuse_permission,
958         .getattr        = fuse_getattr,
959         .setxattr       = fuse_setxattr,
960         .getxattr       = fuse_getxattr,
961         .listxattr      = fuse_listxattr,
962         .removexattr    = fuse_removexattr,
963 };
964
965 static struct file_operations fuse_dir_operations = {
966         .llseek         = generic_file_llseek,
967         .read           = generic_read_dir,
968         .readdir        = fuse_readdir,
969         .open           = fuse_dir_open,
970         .release        = fuse_dir_release,
971 };
972
973 static struct inode_operations fuse_common_inode_operations = {
974         .setattr        = fuse_setattr,
975         .permission     = fuse_permission,
976         .getattr        = fuse_getattr,
977         .setxattr       = fuse_setxattr,
978         .getxattr       = fuse_getxattr,
979         .listxattr      = fuse_listxattr,
980         .removexattr    = fuse_removexattr,
981 };
982
983 static struct inode_operations fuse_symlink_inode_operations = {
984         .setattr        = fuse_setattr,
985         .follow_link    = fuse_follow_link,
986         .put_link       = fuse_put_link,
987         .readlink       = generic_readlink,
988         .getattr        = fuse_getattr,
989         .setxattr       = fuse_setxattr,
990         .getxattr       = fuse_getxattr,
991         .listxattr      = fuse_listxattr,
992         .removexattr    = fuse_removexattr,
993 };
994
995 void fuse_init_common(struct inode *inode)
996 {
997         inode->i_op = &fuse_common_inode_operations;
998 }
999
1000 void fuse_init_dir(struct inode *inode)
1001 {
1002         inode->i_op = &fuse_dir_inode_operations;
1003         inode->i_fop = &fuse_dir_operations;
1004 }
1005
1006 void fuse_init_symlink(struct inode *inode)
1007 {
1008         inode->i_op = &fuse_symlink_inode_operations;
1009 }