- Call softdep_prealloc() before any of the balloc routines in the

snapshot code.
 - Don't fsync() vnodes in prealloc if copy on write is in progress.  It
   is not safe to recurse back into the write path here.

Reported by:	Vladimir Grebenschikov <vova@fbsd.ru>
This commit is contained in:
jeff 2010-05-07 08:45:21 +00:00
parent 0b3e023908
commit 8fb90eedbc
2 changed files with 10 additions and 1 deletions

View File

@ -1002,6 +1002,8 @@ expunge_ufs1(snapvp, cancelip, fs, acctfunc, expungetype, clearmode)
if (lbn < NDADDR) {
blkno = VTOI(snapvp)->i_din1->di_db[lbn];
} else {
if (DOINGSOFTDEP(snapvp))
softdep_prealloc(snapvp, MNT_WAIT);
td->td_pflags |= TDP_COWINPROGRESS;
error = ffs_balloc_ufs1(snapvp, lblktosize(fs, (off_t)lbn),
fs->fs_bsize, KERNCRED, BA_METAONLY, &bp);
@ -1283,6 +1285,8 @@ expunge_ufs2(snapvp, cancelip, fs, acctfunc, expungetype, clearmode)
if (lbn < NDADDR) {
blkno = VTOI(snapvp)->i_din2->di_db[lbn];
} else {
if (DOINGSOFTDEP(snapvp))
softdep_prealloc(snapvp, MNT_WAIT);
td->td_pflags |= TDP_COWINPROGRESS;
error = ffs_balloc_ufs2(snapvp, lblktosize(fs, (off_t)lbn),
fs->fs_bsize, KERNCRED, BA_METAONLY, &bp);
@ -1746,6 +1750,8 @@ ffs_snapblkfree(fs, devvp, bno, size, inum)
goto retry;
TAILQ_FOREACH(ip, &sn->sn_head, i_nextsnap) {
vp = ITOV(ip);
if (DOINGSOFTDEP(vp))
softdep_prealloc(vp, MNT_WAIT);
/*
* Lookup block being written.
*/
@ -2268,6 +2274,8 @@ ffs_copyonwrite(devvp, bp)
}
TAILQ_FOREACH(ip, &sn->sn_head, i_nextsnap) {
vp = ITOV(ip);
if (DOINGSOFTDEP(vp))
softdep_prealloc(vp, MNT_WAIT);
/*
* We ensure that everything of our own that needs to be
* copied will be done at the time that ffs_snapshot is

View File

@ -2475,7 +2475,8 @@ softdep_prealloc(vp, waitok)
* Attempt to sync this vnode once to flush any journal
* work attached to it.
*/
ffs_syncvnode(vp, waitok);
if ((curthread->td_pflags & TDP_COWINPROGRESS) == 0)
ffs_syncvnode(vp, waitok);
ACQUIRE_LOCK(&lk);
process_removes(vp);
if (journal_space(ump, 0) == 0) {