From owner-freebsd-standards@FreeBSD.ORG Mon Jul 29 15:35:05 2013 Return-Path: Delivered-To: freebsd-standards@FreeBSD.org Received: from mx1.freebsd.org (mx1.freebsd.org [8.8.178.115]) (using TLSv1 with cipher ADH-AES256-SHA (256/256 bits)) (No client certificate requested) by hub.freebsd.org (Postfix) with ESMTP id BDF2F39E for ; Mon, 29 Jul 2013 15:35:05 +0000 (UTC) (envelope-from brde@optusnet.com.au) Received: from mail105.syd.optusnet.com.au (mail105.syd.optusnet.com.au [211.29.132.249]) by mx1.freebsd.org (Postfix) with ESMTP id 8257A2DCB for ; Mon, 29 Jul 2013 15:35:04 +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 mail105.syd.optusnet.com.au (Postfix) with ESMTPS id D3EE010414FC; Tue, 30 Jul 2013 01:35:00 +1000 (EST) Date: Tue, 30 Jul 2013 01:34:59 +1000 (EST) From: Bruce Evans X-X-Sender: bde@besplex.bde.org To: Konstantin Belousov Subject: Re: truncate and open(O_TRUNC) times. In-Reply-To: <20130729140654.GO4972@kib.kiev.ua> Message-ID: <20130730011126.V2176@besplex.bde.org> References: <51F5813D.2030806@rtems.org> <20130729191944.M928@besplex.bde.org> <20130729140654.GO4972@kib.kiev.ua> MIME-Version: 1.0 Content-Type: TEXT/PLAIN; charset=US-ASCII; format=flowed X-Optus-CM-Score: 0 X-Optus-CM-Analysis: v=2.1 cv=Yos2GeoX c=1 sm=1 tr=0 a=ebeQFi2P/qHVC0Yw9JDJ4g==:117 a=PO7r1zJSAAAA:8 a=CT-yo7tBpAMA:10 a=kj9zAlcOel0A:10 a=JzwRw_2MAAAA:8 a=X5dPMJUElLQA:10 a=fijM0vgTtP0wRJXSTmoA:9 a=CjuIK1q_8ugA:10 Cc: freebsd-standards@FreeBSD.org X-BeenThere: freebsd-standards@freebsd.org X-Mailman-Version: 2.1.14 Precedence: list List-Id: Standards compliance List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Mon, 29 Jul 2013 15:35:05 -0000 On Mon, 29 Jul 2013, Konstantin Belousov wrote: > On Mon, Jul 29, 2013 at 07:56:34PM +1000, Bruce Evans wrote: >> ... >> POSIX is weirdly different for truncate(). It only requires truncate() >> to change the times if it changed the size (this is not weird, but unusual), >> while it requires ftruncate() to change the times if it succeeded. >> ... >> FreeBSD can't possibly do this as weirdly as POSIX specifies, since >> it uses the same VOP_SETATTR() API to set the size for ftruncate() and >> truncate(), and this API doesn't say who made the call. Most file >> systems seem to force the setting of the times if successful. E.g., >> ffs_truncate() does nothing much except set the times if the size >> didn't change. > > vaattr.va_vaflags could grow a flag to indicate that VOP_SETATTR() > should only change times when size was changed. Indeed. I just checked some details for another bug involving [f]truncate() and the file size limit. They are specified to act the same (SIGFXSZ with no change in the file) above the limit, but for most file systems including ffs, neither checks. So the flag isn't needed to fix this bug. It is write() that acts differently. It is specified to write up to the limit and then return a short write with no SIGXFXSZ if the file pointer is initially before the limit; otherwise SIGFXSZ with no change to the file (or file times?). But for most file systems including ffs, write() fails with SIGFXSZ and no change in the file if the result of a full successful write would be above the limit. This is mostly a bug in POSIX. It makes short write()s possible for any write(), where users can easily arrange for foot shooting using their soft rlimit, but almost no applications understand short writes. Most file systems including ffs never produce short writes -- they back out of failing i/o's if possible, including for the similar ENOSPC error; when backing out is not possible, which is mainly for failing writes into the middle of files, they return -1 with no backing out; applications must assume that the region of the file written to by a failing write is indeterminate, but for writes at EOF this region is null after the backout. Bruce