]> git.kernelconcepts.de Git - karo-tx-linux.git/blobdiff - drivers/mtd/ubi/fastmap.c
mtd: nand: atmel: Add ->setup_data_interface() hooks
[karo-tx-linux.git] / drivers / mtd / ubi / fastmap.c
index c1f5c29e458ef86305376fa7b404f9c5b8e05681..b44c8d348e78ec0b19c884178e54c83a0967dc90 100644 (file)
@@ -828,6 +828,24 @@ static int find_fm_anchor(struct ubi_attach_info *ai)
        return ret;
 }
 
+static struct ubi_ainf_peb *clone_aeb(struct ubi_attach_info *ai,
+                                     struct ubi_ainf_peb *old)
+{
+       struct ubi_ainf_peb *new;
+
+       new = ubi_alloc_aeb(ai, old->pnum, old->ec);
+       if (!new)
+               return NULL;
+
+       new->vol_id = old->vol_id;
+       new->sqnum = old->sqnum;
+       new->lnum = old->lnum;
+       new->scrub = old->scrub;
+       new->copy_flag = old->copy_flag;
+
+       return new;
+}
+
 /**
  * ubi_scan_fastmap - scan the fastmap.
  * @ubi: UBI device object
@@ -847,7 +865,7 @@ int ubi_scan_fastmap(struct ubi_device *ubi, struct ubi_attach_info *ai,
        struct ubi_vid_hdr *vh;
        struct ubi_ec_hdr *ech;
        struct ubi_fastmap_layout *fm;
-       struct ubi_ainf_peb *tmp_aeb, *aeb;
+       struct ubi_ainf_peb *aeb;
        int i, used_blocks, pnum, fm_anchor, ret = 0;
        size_t fm_size;
        __be32 crc, tmp_crc;
@@ -857,9 +875,16 @@ int ubi_scan_fastmap(struct ubi_device *ubi, struct ubi_attach_info *ai,
        if (fm_anchor < 0)
                return UBI_NO_FASTMAP;
 
-       /* Move all (possible) fastmap blocks into our new attach structure. */
-       list_for_each_entry_safe(aeb, tmp_aeb, &scan_ai->fastmap, u.list)
-               list_move_tail(&aeb->u.list, &ai->fastmap);
+       /* Copy all (possible) fastmap blocks into our new attach structure. */
+       list_for_each_entry(aeb, &scan_ai->fastmap, u.list) {
+               struct ubi_ainf_peb *new;
+
+               new = clone_aeb(ai, aeb);
+               if (!new)
+                       return -ENOMEM;
+
+               list_add(&new->u.list, &ai->fastmap);
+       }
 
        down_write(&ubi->fm_protect);
        memset(ubi->fm_buf, 0, ubi->fm_size);