diff options
Diffstat (limited to 'fs/ubifs/replay.c')
| -rw-r--r-- | fs/ubifs/replay.c | 18 | 
1 files changed, 12 insertions, 6 deletions
diff --git a/fs/ubifs/replay.c b/fs/ubifs/replay.c index eed0fcff8d7..d3d6d365bfc 100644 --- a/fs/ubifs/replay.c +++ b/fs/ubifs/replay.c @@ -59,6 +59,7 @@ enum {   * @new_size: truncation new size   * @free: amount of free space in a bud   * @dirty: amount of dirty space in a bud from padding and deletion nodes + * @jhead: journal head number of the bud   *   * UBIFS journal replay must compare node sequence numbers, which means it must   * build a tree of node information to insert into the TNC. @@ -80,6 +81,7 @@ struct replay_entry {  		struct {  			int free;  			int dirty; +			int jhead;  		};  	};  }; @@ -159,6 +161,11 @@ static int set_bud_lprops(struct ubifs_info *c, struct replay_entry *r)  		err = PTR_ERR(lp);  		goto out;  	} + +	/* Make sure the journal head points to the latest bud */ +	err = ubifs_wbuf_seek_nolock(&c->jheads[r->jhead].wbuf, r->lnum, +				     c->leb_size - r->free, UBI_SHORTTERM); +  out:  	ubifs_release_lprops(c);  	return err; @@ -627,10 +634,6 @@ static int replay_bud(struct ubifs_info *c, int lnum, int offs, int jhead,  	ubifs_assert(sleb->endpt - offs >= used);  	ubifs_assert(sleb->endpt % c->min_io_size == 0); -	if (sleb->endpt + c->min_io_size <= c->leb_size && !c->ro_mount) -		err = ubifs_wbuf_seek_nolock(&c->jheads[jhead].wbuf, lnum, -					     sleb->endpt, UBI_SHORTTERM); -  	*dirty = sleb->endpt - offs - used;  	*free = c->leb_size - sleb->endpt; @@ -653,12 +656,14 @@ out_dump:   * @sqnum: sequence number   * @free: amount of free space in bud   * @dirty: amount of dirty space from padding and deletion nodes + * @jhead: journal head number for the bud   *   * This function inserts a reference node to the replay tree and returns zero   * in case of success or a negative error code in case of failure.   */  static int insert_ref_node(struct ubifs_info *c, int lnum, int offs, -			   unsigned long long sqnum, int free, int dirty) +			   unsigned long long sqnum, int free, int dirty, +			   int jhead)  {  	struct rb_node **p = &c->replay_tree.rb_node, *parent = NULL;  	struct replay_entry *r; @@ -688,6 +693,7 @@ static int insert_ref_node(struct ubifs_info *c, int lnum, int offs,  	r->flags = REPLAY_REF;  	r->free = free;  	r->dirty = dirty; +	r->jhead = jhead;  	rb_link_node(&r->rb, parent, p);  	rb_insert_color(&r->rb, &c->replay_tree); @@ -712,7 +718,7 @@ static int replay_buds(struct ubifs_info *c)  		if (err)  			return err;  		err = insert_ref_node(c, b->bud->lnum, b->bud->start, b->sqnum, -				      free, dirty); +				      free, dirty, b->bud->jhead);  		if (err)  			return err;  	}  |