From owner-svn-src-head@FreeBSD.ORG Tue Jul 9 05:39:37 2013 Return-Path: Delivered-To: svn-src-head@freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2001:1900:2254:206a::19:1]) by hub.freebsd.org (Postfix) with ESMTP id C4044DB6; Tue, 9 Jul 2013 05:39:37 +0000 (UTC) (envelope-from brde@optusnet.com.au) Received: from mail110.syd.optusnet.com.au (mail110.syd.optusnet.com.au [211.29.132.97]) by mx1.freebsd.org (Postfix) with ESMTP id 72BED18E6; Tue, 9 Jul 2013 05:39:37 +0000 (UTC) Received: from c122-106-156-23.carlnfd1.nsw.optusnet.com.au (c122-106-156-23.carlnfd1.nsw.optusnet.com.au [122.106.156.23]) by mail110.syd.optusnet.com.au (Postfix) with ESMTPS id 16B6978104C; Tue, 9 Jul 2013 15:39:30 +1000 (EST) Date: Tue, 9 Jul 2013 15:39:29 +1000 (EST) From: Bruce Evans X-X-Sender: bde@besplex.bde.org To: "Pedro F. Giffuni" Subject: Re: svn commit: r253050 - head/sys/fs/ext2fs In-Reply-To: <201307090131.r691V4wJ090149@svn.freebsd.org> Message-ID: <20130709153911.R1312@besplex.bde.org> References: <201307090131.r691V4wJ090149@svn.freebsd.org> MIME-Version: 1.0 Content-Type: TEXT/PLAIN; charset=US-ASCII; format=flowed X-Optus-CM-Score: 0 X-Optus-CM-Analysis: v=2.0 cv=eqSHVfVX c=1 sm=1 a=90iWynEP2-8A:10 a=kj9zAlcOel0A:10 a=PO7r1zJSAAAA:8 a=JzwRw_2MAAAA:8 a=AD96D3NyImQA:10 a=6I5d2MoRAAAA:8 a=KuIX9Q-2l-uLVCl-5lUA:9 a=CjuIK1q_8ugA:10 a=ebeQFi2P/qHVC0Yw9JDJ4g==:117 Cc: svn-src-head@freebsd.org, svn-src-all@freebsd.org, src-committers@freebsd.org X-BeenThere: svn-src-head@freebsd.org X-Mailman-Version: 2.1.14 Precedence: list List-Id: SVN commit messages for the src tree for head/-current List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Tue, 09 Jul 2013 05:39:37 -0000 On Tue, 9 Jul 2013, Pedro F. Giffuni wrote: > Author: pfg > Date: Tue Jul 9 01:31:04 2013 > New Revision: 253050 > URL: http://svnweb.freebsd.org/changeset/base/253050 > > Log: > Enhancement when writing an entire block of a file. > > Merge from UFS r231313: > > This change first attempts the uiomove() to the newly allocated > (and dirty) buffer and only zeros it if the uiomove() fails. The > effect is to eliminate the gratuitous zeroing of the buffer in > the usual case where the uiomove() successfully fills it. > > MFC after: 3 days > > Modified: > head/sys/fs/ext2fs/ext2_vnops.c > > Modified: head/sys/fs/ext2fs/ext2_vnops.c > ============================================================================== > --- head/sys/fs/ext2fs/ext2_vnops.c Tue Jul 9 01:05:28 2013 (r253049) > +++ head/sys/fs/ext2fs/ext2_vnops.c Tue Jul 9 01:31:04 2013 (r253050) > @@ -1812,15 +1812,6 @@ ext2_write(struct vop_write_args *ap) > if (error != 0) > break; > > - /* > - * If the buffer is not valid and we did not clear garbage > - * out above, we have to do so here even though the write > - * covers the entire buffer in order to avoid a mmap()/write > - * race where another process may see the garbage prior to > - * the uiomove() for a write replacing it. > - */ > - if ((bp->b_flags & B_CACHE) == 0 && fs->e2fs_bsize <= xfersize) > - vfs_bio_clrbuf(bp); > if ((ioflag & (IO_SYNC|IO_INVAL)) == (IO_SYNC|IO_INVAL)) > bp->b_flags |= B_NOCACHE; > if (uio->uio_offset + xfersize > ip->i_size) > @@ -1831,6 +1822,26 @@ ext2_write(struct vop_write_args *ap) > > error = > uiomove((char *)bp->b_data + blkoffset, (int)xfersize, uio); > + /* > + * If the buffer is not already filled and we encounter an > + * error while trying to fill it, we have to clear out any > + * garbage data from the pages instantiated for the buffer. > + * If we do not, a failed uiomove() during a write can leave > + * the prior contents of the pages exposed to a userland mmap. > + * > + * Note that we need only clear buffers with a transfer size > + * equal to the block size because buffers with a shorter > + * transfer size were cleared above by the call to ext2_balloc() > + * with the BA_CLRBUF flag set. > + * > + * If the source region for uiomove identically mmaps the > + * buffer, uiomove() performed the NOP copy, and the buffer > + * content remains valid because the page fault handler > + * validated the pages. > + */ > + if (error != 0 && (bp->b_flags & B_CACHE) == 0 && > + fs->e2fs_bsize == xfersize) > + vfs_bio_clrbuf(bp); > if (ioflag & (IO_VMIO|IO_DIRECT)) { > bp->b_flags |= B_RELBUF; > } >