summaryrefslogtreecommitdiff
path: root/cmd/btrfs-clear-bad-nodes
diff options
context:
space:
mode:
authorLuke Shumaker <lukeshu@lukeshu.com>2022-07-07 04:45:21 -0600
committerLuke Shumaker <lukeshu@lukeshu.com>2022-07-08 00:16:02 -0600
commit1bec6c5425f6df339e35d91468d4670f84020215 (patch)
treea1fff593e77142a8540b4c3d4a8eacce9fcfdcc2 /cmd/btrfs-clear-bad-nodes
parent361e24ef2f568fe286f7fcc642e1cc8e626f4a88 (diff)
better clear bad nodes
Diffstat (limited to 'cmd/btrfs-clear-bad-nodes')
-rw-r--r--cmd/btrfs-clear-bad-nodes/main.go81
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 {