UBIFS: reserve more space for index
At the moment UBIFS reserves twice old index size space for the index. But this is not enough in some cases, because if the indexing node are very fragmented and there are many small gaps, while the dirty index has big znodes - in-the-gaps method would fail. Thus, reserve trise as more, in which case we are guaranteed that we can commit in any case. Signed-off-by: Artem Bityutskiy <Artem.Bityutskiy@nokia.com>
This commit is contained in:
parent
1de9415906
commit
b364b41aeb
|
@ -263,8 +263,8 @@ int ubifs_calc_min_idx_lebs(struct ubifs_info *c)
|
||||||
|
|
||||||
idx_size = c->old_idx_sz + c->budg_idx_growth + c->budg_uncommitted_idx;
|
idx_size = c->old_idx_sz + c->budg_idx_growth + c->budg_uncommitted_idx;
|
||||||
|
|
||||||
/* And make sure we have twice the index size of space reserved */
|
/* And make sure we have trice the index size of space reserved */
|
||||||
idx_size <<= 1;
|
idx_size = idx_size + (idx_size << 1);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* We do not maintain 'old_idx_size' as 'old_idx_lebs'/'old_idx_bytes'
|
* We do not maintain 'old_idx_size' as 'old_idx_lebs'/'old_idx_bytes'
|
||||||
|
@ -388,11 +388,11 @@ static int can_use_rp(struct ubifs_info *c)
|
||||||
* This function makes sure UBIFS has enough free eraseblocks for index growth
|
* This function makes sure UBIFS has enough free eraseblocks for index growth
|
||||||
* and data.
|
* and data.
|
||||||
*
|
*
|
||||||
* When budgeting index space, UBIFS reserves twice as more LEBs as the index
|
* When budgeting index space, UBIFS reserves trice as more LEBs as the index
|
||||||
* would take if it was consolidated and written to the flash. This guarantees
|
* would take if it was consolidated and written to the flash. This guarantees
|
||||||
* that the "in-the-gaps" commit method always succeeds and UBIFS will always
|
* that the "in-the-gaps" commit method always succeeds and UBIFS will always
|
||||||
* be able to commit dirty index. So this function basically adds amount of
|
* be able to commit dirty index. So this function basically adds amount of
|
||||||
* budgeted index space to the size of the current index, multiplies this by 2,
|
* budgeted index space to the size of the current index, multiplies this by 3,
|
||||||
* and makes sure this does not exceed the amount of free eraseblocks.
|
* and makes sure this does not exceed the amount of free eraseblocks.
|
||||||
*
|
*
|
||||||
* Notes about @c->min_idx_lebs and @c->lst.idx_lebs variables:
|
* Notes about @c->min_idx_lebs and @c->lst.idx_lebs variables:
|
||||||
|
|
|
@ -290,9 +290,14 @@ int ubifs_find_dirty_leb(struct ubifs_info *c, struct ubifs_lprops *ret_lp,
|
||||||
idx_lp = idx_heap->arr[0];
|
idx_lp = idx_heap->arr[0];
|
||||||
sum = idx_lp->free + idx_lp->dirty;
|
sum = idx_lp->free + idx_lp->dirty;
|
||||||
/*
|
/*
|
||||||
* Since we reserve twice as more space for the index than it
|
* Since we reserve trice as more space for the index than it
|
||||||
* actually takes, it does not make sense to pick indexing LEBs
|
* actually takes, it does not make sense to pick indexing LEBs
|
||||||
* with less than half LEB of dirty space.
|
* with less than, say, half LEB of dirty space. May be half is
|
||||||
|
* not the optimal boundary - this should be tested and
|
||||||
|
* checked. This boundary should determine how much we use
|
||||||
|
* in-the-gaps to consolidate the index comparing to how much
|
||||||
|
* we use garbage collector to consolidate it. The "half"
|
||||||
|
* criteria just feels to be fine.
|
||||||
*/
|
*/
|
||||||
if (sum < min_space || sum < c->half_leb_size)
|
if (sum < min_space || sum < c->half_leb_size)
|
||||||
idx_lp = NULL;
|
idx_lp = NULL;
|
||||||
|
|
|
@ -308,7 +308,7 @@ static inline long long ubifs_reported_space(const struct ubifs_info *c,
|
||||||
{
|
{
|
||||||
int divisor, factor;
|
int divisor, factor;
|
||||||
|
|
||||||
divisor = UBIFS_MAX_DATA_NODE_SZ + (c->max_idx_node_sz << 1);
|
divisor = UBIFS_MAX_DATA_NODE_SZ + (c->max_idx_node_sz * 3);
|
||||||
factor = UBIFS_MAX_DATA_NODE_SZ - UBIFS_DATA_NODE_SZ;
|
factor = UBIFS_MAX_DATA_NODE_SZ - UBIFS_DATA_NODE_SZ;
|
||||||
do_div(free, divisor);
|
do_div(free, divisor);
|
||||||
|
|
||||||
|
|
|
@ -228,10 +228,10 @@ enum {
|
||||||
/* Minimum number of orphan area logical eraseblocks */
|
/* Minimum number of orphan area logical eraseblocks */
|
||||||
#define UBIFS_MIN_ORPH_LEBS 1
|
#define UBIFS_MIN_ORPH_LEBS 1
|
||||||
/*
|
/*
|
||||||
* Minimum number of main area logical eraseblocks (buds, 2 for the index, 1
|
* Minimum number of main area logical eraseblocks (buds, 3 for the index, 1
|
||||||
* for GC, 1 for deletions, and at least 1 for committed data).
|
* for GC, 1 for deletions, and at least 1 for committed data).
|
||||||
*/
|
*/
|
||||||
#define UBIFS_MIN_MAIN_LEBS (UBIFS_MIN_BUD_LEBS + 5)
|
#define UBIFS_MIN_MAIN_LEBS (UBIFS_MIN_BUD_LEBS + 6)
|
||||||
|
|
||||||
/* Minimum number of logical eraseblocks */
|
/* Minimum number of logical eraseblocks */
|
||||||
#define UBIFS_MIN_LEB_CNT (UBIFS_SB_LEBS + UBIFS_MST_LEBS + \
|
#define UBIFS_MIN_LEB_CNT (UBIFS_SB_LEBS + UBIFS_MST_LEBS + \
|
||||||
|
|
Loading…
Reference in a new issue