From: Mark Fasheh <mark.fasheh@oracle.com>
To: Nick Piggin <nickpiggin@yahoo.com.au>
Cc: Linux Memory Management <linux-mm@kvack.org>,
linux-fsdevel@vger.kernel.org,
linux-kernel <linux-kernel@vger.kernel.org>,
OGAWA Hirofumi <hirofumi@mail.parknet.co.jp>,
Andrew Morton <akpm@google.com>
Subject: Re: Status of buffered write path (deadlock fixes)
Date: Fri, 8 Dec 2006 15:48:52 -0800 [thread overview]
Message-ID: <20061208234852.GI4497@ca-server1.us.oracle.com> (raw)
In-Reply-To: <4578DBCA.30604@yahoo.com.au>
On Fri, Dec 08, 2006 at 02:28:10PM +1100, Nick Piggin wrote:
> >In generic_file_buffered_write() we now do:
> >
> > status = a_ops->commit_write(file, page, offset,offset+copied);
> >
> >Which tells the file system to commit only the amount of data that
> >filemap_copy_from_user() was able to pull in, despite our zeroing of
> >the newly allocated buffers in the copied != bytes case. Shouldn't we be
> >doing:
> >
> > status = a_ops->commit_write(file, page, offset,offset+bytes);
> >
> >instead, thus preserving ordered writeout (for ext3, ocfs2, etc) for those
> >parts of the page which are properly allocated and zero'd but haven't been
> >copied into yet? I think that in the case of a crash just after the
> >transaction is closed in ->commit_write(), we might lose those guarantees,
> >exposing stale data on disk.
>
> No, because we might be talking about buffers that haven't been newly
> allocated, but are not uptodate (so the pagecache can contain junk).
>
> We can't zero these guys and do the commit_write, because that exposes
> transient zeroes to a concurrent reader.
Ahh ok - zeroing would populate with incorrect data and we can't write those
buffers because we'd write junk over good data.
And of course, the way it works right now will break ordered write mode.
Sigh.
> What we *could* do, is to do the full length commit_write for uptodate
> pages, even if the copy is short. But we still need to do a zero-length
> commit_write if the page is not uptodate (this would reduce the number
> of new cases that need to be considered).
>
> Does a short commit_write cause a problem for filesystems? They can
> still do any and all operations they would have with a full-length one.
If they've done allocation, yes. You're telling the file system to stop
early in the page, even though there may be BH_New buffers further on which
should be processed (for things like ordered data mode).
Hmm, I think we should just just change functions like walk_page_buffers()
in fs/ext3/inode.c and fs/ocfs2/aops.c to look for BH_New buffers outside
the range specified (they walk the entire buffer list anyway). If it finds
one that's buffer_new() it passes it to the journal unconditionally. You'd
also have to revert the change you did in fs/ext3/inode.c to at least always
make the call to walk_page_buffers().
I really don't like that we're hiding a detail of this interaction so deep
within the file system commit_write() callback. I suppose we can just do our
best to document it.
> But maybe it would be better to eliminate that case. OK.
> How about a zero-length commit_write? In that case again, they should
> be able to remain unchanged *except* that they are not to extend i_size
> or mark the page uptodate.
If we make the change I described above (looking for BH_New buffers outside
the range passed), then zero length or partial shouldn't matter, but zero
length instead of partial would be nicer imho just for the sake of reducing
the total number of cases down to the entire range or zero length.
> >For some reason, I'm not seeing where BH_New is being cleared in case with
> >no errors or faults. Hopefully I'm wrong, but if I'm not I believe we need
> >to clear the flag somewhere (perhaps in block_commit_write()?).
>
> Hmm, it is a bit inconsistent. It seems to be anywhere from prepare_write
> to block_write_full_page.
>
> Where do filesystems need the bit? It would be nice to clear it in
> commit_write if possible. Worst case we'll need a new bit.
->commit_write() would probably do fine. Currently, block_prepare_write()
uses it to know which buffers were newly allocated (the file system specific
get_block_t sets the bit after allocation). I think we could safely move
the clearing of that bit to block_commit_write(), thus still allowing us to
detect and zero those blocks in generic_file_buffered_write()
Thanks,
--Mark
--
Mark Fasheh
Senior Software Developer, Oracle
mark.fasheh@oracle.com
next prev parent reply other threads:[~2006-12-08 23:49 UTC|newest]
Thread overview: 20+ messages / expand[flat|nested] mbox.gz Atom feed top
2006-12-05 6:52 Status of buffered write path (deadlock fixes) Nick Piggin
2006-12-07 19:55 ` Mark Fasheh
2006-12-08 3:28 ` Nick Piggin
2006-12-08 23:48 ` Mark Fasheh [this message]
2006-12-11 9:11 ` Nick Piggin
2006-12-11 14:20 ` Nick Piggin
2006-12-11 15:52 ` Nick Piggin
2006-12-11 16:12 ` Steven Whitehouse
2006-12-11 16:39 ` Nick Piggin
2006-12-11 17:18 ` Steven Whitehouse
2006-12-12 22:31 ` Mark Fasheh
2006-12-13 0:53 ` Nick Piggin
2006-12-13 1:47 ` Trond Myklebust
2006-12-13 1:56 ` Nick Piggin
2006-12-13 2:31 ` Trond Myklebust
2006-12-13 4:03 ` Nick Piggin
2006-12-13 12:21 ` Trond Myklebust
2006-12-13 13:49 ` Peter Staubach
2006-12-13 13:55 ` Trond Myklebust
2006-12-11 18:17 ` OGAWA Hirofumi
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20061208234852.GI4497@ca-server1.us.oracle.com \
--to=mark.fasheh@oracle.com \
--cc=akpm@google.com \
--cc=hirofumi@mail.parknet.co.jp \
--cc=linux-fsdevel@vger.kernel.org \
--cc=linux-kernel@vger.kernel.org \
--cc=linux-mm@kvack.org \
--cc=nickpiggin@yahoo.com.au \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).