lightnvm: pblk: account for write error sectors in emeta
Lines inflicted with write errors lines might be recovered if they have not been recycled after write error garbage collection. Ensure that the emeta accounting of valid lbas is correct for such lines to avoid recovery inconsistencies. Signed-off-by: Hans Holmberg <hans.holmberg@cnexlabs.com> Reviewed-by: Javier González <javier@javigon.com> Signed-off-by: Matias Bjørling <mb@lightnvm.io> Signed-off-by: Jens Axboe <axboe@kernel.dk>
This commit is contained in:
parent
c12fa401ac
commit
ab3887be1e
|
@ -105,14 +105,20 @@ static void pblk_complete_write(struct pblk *pblk, struct nvm_rq *rqd,
|
|||
}
|
||||
|
||||
/* Map remaining sectors in chunk, starting from ppa */
|
||||
static void pblk_map_remaining(struct pblk *pblk, struct ppa_addr *ppa)
|
||||
static void pblk_map_remaining(struct pblk *pblk, struct ppa_addr *ppa,
|
||||
int rqd_ppas)
|
||||
{
|
||||
struct pblk_line *line;
|
||||
struct ppa_addr map_ppa = *ppa;
|
||||
__le64 addr_empty = cpu_to_le64(ADDR_EMPTY);
|
||||
__le64 *lba_list;
|
||||
u64 paddr;
|
||||
int done = 0;
|
||||
int n = 0;
|
||||
|
||||
line = pblk_ppa_to_line(pblk, *ppa);
|
||||
lba_list = emeta_to_lbas(pblk, line->emeta->buf);
|
||||
|
||||
spin_lock(&line->lock);
|
||||
|
||||
while (!done) {
|
||||
|
@ -121,10 +127,17 @@ static void pblk_map_remaining(struct pblk *pblk, struct ppa_addr *ppa)
|
|||
if (!test_and_set_bit(paddr, line->map_bitmap))
|
||||
line->left_msecs--;
|
||||
|
||||
if (n < rqd_ppas && lba_list[paddr] != addr_empty)
|
||||
line->nr_valid_lbas--;
|
||||
|
||||
lba_list[paddr] = addr_empty;
|
||||
|
||||
if (!test_and_set_bit(paddr, line->invalid_bitmap))
|
||||
le32_add_cpu(line->vsc, -1);
|
||||
|
||||
done = nvm_next_ppa_in_chk(pblk->dev, &map_ppa);
|
||||
|
||||
n++;
|
||||
}
|
||||
|
||||
line->w_err_gc->has_write_err = 1;
|
||||
|
@ -202,7 +215,7 @@ static void pblk_submit_rec(struct work_struct *work)
|
|||
|
||||
pblk_log_write_err(pblk, rqd);
|
||||
|
||||
pblk_map_remaining(pblk, ppa_list);
|
||||
pblk_map_remaining(pblk, ppa_list, rqd->nr_ppas);
|
||||
pblk_queue_resubmit(pblk, c_ctx);
|
||||
|
||||
pblk_up_rq(pblk, c_ctx->lun_bitmap);
|
||||
|
|
Loading…
Reference in New Issue