Revert "[XFS] Avoid replaying inode buffer initialisation log items if on-disk version is newer."

This reverts commit b394e43e99.

Lachlan McIlroy says:
    It tried to fix an issue where log replay is replaying an inode cluster
    initialisation transaction that should not be replayed because the inode
    cluster on disk is more up to date.  Since we don't log file sizes (we
    rely on inode flushing to get them to disk) then we can't just replay
    all the transations in the log and expect the inode to be completely
    restored.  We lose file size updates.  Unfortunately this fix is causing
    more (serious) problems than it is fixing.

SGI-PV: 969656
SGI-Modid: xfs-linux-melb:xfs-kern:29804a

Signed-off-by: Lachlan McIlroy <lachlan@sgi.com>
Signed-off-by: Tim Shimmin <tes@sgi.com>
This commit is contained in:
Tim Shimmin 2007-10-01 16:39:37 +10:00 committed by Linus Torvalds
parent a64314e62d
commit 564256c9e0
3 changed files with 3 additions and 54 deletions

View File

@ -52,11 +52,6 @@ typedef struct xfs_buf_log_format_t {
#define XFS_BLI_UDQUOT_BUF 0x4
#define XFS_BLI_PDQUOT_BUF 0x8
#define XFS_BLI_GDQUOT_BUF 0x10
/*
* This flag indicates that the buffer contains newly allocated
* inodes.
*/
#define XFS_BLI_INODE_NEW_BUF 0x20
#define XFS_BLI_CHUNK 128
#define XFS_BLI_SHIFT 7

View File

@ -1874,7 +1874,6 @@ xlog_recover_do_inode_buffer(
/*ARGSUSED*/
STATIC void
xlog_recover_do_reg_buffer(
xfs_mount_t *mp,
xlog_recover_item_t *item,
xfs_buf_t *bp,
xfs_buf_log_format_t *buf_f)
@ -1885,50 +1884,6 @@ xlog_recover_do_reg_buffer(
unsigned int *data_map = NULL;
unsigned int map_size = 0;
int error;
int stale_buf = 1;
/*
* Scan through the on-disk inode buffer and attempt to
* determine if it has been written to since it was logged.
*
* - If any of the magic numbers are incorrect then the buffer is stale
* - If any of the modes are non-zero then the buffer is not stale
* - If all of the modes are zero and at least one of the generation
* counts is non-zero then the buffer is stale
*
* If the end result is a stale buffer then the log buffer is replayed
* otherwise it is skipped.
*
* This heuristic is not perfect. It can be improved by scanning the
* entire inode chunk for evidence that any of the inode clusters have
* been updated. To fix this problem completely we will need a major
* architectural change to the logging system.
*/
if (buf_f->blf_flags & XFS_BLI_INODE_NEW_BUF) {
xfs_dinode_t *dip;
int inodes_per_buf;
int mode_count = 0;
int gen_count = 0;
stale_buf = 0;
inodes_per_buf = XFS_BUF_COUNT(bp) >> mp->m_sb.sb_inodelog;
for (i = 0; i < inodes_per_buf; i++) {
dip = (xfs_dinode_t *)xfs_buf_offset(bp,
i * mp->m_sb.sb_inodesize);
if (be16_to_cpu(dip->di_core.di_magic) !=
XFS_DINODE_MAGIC) {
stale_buf = 1;
break;
}
if (dip->di_core.di_mode)
mode_count++;
if (dip->di_core.di_gen)
gen_count++;
}
if (!mode_count && gen_count)
stale_buf = 1;
}
switch (buf_f->blf_type) {
case XFS_LI_BUF:
@ -1962,7 +1917,7 @@ xlog_recover_do_reg_buffer(
-1, 0, XFS_QMOPT_DOWARN,
"dquot_buf_recover");
}
if (!error && stale_buf)
if (!error)
memcpy(xfs_buf_offset(bp,
(uint)bit << XFS_BLI_SHIFT), /* dest */
item->ri_buf[i].i_addr, /* source */
@ -2134,7 +2089,7 @@ xlog_recover_do_dquot_buffer(
if (log->l_quotaoffs_flag & type)
return;
xlog_recover_do_reg_buffer(mp, item, bp, buf_f);
xlog_recover_do_reg_buffer(item, bp, buf_f);
}
/*
@ -2235,7 +2190,7 @@ xlog_recover_do_buffer_trans(
(XFS_BLI_UDQUOT_BUF|XFS_BLI_PDQUOT_BUF|XFS_BLI_GDQUOT_BUF)) {
xlog_recover_do_dquot_buffer(mp, log, item, bp, buf_f);
} else {
xlog_recover_do_reg_buffer(mp, item, bp, buf_f);
xlog_recover_do_reg_buffer(item, bp, buf_f);
}
if (error)
return XFS_ERROR(error);

View File

@ -966,7 +966,6 @@ xfs_trans_inode_alloc_buf(
ASSERT(atomic_read(&bip->bli_refcount) > 0);
bip->bli_flags |= XFS_BLI_INODE_ALLOC_BUF;
bip->bli_format.blf_flags |= XFS_BLI_INODE_NEW_BUF;
}