On Saturday 22 April 2006 03:27, Vitaly Wool wrote: > thanks! However I meant the following situation: suppose we've > got 500k free, and we're trying to write a new version of 1M > file (i. e. rewrite the old one). How will the filesystem > handle this? I. e. will it refuse the write operation or grant > it? If latter, what will happen if a power failure happens in > the midst of the write (for instance, when 600k is written > already -- there's not enough space to hold both the old and > the new versions so how will the incomplete write be > reverted?) OTOH, if there's enough space to hold both the old > and the new versions, will the power pailure always be handled > by the filesystem in such a way that retains the integrity of > the file being written (i. e. either the old or the new > version). I hope it will, but still being sure is better than > thinking 'probably it will' :):) A lot of what happens when you do this will depends more on the UNIX/Posix filesystem calls than Yaffs. If you hold the new data in memory, and open the old file with O_TRUNC, then write out the update, then the old data is 'lost' from the filesystem on the open(2) call. This frees the storage, so it can be used to hold new data; but leaves you with a big window without data. Under the covers a large write is the same as a sequence of smaller writes, and Yaffs performs the write operation in chunk (nand-page) sized steps. An update that over-writes the existing file, without O_TRUNC, will replace the old chunks (nand-pages) with new ones, containing the updated data (one-by-one in a sequence). If Yaffs runs low on chunks, the garbage collector will erase a block that contained old data. This gets us to the question of 'reserve', and perhaps Charles can tell us how the reserve is managed. I can imagine getting into a corner, when performing an update such as this, where there is insufficient 'elbow' room for the garbage collector to free up a complete block. In which case, somewhere along the sequence of chunk/page writes, it will fail and return a partial write (large buffer) or a failed write (small buffer). Now you are left with new data at the start of the file and old data at the end. Perhaps this is OK for your application(?). On Unix, the semantics of rename(2) help solve this common problem. Write out the new data to a new file (requiring twice the NAND space in the process); close the old file; then rename new file to the name of the old file. If rename(2) fails to fully complete (due to powerdown for example), you either have two files, the old and the new; or you have the new, and the old one is found in lost+found (unless it had multiple links). If rename(2) succeeds, the new file takes the place of old, the old file is unlinked and its storage is released ready for the garbage collector to gobble up. The application will need to 'reopen' the new file. -imcd