3 .\" Copyright (c) 1996 Doug Rabson
5 .\" All rights reserved.
7 .\" This program is free software.
9 .\" Redistribution and use in source and binary forms, with or without
10 .\" modification, are permitted provided that the following conditions
12 .\" 1. Redistributions of source code must retain the above copyright
13 .\" notice, this list of conditions and the following disclaimer.
14 .\" 2. Redistributions in binary form must reproduce the above copyright
15 .\" notice, this list of conditions and the following disclaimer in the
16 .\" documentation and/or other materials provided with the distribution.
18 .\" THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY EXPRESS OR
19 .\" IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
20 .\" OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
21 .\" IN NO EVENT SHALL THE DEVELOPERS BE LIABLE FOR ANY DIRECT, INDIRECT,
22 .\" INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
23 .\" NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
24 .\" DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
25 .\" THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
26 .\" (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
27 .\" THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
37 .Nd read or write a file
43 .Fn VOP_READ "struct vnode *vp" "struct uio *uio" "int ioflag" "struct ucred *cred"
45 .Fn VOP_WRITE "struct vnode *vp" "struct uio *uio" "int ioflag" "struct ucred *cred"
47 These entry points read or write the contents of a file
50 .Bl -tag -width ioflag
54 the location of the data to be read or written
58 the credentials of the caller
63 argument is used to give directives and hints to the filesystem.
64 When attempting a read, the high 16 bits are used to provide a
65 read-ahead hint (in units of filesystem blocks) that the filesystem
66 should attempt. The low 16 bits are a bit mask which can contain
68 .Bl -tag -width IO_NODELOCKED
76 underlying node already locked
79 flag set in file table
81 data already in VMIO space
84 The file should be locked on entry and will still be locked on exit.
86 Zero is returned on success, otherwise an error code is returned.
90 vop_read(struct vnode *vp, struct uio *uio, int ioflag, struct ucred *cred)
95 long size, xfersize, blkoffset;
98 size = block size of filesystem;
100 for (error = 0, bp = NULL; uio->uio_resid > 0; bp = NULL) {
101 bytesinfile = size of file - uio->uio_offset;
102 if (bytesinfile <= 0)
105 lbn = uio->uio_offset / size;
106 blkoffset = uio->uio_offset - lbn * size;
108 xfersize = size - blkoffset;
109 if (uio->uio_resid < xfersize)
110 xfersize = uio->uio_resid;
111 if (bytesinfile < xfersize)
112 xfersize = bytesinfile;
114 error = bread(vp, lbn, size, NOCRED, &bp);
122 * We should only get non-zero b_resid when an I/O error
123 * has occurred, which should cause us to break above.
124 * However, if the short read did not cause an error,
125 * then we want to ensure that we do not uiomove bad
126 * or uninitialized data.
129 if (size < xfersize) {
135 error = uiomove((char *)bp->b_data + blkoffset, (int)xfersize, uio);
148 vop_write(struct vnode *vp, struct uio *uio, int ioflag, struct ucred *cred)
152 daddr_t lbn, nextlbn;
154 long size, resid, xfersize, blkoffset;
158 osize = size of file;
159 size = block size of filesystem;
160 resid = uio->uio_resid;
161 if (ioflag & IO_SYNC)
166 for (error = 0; uio->uio_resid > 0;) {
167 lbn = uio->uio_offset / size;
168 blkoffset = uio->uio_offset - lbn * size;
170 xfersize = size - blkoffset;
171 if (uio->uio_resid < xfersize)
172 xfersize = uio->uio_resid;
174 if (uio->uio_offset + xfersize > size of file)
175 vnode_pager_setsize(vp, uio->uio_offset + xfersize);
182 error = find_block_in_file(vp, lbn, blkoffset + xfersize,
187 if (uio->uio_offset + xfersize > size of file)
188 set size of file to uio->uio_offset + xfersize;
190 error = uiomove((char *)bp->b_data + blkoffset, (int) xfersize, uio);
191 /* XXX ufs does not check the error here. Why? */
193 if (ioflag & IO_VMIO)
194 bp->b_flags |= B_RELBUF; /* ??? */
196 if (ioflag & IO_SYNC)
198 else if (xfersize + blkoffset == size)
203 if (error || xfersize == 0)
208 if (ioflag & IO_UNIT) {
209 VOP_TRUNCATE(vp, osize, ioflag & IO_SYNC, cred, uio->uio_procp);
210 uio->uio_offset -= resid - uio->uio_resid;
211 uio->uio_resid = resid;
213 } else if (resid > uio->uio_resid && (ioflag & IO_SYNC)) {
215 error = VOP_UPDATE(vp, &tv, &tv, 1); /* XXX what does this do? */
224 An attempt was made to write a file that exceeds the process's file size
225 limit or the maximum file size.
227 The filesystem is full.
229 An append-only flag is set on the file, but the caller is attempting to
230 write before the current end of file.
236 This man page was written by