From e2cdb05eac6726c59fe1831876fddd8037156d67 Mon Sep 17 00:00:00 2001 From: Luke Shumaker Date: Sun, 28 Aug 2022 17:55:36 -0600 Subject: btrfs: Split off btrfstree and btrfsprim sub-packages --- lib/btrfsprogs/btrfsinspect/mount.go | 19 ++-- lib/btrfsprogs/btrfsinspect/print_tree.go | 82 ++++++++-------- .../btrfsinspect/rebuildnodes/rebuildnodes.go | 64 +++++++------ lib/btrfsprogs/btrfsinspect/scandevices.go | 20 ++-- lib/btrfsprogs/btrfsutil/broken_btree.go | 106 ++++++++++++--------- lib/btrfsprogs/btrfsutil/csums.go | 7 +- lib/btrfsprogs/btrfsutil/walk.go | 26 ++--- 7 files changed, 174 insertions(+), 150 deletions(-) (limited to 'lib/btrfsprogs') diff --git a/lib/btrfsprogs/btrfsinspect/mount.go b/lib/btrfsprogs/btrfsinspect/mount.go index dbab7c7..5905034 100644 --- a/lib/btrfsprogs/btrfsinspect/mount.go +++ b/lib/btrfsprogs/btrfsinspect/mount.go @@ -23,6 +23,7 @@ import ( "git.lukeshu.com/btrfs-progs-ng/lib/btrfs" "git.lukeshu.com/btrfs-progs-ng/lib/btrfs/btrfsitem" + "git.lukeshu.com/btrfs-progs-ng/lib/btrfs/btrfsprim" "git.lukeshu.com/btrfs-progs-ng/lib/btrfsprogs/btrfsutil" "git.lukeshu.com/btrfs-progs-ng/lib/containers" "git.lukeshu.com/btrfs-progs-ng/lib/maps" @@ -43,7 +44,7 @@ func MountRO(ctx context.Context, fs *btrfs.FS, mountpoint string) error { rootSubvol := &subvolume{ Subvolume: btrfs.Subvolume{ FS: btrfsutil.NewBrokenTrees(ctx, fs), - TreeID: btrfs.FS_TREE_OBJECTID, + TreeID: btrfsprim.FS_TREE_OBJECTID, }, DeviceName: deviceName, Mountpoint: mountpoint, @@ -152,7 +153,7 @@ func inodeItemToFUSE(itemBody btrfsitem.Inode) fuseops.InodeAttributes { } } -func (sv *subvolume) LoadDir(inode btrfs.ObjID) (val *btrfs.Dir, err error) { +func (sv *subvolume) LoadDir(inode btrfsprim.ObjID) (val *btrfs.Dir, err error) { val, err = sv.Subvolume.LoadDir(inode) if val != nil { haveSubvolumes := false @@ -232,7 +233,7 @@ func (sv *subvolume) LookUpInode(_ context.Context, op *fuseops.LookUpInodeOp) e op.Parent = fuseops.InodeID(parent) } - dir, err := sv.LoadDir(btrfs.ObjID(op.Parent)) + dir, err := sv.LoadDir(btrfsprim.ObjID(op.Parent)) if err != nil { return err } @@ -283,7 +284,7 @@ func (sv *subvolume) GetInodeAttributes(_ context.Context, op *fuseops.GetInodeA op.Inode = fuseops.InodeID(inode) } - bareInode, err := sv.LoadBareInode(btrfs.ObjID(op.Inode)) + bareInode, err := sv.LoadBareInode(btrfsprim.ObjID(op.Inode)) if err != nil { return err } @@ -301,7 +302,7 @@ func (sv *subvolume) OpenDir(_ context.Context, op *fuseops.OpenDirOp) error { op.Inode = fuseops.InodeID(inode) } - dir, err := sv.LoadDir(btrfs.ObjID(op.Inode)) + dir, err := sv.LoadDir(btrfsprim.ObjID(op.Inode)) if err != nil { return err } @@ -354,7 +355,7 @@ func (sv *subvolume) ReleaseDirHandle(_ context.Context, op *fuseops.ReleaseDirH } func (sv *subvolume) OpenFile(_ context.Context, op *fuseops.OpenFileOp) error { - file, err := sv.LoadFile(btrfs.ObjID(op.Inode)) + file, err := sv.LoadFile(btrfsprim.ObjID(op.Inode)) if err != nil { return err } @@ -398,7 +399,7 @@ func (sv *subvolume) ReleaseFileHandle(_ context.Context, op *fuseops.ReleaseFil } func (sv *subvolume) ReadSymlink(_ context.Context, op *fuseops.ReadSymlinkOp) error { - file, err := sv.LoadFile(btrfs.ObjID(op.Inode)) + file, err := sv.LoadFile(btrfsprim.ObjID(op.Inode)) if err != nil { return err } @@ -420,7 +421,7 @@ func (sv *subvolume) ListXattr(_ context.Context, op *fuseops.ListXattrOp) error op.Inode = fuseops.InodeID(inode) } - fullInode, err := sv.LoadFullInode(btrfs.ObjID(op.Inode)) + fullInode, err := sv.LoadFullInode(btrfsprim.ObjID(op.Inode)) if err != nil { return err } @@ -452,7 +453,7 @@ func (sv *subvolume) GetXattr(_ context.Context, op *fuseops.GetXattrOp) error { op.Inode = fuseops.InodeID(inode) } - fullInode, err := sv.LoadFullInode(btrfs.ObjID(op.Inode)) + fullInode, err := sv.LoadFullInode(btrfsprim.ObjID(op.Inode)) if err != nil { return err } diff --git a/lib/btrfsprogs/btrfsinspect/print_tree.go b/lib/btrfsprogs/btrfsinspect/print_tree.go index 1568245..9e5a5d1 100644 --- a/lib/btrfsprogs/btrfsinspect/print_tree.go +++ b/lib/btrfsprogs/btrfsinspect/print_tree.go @@ -16,7 +16,9 @@ import ( "git.lukeshu.com/btrfs-progs-ng/lib/binstruct" "git.lukeshu.com/btrfs-progs-ng/lib/btrfs" "git.lukeshu.com/btrfs-progs-ng/lib/btrfs/btrfsitem" + "git.lukeshu.com/btrfs-progs-ng/lib/btrfs/btrfsprim" "git.lukeshu.com/btrfs-progs-ng/lib/btrfs/btrfssum" + "git.lukeshu.com/btrfs-progs-ng/lib/btrfs/btrfstree" "git.lukeshu.com/btrfs-progs-ng/lib/btrfs/btrfsvol" "git.lukeshu.com/btrfs-progs-ng/lib/diskio" "git.lukeshu.com/btrfs-progs-ng/lib/slices" @@ -31,50 +33,50 @@ func DumpTrees(ctx context.Context, out io.Writer, fs *btrfs.FS) { if superblock.RootTree != 0 { fmt.Fprintf(out, "root tree\n") - printTree(ctx, out, fs, btrfs.ROOT_TREE_OBJECTID) + printTree(ctx, out, fs, btrfsprim.ROOT_TREE_OBJECTID) } if superblock.ChunkTree != 0 { fmt.Fprintf(out, "chunk tree\n") - printTree(ctx, out, fs, btrfs.CHUNK_TREE_OBJECTID) + printTree(ctx, out, fs, btrfsprim.CHUNK_TREE_OBJECTID) } if superblock.LogTree != 0 { fmt.Fprintf(out, "log root tree\n") - printTree(ctx, out, fs, btrfs.TREE_LOG_OBJECTID) + printTree(ctx, out, fs, btrfsprim.TREE_LOG_OBJECTID) } if superblock.BlockGroupRoot != 0 { fmt.Fprintf(out, "block group tree\n") - printTree(ctx, out, fs, btrfs.BLOCK_GROUP_TREE_OBJECTID) + printTree(ctx, out, fs, btrfsprim.BLOCK_GROUP_TREE_OBJECTID) } fs.TreeWalk( ctx, - btrfs.ROOT_TREE_OBJECTID, - func(err *btrfs.TreeError) { + btrfsprim.ROOT_TREE_OBJECTID, + func(err *btrfstree.TreeError) { dlog.Error(ctx, err) }, - btrfs.TreeWalkHandler{ - Item: func(_ btrfs.TreePath, item btrfs.Item) error { + btrfstree.TreeWalkHandler{ + Item: func(_ btrfstree.TreePath, item btrfstree.Item) error { if item.Key.ItemType != btrfsitem.ROOT_ITEM_KEY { return nil } - treeName, ok := map[btrfs.ObjID]string{ - btrfs.ROOT_TREE_OBJECTID: "root", - btrfs.EXTENT_TREE_OBJECTID: "extent", - btrfs.CHUNK_TREE_OBJECTID: "chunk", - btrfs.DEV_TREE_OBJECTID: "device", - btrfs.FS_TREE_OBJECTID: "fs", - btrfs.ROOT_TREE_DIR_OBJECTID: "directory", - btrfs.CSUM_TREE_OBJECTID: "checksum", - btrfs.ORPHAN_OBJECTID: "orphan", - btrfs.TREE_LOG_OBJECTID: "log", - btrfs.TREE_LOG_FIXUP_OBJECTID: "log fixup", - btrfs.TREE_RELOC_OBJECTID: "reloc", - btrfs.DATA_RELOC_TREE_OBJECTID: "data reloc", - btrfs.EXTENT_CSUM_OBJECTID: "extent checksum", - btrfs.QUOTA_TREE_OBJECTID: "quota", - btrfs.UUID_TREE_OBJECTID: "uuid", - btrfs.FREE_SPACE_TREE_OBJECTID: "free space", - btrfs.MULTIPLE_OBJECTIDS: "multiple", - btrfs.BLOCK_GROUP_TREE_OBJECTID: "block group", + treeName, ok := map[btrfsprim.ObjID]string{ + btrfsprim.ROOT_TREE_OBJECTID: "root", + btrfsprim.EXTENT_TREE_OBJECTID: "extent", + btrfsprim.CHUNK_TREE_OBJECTID: "chunk", + btrfsprim.DEV_TREE_OBJECTID: "device", + btrfsprim.FS_TREE_OBJECTID: "fs", + btrfsprim.ROOT_TREE_DIR_OBJECTID: "directory", + btrfsprim.CSUM_TREE_OBJECTID: "checksum", + btrfsprim.ORPHAN_OBJECTID: "orphan", + btrfsprim.TREE_LOG_OBJECTID: "log", + btrfsprim.TREE_LOG_FIXUP_OBJECTID: "log fixup", + btrfsprim.TREE_RELOC_OBJECTID: "reloc", + btrfsprim.DATA_RELOC_TREE_OBJECTID: "data reloc", + btrfsprim.EXTENT_CSUM_OBJECTID: "extent checksum", + btrfsprim.QUOTA_TREE_OBJECTID: "quota", + btrfsprim.UUID_TREE_OBJECTID: "uuid", + btrfsprim.FREE_SPACE_TREE_OBJECTID: "free space", + btrfsprim.MULTIPLE_OBJECTIDS: "multiple", + btrfsprim.BLOCK_GROUP_TREE_OBJECTID: "block group", }[item.Key.ObjectID] if !ok { treeName = "file" @@ -93,22 +95,22 @@ func DumpTrees(ctx context.Context, out io.Writer, fs *btrfs.FS) { // printTree mimics btrfs-progs // kernel-shared/print-tree.c:btrfs_print_tree() and // kernel-shared/print-tree.c:btrfs_print_leaf() -func printTree(ctx context.Context, out io.Writer, fs *btrfs.FS, treeID btrfs.ObjID) { +func printTree(ctx context.Context, out io.Writer, fs *btrfs.FS, treeID btrfsprim.ObjID) { var itemOffset uint32 - handlers := btrfs.TreeWalkHandler{ - Node: func(path btrfs.TreePath, nodeRef *diskio.Ref[btrfsvol.LogicalAddr, btrfs.Node]) error { + handlers := btrfstree.TreeWalkHandler{ + Node: func(path btrfstree.TreePath, nodeRef *diskio.Ref[btrfsvol.LogicalAddr, btrfstree.Node]) error { printHeaderInfo(out, nodeRef.Data) - itemOffset = nodeRef.Data.Size - uint32(binstruct.StaticSize(btrfs.NodeHeader{})) + itemOffset = nodeRef.Data.Size - uint32(binstruct.StaticSize(btrfstree.NodeHeader{})) return nil }, - PreKeyPointer: func(_ btrfs.TreePath, item btrfs.KeyPointer) error { + PreKeyPointer: func(_ btrfstree.TreePath, item btrfstree.KeyPointer) error { fmt.Fprintf(out, "\t%v block %v gen %v\n", fmtKey(item.Key), item.BlockPtr, item.Generation) return nil }, - Item: func(path btrfs.TreePath, item btrfs.Item) error { + Item: func(path btrfstree.TreePath, item btrfstree.Item) error { i := path.Node(-1).FromItemIdx bs, _ := binstruct.Marshal(item.Body) itemSize := uint32(len(bs)) @@ -303,7 +305,7 @@ func printTree(ctx context.Context, out io.Writer, fs *btrfs.FS, treeID btrfs.Ob fmt.Fprintf(out, "\t\tpersistent item objectid %v offset %v\n", item.Key.ObjectID.Format(item.Key.ItemType), item.Key.Offset) switch item.Key.ObjectID { - case btrfs.DEV_STATS_OBJECTID: + case btrfsprim.DEV_STATS_OBJECTID: fmt.Fprintf(out, "\t\tdevice stats\n") fmt.Fprintf(out, "\t\twrite_errs %v read_errs %v flush_errs %v corruption_errs %v generation %v\n", body.Values[btrfsitem.DEV_STAT_WRITE_ERRS], @@ -347,7 +349,7 @@ func printTree(ctx context.Context, out io.Writer, fs *btrfs.FS, treeID btrfs.Ob fs.TreeWalk( ctx, treeID, - func(err *btrfs.TreeError) { + func(err *btrfstree.TreeError) { dlog.Error(ctx, err) }, handlers, @@ -355,7 +357,7 @@ func printTree(ctx context.Context, out io.Writer, fs *btrfs.FS, treeID btrfs.Ob } // printHeaderInfo mimics btrfs-progs kernel-shared/print-tree.c:print_header_info() -func printHeaderInfo(out io.Writer, node btrfs.Node) { +func printHeaderInfo(out io.Writer, node btrfstree.Node) { var typename string if node.Head.Level > 0 { // internal node typename = "node" @@ -400,7 +402,7 @@ func printExtentInlineRefs(out io.Writer, refs []btrfsitem.ExtentInlineRef) { switch ref.Type { case btrfsitem.TREE_BLOCK_REF_KEY: fmt.Fprintf(out, "\t\ttree block backref root %v\n", - btrfs.ObjID(ref.Offset)) + btrfsprim.ObjID(ref.Offset)) case btrfsitem.SHARED_BLOCK_REF_KEY: fmt.Fprintf(out, "\t\tshared block backref parent %v\n", ref.Offset) @@ -420,7 +422,7 @@ func printExtentInlineRefs(out io.Writer, refs []btrfsitem.ExtentInlineRef) { } // mimics print-tree.c:btrfs_print_key() -func fmtKey(key btrfs.Key) string { +func fmtKey(key btrfsprim.Key) string { var out strings.Builder fmt.Fprintf(&out, "key (%v %v", key.ObjectID.Format(key.ItemType), key.ItemType) switch key.ItemType { @@ -429,7 +431,7 @@ func fmtKey(key btrfs.Key) string { case btrfsitem.UUID_SUBVOL_KEY, btrfsitem.UUID_RECEIVED_SUBVOL_KEY: fmt.Fprintf(&out, " %#08x)", key.Offset) case btrfsitem.ROOT_ITEM_KEY: - fmt.Fprintf(&out, " %v)", btrfs.ObjID(key.Offset)) + fmt.Fprintf(&out, " %v)", btrfsprim.ObjID(key.Offset)) default: if key.Offset == math.MaxUint64 { fmt.Fprintf(&out, " -1)") @@ -440,7 +442,7 @@ func fmtKey(key btrfs.Key) string { return out.String() } -func fmtTime(t btrfs.Time) string { +func fmtTime(t btrfsprim.Time) string { return fmt.Sprintf("%v.%v (%v)", t.Sec, t.NSec, t.ToStd().Format("2006-01-02 15:04:05")) } diff --git a/lib/btrfsprogs/btrfsinspect/rebuildnodes/rebuildnodes.go b/lib/btrfsprogs/btrfsinspect/rebuildnodes/rebuildnodes.go index 4302d6a..5923b6c 100644 --- a/lib/btrfsprogs/btrfsinspect/rebuildnodes/rebuildnodes.go +++ b/lib/btrfsprogs/btrfsinspect/rebuildnodes/rebuildnodes.go @@ -13,6 +13,8 @@ import ( "github.com/datawire/dlib/dlog" "git.lukeshu.com/btrfs-progs-ng/lib/btrfs" + "git.lukeshu.com/btrfs-progs-ng/lib/btrfs/btrfsprim" + "git.lukeshu.com/btrfs-progs-ng/lib/btrfs/btrfstree" "git.lukeshu.com/btrfs-progs-ng/lib/btrfs/btrfsvol" "git.lukeshu.com/btrfs-progs-ng/lib/btrfsprogs/btrfsinspect" "git.lukeshu.com/btrfs-progs-ng/lib/btrfsprogs/btrfsutil" @@ -45,13 +47,13 @@ func RebuildNodes(ctx context.Context, fs *btrfs.FS, nodeScanResults btrfsinspec return rebuiltNodes, nil } -var maxKey = btrfs.Key{ +var maxKey = btrfsprim.Key{ ObjectID: math.MaxUint64, ItemType: math.MaxUint8, Offset: math.MaxUint64, } -func keyMm(key btrfs.Key) btrfs.Key { +func keyMm(key btrfsprim.Key) btrfsprim.Key { switch { case key.Offset > 0: key.Offset-- @@ -63,10 +65,10 @@ func keyMm(key btrfs.Key) btrfs.Key { return key } -func spanOfTreePath(fs *btrfs.FS, path btrfs.TreePath) (btrfs.Key, btrfs.Key) { +func spanOfTreePath(fs *btrfs.FS, path btrfstree.TreePath) (btrfsprim.Key, btrfsprim.Key) { // tree root error if len(path) == 0 { - return btrfs.Key{}, maxKey + return btrfsprim.Key{}, maxKey } // item error @@ -81,11 +83,11 @@ func spanOfTreePath(fs *btrfs.FS, path btrfs.TreePath) (btrfs.Key, btrfs.Key) { // // assume that path.Node(-1).ToNodeAddr is not readable, but that path.Node(-2).ToNodeAddr is. if len(path) == 1 { - return btrfs.Key{}, maxKey + return btrfsprim.Key{}, maxKey } parentNode, _ := fs.ReadNode(path.Parent()) low := parentNode.Data.BodyInternal[path.Node(-1).FromItemIdx].Key - var high btrfs.Key + var high btrfsprim.Key if path.Node(-1).FromItemIdx+1 < len(parentNode.Data.BodyInternal) { high = keyMm(parentNode.Data.BodyInternal[path.Node(-1).FromItemIdx+1].Key) } else { @@ -95,21 +97,21 @@ func spanOfTreePath(fs *btrfs.FS, path btrfs.TreePath) (btrfs.Key, btrfs.Key) { return low, high } -func walkFromNode(ctx context.Context, fs *btrfs.FS, nodeAddr btrfsvol.LogicalAddr, errHandle func(*btrfs.TreeError), cbs btrfs.TreeWalkHandler) { +func walkFromNode(ctx context.Context, fs *btrfs.FS, nodeAddr btrfsvol.LogicalAddr, errHandle func(*btrfstree.TreeError), cbs btrfstree.TreeWalkHandler) { sb, _ := fs.Superblock() - nodeRef, _ := btrfs.ReadNode[btrfsvol.LogicalAddr](fs, *sb, nodeAddr, btrfs.NodeExpectations{ + nodeRef, _ := btrfstree.ReadNode[btrfsvol.LogicalAddr](fs, *sb, nodeAddr, btrfstree.NodeExpectations{ LAddr: containers.Optional[btrfsvol.LogicalAddr]{OK: true, Val: nodeAddr}, }) if nodeRef == nil { return } - treeInfo := btrfs.TreeRoot{ + treeInfo := btrfstree.TreeRoot{ TreeID: nodeRef.Data.Head.Owner, RootNode: nodeAddr, Level: nodeRef.Data.Head.Level, Generation: nodeRef.Data.Head.Generation, } - fs.RawTreeWalk(ctx, treeInfo, errHandle, cbs) + btrfstree.TreesImpl{NodeSource: fs}.RawTreeWalk(ctx, treeInfo, errHandle, cbs) } func countNodes(nodeScanResults btrfsinspect.ScanDevicesResult) int { @@ -135,8 +137,8 @@ func lostAndFoundNodes(ctx context.Context, fs *btrfs.FS, nodeScanResults btrfsi attachedNodes := make(map[btrfsvol.LogicalAddr]struct{}) btrfsutil.WalkAllTrees(ctx, fs, btrfsutil.WalkAllTreesHandler{ - TreeWalkHandler: btrfs.TreeWalkHandler{ - Node: func(path btrfs.TreePath, _ *diskio.Ref[btrfsvol.LogicalAddr, btrfs.Node]) error { + TreeWalkHandler: btrfstree.TreeWalkHandler{ + Node: func(path btrfstree.TreePath, _ *diskio.Ref[btrfsvol.LogicalAddr, btrfstree.Node]) error { attachedNodes[path.Node(-1).ToNodeAddr] = struct{}{} done++ progress(done) @@ -174,11 +176,11 @@ func lostAndFoundNodes(ctx context.Context, fs *btrfs.FS, nodeScanResults btrfsi } walkCtx, cancel := context.WithCancel(ctx) walkFromNode(walkCtx, fs, potentialRoot, - func(err *btrfs.TreeError) { + func(err *btrfstree.TreeError) { // do nothing }, - btrfs.TreeWalkHandler{ - PreNode: func(path btrfs.TreePath) error { + btrfstree.TreeWalkHandler{ + PreNode: func(path btrfstree.TreePath) error { nodeAddr := path.Node(-1).ToNodeAddr if nodeAddr != potentialRoot { delete(orphanedRoots, nodeAddr) @@ -197,13 +199,13 @@ func lostAndFoundNodes(ctx context.Context, fs *btrfs.FS, nodeScanResults btrfsi return orphanedRoots, nil } -func getChunkTreeUUID(ctx context.Context, fs *btrfs.FS) (btrfs.UUID, bool) { +func getChunkTreeUUID(ctx context.Context, fs *btrfs.FS) (btrfsprim.UUID, bool) { ctx, cancel := context.WithCancel(ctx) - var ret btrfs.UUID + var ret btrfsprim.UUID var retOK bool btrfsutil.WalkAllTrees(ctx, fs, btrfsutil.WalkAllTreesHandler{ - TreeWalkHandler: btrfs.TreeWalkHandler{ - Node: func(path btrfs.TreePath, node *diskio.Ref[btrfsvol.LogicalAddr, btrfs.Node]) error { + TreeWalkHandler: btrfstree.TreeWalkHandler{ + Node: func(path btrfstree.TreePath, node *diskio.Ref[btrfsvol.LogicalAddr, btrfstree.Node]) error { ret = node.Data.Head.ChunkTreeUUID retOK = true cancel() @@ -219,8 +221,8 @@ func getChunkTreeUUID(ctx context.Context, fs *btrfs.FS) (btrfs.UUID, bool) { type RebuiltNode struct { Err error - MinKey, MaxKey btrfs.Key - btrfs.Node + MinKey, MaxKey btrfsprim.Key + btrfstree.Node } func reInitBrokenNodes(ctx context.Context, fs *btrfs.FS, nodeScanResults btrfsinspect.ScanDevicesResult, foundRoots map[btrfsvol.LogicalAddr]struct{}) (map[btrfsvol.LogicalAddr]*RebuiltNode, error) { @@ -247,20 +249,20 @@ func reInitBrokenNodes(ctx context.Context, fs *btrfs.FS, nodeScanResults btrfsi var done int rebuiltNodes := make(map[btrfsvol.LogicalAddr]*RebuiltNode) - walkHandler := btrfs.TreeWalkHandler{ - Node: func(_ btrfs.TreePath, _ *diskio.Ref[btrfsvol.LogicalAddr, btrfs.Node]) error { + walkHandler := btrfstree.TreeWalkHandler{ + Node: func(_ btrfstree.TreePath, _ *diskio.Ref[btrfsvol.LogicalAddr, btrfstree.Node]) error { done++ progress(done) return nil }, - BadNode: func(path btrfs.TreePath, node *diskio.Ref[btrfsvol.LogicalAddr, btrfs.Node], err error) error { + BadNode: func(path btrfstree.TreePath, node *diskio.Ref[btrfsvol.LogicalAddr, btrfstree.Node], err error) error { min, max := spanOfTreePath(fs, path) rebuiltNodes[path.Node(-1).ToNodeAddr] = &RebuiltNode{ Err: err, MinKey: min, MaxKey: max, - Node: btrfs.Node{ - Head: btrfs.NodeHeader{ + Node: btrfstree.Node{ + Head: btrfstree.NodeHeader{ MetadataUUID: sb.EffectiveMetadataUUID(), Addr: path.Node(-1).ToNodeAddr, ChunkTreeUUID: chunkTreeUUID, @@ -282,7 +284,7 @@ func reInitBrokenNodes(ctx context.Context, fs *btrfs.FS, nodeScanResults btrfsi }) for foundRoot := range foundRoots { walkFromNode(ctx, fs, foundRoot, - func(err *btrfs.TreeError) { + func(err *btrfstree.TreeError) { // do nothing }, walkHandler) @@ -293,8 +295,8 @@ func reInitBrokenNodes(ctx context.Context, fs *btrfs.FS, nodeScanResults btrfsi func reAttachNodes(ctx context.Context, fs *btrfs.FS, foundRoots map[btrfsvol.LogicalAddr]struct{}, rebuiltNodes map[btrfsvol.LogicalAddr]*RebuiltNode) error { // Index 'rebuiltNodes' for fast lookups. - gaps := make(map[btrfs.ObjID]map[uint8][]*RebuiltNode) - maxLevel := make(map[btrfs.ObjID]uint8) + gaps := make(map[btrfsprim.ObjID]map[uint8][]*RebuiltNode) + maxLevel := make(map[btrfsprim.ObjID]uint8) for _, node := range rebuiltNodes { maxLevel[node.Head.Owner] = slices.Max(maxLevel[node.Head.Owner], node.Head.Level) @@ -314,7 +316,7 @@ func reAttachNodes(ctx context.Context, fs *btrfs.FS, foundRoots map[btrfsvol.Lo // Attach foundRoots to the gaps. sb, _ := fs.Superblock() for foundLAddr := range foundRoots { - foundRef, err := btrfs.ReadNode[btrfsvol.LogicalAddr](fs, *sb, foundLAddr, btrfs.NodeExpectations{ + foundRef, err := btrfstree.ReadNode[btrfsvol.LogicalAddr](fs, *sb, foundLAddr, btrfstree.NodeExpectations{ LAddr: containers.Optional[btrfsvol.LogicalAddr]{OK: true, Val: foundLAddr}, }) if foundRef == nil { @@ -352,7 +354,7 @@ func reAttachNodes(ctx context.Context, fs *btrfs.FS, foundRoots map[btrfsvol.Lo continue } parent := parentGen[parentIdx] - parent.BodyInternal = append(parent.BodyInternal, btrfs.KeyPointer{ + parent.BodyInternal = append(parent.BodyInternal, btrfstree.KeyPointer{ Key: foundMinKey, BlockPtr: foundLAddr, Generation: foundRef.Data.Head.Generation, diff --git a/lib/btrfsprogs/btrfsinspect/scandevices.go b/lib/btrfsprogs/btrfsinspect/scandevices.go index 66a14c3..c25a86f 100644 --- a/lib/btrfsprogs/btrfsinspect/scandevices.go +++ b/lib/btrfsprogs/btrfsinspect/scandevices.go @@ -17,7 +17,9 @@ import ( "git.lukeshu.com/btrfs-progs-ng/lib/binstruct" "git.lukeshu.com/btrfs-progs-ng/lib/btrfs" "git.lukeshu.com/btrfs-progs-ng/lib/btrfs/btrfsitem" + "git.lukeshu.com/btrfs-progs-ng/lib/btrfs/btrfsprim" "git.lukeshu.com/btrfs-progs-ng/lib/btrfs/btrfssum" + "git.lukeshu.com/btrfs-progs-ng/lib/btrfs/btrfstree" "git.lukeshu.com/btrfs-progs-ng/lib/btrfs/btrfsvol" "git.lukeshu.com/btrfs-progs-ng/lib/btrfsprogs/btrfsutil" ) @@ -55,35 +57,35 @@ func ScanDevices(ctx context.Context, fs *btrfs.FS) (ScanDevicesResult, error) { type ScanOneDeviceResult struct { Checksums btrfssum.SumRun[btrfsvol.PhysicalAddr] FoundNodes map[btrfsvol.LogicalAddr][]btrfsvol.PhysicalAddr - FoundChunks []btrfs.SysChunk + FoundChunks []btrfstree.SysChunk FoundBlockGroups []SysBlockGroup FoundDevExtents []SysDevExtent FoundExtentCSums []SysExtentCSum } type SysBlockGroup struct { - Key btrfs.Key + Key btrfsprim.Key BG btrfsitem.BlockGroup } type SysDevExtent struct { - Key btrfs.Key + Key btrfsprim.Key DevExt btrfsitem.DevExtent } type SysExtentCSum struct { - Generation btrfs.Generation + Generation btrfsprim.Generation Sums btrfsitem.ExtentCSum } // ScanOneDevice mostly mimics btrfs-progs // cmds/rescue-chunk-recover.c:scan_one_device(). -func ScanOneDevice(ctx context.Context, dev *btrfs.Device, sb btrfs.Superblock) (ScanOneDeviceResult, error) { +func ScanOneDevice(ctx context.Context, dev *btrfs.Device, sb btrfstree.Superblock) (ScanOneDeviceResult, error) { result := ScanOneDeviceResult{ FoundNodes: make(map[btrfsvol.LogicalAddr][]btrfsvol.PhysicalAddr), } - sbSize := btrfsvol.PhysicalAddr(binstruct.StaticSize(btrfs.Superblock{})) + sbSize := btrfsvol.PhysicalAddr(binstruct.StaticSize(btrfstree.Superblock{})) devSize := dev.Size() if sb.NodeSize < sb.SectorSize { @@ -141,9 +143,9 @@ func ScanOneDevice(ctx context.Context, dev *btrfs.Device, sb btrfs.Superblock) } if checkForNode { - nodeRef, err := btrfs.ReadNode[btrfsvol.PhysicalAddr](dev, sb, pos, btrfs.NodeExpectations{}) + nodeRef, err := btrfstree.ReadNode[btrfsvol.PhysicalAddr](dev, sb, pos, btrfstree.NodeExpectations{}) if err != nil { - if !errors.Is(err, btrfs.ErrNotANode) { + if !errors.Is(err, btrfstree.ErrNotANode) { dlog.Errorf(ctx, "... dev[%q] error: %v", dev.Name(), err) } } else { @@ -159,7 +161,7 @@ func ScanOneDevice(ctx context.Context, dev *btrfs.Device, sb btrfs.Superblock) } //dlog.Tracef(ctx, "... dev[%q] node@%v: item %v: found chunk", // dev.Name(), nodeRef.Addr, i) - result.FoundChunks = append(result.FoundChunks, btrfs.SysChunk{ + result.FoundChunks = append(result.FoundChunks, btrfstree.SysChunk{ Key: item.Key, Chunk: chunk, }) diff --git a/lib/btrfsprogs/btrfsutil/broken_btree.go b/lib/btrfsprogs/btrfsutil/broken_btree.go index 3a8fb4b..6afaceb 100644 --- a/lib/btrfsprogs/btrfsutil/broken_btree.go +++ b/lib/btrfsprogs/btrfsutil/broken_btree.go @@ -15,6 +15,8 @@ import ( "github.com/datawire/dlib/dlog" "git.lukeshu.com/btrfs-progs-ng/lib/btrfs" + "git.lukeshu.com/btrfs-progs-ng/lib/btrfs/btrfsprim" + "git.lukeshu.com/btrfs-progs-ng/lib/btrfs/btrfstree" "git.lukeshu.com/btrfs-progs-ng/lib/btrfs/btrfsvol" "git.lukeshu.com/btrfs-progs-ng/lib/containers" "git.lukeshu.com/btrfs-progs-ng/lib/diskio" @@ -22,18 +24,18 @@ import ( ) type indexValue struct { - Key btrfs.Key + Key btrfsprim.Key ItemSize uint32 - Path btrfs.TreePath + Path btrfstree.TreePath } -var maxKey = btrfs.Key{ +var maxKey = btrfsprim.Key{ ObjectID: math.MaxUint64, ItemType: math.MaxUint8, Offset: math.MaxUint64, } -func keyMm(key btrfs.Key) btrfs.Key { +func keyMm(key btrfsprim.Key) btrfsprim.Key { switch { case key.Offset > 0: key.Offset-- @@ -45,10 +47,10 @@ func keyMm(key btrfs.Key) btrfs.Key { return key } -func span(fs *btrfs.FS, path btrfs.TreePath) (btrfs.Key, btrfs.Key) { +func span(fs *btrfs.FS, path btrfstree.TreePath) (btrfsprim.Key, btrfsprim.Key) { // tree root error if len(path) == 0 { - return btrfs.Key{}, maxKey + return btrfsprim.Key{}, maxKey } // item error @@ -63,11 +65,11 @@ func span(fs *btrfs.FS, path btrfs.TreePath) (btrfs.Key, btrfs.Key) { // // assume that path.Node(-1).NodeAddr is not readable, but that path.Node(-2).NodeAddr is. if len(path) == 1 { - return btrfs.Key{}, maxKey + return btrfsprim.Key{}, maxKey } parentNode, _ := fs.ReadNode(path.Parent()) low := parentNode.Data.BodyInternal[path.Node(-1).FromItemIdx].Key - var high btrfs.Key + var high btrfsprim.Key if path.Node(-1).FromItemIdx+1 < len(parentNode.Data.BodyInternal) { high = keyMm(parentNode.Data.BodyInternal[path.Node(-1).FromItemIdx+1].Key) } else { @@ -78,29 +80,29 @@ func span(fs *btrfs.FS, path btrfs.TreePath) (btrfs.Key, btrfs.Key) { } type spanError struct { - End btrfs.Key + End btrfsprim.Key Err error } type cachedIndex struct { TreeRootErr error - Items *containers.RBTree[btrfs.Key, indexValue] - Errors map[int]map[btrfs.Key][]spanError + Items *containers.RBTree[btrfsprim.Key, indexValue] + Errors map[int]map[btrfsprim.Key][]spanError } type brokenTrees struct { ctx context.Context inner *btrfs.FS - // btrfs.ROOT_TREE_OBJECTID + // btrfsprim.ROOT_TREE_OBJECTID rootTreeMu sync.Mutex rootTreeIndex *cachedIndex // for all other trees treeMu sync.Mutex - treeIndexes map[btrfs.ObjID]cachedIndex + treeIndexes map[btrfsprim.ObjID]cachedIndex } -var _ btrfs.Trees = (*brokenTrees)(nil) +var _ btrfstree.Trees = (*brokenTrees)(nil) // NewBrokenTrees wraps a *btrfs.FS to support looking up information // from broken trees. @@ -120,47 +122,59 @@ var _ btrfs.Trees = (*brokenTrees)(nil) // .TreeWalk to build an out-of-FS index of all of the items in the // tree, and re-implements TreeLookup, TreeSearch, and TreeSearchAll // using that index. -func NewBrokenTrees(ctx context.Context, inner *btrfs.FS) btrfs.Trees { +func NewBrokenTrees(ctx context.Context, inner *btrfs.FS) interface { + btrfstree.Trees + Superblock() (*btrfstree.Superblock, error) + ReadAt(p []byte, off btrfsvol.LogicalAddr) (int, error) +} { return &brokenTrees{ ctx: ctx, inner: inner, } } -func (bt *brokenTrees) treeIndex(treeID btrfs.ObjID) cachedIndex { - var treeRoot *btrfs.TreeRoot +func (bt *brokenTrees) treeIndex(treeID btrfsprim.ObjID) cachedIndex { + var treeRoot *btrfstree.TreeRoot var err error - if treeID == btrfs.ROOT_TREE_OBJECTID { + if treeID == btrfsprim.ROOT_TREE_OBJECTID { bt.rootTreeMu.Lock() defer bt.rootTreeMu.Unlock() if bt.rootTreeIndex != nil { return *bt.rootTreeIndex } - treeRoot, err = btrfs.LookupTreeRoot(bt.inner, treeID) + var sb *btrfstree.Superblock + sb, err = bt.inner.Superblock() + if err == nil { + treeRoot, err = btrfstree.LookupTreeRoot(bt.inner, *sb, treeID) + } } else { bt.treeMu.Lock() defer bt.treeMu.Unlock() if bt.treeIndexes == nil { - bt.treeIndexes = make(map[btrfs.ObjID]cachedIndex) + bt.treeIndexes = make(map[btrfsprim.ObjID]cachedIndex) } if cacheEntry, exists := bt.treeIndexes[treeID]; exists { return cacheEntry } - treeRoot, err = btrfs.LookupTreeRoot(bt, treeID) + var sb *btrfstree.Superblock + sb, err = bt.inner.Superblock() + if err == nil { + treeRoot, err = btrfstree.LookupTreeRoot(bt, *sb, treeID) + } } var cacheEntry cachedIndex - cacheEntry.Errors = make(map[int]map[btrfs.Key][]spanError) + cacheEntry.Errors = make(map[int]map[btrfsprim.Key][]spanError) if err != nil { cacheEntry.TreeRootErr = err } else { - cacheEntry.Items = &containers.RBTree[btrfs.Key, indexValue]{ - KeyFn: func(iv indexValue) btrfs.Key { return iv.Key }, + cacheEntry.Items = &containers.RBTree[btrfsprim.Key, indexValue]{ + KeyFn: func(iv indexValue) btrfsprim.Key { return iv.Key }, } dlog.Infof(bt.ctx, "indexing tree %v...", treeID) - bt.inner.RawTreeWalk( + btrfstree.TreesImpl{NodeSource: bt.inner}.RawTreeWalk( bt.ctx, *treeRoot, - func(err *btrfs.TreeError) { + func(err *btrfstree.TreeError) { if len(err.Path) > 0 && err.Path.Node(-1).ToNodeAddr == 0 { // This is a panic because on the filesystems I'm working with it more likely // indicates a bug in my item parser than a problem with the filesystem. @@ -169,7 +183,7 @@ func (bt *brokenTrees) treeIndex(treeID btrfs.ObjID) cachedIndex { invLvl := len(err.Path) lvlErrs, ok := cacheEntry.Errors[invLvl] if !ok { - lvlErrs = make(map[btrfs.Key][]spanError) + lvlErrs = make(map[btrfsprim.Key][]spanError) cacheEntry.Errors[invLvl] = lvlErrs } beg, end := span(bt.inner, err.Path) @@ -178,8 +192,8 @@ func (bt *brokenTrees) treeIndex(treeID btrfs.ObjID) cachedIndex { Err: err, }) }, - btrfs.TreeWalkHandler{ - Item: func(path btrfs.TreePath, item btrfs.Item) error { + btrfstree.TreeWalkHandler{ + Item: func(path btrfstree.TreePath, item btrfstree.Item) error { if cacheEntry.Items.Lookup(item.Key) != nil { // This is a panic because I'm not really sure what the best way to // handle this is, and so if this happens I want the program to crash @@ -197,7 +211,7 @@ func (bt *brokenTrees) treeIndex(treeID btrfs.ObjID) cachedIndex { ) dlog.Infof(bt.ctx, "... done indexing tree %v", treeID) } - if treeID == btrfs.ROOT_TREE_OBJECTID { + if treeID == btrfsprim.ROOT_TREE_OBJECTID { bt.rootTreeIndex = &cacheEntry } else { bt.treeIndexes[treeID] = cacheEntry @@ -205,29 +219,29 @@ func (bt *brokenTrees) treeIndex(treeID btrfs.ObjID) cachedIndex { return cacheEntry } -func (bt *brokenTrees) TreeLookup(treeID btrfs.ObjID, key btrfs.Key) (btrfs.Item, error) { - item, err := bt.TreeSearch(treeID, btrfs.KeySearch(key.Cmp)) +func (bt *brokenTrees) TreeLookup(treeID btrfsprim.ObjID, key btrfsprim.Key) (btrfstree.Item, error) { + item, err := bt.TreeSearch(treeID, btrfstree.KeySearch(key.Cmp)) if err != nil { err = fmt.Errorf("item with key=%v: %w", key, err) } return item, err } -func (bt *brokenTrees) TreeSearch(treeID btrfs.ObjID, fn func(btrfs.Key, uint32) int) (btrfs.Item, error) { +func (bt *brokenTrees) TreeSearch(treeID btrfsprim.ObjID, fn func(btrfsprim.Key, uint32) int) (btrfstree.Item, error) { index := bt.treeIndex(treeID) if index.TreeRootErr != nil { - return btrfs.Item{}, index.TreeRootErr + return btrfstree.Item{}, index.TreeRootErr } indexItem := index.Items.Search(func(indexItem indexValue) int { return fn(indexItem.Key, indexItem.ItemSize) }) if indexItem == nil { - return btrfs.Item{}, iofs.ErrNotExist + return btrfstree.Item{}, iofs.ErrNotExist } node, err := bt.inner.ReadNode(indexItem.Value.Path.Parent()) if err != nil { - return btrfs.Item{}, err + return btrfstree.Item{}, err } item := node.Data.BodyLeaf[indexItem.Value.Path.Node(-1).FromItemIdx] @@ -235,7 +249,7 @@ func (bt *brokenTrees) TreeSearch(treeID btrfs.ObjID, fn func(btrfs.Key, uint32) return item, nil } -func (bt *brokenTrees) TreeSearchAll(treeID btrfs.ObjID, fn func(btrfs.Key, uint32) int) ([]btrfs.Item, error) { +func (bt *brokenTrees) TreeSearchAll(treeID btrfsprim.ObjID, fn func(btrfsprim.Key, uint32) int) ([]btrfstree.Item, error) { index := bt.treeIndex(treeID) if index.TreeRootErr != nil { return nil, index.TreeRootErr @@ -247,8 +261,8 @@ func (bt *brokenTrees) TreeSearchAll(treeID btrfs.ObjID, fn func(btrfs.Key, uint return nil, iofs.ErrNotExist } - ret := make([]btrfs.Item, len(indexItems)) - var node *diskio.Ref[btrfsvol.LogicalAddr, btrfs.Node] + ret := make([]btrfstree.Item, len(indexItems)) + var node *diskio.Ref[btrfsvol.LogicalAddr, btrfstree.Node] for i := range indexItems { if node == nil || node.Addr != indexItems[i].Path.Node(-2).ToNodeAddr { var err error @@ -283,18 +297,18 @@ func (bt *brokenTrees) TreeSearchAll(treeID btrfs.ObjID, fn func(btrfs.Key, uint return ret, nil } -func (bt *brokenTrees) TreeWalk(ctx context.Context, treeID btrfs.ObjID, errHandle func(*btrfs.TreeError), cbs btrfs.TreeWalkHandler) { +func (bt *brokenTrees) TreeWalk(ctx context.Context, treeID btrfsprim.ObjID, errHandle func(*btrfstree.TreeError), cbs btrfstree.TreeWalkHandler) { index := bt.treeIndex(treeID) if index.TreeRootErr != nil { - errHandle(&btrfs.TreeError{ - Path: btrfs.TreePath{{ + errHandle(&btrfstree.TreeError{ + Path: btrfstree.TreePath{{ FromTree: treeID, }}, Err: index.TreeRootErr, }) return } - var node *diskio.Ref[btrfsvol.LogicalAddr, btrfs.Node] + var node *diskio.Ref[btrfsvol.LogicalAddr, btrfstree.Node] _ = index.Items.Walk(func(indexItem *containers.RBNode[indexValue]) error { if ctx.Err() != nil { return ctx.Err() @@ -307,20 +321,20 @@ func (bt *brokenTrees) TreeWalk(ctx context.Context, treeID btrfs.ObjID, errHand var err error node, err = bt.inner.ReadNode(indexItem.Value.Path.Parent()) if err != nil { - errHandle(&btrfs.TreeError{Path: indexItem.Value.Path, Err: err}) + errHandle(&btrfstree.TreeError{Path: indexItem.Value.Path, Err: err}) return nil } } item := node.Data.BodyLeaf[indexItem.Value.Path.Node(-1).FromItemIdx] if err := cbs.Item(indexItem.Value.Path, item); err != nil { - errHandle(&btrfs.TreeError{Path: indexItem.Value.Path, Err: err}) + errHandle(&btrfstree.TreeError{Path: indexItem.Value.Path, Err: err}) } } return nil }) } -func (bt *brokenTrees) Superblock() (*btrfs.Superblock, error) { +func (bt *brokenTrees) Superblock() (*btrfstree.Superblock, error) { return bt.inner.Superblock() } diff --git a/lib/btrfsprogs/btrfsutil/csums.go b/lib/btrfsprogs/btrfsutil/csums.go index 3c3d85f..a49f584 100644 --- a/lib/btrfsprogs/btrfsutil/csums.go +++ b/lib/btrfsprogs/btrfsutil/csums.go @@ -9,11 +9,12 @@ import ( "git.lukeshu.com/btrfs-progs-ng/lib/btrfs" "git.lukeshu.com/btrfs-progs-ng/lib/btrfs/btrfsitem" + "git.lukeshu.com/btrfs-progs-ng/lib/btrfs/btrfsprim" "git.lukeshu.com/btrfs-progs-ng/lib/btrfs/btrfssum" "git.lukeshu.com/btrfs-progs-ng/lib/btrfs/btrfsvol" ) -func ChecksumLogical(fs btrfs.Trees, alg btrfssum.CSumType, laddr btrfsvol.LogicalAddr) (btrfssum.CSum, error) { +func ChecksumLogical(fs *btrfs.FS, alg btrfssum.CSumType, laddr btrfsvol.LogicalAddr) (btrfssum.CSum, error) { var dat [btrfssum.BlockSize]byte if _, err := fs.ReadAt(dat[:], laddr); err != nil { return btrfssum.CSum{}, err @@ -37,8 +38,8 @@ func ChecksumQualifiedPhysical(fs *btrfs.FS, alg btrfssum.CSumType, paddr btrfsv return ChecksumPhysical(dev, alg, paddr.Addr) } -func LookupCSum(fs btrfs.Trees, alg btrfssum.CSumType, laddr btrfsvol.LogicalAddr) (btrfssum.SumRun[btrfsvol.LogicalAddr], error) { - item, err := fs.TreeSearch(btrfs.CSUM_TREE_OBJECTID, func(key btrfs.Key, size uint32) int { +func LookupCSum(fs *btrfs.FS, alg btrfssum.CSumType, laddr btrfsvol.LogicalAddr) (btrfssum.SumRun[btrfsvol.LogicalAddr], error) { + item, err := fs.TreeSearch(btrfsprim.CSUM_TREE_OBJECTID, func(key btrfsprim.Key, size uint32) int { itemBeg := btrfsvol.LogicalAddr(key.ObjectID) numSums := int64(size) / int64(alg.Size()) itemEnd := itemBeg + btrfsvol.LogicalAddr(numSums*btrfssum.BlockSize) diff --git a/lib/btrfsprogs/btrfsutil/walk.go b/lib/btrfsprogs/btrfsutil/walk.go index c597e5e..2809737 100644 --- a/lib/btrfsprogs/btrfsutil/walk.go +++ b/lib/btrfsprogs/btrfsutil/walk.go @@ -10,11 +10,13 @@ import ( "git.lukeshu.com/btrfs-progs-ng/lib/btrfs" "git.lukeshu.com/btrfs-progs-ng/lib/btrfs/btrfsitem" + "git.lukeshu.com/btrfs-progs-ng/lib/btrfs/btrfsprim" + "git.lukeshu.com/btrfs-progs-ng/lib/btrfs/btrfstree" ) type WalkError struct { TreeName string - Err *btrfs.TreeError + Err *btrfstree.TreeError } func (e *WalkError) Unwrap() error { return e.Err } @@ -26,10 +28,10 @@ func (e *WalkError) Error() string { type WalkAllTreesHandler struct { Err func(*WalkError) // Callbacks for entire trees - PreTree func(name string, id btrfs.ObjID) - PostTree func(name string, id btrfs.ObjID) + PreTree func(name string, id btrfsprim.ObjID) + PostTree func(name string, id btrfsprim.ObjID) // Callbacks for nodes or smaller - btrfs.TreeWalkHandler + btrfstree.TreeWalkHandler } // WalkAllTrees walks all trees in a *btrfs.FS. Rather than returning @@ -40,31 +42,31 @@ func WalkAllTrees(ctx context.Context, fs *btrfs.FS, cbs WalkAllTreesHandler) { trees := []struct { Name string - ID btrfs.ObjID + ID btrfsprim.ObjID }{ { Name: "root tree", - ID: btrfs.ROOT_TREE_OBJECTID, + ID: btrfsprim.ROOT_TREE_OBJECTID, }, { Name: "chunk tree", - ID: btrfs.CHUNK_TREE_OBJECTID, + ID: btrfsprim.CHUNK_TREE_OBJECTID, }, { Name: "log tree", - ID: btrfs.TREE_LOG_OBJECTID, + ID: btrfsprim.TREE_LOG_OBJECTID, }, { Name: "block group tree", - ID: btrfs.BLOCK_GROUP_TREE_OBJECTID, + ID: btrfsprim.BLOCK_GROUP_TREE_OBJECTID, }, } origItem := cbs.Item - cbs.Item = func(path btrfs.TreePath, item btrfs.Item) error { + cbs.Item = func(path btrfstree.TreePath, item btrfstree.Item) error { if item.Key.ItemType == btrfsitem.ROOT_ITEM_KEY { trees = append(trees, struct { Name string - ID btrfs.ObjID + ID btrfsprim.ObjID }{ Name: fmt.Sprintf("tree %v (via %v %v)", item.Key.ObjectID.Format(0), treeName, path), @@ -86,7 +88,7 @@ func WalkAllTrees(ctx context.Context, fs *btrfs.FS, cbs WalkAllTreesHandler) { fs.TreeWalk( ctx, tree.ID, - func(err *btrfs.TreeError) { cbs.Err(&WalkError{TreeName: treeName, Err: err}) }, + func(err *btrfstree.TreeError) { cbs.Err(&WalkError{TreeName: treeName, Err: err}) }, cbs.TreeWalkHandler, ) if cbs.PostTree != nil { -- cgit v1.2.3-2-g168b