aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorSascha Hauer <s.hauer@pengutronix.de>2018-09-07 08:36:37 -0400
committerRichard Weinberger <richard@nod.at>2018-10-23 07:48:40 -0400
commit6f06d96fdf624be3e1d65c6100704a1fd79a30b7 (patch)
tree9f73bc0c8b651130327943b8b198aa781513e50e
parent6a98bc4614de8fac8c6d520a6b20b194e23c9936 (diff)
ubifs: Add auth nodes to garbage collector journal head
To be able to authenticate the garbage collector journal head add authentication nodes to the buds the garbage collector creates. Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de> Signed-off-by: Richard Weinberger <richard@nod.at>
-rw-r--r--fs/ubifs/gc.c46
1 files changed, 43 insertions, 3 deletions
diff --git a/fs/ubifs/gc.c b/fs/ubifs/gc.c
index 399d764f83cb..bf75fdc76fc3 100644
--- a/fs/ubifs/gc.c
+++ b/fs/ubifs/gc.c
@@ -365,12 +365,13 @@ static int move_nodes(struct ubifs_info *c, struct ubifs_scan_leb *sleb)
365 365
366 /* Write nodes to their new location. Use the first-fit strategy */ 366 /* Write nodes to their new location. Use the first-fit strategy */
367 while (1) { 367 while (1) {
368 int avail; 368 int avail, moved = 0;
369 struct ubifs_scan_node *snod, *tmp; 369 struct ubifs_scan_node *snod, *tmp;
370 370
371 /* Move data nodes */ 371 /* Move data nodes */
372 list_for_each_entry_safe(snod, tmp, &sleb->nodes, list) { 372 list_for_each_entry_safe(snod, tmp, &sleb->nodes, list) {
373 avail = c->leb_size - wbuf->offs - wbuf->used; 373 avail = c->leb_size - wbuf->offs - wbuf->used -
374 ubifs_auth_node_sz(c);
374 if (snod->len > avail) 375 if (snod->len > avail)
375 /* 376 /*
376 * Do not skip data nodes in order to optimize 377 * Do not skip data nodes in order to optimize
@@ -378,14 +379,21 @@ static int move_nodes(struct ubifs_info *c, struct ubifs_scan_leb *sleb)
378 */ 379 */
379 break; 380 break;
380 381
382 err = ubifs_shash_update(c, c->jheads[GCHD].log_hash,
383 snod->node, snod->len);
384 if (err)
385 goto out;
386
381 err = move_node(c, sleb, snod, wbuf); 387 err = move_node(c, sleb, snod, wbuf);
382 if (err) 388 if (err)
383 goto out; 389 goto out;
390 moved = 1;
384 } 391 }
385 392
386 /* Move non-data nodes */ 393 /* Move non-data nodes */
387 list_for_each_entry_safe(snod, tmp, &nondata, list) { 394 list_for_each_entry_safe(snod, tmp, &nondata, list) {
388 avail = c->leb_size - wbuf->offs - wbuf->used; 395 avail = c->leb_size - wbuf->offs - wbuf->used -
396 ubifs_auth_node_sz(c);
389 if (avail < min) 397 if (avail < min)
390 break; 398 break;
391 399
@@ -403,9 +411,41 @@ static int move_nodes(struct ubifs_info *c, struct ubifs_scan_leb *sleb)
403 continue; 411 continue;
404 } 412 }
405 413
414 err = ubifs_shash_update(c, c->jheads[GCHD].log_hash,
415 snod->node, snod->len);
416 if (err)
417 goto out;
418
406 err = move_node(c, sleb, snod, wbuf); 419 err = move_node(c, sleb, snod, wbuf);
407 if (err) 420 if (err)
408 goto out; 421 goto out;
422 moved = 1;
423 }
424
425 if (ubifs_authenticated(c) && moved) {
426 struct ubifs_auth_node *auth;
427
428 auth = kmalloc(ubifs_auth_node_sz(c), GFP_NOFS);
429 if (!auth) {
430 err = -ENOMEM;
431 goto out;
432 }
433
434 err = ubifs_prepare_auth_node(c, auth,
435 c->jheads[GCHD].log_hash);
436 if (err) {
437 kfree(auth);
438 goto out;
439 }
440
441 err = ubifs_wbuf_write_nolock(wbuf, auth,
442 ubifs_auth_node_sz(c));
443 if (err) {
444 kfree(auth);
445 goto out;
446 }
447
448 ubifs_add_dirt(c, wbuf->lnum, ubifs_auth_node_sz(c));
409 } 449 }
410 450
411 if (list_empty(&sleb->nodes) && list_empty(&nondata)) 451 if (list_empty(&sleb->nodes) && list_empty(&nondata))