Commit e6963ec2 authored by Nathan Scott's avatar Nathan Scott Committed by Christoph Hellwig

[XFS] Fix two remaining indentation inconsistencies.

SGI Modid: 2.5.x-xfs:slinx:149400a
parent 62b96d76
...@@ -530,7 +530,8 @@ xlog_find_verify_log_record( ...@@ -530,7 +530,8 @@ xlog_find_verify_log_record(
* Return: zero if normal, non-zero if error. * Return: zero if normal, non-zero if error.
*/ */
int int
xlog_find_head(xlog_t *log, xlog_find_head(
xlog_t *log,
xfs_daddr_t *return_head_blk) xfs_daddr_t *return_head_blk)
{ {
xfs_buf_t *bp; xfs_buf_t *bp;
...@@ -545,7 +546,7 @@ xlog_find_head(xlog_t *log, ...@@ -545,7 +546,7 @@ xlog_find_head(xlog_t *log,
if ((error = xlog_find_zeroed(log, &first_blk)) == -1) { if ((error = xlog_find_zeroed(log, &first_blk)) == -1) {
*return_head_blk = first_blk; *return_head_blk = first_blk;
/* is the whole lot zeroed? */ /* Is the whole lot zeroed? */
if (!first_blk) { if (!first_blk) {
/* Linux XFS shouldn't generate totally zeroed logs - /* Linux XFS shouldn't generate totally zeroed logs -
* mkfs etc write a dummy unmount record to a fresh * mkfs etc write a dummy unmount record to a fresh
...@@ -569,7 +570,7 @@ xlog_find_head(xlog_t *log, ...@@ -569,7 +570,7 @@ xlog_find_head(xlog_t *log,
offset = xlog_align(log, 0, 1, bp); offset = xlog_align(log, 0, 1, bp);
first_half_cycle = GET_CYCLE(offset, ARCH_CONVERT); first_half_cycle = GET_CYCLE(offset, ARCH_CONVERT);
last_blk = head_blk = log_bbnum-1; /* get cycle # of last block */ last_blk = head_blk = log_bbnum - 1; /* get cycle # of last block */
if ((error = xlog_bread(log, last_blk, 1, bp))) if ((error = xlog_bread(log, last_blk, 1, bp)))
goto bp_err; goto bp_err;
offset = xlog_align(log, last_blk, 1, bp); offset = xlog_align(log, last_blk, 1, bp);
...@@ -589,44 +590,47 @@ xlog_find_head(xlog_t *log, ...@@ -589,44 +590,47 @@ xlog_find_head(xlog_t *log,
*/ */
if (first_half_cycle == last_half_cycle) { if (first_half_cycle == last_half_cycle) {
/* /*
* In this case we believe that the entire log should have cycle * In this case we believe that the entire log should have
* number last_half_cycle. We need to scan backwards from the * cycle number last_half_cycle. We need to scan backwards
* end verifying that there are no holes still containing * from the end verifying that there are no holes still
* last_half_cycle - 1. If we find such a hole, then the start * containing last_half_cycle - 1. If we find such a hole,
* of that hole will be the new head. The simple case looks like * then the start of that hole will be the new head. The
* simple case looks like
* x | x ... | x - 1 | x * x | x ... | x - 1 | x
* Another case that fits this picture would be * Another case that fits this picture would be
* x | x + 1 | x ... | x * x | x + 1 | x ... | x
* In this case the head really is somwhere at the end of the * In this case the head really is somwhere at the end of the
* log, as one of the latest writes at the beginning was incomplete. * log, as one of the latest writes at the beginning was
* incomplete.
* One more case is * One more case is
* x | x + 1 | x ... | x - 1 | x * x | x + 1 | x ... | x - 1 | x
* This is really the combination of the above two cases, and the * This is really the combination of the above two cases, and
* head has to end up at the start of the x-1 hole at the end of * the head has to end up at the start of the x-1 hole at the
* the log. * end of the log.
* *
* In the 256k log case, we will read from the beginning to the * In the 256k log case, we will read from the beginning to the
* end of the log and search for cycle numbers equal to x-1. We * end of the log and search for cycle numbers equal to x-1.
* don't worry about the x+1 blocks that we encounter, because * We don't worry about the x+1 blocks that we encounter,
* we know that they cannot be the head since the log started with * because we know that they cannot be the head since the log
* x. * started with x.
*/ */
head_blk = log_bbnum; head_blk = log_bbnum;
stop_on_cycle = last_half_cycle - 1; stop_on_cycle = last_half_cycle - 1;
} else { } else {
/* /*
* In this case we want to find the first block with cycle number * In this case we want to find the first block with cycle
* matching last_half_cycle. We expect the log to be some * number matching last_half_cycle. We expect the log to be
* variation on * some variation on
* x + 1 ... | x ... * x + 1 ... | x ...
* The first block with cycle number x (last_half_cycle) will be * The first block with cycle number x (last_half_cycle) will
* where the new head belongs. First we do a binary search for * be where the new head belongs. First we do a binary search
* the first occurrence of last_half_cycle. The binary search * for the first occurrence of last_half_cycle. The binary
* may not be totally accurate, so then we scan back from there * search may not be totally accurate, so then we scan back
* looking for occurrences of last_half_cycle before us. If * from there looking for occurrences of last_half_cycle before
* that backwards scan wraps around the beginning of the log, * us. If that backwards scan wraps around the beginning of
* then we look for occurrences of last_half_cycle - 1 at the * the log, then we look for occurrences of last_half_cycle - 1
* end of the log. The cases we're looking for look like * at the end of the log. The cases we're looking for look
* like
* x + 1 ... | x | x + 1 | x ... * x + 1 ... | x | x + 1 | x ...
* ^ binary search stopped here * ^ binary search stopped here
* or * or
...@@ -653,42 +657,46 @@ xlog_find_head(xlog_t *log, ...@@ -653,42 +657,46 @@ xlog_find_head(xlog_t *log,
* in one buffer. * in one buffer.
*/ */
start_blk = head_blk - num_scan_bblks; start_blk = head_blk - num_scan_bblks;
if ((error = xlog_find_verify_cycle(log, start_blk, num_scan_bblks, if ((error = xlog_find_verify_cycle(log,
start_blk, num_scan_bblks,
stop_on_cycle, &new_blk))) stop_on_cycle, &new_blk)))
goto bp_err; goto bp_err;
if (new_blk != -1) if (new_blk != -1)
head_blk = new_blk; head_blk = new_blk;
} else { /* need to read 2 parts of log */ } else { /* need to read 2 parts of log */
/* /*
* We are going to scan backwards in the log in two parts. First * We are going to scan backwards in the log in two parts.
* we scan the physical end of the log. In this part of the log, * First we scan the physical end of the log. In this part
* we are looking for blocks with cycle number last_half_cycle - 1. * of the log, we are looking for blocks with cycle number
* If we find one, then we know that the log starts there, as we've * last_half_cycle - 1.
* found a hole that didn't get written in going around the end * If we find one, then we know that the log starts there, as
* of the physical log. The simple case for this is * we've found a hole that didn't get written in going around
* the end of the physical log. The simple case for this is
* x + 1 ... | x ... | x - 1 | x * x + 1 ... | x ... | x - 1 | x
* <---------> less than scan distance * <---------> less than scan distance
* If all of the blocks at the end of the log have cycle number * If all of the blocks at the end of the log have cycle number
* last_half_cycle, then we check the blocks at the start of the * last_half_cycle, then we check the blocks at the start of
* log looking for occurrences of last_half_cycle. If we find one, * the log looking for occurrences of last_half_cycle. If we
* then our current estimate for the location of the first * find one, then our current estimate for the location of the
* occurrence of last_half_cycle is wrong and we move back to the * first occurrence of last_half_cycle is wrong and we move
* hole we've found. This case looks like * back to the hole we've found. This case looks like
* x + 1 ... | x | x + 1 | x ... * x + 1 ... | x | x + 1 | x ...
* ^ binary search stopped here * ^ binary search stopped here
* Another case we need to handle that only occurs in 256k logs is * Another case we need to handle that only occurs in 256k
* logs is
* x + 1 ... | x ... | x+1 | x ... * x + 1 ... | x ... | x+1 | x ...
* ^ binary search stops here * ^ binary search stops here
* In a 256k log, the scan at the end of the log will see the x+1 * In a 256k log, the scan at the end of the log will see the
* blocks. We need to skip past those since that is certainly not * x + 1 blocks. We need to skip past those since that is
* the head of the log. By searching for last_half_cycle-1 we * certainly not the head of the log. By searching for
* accomplish that. * last_half_cycle-1 we accomplish that.
*/ */
start_blk = log_bbnum - num_scan_bblks + head_blk; start_blk = log_bbnum - num_scan_bblks + head_blk;
ASSERT(head_blk <= INT_MAX && (xfs_daddr_t) num_scan_bblks-head_blk >= 0); ASSERT(head_blk <= INT_MAX &&
(xfs_daddr_t) num_scan_bblks - head_blk >= 0);
if ((error = xlog_find_verify_cycle(log, start_blk, if ((error = xlog_find_verify_cycle(log, start_blk,
num_scan_bblks-(int)head_blk, (stop_on_cycle - 1), num_scan_bblks - (int)head_blk,
&new_blk))) (stop_on_cycle - 1), &new_blk)))
goto bp_err; goto bp_err;
if (new_blk != -1) { if (new_blk != -1) {
head_blk = new_blk; head_blk = new_blk;
...@@ -696,20 +704,21 @@ xlog_find_head(xlog_t *log, ...@@ -696,20 +704,21 @@ xlog_find_head(xlog_t *log,
} }
/* /*
* Scan beginning of log now. The last part of the physical log * Scan beginning of log now. The last part of the physical
* is good. This scan needs to verify that it doesn't find the * log is good. This scan needs to verify that it doesn't find
* last_half_cycle. * the last_half_cycle.
*/ */
start_blk = 0; start_blk = 0;
ASSERT(head_blk <= INT_MAX); ASSERT(head_blk <= INT_MAX);
if ((error = xlog_find_verify_cycle(log, start_blk, (int) head_blk, if ((error = xlog_find_verify_cycle(log,
start_blk, (int)head_blk,
stop_on_cycle, &new_blk))) stop_on_cycle, &new_blk)))
goto bp_err; goto bp_err;
if (new_blk != -1) if (new_blk != -1)
head_blk = new_blk; head_blk = new_blk;
} }
bad_blk: bad_blk:
/* /*
* Now we need to make sure head_blk is not pointing to a block in * Now we need to make sure head_blk is not pointing to a block in
* the middle of a log record. * the middle of a log record.
...@@ -719,10 +728,8 @@ xlog_find_head(xlog_t *log, ...@@ -719,10 +728,8 @@ xlog_find_head(xlog_t *log,
start_blk = head_blk - num_scan_bblks; /* don't read head_blk */ start_blk = head_blk - num_scan_bblks; /* don't read head_blk */
/* start ptr at last block ptr before head_blk */ /* start ptr at last block ptr before head_blk */
if ((error = xlog_find_verify_log_record(log, if ((error = xlog_find_verify_log_record(log, start_blk,
start_blk, &head_blk, 0)) == -1) {
&head_blk,
0)) == -1) {
error = XFS_ERROR(EIO); error = XFS_ERROR(EIO);
goto bp_err; goto bp_err;
} else if (error) } else if (error)
...@@ -730,18 +737,16 @@ xlog_find_head(xlog_t *log, ...@@ -730,18 +737,16 @@ xlog_find_head(xlog_t *log,
} else { } else {
start_blk = 0; start_blk = 0;
ASSERT(head_blk <= INT_MAX); ASSERT(head_blk <= INT_MAX);
if ((error = xlog_find_verify_log_record(log, if ((error = xlog_find_verify_log_record(log, start_blk,
start_blk, &head_blk, 0)) == -1) {
&head_blk,
0)) == -1) {
/* We hit the beginning of the log during our search */ /* We hit the beginning of the log during our search */
start_blk = log_bbnum - num_scan_bblks + head_blk; start_blk = log_bbnum - num_scan_bblks + head_blk;
new_blk = log_bbnum; new_blk = log_bbnum;
ASSERT(start_blk <= INT_MAX && (xfs_daddr_t) log_bbnum-start_blk >= 0); ASSERT(start_blk <= INT_MAX &&
(xfs_daddr_t) log_bbnum-start_blk >= 0);
ASSERT(head_blk <= INT_MAX); ASSERT(head_blk <= INT_MAX);
if ((error = xlog_find_verify_log_record(log, if ((error = xlog_find_verify_log_record(log,
start_blk, start_blk, &new_blk,
&new_blk,
(int)head_blk)) == -1) { (int)head_blk)) == -1) {
error = XFS_ERROR(EIO); error = XFS_ERROR(EIO);
goto bp_err; goto bp_err;
...@@ -766,14 +771,13 @@ xlog_find_head(xlog_t *log, ...@@ -766,14 +771,13 @@ xlog_find_head(xlog_t *log,
*/ */
return 0; return 0;
bp_err: bp_err:
xlog_put_bp(bp); xlog_put_bp(bp);
if (error) if (error)
xlog_warn("XFS: failed to find log head"); xlog_warn("XFS: failed to find log head");
return error; return error;
} /* xlog_find_head */ }
/* /*
* Find the sync block number or the tail of the log. * Find the sync block number or the tail of the log.
...@@ -3418,7 +3422,8 @@ xlog_unpack_data( ...@@ -3418,7 +3422,8 @@ xlog_unpack_data(
* here. * here.
*/ */
STATIC int STATIC int
xlog_do_recovery_pass(xlog_t *log, xlog_do_recovery_pass(
xlog_t *log,
xfs_daddr_t head_blk, xfs_daddr_t head_blk,
xfs_daddr_t tail_blk, xfs_daddr_t tail_blk,
int pass) int pass)
...@@ -3427,23 +3432,20 @@ xlog_do_recovery_pass(xlog_t *log, ...@@ -3427,23 +3432,20 @@ xlog_do_recovery_pass(xlog_t *log,
xfs_daddr_t blk_no; xfs_daddr_t blk_no;
xfs_caddr_t bufaddr, offset; xfs_caddr_t bufaddr, offset;
xfs_buf_t *hbp, *dbp; xfs_buf_t *hbp, *dbp;
int error, h_size; int error = 0, h_size;
int bblks, split_bblks; int bblks, split_bblks;
int hblks, split_hblks, wrapped_hblks; int hblks, split_hblks, wrapped_hblks;
xlog_recover_t *rhash[XLOG_RHASH_SIZE]; xlog_recover_t *rhash[XLOG_RHASH_SIZE];
error = 0;
/* /*
* Read the header of the tail block and get the iclog buffer size from * Read the header of the tail block and get the iclog buffer size from
* h_size. Use this to tell how many sectors make up the log header. * h_size. Use this to tell how many sectors make up the log header.
*/ */
if (XFS_SB_VERSION_HASLOGV2(&log->l_mp->m_sb)) { if (XFS_SB_VERSION_HASLOGV2(&log->l_mp->m_sb)) {
/* /*
* When using variable length iclogs, read first sector of iclog * When using variable length iclogs, read first sector of
* header and extract the header size from it. Get a new hbp that * iclog header and extract the header size from it. Get a
* is the correct size. * new hbp that is the correct size.
*/ */
hbp = xlog_get_bp(log, 1); hbp = xlog_get_bp(log, 1);
if (!hbp) if (!hbp)
...@@ -3454,14 +3456,17 @@ xlog_do_recovery_pass(xlog_t *log, ...@@ -3454,14 +3456,17 @@ xlog_do_recovery_pass(xlog_t *log,
rhead = (xlog_rec_header_t *)offset; rhead = (xlog_rec_header_t *)offset;
ASSERT(INT_GET(rhead->h_magicno, ARCH_CONVERT) == ASSERT(INT_GET(rhead->h_magicno, ARCH_CONVERT) ==
XLOG_HEADER_MAGIC_NUM); XLOG_HEADER_MAGIC_NUM);
if ((INT_GET(rhead->h_version, ARCH_CONVERT) & (~XLOG_VERSION_OKBITS)) != 0) { if ((INT_GET(rhead->h_version, ARCH_CONVERT) &
xlog_warn("XFS: xlog_do_recovery_pass: unrecognised log version number."); (~XLOG_VERSION_OKBITS)) != 0) {
xlog_warn(
"XFS: xlog_do_recovery_pass: unrecognised log version number.");
error = XFS_ERROR(EIO); error = XFS_ERROR(EIO);
goto bread_err1; goto bread_err1;
} }
h_size = INT_GET(rhead->h_size, ARCH_CONVERT); h_size = INT_GET(rhead->h_size, ARCH_CONVERT);
if ((INT_GET(rhead->h_version, ARCH_CONVERT) & XLOG_VERSION_2) && if ((INT_GET(rhead->h_version, ARCH_CONVERT)
& XLOG_VERSION_2) &&
(h_size > XLOG_HEADER_CYCLE_SIZE)) { (h_size > XLOG_HEADER_CYCLE_SIZE)) {
hblks = h_size / XLOG_HEADER_CYCLE_SIZE; hblks = h_size / XLOG_HEADER_CYCLE_SIZE;
if (h_size % XLOG_HEADER_CYCLE_SIZE) if (h_size % XLOG_HEADER_CYCLE_SIZE)
...@@ -3469,11 +3474,11 @@ xlog_do_recovery_pass(xlog_t *log, ...@@ -3469,11 +3474,11 @@ xlog_do_recovery_pass(xlog_t *log,
xlog_put_bp(hbp); xlog_put_bp(hbp);
hbp = xlog_get_bp(log, hblks); hbp = xlog_get_bp(log, hblks);
} else { } else {
hblks=1; hblks = 1;
} }
} else { } else {
ASSERT(log->l_sectbb_log == 0); ASSERT(log->l_sectbb_log == 0);
hblks=1; hblks = 1;
hbp = xlog_get_bp(log, 1); hbp = xlog_get_bp(log, 1);
h_size = XLOG_BIG_RECORD_BSIZE; h_size = XLOG_BIG_RECORD_BSIZE;
} }
...@@ -3493,12 +3498,18 @@ xlog_do_recovery_pass(xlog_t *log, ...@@ -3493,12 +3498,18 @@ xlog_do_recovery_pass(xlog_t *log,
goto bread_err2; goto bread_err2;
offset = xlog_align(log, blk_no, hblks, hbp); offset = xlog_align(log, blk_no, hblks, hbp);
rhead = (xlog_rec_header_t *)offset; rhead = (xlog_rec_header_t *)offset;
ASSERT(INT_GET(rhead->h_magicno, ARCH_CONVERT) == XLOG_HEADER_MAGIC_NUM); ASSERT(INT_GET(rhead->h_magicno, ARCH_CONVERT) ==
ASSERT(BTOBB(INT_GET(rhead->h_len, ARCH_CONVERT) <= INT_MAX)); XLOG_HEADER_MAGIC_NUM);
bblks = (int) BTOBB(INT_GET(rhead->h_len, ARCH_CONVERT)); /* blocks in data section */ ASSERT(BTOBB(INT_GET(rhead->h_len, ARCH_CONVERT) <=
INT_MAX));
if (unlikely((INT_GET(rhead->h_magicno, ARCH_CONVERT) != XLOG_HEADER_MAGIC_NUM) || /* blocks in data section */
(BTOBB(INT_GET(rhead->h_len, ARCH_CONVERT) > INT_MAX)) || bblks = (int)BTOBB(INT_GET(rhead->h_len, ARCH_CONVERT));
if (unlikely(
(INT_GET(rhead->h_magicno, ARCH_CONVERT) !=
XLOG_HEADER_MAGIC_NUM) ||
(BTOBB(INT_GET(rhead->h_len, ARCH_CONVERT) >
INT_MAX)) ||
(bblks <= 0) || (bblks <= 0) ||
(blk_no > log->l_logBBsize))) { (blk_no > log->l_logBBsize))) {
XFS_ERROR_REPORT("xlog_do_recovery_pass(1)", XFS_ERROR_REPORT("xlog_do_recovery_pass(1)",
...@@ -3507,28 +3518,33 @@ xlog_do_recovery_pass(xlog_t *log, ...@@ -3507,28 +3518,33 @@ xlog_do_recovery_pass(xlog_t *log,
goto bread_err2; goto bread_err2;
} }
if ((INT_GET(rhead->h_version, ARCH_CONVERT) & (~XLOG_VERSION_OKBITS)) != 0) { if ((INT_GET(rhead->h_version, ARCH_CONVERT) &
xlog_warn("XFS: xlog_do_recovery_pass: unrecognised log version number."); (~XLOG_VERSION_OKBITS)) != 0) {
xlog_warn(
"XFS: xlog_do_recovery_pass: unrecognised log version number.");
error = XFS_ERROR(EIO); error = XFS_ERROR(EIO);
goto bread_err2; goto bread_err2;
} }
bblks = (int) BTOBB(INT_GET(rhead->h_len, ARCH_CONVERT)); /* blocks in data section */ /* blocks in data section */
bblks = (int)BTOBB(INT_GET(rhead->h_len, ARCH_CONVERT));
if (bblks > 0) { if (bblks > 0) {
if ((error = xlog_bread(log, blk_no+hblks, bblks, dbp))) if ((error = xlog_bread(log, blk_no + hblks,
bblks, dbp)))
goto bread_err2; goto bread_err2;
offset = xlog_align(log, blk_no+hblks, bblks, dbp); offset = xlog_align(log, blk_no + hblks,
bblks, dbp);
xlog_unpack_data(rhead, offset, log); xlog_unpack_data(rhead, offset, log);
if ((error = xlog_recover_process_data(log, rhash, if ((error = xlog_recover_process_data(log,
rhead, offset, pass))) rhash, rhead, offset, pass)))
goto bread_err2; goto bread_err2;
} }
blk_no += (bblks+hblks); blk_no += (bblks+hblks);
} }
} else { } else {
/* /*
* Perform recovery around the end of the physical log. When the head * Perform recovery around the end of the physical log.
* is not on the same cycle number as the tail, we can't do a sequential * When the head is not on the same cycle number as the tail,
* recovery as above. * we can't do a sequential recovery as above.
*/ */
blk_no = tail_blk; blk_no = tail_blk;
while (blk_no < log->l_logBBsize) { while (blk_no < log->l_logBBsize) {
...@@ -3538,52 +3554,67 @@ xlog_do_recovery_pass(xlog_t *log, ...@@ -3538,52 +3554,67 @@ xlog_do_recovery_pass(xlog_t *log,
wrapped_hblks = 0; wrapped_hblks = 0;
if (blk_no+hblks <= log->l_logBBsize) { if (blk_no+hblks <= log->l_logBBsize) {
/* Read header in one read */ /* Read header in one read */
if ((error = xlog_bread(log, blk_no, hblks, hbp))) if ((error = xlog_bread(log, blk_no,
hblks, hbp)))
goto bread_err2; goto bread_err2;
offset = xlog_align(log, blk_no, hblks, hbp); offset = xlog_align(log, blk_no, hblks, hbp);
} else { } else {
/* This log record is split across physical end of log */ /* This LR is split across physical log end */
offset = NULL; offset = NULL;
split_hblks = 0; split_hblks = 0;
if (blk_no != log->l_logBBsize) { if (blk_no != log->l_logBBsize) {
/* some data is before physical end of log */ /* some data before physical log end */
ASSERT(blk_no <= INT_MAX); ASSERT(blk_no <= INT_MAX);
split_hblks = log->l_logBBsize - (int)blk_no; split_hblks = log->l_logBBsize - (int)blk_no;
ASSERT(split_hblks > 0); ASSERT(split_hblks > 0);
if ((error = xlog_bread(log, blk_no, split_hblks, hbp))) if ((error = xlog_bread(log, blk_no,
split_hblks, hbp)))
goto bread_err2; goto bread_err2;
offset = xlog_align(log, blk_no, split_hblks, hbp); offset = xlog_align(log, blk_no,
split_hblks, hbp);
} }
/* /*
* Note: this black magic still works with large sector * Note: this black magic still works with
* sizes (non-512) only because: * large sector sizes (non-512) only because:
* - we increased the buffer size originally by 1 sector * - we increased the buffer size originally
* giving us enough extra space for the second read; * by 1 sector giving us enough extra space
* - the log start is guaranteed to be sector aligned; * for the second read;
* - we read the log end (LR header start) _first_, then * - the log start is guaranteed to be sector
* the log start (LR header end) - order is important. * aligned;
* - we read the log end (LR header start)
* _first_, then the log start (LR header end)
* - order is important.
*/ */
bufaddr = XFS_BUF_PTR(hbp); bufaddr = XFS_BUF_PTR(hbp);
XFS_BUF_SET_PTR(hbp, bufaddr + BBTOB(split_hblks), XFS_BUF_SET_PTR(hbp,
bufaddr + BBTOB(split_hblks),
BBTOB(hblks - split_hblks)); BBTOB(hblks - split_hblks));
wrapped_hblks = hblks - split_hblks; wrapped_hblks = hblks - split_hblks;
if ((error = xlog_bread(log, 0, wrapped_hblks, hbp))) if ((error = xlog_bread(log, 0,
wrapped_hblks, hbp)))
goto bread_err2; goto bread_err2;
XFS_BUF_SET_PTR(hbp, bufaddr, hblks); XFS_BUF_SET_PTR(hbp, bufaddr, hblks);
if (!offset) if (!offset)
offset = xlog_align(log, 0, wrapped_hblks, hbp); offset = xlog_align(log, 0,
wrapped_hblks, hbp);
} }
rhead = (xlog_rec_header_t *)offset; rhead = (xlog_rec_header_t *)offset;
ASSERT(INT_GET(rhead->h_magicno, ARCH_CONVERT) == XLOG_HEADER_MAGIC_NUM); ASSERT(INT_GET(rhead->h_magicno, ARCH_CONVERT) ==
ASSERT(BTOBB(INT_GET(rhead->h_len, ARCH_CONVERT) <= INT_MAX)); XLOG_HEADER_MAGIC_NUM);
bblks = (int) BTOBB(INT_GET(rhead->h_len, ARCH_CONVERT)); ASSERT(BTOBB(INT_GET(rhead->h_len, ARCH_CONVERT) <=
INT_MAX));
bblks = (int)BTOBB(INT_GET(rhead->h_len, ARCH_CONVERT));
/* LR body must have data or it wouldn't have been written */ /* LR body must have data or it wouldn't have been
* written */
ASSERT(bblks > 0); ASSERT(bblks > 0);
blk_no += hblks; /* successfully read header */ blk_no += hblks; /* successfully read header */
if (unlikely((INT_GET(rhead->h_magicno, ARCH_CONVERT) != XLOG_HEADER_MAGIC_NUM) || if (unlikely(
(BTOBB(INT_GET(rhead->h_len, ARCH_CONVERT) > INT_MAX)) || (INT_GET(rhead->h_magicno, ARCH_CONVERT) !=
XLOG_HEADER_MAGIC_NUM) ||
(BTOBB(INT_GET(rhead->h_len, ARCH_CONVERT) >
INT_MAX)) ||
(bblks <= 0))) { (bblks <= 0))) {
XFS_ERROR_REPORT("xlog_do_recovery_pass(2)", XFS_ERROR_REPORT("xlog_do_recovery_pass(2)",
XFS_ERRLEVEL_LOW, log->l_mp); XFS_ERRLEVEL_LOW, log->l_mp);
...@@ -3593,42 +3624,53 @@ xlog_do_recovery_pass(xlog_t *log, ...@@ -3593,42 +3624,53 @@ xlog_do_recovery_pass(xlog_t *log,
/* Read in data for log record */ /* Read in data for log record */
if (blk_no+bblks <= log->l_logBBsize) { if (blk_no+bblks <= log->l_logBBsize) {
if ((error = xlog_bread(log, blk_no, bblks, dbp))) if ((error = xlog_bread(log, blk_no,
bblks, dbp)))
goto bread_err2; goto bread_err2;
offset = xlog_align(log, blk_no, bblks, dbp); offset = xlog_align(log, blk_no, bblks, dbp);
} else { } else {
/* This log record is split across physical end of log */ /* This log record is split across the
* physical end of log */
offset = NULL; offset = NULL;
split_bblks = 0; split_bblks = 0;
if (blk_no != log->l_logBBsize) { if (blk_no != log->l_logBBsize) {
/* some data is before physical end of log */ /* some data is before the physical
* end of log */
ASSERT(!wrapped_hblks); ASSERT(!wrapped_hblks);
ASSERT(blk_no <= INT_MAX); ASSERT(blk_no <= INT_MAX);
split_bblks = log->l_logBBsize - (int)blk_no; split_bblks =
log->l_logBBsize - (int)blk_no;
ASSERT(split_bblks > 0); ASSERT(split_bblks > 0);
if ((error = xlog_bread(log, blk_no, split_bblks, dbp))) if ((error = xlog_bread(log, blk_no,
split_bblks, dbp)))
goto bread_err2; goto bread_err2;
offset = xlog_align(log, blk_no, split_bblks, dbp); offset = xlog_align(log, blk_no,
split_bblks, dbp);
} }
/* /*
* Note: this black magic still works with large sector * Note: this black magic still works with
* sizes (non-512) only because: * large sector sizes (non-512) only because:
* - we increased the buffer size originally by 1 sector * - we increased the buffer size originally
* giving us enough extra space for the second read; * by 1 sector giving us enough extra space
* - the log start is guaranteed to be sector aligned; * for the second read;
* - we read the log end (LR header start) _first_, then * - the log start is guaranteed to be sector
* the log start (LR header end) - order is important. * aligned;
* - we read the log end (LR header start)
* _first_, then the log start (LR header end)
* - order is important.
*/ */
bufaddr = XFS_BUF_PTR(dbp); bufaddr = XFS_BUF_PTR(dbp);
XFS_BUF_SET_PTR(dbp, bufaddr + BBTOB(split_bblks), XFS_BUF_SET_PTR(dbp,
bufaddr + BBTOB(split_bblks),
BBTOB(bblks - split_bblks)); BBTOB(bblks - split_bblks));
if ((error = xlog_bread(log, wrapped_hblks, if ((error = xlog_bread(log, wrapped_hblks,
bblks - split_bblks, dbp))) bblks - split_bblks, dbp)))
goto bread_err2; goto bread_err2;
XFS_BUF_SET_PTR(dbp, bufaddr, XLOG_BIG_RECORD_BSIZE); XFS_BUF_SET_PTR(dbp, bufaddr,
XLOG_BIG_RECORD_BSIZE);
if (!offset) if (!offset)
offset = xlog_align(log, wrapped_hblks, offset = xlog_align(log, wrapped_hblks,
BBTOB(bblks - split_bblks), dbp); bblks - split_bblks, dbp);
} }
xlog_unpack_data(rhead, offset, log); xlog_unpack_data(rhead, offset, log);
if ((error = xlog_recover_process_data(log, rhash, if ((error = xlog_recover_process_data(log, rhash,
...@@ -3646,9 +3688,11 @@ xlog_do_recovery_pass(xlog_t *log, ...@@ -3646,9 +3688,11 @@ xlog_do_recovery_pass(xlog_t *log,
goto bread_err2; goto bread_err2;
offset = xlog_align(log, blk_no, hblks, hbp); offset = xlog_align(log, blk_no, hblks, hbp);
rhead = (xlog_rec_header_t *)offset; rhead = (xlog_rec_header_t *)offset;
ASSERT(INT_GET(rhead->h_magicno, ARCH_CONVERT) == XLOG_HEADER_MAGIC_NUM); ASSERT(INT_GET(rhead->h_magicno, ARCH_CONVERT) ==
ASSERT(BTOBB(INT_GET(rhead->h_len, ARCH_CONVERT) <= INT_MAX)); XLOG_HEADER_MAGIC_NUM);
bblks = (int) BTOBB(INT_GET(rhead->h_len, ARCH_CONVERT)); ASSERT(BTOBB(INT_GET(rhead->h_len, ARCH_CONVERT) <=
INT_MAX));
bblks = (int)BTOBB(INT_GET(rhead->h_len, ARCH_CONVERT));
ASSERT(bblks > 0); ASSERT(bblks > 0);
if ((error = xlog_bread(log, blk_no+hblks, bblks, dbp))) if ((error = xlog_bread(log, blk_no+hblks, bblks, dbp)))
goto bread_err2; goto bread_err2;
...@@ -3661,11 +3705,10 @@ xlog_do_recovery_pass(xlog_t *log, ...@@ -3661,11 +3705,10 @@ xlog_do_recovery_pass(xlog_t *log,
} }
} }
bread_err2: bread_err2:
xlog_put_bp(dbp); xlog_put_bp(dbp);
bread_err1: bread_err1:
xlog_put_bp(hbp); xlog_put_bp(hbp);
return error; return error;
} }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment