summaryrefslogtreecommitdiff
path: root/pkg/btrfs/btrfsitem/items.go
diff options
context:
space:
mode:
Diffstat (limited to 'pkg/btrfs/btrfsitem/items.go')
-rw-r--r--pkg/btrfs/btrfsitem/items.go21
1 files changed, 21 insertions, 0 deletions
diff --git a/pkg/btrfs/btrfsitem/items.go b/pkg/btrfs/btrfsitem/items.go
index 51e6344..91b7029 100644
--- a/pkg/btrfs/btrfsitem/items.go
+++ b/pkg/btrfs/btrfsitem/items.go
@@ -1,6 +1,10 @@
package btrfsitem
import (
+ "fmt"
+ "reflect"
+
+ "lukeshu.com/btrfs-tools/pkg/binstruct"
"lukeshu.com/btrfs-tools/pkg/btrfs/internal"
)
@@ -9,3 +13,20 @@ type Type = internal.ItemType
type Item interface {
isItem()
}
+
+func UnmarshalItem(keytyp Type, dat []byte) (Item, error) {
+ gotyp, ok := keytype2gotype[keytyp]
+ if !ok {
+ return nil, fmt.Errorf("btrfsitem.UnmarshalItem: unknown item type: %v", keytyp)
+ }
+ retPtr := reflect.New(gotyp)
+ n, err := binstruct.Unmarshal(dat, retPtr.Interface())
+ if err != nil {
+ return nil, fmt.Errorf("btrfsitem.UnmarshalItem: %w", err)
+ }
+ if n < len(dat) {
+ return nil, fmt.Errorf("btrfsitem.UnmarshalItem: left over data: got %d bytes but only consumed %d",
+ len(dat), n)
+ }
+ return retPtr.Elem().Interface().(Item), nil
+}