91bd05377c003251ae1adfb33d5174049824c3e9
[linux-2.6.git] / fs / nfs / file.c
1 /*
2  *  linux/fs/nfs/file.c
3  *
4  *  Copyright (C) 1992  Rick Sladkey
5  *
6  *  Changes Copyright (C) 1994 by Florian La Roche
7  *   - Do not copy data too often around in the kernel.
8  *   - In nfs_file_read the return value of kmalloc wasn't checked.
9  *   - Put in a better version of read look-ahead buffering. Original idea
10  *     and implementation by Wai S Kok elekokws@ee.nus.sg.
11  *
12  *  Expire cache on write to a file by Wai S Kok (Oct 1994).
13  *
14  *  Total rewrite of read side for new NFS buffer cache.. Linus.
15  *
16  *  nfs regular file handling functions
17  */
18
19 #include <linux/time.h>
20 #include <linux/kernel.h>
21 #include <linux/errno.h>
22 #include <linux/fcntl.h>
23 #include <linux/stat.h>
24 #include <linux/nfs_fs.h>
25 #include <linux/nfs_mount.h>
26 #include <linux/mm.h>
27 #include <linux/slab.h>
28 #include <linux/pagemap.h>
29 #include <linux/smp_lock.h>
30
31 #include <asm/uaccess.h>
32 #include <asm/system.h>
33
34 #define NFSDBG_FACILITY         NFSDBG_FILE
35
36 static int nfs_file_open(struct inode *, struct file *);
37 static int nfs_file_release(struct inode *, struct file *);
38 static int  nfs_file_mmap(struct file *, struct vm_area_struct *);
39 static ssize_t nfs_file_sendfile(struct file *, loff_t *, size_t, read_actor_t, void *);
40 static ssize_t nfs_file_read(struct kiocb *, char __user *, size_t, loff_t);
41 static ssize_t nfs_file_write(struct kiocb *, const char __user *, size_t, loff_t);
42 static int  nfs_file_flush(struct file *);
43 static int  nfs_fsync(struct file *, struct dentry *dentry, int datasync);
44 static int nfs_check_flags(int flags);
45
46 struct file_operations nfs_file_operations = {
47         .llseek         = remote_llseek,
48         .read           = do_sync_read,
49         .write          = do_sync_write,
50         .aio_read               = nfs_file_read,
51         .aio_write              = nfs_file_write,
52         .mmap           = nfs_file_mmap,
53         .open           = nfs_file_open,
54         .flush          = nfs_file_flush,
55         .release        = nfs_file_release,
56         .fsync          = nfs_fsync,
57         .lock           = nfs_lock,
58         .sendfile       = nfs_file_sendfile,
59         .check_flags    = nfs_check_flags,
60 };
61
62 struct inode_operations nfs_file_inode_operations = {
63         .permission     = nfs_permission,
64         .getattr        = nfs_getattr,
65         .setattr        = nfs_setattr,
66 };
67
68 /* Hack for future NFS swap support */
69 #ifndef IS_SWAPFILE
70 # define IS_SWAPFILE(inode)     (0)
71 #endif
72
73 static int nfs_check_flags(int flags)
74 {
75         if ((flags & (O_APPEND | O_DIRECT)) == (O_APPEND | O_DIRECT))
76                 return -EINVAL;
77
78         return 0;
79 }
80
81 /*
82  * Open file
83  */
84 static int
85 nfs_file_open(struct inode *inode, struct file *filp)
86 {
87         struct nfs_server *server = NFS_SERVER(inode);
88         int (*open)(struct inode *, struct file *);
89         int res;
90
91         res = nfs_check_flags(filp->f_flags);
92         if (res)
93                 return res;
94
95         lock_kernel();
96         /* Do NFSv4 open() call */
97         if ((open = server->rpc_ops->file_open) != NULL)
98                 res = open(inode, filp);
99         unlock_kernel();
100         return res;
101 }
102
103 static int
104 nfs_file_release(struct inode *inode, struct file *filp)
105 {
106         return NFS_PROTO(inode)->file_release(inode, filp);
107 }
108
109 /*
110  * Flush all dirty pages, and check for write errors.
111  *
112  */
113 static int
114 nfs_file_flush(struct file *file)
115 {
116         struct inode    *inode = file->f_dentry->d_inode;
117         int             status;
118
119         dfprintk(VFS, "nfs: flush(%s/%ld)\n", inode->i_sb->s_id, inode->i_ino);
120
121         if ((file->f_mode & FMODE_WRITE) == 0)
122                 return 0;
123         lock_kernel();
124         /* Ensure that data+attribute caches are up to date after close() */
125         status = nfs_wb_all(inode);
126         if (!status) {
127                 status = file->f_error;
128                 file->f_error = 0;
129                 if (!status)
130                         __nfs_revalidate_inode(NFS_SERVER(inode), inode);
131         }
132         unlock_kernel();
133         return status;
134 }
135
136 static ssize_t
137 nfs_file_read(struct kiocb *iocb, char __user * buf, size_t count, loff_t pos)
138 {
139         struct dentry * dentry = iocb->ki_filp->f_dentry;
140         struct inode * inode = dentry->d_inode;
141         ssize_t result;
142
143 #ifdef CONFIG_NFS_DIRECTIO
144         if (iocb->ki_filp->f_flags & O_DIRECT)
145                 return nfs_file_direct_read(iocb, buf, count, pos);
146 #endif
147
148         dfprintk(VFS, "nfs: read(%s/%s, %lu@%lu)\n",
149                 dentry->d_parent->d_name.name, dentry->d_name.name,
150                 (unsigned long) count, (unsigned long) pos);
151
152         result = nfs_revalidate_inode(NFS_SERVER(inode), inode);
153         if (!result)
154                 result = generic_file_aio_read(iocb, buf, count, pos);
155         return result;
156 }
157
158 static ssize_t
159 nfs_file_sendfile(struct file *f
160                         if (IS_GETLK(cmd))
161                                 status = LOCK_USE_CLNT;
162                         goto out_ok;
163                 }
164         }
165
166         /*
167          * No BSD flocks over NFS allowed.
168          * Note: we could try to fake a POSIX lock request here by
169          * using ((u32) filp | 0x80000000) or some such as the pid.
170          * Not sure whether that would be unique, though, or whether
171          * that would break in other places.
172          */
173         if (!fl->fl_owner || !(fl->fl_flags & FL_POSIX))
174                 return -ENOLCK;
175
176         /*
177          * Flush all pending writes before doing anything
178          * with locks..
179          */
180         status = filemap_fdatawrite(filp->f_mapping);
181         down(&inode->i_sem);
182         status2 = nfs_wb_all(inode);
183         if (!status)
184                 status = status2;
185         up(&inode->i_sem);
186         status2 = filemap_fdatawait(filp->f_mapping);
187         if (!status)
188                 status = status2;
189         if (status < 0)
190                 return status;
191
192         lock_kernel();
193         status = NFS_PROTO(inode)->lock(filp, cmd, fl);
194         unlock_kernel();
195         if (status < 0)
196                 return status;
197         
198         status = 0;
199
200         /*
201          * Make sure we clear the cache whenever we try to get the lock.
202          * This makes locking act as a cache coherency point.
203          */
204  out_ok:
205         if ((IS_SETLK(cmd) || IS_SETLKW(cmd)) && fl->fl_type != F_UNLCK) {
206                 filemap_fdatawrite(filp->f_mapping);
207                 down(&inode->i_sem);
208                 nfs_wb_all(inode);      /* we may have slept */
209                 up(&inode->i_sem);
210                 filemap_fdatawait(filp->f_mapping);
211                 nfs_zap_caches(inode);
212         }
213         return status;
214 }