From 3b9d52b2e8020cce65d55516db36580d58a51f0b Mon Sep 17 00:00:00 2001 From: Michael Meffie Date: Sat, 8 Nov 2014 13:14:27 -0500 Subject: [PATCH 1/1] vldb_check: rebuild free list with -fix Rebuild the vldb free chain in addition to the hash chains when vldb_check is run with the -fix option. Print a FIX: message for entries added to the free chain. Example vldb with a broken free chain. $ vldb_check vldb.broken address 199364 (offset 0x30b04): Free vlentry not on free chain address 223192 (offset 0x36818): Free vlentry not on free chain address 235180 (offset 0x396ec): Free vlentry not on free chain Scanning 1707 entries for possible repairs $ vldb_check -fix vldb.broken Rebuilding 1707 entries FIX: Putting free entry on the free chain: addr=199364 (offset 0x30b04) FIX: Putting free entry on the free chain: addr=223192 (offset 0x36818) FIX: Putting free entry on the free chain: addr=235180 (offset 0x396ec) Thanks to Kostas Liakakis for reporting this bug. Change-Id: I57d6b17263ffe5f8818f70f8260a0dce8d85ab1f Reviewed-on: http://gerrit.openafs.org/11598 Reviewed-by: Benjamin Kaduk Tested-by: BuildBot --- src/vlserver/vldb_check.c | 15 ++++++++++++++- 1 file changed, 14 insertions(+), 1 deletion(-) diff --git a/src/vlserver/vldb_check.c b/src/vlserver/vldb_check.c index 33938b9..0a9d2e0 100644 --- a/src/vlserver/vldb_check.c +++ b/src/vlserver/vldb_check.c @@ -1429,8 +1429,9 @@ WorkerBee(struct cmd_syndesc *as, void *arock) if (fix) { /* - * If we are fixing we will rebuild all the hash lists from the ground up + * If we are fixing we will rebuild the free and hash lists from the ground up. */ + header.vital_header.freePtr = 0; memcpy(oldnamehash, header.VolnameHash, sizeof(oldnamehash)); memset(header.VolnameHash, 0, sizeof(header.VolnameHash)); @@ -1585,6 +1586,18 @@ WorkerBee(struct cmd_syndesc *as, void *arock) } writeMH(record[i].addr, block, MHblock); } + } else if (record[i].type & FR) { + if (fix) { + readentry(record[i].addr, &vlentry, &type); + vlentry.nextIdHash[0] = header.vital_header.freePtr; + header.vital_header.freePtr = record[i].addr; + if ((record[i].type & FRC) == 0) { + quiet_println + ("FIX: Putting free entry on the free chain: addr=%lu (offset 0x%0x)\n", + record[i].addr, OFFSET(record[i].addr)); + } + writeentry(record[i].addr, &vlentry); + } } } if (fix) { -- 1.9.4