Skip to content

mantaray: directory-only Add() leaves refBytesSize=0; forks silently lost on round-trip #5483

@mfw78

Description

@mfw78

Context

bee master at 253ecd81. Affects every release since the v0.2 codec.

Summary

pkg/manifest/mantaray/node.go::Add defers setting n.refBytesSize until the first non-empty entry is added. Bee itself calls Add with an empty entry at pkg/api/bzz.go:266 (swarm.ZeroAddress.Bytes() is nil) for the root metadata. If that node then accumulates forks, MarshalBinary writes refBytesSize = 0 while the fork bodies still carry full-width refs, and UnmarshalBinary at pkg/manifest/mantaray/marshal.go:280 silently drops them on reload.

mantaray-js documents this with a FIXME in src/node.ts; downstream Rust consumers hit it in the wild.

Repro

n := mantaray.New()
n.SetObfuscationKey(mantaray.ZeroObfuscationKey)
for _, p := range [][]byte{[]byte("foo"), []byte("bar")} {
    _ = n.Add(ctx, p, nil, map[string]string{"k": "v"}, ls)  // empty entry
}
_ = n.Save(ctx, ls)
_, err := mantaray.NewNodeRef(n.Reference()).LookupNode(ctx, []byte("foo"), ls)
// err == ErrNotFound — fork silently dropped

Expected

Round-trip preserves the trie.

Proposed fix

Infer refBytesSize at the top of MarshalBinary when Add never set it — from the node's own entry width if present, else the first child fork's saved ref width. PR with patch + regression test (TestPersistDirectoryOnlyAdds) to follow.

AI Disclosure

  • This issue contains suggestions and text generated by an LLM.
  • I have reviewed the AI generated content thoroughly.
  • I possess the technical expertise to responsibly review the AI generated content mentioned in this issue.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions