/* This routine finds (to an approximation) the first block in the physical log which contains the given cycle. It uses a binary search algorithm. Note that the algorithm can not be perfect because the disk will not necessarily be perfect.  */
STATIC int xlog_find_cycle_start(xlog_t *log, xfs_buf_t *bp, xfs_daddr_t first_blk, xfs_daddr_t *last_blk, uint cycle)
/* This routine finds (to an approximation) the first block in the physical log which contains the given cycle. It uses a binary search algorithm. Note that the algorithm can not be perfect because the disk will not necessarily be perfect.  */
STATIC int xlog_find_cycle_start(xlog_t *log, xfs_buf_t *bp, xfs_daddr_t first_blk, xfs_daddr_t *last_blk, uint cycle)
{
	xfs_caddr_t	offset;
	xfs_daddr_t	mid_blk;
	uint		mid_cycle;
	int		error;
	mid_blk = BLK_AVG(first_blk, *last_blk);
	while (mid_blk != first_blk && mid_blk != *last_blk) {
		error = xlog_bread(log, mid_blk, 1, bp, &offset);
		if (error)
			return error;
		mid_cycle = xlog_get_cycle(offset);
		if (mid_cycle == cycle) {
			*last_blk = mid_blk;
		} else {
			first_blk = mid_blk;
		}
		mid_blk = BLK_AVG(first_blk, *last_blk);
	}
	ASSERT((mid_blk == first_blk && mid_blk+1 == *last_blk) ||
	       (mid_blk == *last_blk && mid_blk-1 == first_blk));
	return 0;
}