diff options
author | Luke Shumaker <lukeshu@lukeshu.com> | 2022-07-07 04:45:21 -0600 |
---|---|---|
committer | Luke Shumaker <lukeshu@lukeshu.com> | 2022-07-08 00:16:02 -0600 |
commit | 1bec6c5425f6df339e35d91468d4670f84020215 (patch) | |
tree | a1fff593e77142a8540b4c3d4a8eacce9fcfdcc2 /cmd | |
parent | 361e24ef2f568fe286f7fcc642e1cc8e626f4a88 (diff) |
better clear bad nodes
Diffstat (limited to 'cmd')
-rw-r--r-- | cmd/btrfs-clear-bad-nodes/main.go | 81 |
1 files changed, 26 insertions, 55 deletions
diff --git a/cmd/btrfs-clear-bad-nodes/main.go b/cmd/btrfs-clear-bad-nodes/main.go index 098d862..ddd8cd3 100644 --- a/cmd/btrfs-clear-bad-nodes/main.go +++ b/cmd/btrfs-clear-bad-nodes/main.go @@ -5,7 +5,6 @@ import ( "os" "lukeshu.com/btrfs-tools/pkg/btrfs" - "lukeshu.com/btrfs-tools/pkg/btrfs/btrfsitem" "lukeshu.com/btrfs-tools/pkg/btrfs/btrfsvol" "lukeshu.com/btrfs-tools/pkg/btrfsmisc" "lukeshu.com/btrfs-tools/pkg/util" @@ -33,6 +32,9 @@ func Main(imgfilenames ...string) (err error) { maybeSetErr(fs.Close()) }() + var uuidsInited bool + var metadataUUID, chunkTreeUUID btrfs.UUID + var treeName string var treeID btrfs.ObjID btrfsmisc.WalkFS(fs, btrfsmisc.WalkFSHandler{ @@ -47,63 +49,32 @@ func Main(imgfilenames ...string) (err error) { TreeWalkHandler: btrfs.TreeWalkHandler{ Node: func(path btrfs.TreePath, node *util.Ref[btrfsvol.LogicalAddr, btrfs.Node], err error) error { if node == nil || err == nil { + if !uuidsInited { + metadataUUID = node.Data.Head.MetadataUUID + chunkTreeUUID = node.Data.Head.ChunkTreeUUID + uuidsInited = true + } return nil } origErr := err - if len(path) < 2 { - sb, err := fs.Superblock() - if err != nil { - return err - } - chunkRoot, err := fs.TreeLookup(sb.Data.RootTree, btrfs.Key{ - ObjectID: btrfs.CHUNK_TREE_OBJECTID, - ItemType: btrfsitem.ROOT_ITEM_KEY, - Offset: 0, - }) - if err != nil { - return err - } - chunkRootBody, ok := chunkRoot.Body.(btrfsitem.Root) - if !ok { - return fmt.Errorf("CHUNK_TREE_OBJECTID ROOT_ITEM has malformed body") - } - node.Data = btrfs.Node{ - Size: node.Data.Size, - ChecksumType: node.Data.ChecksumType, - Head: btrfs.NodeHeader{ - //Checksum: filled below, - MetadataUUID: sb.Data.EffectiveMetadataUUID(), - Addr: node.Addr, - Flags: btrfs.NodeWritten, - BackrefRev: btrfs.MixedBackrefRev, - ChunkTreeUUID: chunkRootBody.UUID, - Generation: 0, - Owner: treeID, - NumItems: 0, - Level: 0, - }, - } - } else { - parentNode, err := fs.ReadNode(path[len(path)-2].NodeAddr) - if err != nil { - return err - } - node.Data = btrfs.Node{ - Size: node.Data.Size, - ChecksumType: node.Data.ChecksumType, - Head: btrfs.NodeHeader{ - //Checksum: filled below, - MetadataUUID: parentNode.Data.Head.MetadataUUID, - Addr: node.Addr, - Flags: btrfs.NodeWritten, - BackrefRev: parentNode.Data.Head.BackrefRev, - ChunkTreeUUID: parentNode.Data.Head.ChunkTreeUUID, - Generation: 0, - Owner: parentNode.Data.Head.Owner, - NumItems: 0, - Level: parentNode.Data.Head.Level - 1, - }, - } + if !uuidsInited { + return fmt.Errorf("cannot repair node@%v: not (yet?) sure what the chunk tree UUID is", node.Addr) + } + node.Data = btrfs.Node{ + Size: node.Data.Size, + ChecksumType: node.Data.ChecksumType, + Head: btrfs.NodeHeader{ + //Checksum: filled below, + MetadataUUID: metadataUUID, + Addr: node.Addr, + Flags: btrfs.NodeWritten, + BackrefRev: btrfs.MixedBackrefRev, + ChunkTreeUUID: chunkTreeUUID, + Generation: 0, + Owner: treeID, + NumItems: 0, + Level: path[len(path)-1].NodeLevel, + }, } node.Data.Head.Checksum, err = node.Data.CalculateChecksum() if err != nil { |