summaryrefslogtreecommitdiff
path: root/lib/btrfsutil
diff options
context:
space:
mode:
authorLuke Shumaker <lukeshu@lukeshu.com>2023-03-16 09:17:35 -0600
committerLuke Shumaker <lukeshu@lukeshu.com>2023-03-17 18:38:44 -0400
commit1bc243ca607c22e232017b0f1b4badcde288a9b3 (patch)
tree7273d158c1184d2c582a15fc36af695eb1a20943 /lib/btrfsutil
parent0f85e72d1331b49b52925d6cc5ad083a0376104c (diff)
btrfstree: Have ReadNode return a *Node rather than a *diskio.Ref[Addr, Node]
... and take a ReaderAt instead of a diskio.File.
Diffstat (limited to 'lib/btrfsutil')
-rw-r--r--lib/btrfsutil/graph.go32
-rw-r--r--lib/btrfsutil/listnodes.go5
-rw-r--r--lib/btrfsutil/old_rebuilt_forrest.go37
-rw-r--r--lib/btrfsutil/rebuilt_readitem.go28
-rw-r--r--lib/btrfsutil/scan.go9
-rw-r--r--lib/btrfsutil/skinny_paths.go24
6 files changed, 66 insertions, 69 deletions
diff --git a/lib/btrfsutil/graph.go b/lib/btrfsutil/graph.go
index 09a17b4..a7c299a 100644
--- a/lib/btrfsutil/graph.go
+++ b/lib/btrfsutil/graph.go
@@ -149,29 +149,29 @@ func NewGraph(sb btrfstree.Superblock) *Graph {
return g
}
-func (g Graph) InsertNode(nodeRef *diskio.Ref[btrfsvol.LogicalAddr, btrfstree.Node]) {
+func (g Graph) InsertNode(node *btrfstree.Node) {
nodeData := GraphNode{
- Level: nodeRef.Data.Head.Level,
- Generation: nodeRef.Data.Head.Generation,
- Owner: nodeRef.Data.Head.Owner,
+ Level: node.Head.Level,
+ Generation: node.Head.Generation,
+ Owner: node.Head.Owner,
}
- if nodeRef.Data.Head.Level == 0 {
+ if node.Head.Level == 0 {
cnt := 0
- for _, item := range nodeRef.Data.BodyLeaf {
+ for _, item := range node.BodyLeaf {
if _, ok := item.Body.(*btrfsitem.Root); ok {
cnt++
}
}
kps := make([]GraphEdge, 0, cnt)
- keys := make([]btrfsprim.Key, len(nodeRef.Data.BodyLeaf))
+ keys := make([]btrfsprim.Key, len(node.BodyLeaf))
nodeData.Items = keys
- g.Nodes[nodeRef.Addr] = nodeData
- for i, item := range nodeRef.Data.BodyLeaf {
+ g.Nodes[node.Head.Addr] = nodeData
+ for i, item := range node.BodyLeaf {
keys[i] = item.Key
if itemBody, ok := item.Body.(*btrfsitem.Root); ok {
kps = append(kps, GraphEdge{
- FromRoot: nodeRef.Addr,
+ FromRoot: node.Head.Addr,
FromItem: i,
FromTree: item.Key.ObjectID,
ToNode: itemBody.ByteNr,
@@ -182,15 +182,15 @@ func (g Graph) InsertNode(nodeRef *diskio.Ref[btrfsvol.LogicalAddr, btrfstree.No
}
}
} else {
- g.Nodes[nodeRef.Addr] = nodeData
- kps := make([]GraphEdge, len(nodeRef.Data.BodyInterior))
- for i, kp := range nodeRef.Data.BodyInterior {
+ g.Nodes[node.Head.Addr] = nodeData
+ kps := make([]GraphEdge, len(node.BodyInterior))
+ for i, kp := range node.BodyInterior {
kps[i] = GraphEdge{
- FromNode: nodeRef.Addr,
+ FromNode: node.Head.Addr,
FromItem: i,
- FromTree: nodeRef.Data.Head.Owner,
+ FromTree: node.Head.Owner,
ToNode: kp.BlockPtr,
- ToLevel: nodeRef.Data.Head.Level - 1,
+ ToLevel: node.Head.Level - 1,
ToKey: kp.Key,
ToGeneration: kp.Generation,
}
diff --git a/lib/btrfsutil/listnodes.go b/lib/btrfsutil/listnodes.go
index 5505d23..70b647c 100644
--- a/lib/btrfsutil/listnodes.go
+++ b/lib/btrfsutil/listnodes.go
@@ -11,7 +11,6 @@ import (
"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"
"git.lukeshu.com/btrfs-progs-ng/lib/maps"
"git.lukeshu.com/btrfs-progs-ng/lib/textui"
)
@@ -44,8 +43,8 @@ func (*nodeScanner) ScanSector(context.Context, *btrfs.Device, btrfsvol.Physical
return nil
}
-func (s *nodeScanner) ScanNode(_ context.Context, nodeRef *diskio.Ref[btrfsvol.PhysicalAddr, btrfstree.Node]) error {
- s.nodes.Insert(nodeRef.Data.Head.Addr)
+func (s *nodeScanner) ScanNode(_ context.Context, _ btrfsvol.PhysicalAddr, node *btrfstree.Node) error {
+ s.nodes.Insert(node.Head.Addr)
return nil
}
diff --git a/lib/btrfsutil/old_rebuilt_forrest.go b/lib/btrfsutil/old_rebuilt_forrest.go
index d49f34e..2ec1d83 100644
--- a/lib/btrfsutil/old_rebuilt_forrest.go
+++ b/lib/btrfsutil/old_rebuilt_forrest.go
@@ -17,7 +17,6 @@ import (
"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"
)
type oldRebuiltTree struct {
@@ -226,12 +225,12 @@ func (bt *OldRebuiltForrest) TreeSearch(treeID btrfsprim.ObjID, searcher btrfstr
itemPath := bt.arena.Inflate(indexItem.Value.Path)
node, err := bt.inner.ReadNode(itemPath.Parent())
- defer btrfstree.FreeNodeRef(node)
+ defer node.Free()
if err != nil {
return btrfstree.Item{}, fmt.Errorf("item with %s: %w", searcher, bt.addErrs(tree, searcher.Search, err))
}
- item := node.Data.BodyLeaf[itemPath.Node(-1).FromItemSlot]
+ item := node.BodyLeaf[itemPath.Node(-1).FromItemSlot]
item.Body = item.Body.CloneItem()
// Since we were only asked to return 1 item, it isn't
@@ -259,22 +258,22 @@ func (bt *OldRebuiltForrest) TreeSearchAll(treeID btrfsprim.ObjID, searcher btrf
}
ret := make([]btrfstree.Item, len(indexItems))
- var node *diskio.Ref[btrfsvol.LogicalAddr, btrfstree.Node]
+ var node *btrfstree.Node
for i := range indexItems {
itemPath := bt.arena.Inflate(indexItems[i].Path)
- if node == nil || node.Addr != itemPath.Node(-2).ToNodeAddr {
+ if node == nil || node.Head.Addr != itemPath.Node(-2).ToNodeAddr {
var err error
- btrfstree.FreeNodeRef(node)
+ node.Free()
node, err = bt.inner.ReadNode(itemPath.Parent())
if err != nil {
- btrfstree.FreeNodeRef(node)
+ node.Free()
return nil, fmt.Errorf("items with %s: %w", searcher, bt.addErrs(tree, searcher.Search, err))
}
}
- ret[i] = node.Data.BodyLeaf[itemPath.Node(-1).FromItemSlot]
+ ret[i] = node.BodyLeaf[itemPath.Node(-1).FromItemSlot]
ret[i].Body = ret[i].Body.CloneItem()
}
- btrfstree.FreeNodeRef(node)
+ node.Free()
err := bt.addErrs(tree, searcher.Search, nil)
if err != nil {
@@ -298,7 +297,7 @@ func (bt *OldRebuiltForrest) TreeWalk(ctx context.Context, treeID btrfsprim.ObjI
if cbs.Item == nil {
return
}
- var node *diskio.Ref[btrfsvol.LogicalAddr, btrfstree.Node]
+ var node *btrfstree.Node
tree.Items.Range(func(indexItem *containers.RBNode[oldRebuiltTreeValue]) bool {
if ctx.Err() != nil {
return false
@@ -307,23 +306,23 @@ func (bt *OldRebuiltForrest) TreeWalk(ctx context.Context, treeID btrfsprim.ObjI
return false
}
itemPath := bt.arena.Inflate(indexItem.Value.Path)
- if node == nil || node.Addr != itemPath.Node(-2).ToNodeAddr {
+ if node == nil || node.Head.Addr != itemPath.Node(-2).ToNodeAddr {
var err error
- btrfstree.FreeNodeRef(node)
+ node.Free()
node, err = bt.inner.ReadNode(itemPath.Parent())
if err != nil {
- btrfstree.FreeNodeRef(node)
+ node.Free()
errHandle(&btrfstree.TreeError{Path: itemPath, Err: err})
return true
}
}
- item := node.Data.BodyLeaf[itemPath.Node(-1).FromItemSlot]
+ item := node.BodyLeaf[itemPath.Node(-1).FromItemSlot]
if err := cbs.Item(itemPath, item); err != nil {
errHandle(&btrfstree.TreeError{Path: itemPath, Err: err})
}
return true
})
- btrfstree.FreeNodeRef(node)
+ node.Free()
}
func (bt *OldRebuiltForrest) Superblock() (*btrfstree.Superblock, error) {
@@ -343,8 +342,8 @@ func (bt *OldRebuiltForrest) Augment(treeID btrfsprim.ObjID, nodeAddr btrfsvol.L
if tree.RootErr != nil {
return nil, tree.RootErr
}
- nodeRef, err := btrfstree.ReadNode[btrfsvol.LogicalAddr](bt.inner, *sb, nodeAddr, btrfstree.NodeExpectations{})
- defer btrfstree.FreeNodeRef(nodeRef)
+ node, err := btrfstree.ReadNode[btrfsvol.LogicalAddr](bt.inner, *sb, nodeAddr, btrfstree.NodeExpectations{})
+ defer node.Free()
if err != nil {
return nil, err
}
@@ -352,8 +351,8 @@ func (bt *OldRebuiltForrest) Augment(treeID btrfsprim.ObjID, nodeAddr btrfsvol.L
bt.rawTreeWalk(btrfstree.TreeRoot{
TreeID: treeID,
RootNode: nodeAddr,
- Level: nodeRef.Data.Head.Level,
- Generation: nodeRef.Data.Head.Generation,
+ Level: node.Head.Level,
+ Generation: node.Head.Generation,
}, tree, &ret)
return ret, nil
}
diff --git a/lib/btrfsutil/rebuilt_readitem.go b/lib/btrfsutil/rebuilt_readitem.go
index 016299c..b1a0656 100644
--- a/lib/btrfsutil/rebuilt_readitem.go
+++ b/lib/btrfsutil/rebuilt_readitem.go
@@ -49,7 +49,7 @@ type KeyIO struct {
Sizes map[ItemPtr]SizeAndErr // EXTENT_CSUM and EXTENT_DATA
mu sync.Mutex
- cache containers.ARCache[btrfsvol.LogicalAddr, *diskio.Ref[btrfsvol.LogicalAddr, btrfstree.Node]]
+ cache containers.ARCache[btrfsvol.LogicalAddr, *btrfstree.Node]
}
func NewKeyIO(file diskio.File[btrfsvol.LogicalAddr], sb btrfstree.Superblock) *KeyIO {
@@ -61,19 +61,19 @@ func NewKeyIO(file diskio.File[btrfsvol.LogicalAddr], sb btrfstree.Superblock) *
Names: make(map[ItemPtr][]byte),
Sizes: make(map[ItemPtr]SizeAndErr),
- cache: containers.ARCache[btrfsvol.LogicalAddr, *diskio.Ref[btrfsvol.LogicalAddr, btrfstree.Node]]{
+ cache: containers.ARCache[btrfsvol.LogicalAddr, *btrfstree.Node]{
MaxLen: textui.Tunable(8),
- OnRemove: func(_ btrfsvol.LogicalAddr, nodeRef *diskio.Ref[btrfsvol.LogicalAddr, btrfstree.Node]) {
- btrfstree.FreeNodeRef(nodeRef)
+ OnRemove: func(_ btrfsvol.LogicalAddr, node *btrfstree.Node) {
+ node.Free()
},
},
}
}
-func (o *KeyIO) InsertNode(nodeRef *diskio.Ref[btrfsvol.LogicalAddr, btrfstree.Node]) {
- for i, item := range nodeRef.Data.BodyLeaf {
+func (o *KeyIO) InsertNode(node *btrfstree.Node) {
+ for i, item := range node.BodyLeaf {
ptr := ItemPtr{
- Node: nodeRef.Addr,
+ Node: node.Head.Addr,
Slot: i,
}
switch itemBody := item.Body.(type) {
@@ -102,12 +102,12 @@ func (o *KeyIO) InsertNode(nodeRef *diskio.Ref[btrfsvol.LogicalAddr, btrfstree.N
case btrfsprim.INODE_ITEM_KEY:
o.Flags[ptr] = FlagsAndErr{
Err: fmt.Errorf("error decoding item: ptr=%v (tree=%v key=%v): %w",
- ptr, nodeRef.Data.Head.Owner, item.Key, itemBody.Err),
+ ptr, node.Head.Owner, item.Key, itemBody.Err),
}
case btrfsprim.EXTENT_CSUM_KEY, btrfsprim.EXTENT_DATA_KEY:
o.Sizes[ptr] = SizeAndErr{
Err: fmt.Errorf("error decoding item: ptr=%v (tree=%v key=%v): %w",
- ptr, nodeRef.Data.Head.Owner, item.Key, itemBody.Err),
+ ptr, node.Head.Owner, item.Key, itemBody.Err),
}
}
}
@@ -118,7 +118,7 @@ func (o *KeyIO) SetGraph(graph Graph) {
o.graph = graph
}
-func (o *KeyIO) readNode(ctx context.Context, laddr btrfsvol.LogicalAddr) *diskio.Ref[btrfsvol.LogicalAddr, btrfstree.Node] {
+func (o *KeyIO) readNode(ctx context.Context, laddr btrfsvol.LogicalAddr) *btrfstree.Node {
if cached, ok := o.cache.Load(laddr); ok {
dlog.Tracef(ctx, "cache-hit node@%v", laddr)
return cached
@@ -130,7 +130,7 @@ func (o *KeyIO) readNode(ctx context.Context, laddr btrfsvol.LogicalAddr) *diski
}
dlog.Debugf(ctx, "cache-miss node@%v, reading...", laddr)
- ref, err := btrfstree.ReadNode(o.rawFile, o.sb, laddr, btrfstree.NodeExpectations{
+ node, err := btrfstree.ReadNode[btrfsvol.LogicalAddr](o.rawFile, o.sb, laddr, btrfstree.NodeExpectations{
LAddr: containers.Optional[btrfsvol.LogicalAddr]{OK: true, Val: laddr},
Level: containers.Optional[uint8]{OK: true, Val: graphInfo.Level},
Generation: containers.Optional[btrfsprim.Generation]{OK: true, Val: graphInfo.Generation},
@@ -148,9 +148,9 @@ func (o *KeyIO) readNode(ctx context.Context, laddr btrfsvol.LogicalAddr) *diski
panic(fmt.Errorf("should not happen: i/o error: %w", err))
}
- o.cache.Store(laddr, ref)
+ o.cache.Store(laddr, node)
- return ref
+ return node
}
func (o *KeyIO) ReadItem(ctx context.Context, ptr ItemPtr) btrfsitem.Item {
@@ -162,7 +162,7 @@ func (o *KeyIO) ReadItem(ctx context.Context, ptr ItemPtr) btrfsitem.Item {
if ptr.Slot < 0 {
panic(fmt.Errorf("should not happen: btrfsutil.KeyIO.ReadItem called for negative item slot: %v", ptr.Slot))
}
- items := o.readNode(ctx, ptr.Node).Data.BodyLeaf
+ items := o.readNode(ctx, ptr.Node).BodyLeaf
if ptr.Slot >= len(items) {
panic(fmt.Errorf("should not happen: btrfsutil.KeyIO.ReadItem called for out-of-bounds item slot: slot=%v len=%v",
ptr.Slot, len(items)))
diff --git a/lib/btrfsutil/scan.go b/lib/btrfsutil/scan.go
index 97220aa..05b27d5 100644
--- a/lib/btrfsutil/scan.go
+++ b/lib/btrfsutil/scan.go
@@ -19,7 +19,6 @@ import (
"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/textui"
)
@@ -30,7 +29,7 @@ type DeviceScannerFactory[Stats comparable, Result any] func(ctx context.Context
type DeviceScanner[Stats comparable, Result any] interface {
ScanStats() Stats
ScanSector(ctx context.Context, dev *btrfs.Device, paddr btrfsvol.PhysicalAddr) error
- ScanNode(ctx context.Context, nodeRef *diskio.Ref[btrfsvol.PhysicalAddr, btrfstree.Node]) error
+ ScanNode(ctx context.Context, addr btrfsvol.PhysicalAddr, node *btrfstree.Node) error
ScanDone(ctx context.Context) (Result, error)
}
@@ -123,19 +122,19 @@ func ScanOneDevice[Stats comparable, Result any](ctx context.Context, dev *btrfs
}
if checkForNode {
- nodeRef, err := btrfstree.ReadNode[btrfsvol.PhysicalAddr](dev, *sb, pos, btrfstree.NodeExpectations{})
+ node, err := btrfstree.ReadNode[btrfsvol.PhysicalAddr](dev, *sb, pos, btrfstree.NodeExpectations{})
if err != nil {
if !errors.Is(err, btrfstree.ErrNotANode) {
dlog.Errorf(ctx, "error: %v", err)
}
} else {
- if err := scanner.ScanNode(ctx, nodeRef); err != nil {
+ if err := scanner.ScanNode(ctx, pos, node); err != nil {
var zero Result
return zero, err
}
minNextNode = pos + btrfsvol.PhysicalAddr(sb.NodeSize)
}
- btrfstree.FreeNodeRef(nodeRef)
+ node.Free()
}
}
diff --git a/lib/btrfsutil/skinny_paths.go b/lib/btrfsutil/skinny_paths.go
index adf539b..1361fff 100644
--- a/lib/btrfsutil/skinny_paths.go
+++ b/lib/btrfsutil/skinny_paths.go
@@ -54,26 +54,26 @@ func (a *SkinnyPathArena) getItem(parent btrfstree.TreePath, itemSlot int) (btrf
return ret, nil
}
- node, err := btrfstree.ReadNode(a.FS, a.SB, parent.Node(-1).ToNodeAddr, btrfstree.NodeExpectations{})
- defer btrfstree.FreeNodeRef(node)
+ node, err := btrfstree.ReadNode[btrfsvol.LogicalAddr](a.FS, a.SB, parent.Node(-1).ToNodeAddr, btrfstree.NodeExpectations{})
+ defer node.Free()
if err != nil {
return btrfstree.TreePathElem{}, err
}
- if node.Data.Head.Level > 0 {
- if itemSlot >= len(node.Data.BodyInterior) {
+ if node.Head.Level > 0 {
+ if itemSlot >= len(node.BodyInterior) {
panic("should not happen")
}
- for i, item := range node.Data.BodyInterior {
+ for i, item := range node.BodyInterior {
toMaxKey := parent.Node(-1).ToMaxKey
- if i+1 < len(node.Data.BodyInterior) {
- toMaxKey = node.Data.BodyInterior[i+1].Key.Mm()
+ if i+1 < len(node.BodyInterior) {
+ toMaxKey = node.BodyInterior[i+1].Key.Mm()
}
elem := btrfstree.TreePathElem{
- FromTree: node.Data.Head.Owner,
+ FromTree: node.Head.Owner,
FromItemSlot: i,
ToNodeAddr: item.BlockPtr,
ToNodeGeneration: item.Generation,
- ToNodeLevel: node.Data.Head.Level - 1,
+ ToNodeLevel: node.Head.Level - 1,
ToKey: item.Key,
ToMaxKey: toMaxKey,
}
@@ -83,12 +83,12 @@ func (a *SkinnyPathArena) getItem(parent btrfstree.TreePath, itemSlot int) (btrf
}
}
} else {
- if itemSlot >= len(node.Data.BodyLeaf) {
+ if itemSlot >= len(node.BodyLeaf) {
panic("should not happen")
}
- for i, item := range node.Data.BodyLeaf {
+ for i, item := range node.BodyLeaf {
elem := btrfstree.TreePathElem{
- FromTree: node.Data.Head.Owner,
+ FromTree: node.Head.Owner,
FromItemSlot: i,
ToKey: item.Key,
ToMaxKey: item.Key,