diff options
-rw-r--r-- | fs/xfs/xfs_log_recover.c | 44 |
1 files changed, 23 insertions, 21 deletions
diff --git a/fs/xfs/xfs_log_recover.c b/fs/xfs/xfs_log_recover.c index 8a7d8a79a7be..1fd5787add99 100644 --- a/fs/xfs/xfs_log_recover.c +++ b/fs/xfs/xfs_log_recover.c | |||
@@ -2399,8 +2399,11 @@ xlog_recover_do_reg_buffer( | |||
2399 | * Simple algorithm: if we have found a QUOTAOFF log item of the same type | 2399 | * Simple algorithm: if we have found a QUOTAOFF log item of the same type |
2400 | * (ie. USR or GRP), then just toss this buffer away; don't recover it. | 2400 | * (ie. USR or GRP), then just toss this buffer away; don't recover it. |
2401 | * Else, treat it as a regular buffer and do recovery. | 2401 | * Else, treat it as a regular buffer and do recovery. |
2402 | * | ||
2403 | * Return false if the buffer was tossed and true if we recovered the buffer to | ||
2404 | * indicate to the caller if the buffer needs writing. | ||
2402 | */ | 2405 | */ |
2403 | STATIC void | 2406 | STATIC bool |
2404 | xlog_recover_do_dquot_buffer( | 2407 | xlog_recover_do_dquot_buffer( |
2405 | struct xfs_mount *mp, | 2408 | struct xfs_mount *mp, |
2406 | struct xlog *log, | 2409 | struct xlog *log, |
@@ -2415,9 +2418,8 @@ xlog_recover_do_dquot_buffer( | |||
2415 | /* | 2418 | /* |
2416 | * Filesystems are required to send in quota flags at mount time. | 2419 | * Filesystems are required to send in quota flags at mount time. |
2417 | */ | 2420 | */ |
2418 | if (mp->m_qflags == 0) { | 2421 | if (!mp->m_qflags) |
2419 | return; | 2422 | return false; |
2420 | } | ||
2421 | 2423 | ||
2422 | type = 0; | 2424 | type = 0; |
2423 | if (buf_f->blf_flags & XFS_BLF_UDQUOT_BUF) | 2425 | if (buf_f->blf_flags & XFS_BLF_UDQUOT_BUF) |
@@ -2430,9 +2432,10 @@ xlog_recover_do_dquot_buffer( | |||
2430 | * This type of quotas was turned off, so ignore this buffer | 2432 | * This type of quotas was turned off, so ignore this buffer |
2431 | */ | 2433 | */ |
2432 | if (log->l_quotaoffs_flag & type) | 2434 | if (log->l_quotaoffs_flag & type) |
2433 | return; | 2435 | return false; |
2434 | 2436 | ||
2435 | xlog_recover_do_reg_buffer(mp, item, bp, buf_f); | 2437 | xlog_recover_do_reg_buffer(mp, item, bp, buf_f); |
2438 | return true; | ||
2436 | } | 2439 | } |
2437 | 2440 | ||
2438 | /* | 2441 | /* |
@@ -2525,14 +2528,18 @@ xlog_recover_buffer_pass2( | |||
2525 | 2528 | ||
2526 | if (buf_f->blf_flags & XFS_BLF_INODE_BUF) { | 2529 | if (buf_f->blf_flags & XFS_BLF_INODE_BUF) { |
2527 | error = xlog_recover_do_inode_buffer(mp, item, bp, buf_f); | 2530 | error = xlog_recover_do_inode_buffer(mp, item, bp, buf_f); |
2531 | if (error) | ||
2532 | goto out_release; | ||
2528 | } else if (buf_f->blf_flags & | 2533 | } else if (buf_f->blf_flags & |
2529 | (XFS_BLF_UDQUOT_BUF|XFS_BLF_PDQUOT_BUF|XFS_BLF_GDQUOT_BUF)) { | 2534 | (XFS_BLF_UDQUOT_BUF|XFS_BLF_PDQUOT_BUF|XFS_BLF_GDQUOT_BUF)) { |
2530 | xlog_recover_do_dquot_buffer(mp, log, item, bp, buf_f); | 2535 | bool dirty; |
2536 | |||
2537 | dirty = xlog_recover_do_dquot_buffer(mp, log, item, bp, buf_f); | ||
2538 | if (!dirty) | ||
2539 | goto out_release; | ||
2531 | } else { | 2540 | } else { |
2532 | xlog_recover_do_reg_buffer(mp, item, bp, buf_f); | 2541 | xlog_recover_do_reg_buffer(mp, item, bp, buf_f); |
2533 | } | 2542 | } |
2534 | if (error) | ||
2535 | goto out_release; | ||
2536 | 2543 | ||
2537 | /* | 2544 | /* |
2538 | * Perform delayed write on the buffer. Asynchronous writes will be | 2545 | * Perform delayed write on the buffer. Asynchronous writes will be |
@@ -3022,9 +3029,16 @@ xlog_recover_dquot_pass2( | |||
3022 | return -EIO; | 3029 | return -EIO; |
3023 | ASSERT(dq_f->qlf_len == 1); | 3030 | ASSERT(dq_f->qlf_len == 1); |
3024 | 3031 | ||
3032 | /* | ||
3033 | * At this point we are assuming that the dquots have been allocated | ||
3034 | * and hence the buffer has valid dquots stamped in it. It should, | ||
3035 | * therefore, pass verifier validation. If the dquot is bad, then the | ||
3036 | * we'll return an error here, so we don't need to specifically check | ||
3037 | * the dquot in the buffer after the verifier has run. | ||
3038 | */ | ||
3025 | error = xfs_trans_read_buf(mp, NULL, mp->m_ddev_targp, dq_f->qlf_blkno, | 3039 | error = xfs_trans_read_buf(mp, NULL, mp->m_ddev_targp, dq_f->qlf_blkno, |
3026 | XFS_FSB_TO_BB(mp, dq_f->qlf_len), 0, &bp, | 3040 | XFS_FSB_TO_BB(mp, dq_f->qlf_len), 0, &bp, |
3027 | NULL); | 3041 | &xfs_dquot_buf_ops); |
3028 | if (error) | 3042 | if (error) |
3029 | return error; | 3043 | return error; |
3030 | 3044 | ||
@@ -3032,18 +3046,6 @@ xlog_recover_dquot_pass2( | |||
3032 | ddq = (xfs_disk_dquot_t *)xfs_buf_offset(bp, dq_f->qlf_boffset); | 3046 | ddq = (xfs_disk_dquot_t *)xfs_buf_offset(bp, dq_f->qlf_boffset); |
3033 | 3047 | ||
3034 | /* | 3048 | /* |
3035 | * At least the magic num portion should be on disk because this | ||
3036 | * was among a chunk of dquots created earlier, and we did some | ||
3037 | * minimal initialization then. | ||
3038 | */ | ||
3039 | error = xfs_dqcheck(mp, ddq, dq_f->qlf_id, 0, XFS_QMOPT_DOWARN, | ||
3040 | "xlog_recover_dquot_pass2"); | ||
3041 | if (error) { | ||
3042 | xfs_buf_relse(bp); | ||
3043 | return -EIO; | ||
3044 | } | ||
3045 | |||
3046 | /* | ||
3047 | * If the dquot has an LSN in it, recover the dquot only if it's less | 3049 | * If the dquot has an LSN in it, recover the dquot only if it's less |
3048 | * than the lsn of the transaction we are replaying. | 3050 | * than the lsn of the transaction we are replaying. |
3049 | */ | 3051 | */ |