ref: eeadac1851149248e788579cc83b925c27c2a8e1
parent: 1a7dc68faded3f77a171d9d640542524ad8f3bd5
author: Runxi Yu <me@runxiyu.org>
date: Fri Feb 20 22:57:20 EST 2026
objectstore/loose: Verify the length where possible.
--- a/objectstore/loose/parse.go
+++ b/objectstore/loose/parse.go
@@ -23,11 +23,15 @@
// parseRaw parses a loose object payload in "type size\0content" format.
func parseRaw(raw []byte) (objecttype.Type, []byte, error) {- ty, _, headerLen, ok := objectheader.Parse(raw)
+ ty, size, headerLen, ok := objectheader.Parse(raw)
if !ok { return objecttype.TypeInvalid, nil, errors.New("objectstore/loose: malformed object header")}
- return ty, raw[headerLen:], nil
+ content := raw[headerLen:]
+ if int64(len(content)) != size {+ return objecttype.TypeInvalid, nil, errors.New("objectstore/loose: object header size/content mismatch")+ }
+ return ty, content, nil
}
// readHeader reads and parses a loose object header from br.
--- a/objectstore/loose/read_bytes.go
+++ b/objectstore/loose/read_bytes.go
@@ -12,7 +12,14 @@
return nil, err
}
defer func() { _ = file.Close() }()- return decodeAll(file)
+ raw, err := decodeAll(file)
+ if err != nil {+ return nil, err
+ }
+ if _, _, err := parseRaw(raw); err != nil {+ return nil, err
+ }
+ return raw, nil
}
// ReadBytesContent reads an object's type and content bytes.
@@ -21,7 +28,7 @@
if err != nil {return objecttype.TypeInvalid, nil, err
}
- ty, content, err := parseRaw(raw)
+ ty, content, err := parseRaw(raw) // Just for the size check.
if err != nil {return objecttype.TypeInvalid, nil, err
}
--
⑨