UBI: add ubi_leb_map interface
The idea of this interface belongs to Adrian Hunter. The interface is extremely useful when one has to have a guarantee that an LEB will contain all 0xFFs even in case of an unclean reboot. UBI does have an 'ubi_leb_erase()' call which may do this, but it is stupid and ineffecient, because it flushes whole queue. I should be re-worked to just be a pair of unmap, map calls. The user of the interfaci is UBIFS at the moment. Signed-off-by: Artem Bityutskiy <Artem.Bityutskiy@nokia.com>
This commit is contained in:
parent
94780d4de2
commit
393852ecfe
@ -656,11 +656,14 @@ retry:
|
|||||||
goto write_error;
|
goto write_error;
|
||||||
}
|
}
|
||||||
|
|
||||||
err = ubi_io_write_data(ubi, buf, pnum, offset, len);
|
if (len) {
|
||||||
if (err) {
|
err = ubi_io_write_data(ubi, buf, pnum, offset, len);
|
||||||
ubi_warn("failed to write %d bytes at offset %d of LEB %d:%d, "
|
if (err) {
|
||||||
"PEB %d", len, offset, vol_id, lnum, pnum);
|
ubi_warn("failed to write %d bytes at offset %d of "
|
||||||
goto write_error;
|
"LEB %d:%d, PEB %d", len, offset, vol_id,
|
||||||
|
lnum, pnum);
|
||||||
|
goto write_error;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
vol->eba_tbl[lnum] = pnum;
|
vol->eba_tbl[lnum] = pnum;
|
||||||
|
@ -546,6 +546,51 @@ int ubi_leb_unmap(struct ubi_volume_desc *desc, int lnum)
|
|||||||
}
|
}
|
||||||
EXPORT_SYMBOL_GPL(ubi_leb_unmap);
|
EXPORT_SYMBOL_GPL(ubi_leb_unmap);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* ubi_leb_map - map logical erasblock to a physical eraseblock.
|
||||||
|
* @desc: volume descriptor
|
||||||
|
* @lnum: logical eraseblock number
|
||||||
|
* @dtype: expected data type
|
||||||
|
*
|
||||||
|
* This function maps an un-mapped logical eraseblock @lnum to a physical
|
||||||
|
* eraseblock. This means, that after a successfull invocation of this
|
||||||
|
* function the logical eraseblock @lnum will be empty (contain only %0xFF
|
||||||
|
* bytes) and be mapped to a physical eraseblock, even if an unclean reboot
|
||||||
|
* happens.
|
||||||
|
*
|
||||||
|
* This function returns zero in case of success, %-EBADF if the volume is
|
||||||
|
* damaged because of an interrupted update, %-EBADMSG if the logical
|
||||||
|
* eraseblock is already mapped, and other negative error codes in case of
|
||||||
|
* other failures.
|
||||||
|
*/
|
||||||
|
int ubi_leb_map(struct ubi_volume_desc *desc, int lnum, int dtype)
|
||||||
|
{
|
||||||
|
struct ubi_volume *vol = desc->vol;
|
||||||
|
struct ubi_device *ubi = vol->ubi;
|
||||||
|
int vol_id = vol->vol_id;
|
||||||
|
|
||||||
|
dbg_msg("unmap LEB %d:%d", vol_id, lnum);
|
||||||
|
|
||||||
|
if (desc->mode == UBI_READONLY || vol->vol_type == UBI_STATIC_VOLUME)
|
||||||
|
return -EROFS;
|
||||||
|
|
||||||
|
if (lnum < 0 || lnum >= vol->reserved_pebs)
|
||||||
|
return -EINVAL;
|
||||||
|
|
||||||
|
if (dtype != UBI_LONGTERM && dtype != UBI_SHORTTERM &&
|
||||||
|
dtype != UBI_UNKNOWN)
|
||||||
|
return -EINVAL;
|
||||||
|
|
||||||
|
if (vol->upd_marker)
|
||||||
|
return -EBADF;
|
||||||
|
|
||||||
|
if (vol->eba_tbl[lnum] >= 0)
|
||||||
|
return -EBADMSG;
|
||||||
|
|
||||||
|
return ubi_eba_write_leb(ubi, vol_id, lnum, NULL, 0, 0, dtype);
|
||||||
|
}
|
||||||
|
EXPORT_SYMBOL_GPL(ubi_leb_map);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* ubi_is_mapped - check if logical eraseblock is mapped.
|
* ubi_is_mapped - check if logical eraseblock is mapped.
|
||||||
* @desc: volume descriptor
|
* @desc: volume descriptor
|
||||||
|
@ -167,6 +167,7 @@ int ubi_leb_change(struct ubi_volume_desc *desc, int lnum, const void *buf,
|
|||||||
int len, int dtype);
|
int len, int dtype);
|
||||||
int ubi_leb_erase(struct ubi_volume_desc *desc, int lnum);
|
int ubi_leb_erase(struct ubi_volume_desc *desc, int lnum);
|
||||||
int ubi_leb_unmap(struct ubi_volume_desc *desc, int lnum);
|
int ubi_leb_unmap(struct ubi_volume_desc *desc, int lnum);
|
||||||
|
int ubi_leb_map(struct ubi_volume_desc *desc, int lnum, int dtype);
|
||||||
int ubi_is_mapped(struct ubi_volume_desc *desc, int lnum);
|
int ubi_is_mapped(struct ubi_volume_desc *desc, int lnum);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
Loading…
Reference in New Issue
Block a user