Skip to content

v0.9.0

Latest

Choose a tag to compare

@genedna genedna released this 04 Sep 13:55
· 3 commits to main since this release
5223b6b

git-internal v0.9.0

Release date: 2026-09-04 · Crate: git-internal 0.9.0 · Full changelog: CHANGELOG.md

git-internal 0.9.0 adds BLAKE3-256 object IDs as a git-internal / Libra extension, backed by an explicit-kind hash API and fully cross-verified pack/idx/protocol integrity. It also hardens pack decoding and smart-protocol negotiation to fail closed instead of silently falling back.

Important

This is a 0.x breaking minor release. New enum variants and fail-closed protocol changes require downstream code adjustments — see the Migration section below.

Highlights

BLAKE3-256 object IDs (git-internal / Libra extension)

  • HashKind::Blake3, ObjectHash::Blake3 and HashAlgorithm::Blake3 (32-byte / 64-hex digests) join SHA-1 and SHA-256. BLAKE3 is a separate object namespace: it is never inferred from an ID's width, only from an explicit repository kind or a blake3:HEX tagged ID.
  • Every layer supports it end-to-end: loose objects, trees/commits/tags/notes, pack encode/decode, idx v2, .git/index, cache spill paths (kind-namespaced), and the smart protocol (object-format=blake3).
  • The AI IntegrityHash remains SHA-256 regardless of the repository kind.

Explicit-kind ("context") API

New _for_kind / _with_kind APIs never read the thread-local HashKind and never infer an algorithm from length — they fail closed with diagnostic HashErrors instead:

  • Hashing/parsing: ObjectHash::{new_for_kind, from_type_and_data_for_kind, from_hex_for_kind, from_bytes_for_kind, from_stream_for_kind, zero_for_kind, ensure_kind, to_tagged_string, from_tagged_str}, HashAlgorithm::new_for_kind.
  • Object model: Blob::from_content_with_kind, Tree::from_tree_items_with_kind / rehash_with_kind, Commit::new_with_kind, Tag::new_with_kind, Note::new_with_kind, ObjectTrait::from_buf_read_with_kind, and more.
  • Pack / idx / index: Pack::new_with_hash_kind, PackEncoder::new_with_hash_kind, encode_and_output_to_files_with_hash_kind, PackStats::analyze_with_hash_kind, pack_index::parse_idx_v2_from, Index::{from_file,to_file,load,save,refresh}_with_hash_kind.
  • Protocol: RepositoryAccess::object_hash_kind(), SmartProtocol::ensure_hash_kind_consistency, PackGenerator::new_with_hash_kind.

Hardened pack / idx / protocol integrity

  • Pack decoding now cross-verifies every object against an existing .idx (streamed content hash, CRC over the encoded entry, real start offset), always rebuilds delta payloads, and treats a present-but-invalid .idx as an error instead of falling back to a scan.
  • The shared idx v2 reader validates fanout, strictly ascending names, unique offsets, large-offset slots and both checksums.
  • Smart-protocol negotiation is fail-closed: an unknown or mismatching object-format is a hard ProtocolError::InvalidRequest (no warn-and-ignore, no SHA-1 fallback), and the repository/local/wire kind invariant is re-checked at every await and side-effect boundary.
  • Upload-pack streams carry Result<Vec<u8>, ProtocolError> items so producer failures are reported instead of surfacing as truncated packs.

Fixed

  • IdxBuilder now includes the pack checksum in the idx checksum (matching Git).
  • Encoder idx CRC32 values are computed over the encoded pack entry, not the decompressed content.
  • Thin/malformed packs whose delta base never appears return an error instead of panicking.
  • Signature formats negative half-hour time zones correctly.

Deprecated

  • ObjectHash::from_bytes_infer_kind — width inference can never distinguish SHA-256 from BLAKE3.

Migration (0.8.7 → 0.9.0)

  1. Exhaustive match expressions over HashKind, ObjectHash or HashAlgorithm will fail to compile until a Blake3 arm is added (the enums are intentionally not #[non_exhaustive]).
  2. Replace length inference with explicit kinds. ObjectHash::from_str returns Sha256 for any 64-hex ID — including BLAKE3 — and from_bytes_infer_kind does the same for raw 32-byte digests. Parse IDs with from_hex_for_kind(repository_kind, …) at every boundary that may serve more than one repository. Where tagged IDs are accepted, follow from_tagged_str with ensure_kind(repository_kind).
  3. Implement RepositoryAccess::object_hash_kind() for repositories whose format is known; the smart protocol binds to it at construction.
  4. Handle Err items in upload-pack streams.
  5. Single-repository flows using set_hash_kind and the thread-local constructors (ObjectHash::new, from_bytes, Blob::from_content, …) keep working unchanged.

See docs/development/blake3-integration.md for the full downstream handoff contract, compatibility matrix, and acceptance checklist.

Compatibility

SHA-1 SHA-256 BLAKE3
Standard Git ✘ (extension)
In-place migration not supported; create new repositories with core.objectformat=blake3
Pack kind sniffing impossible by design (32-byte width is shared); supply the kind explicitly
AI IntegrityHash SHA-256 SHA-256 SHA-256 (unchanged)

Known limitations

  • The unified-diff writer does not emit \ No newline at end of file markers, so a change touching only a file's terminal newline is not representable (tracked as FIX-05).

Verification

  • Full test suite green: 361 passed (355 unit, 4 integration, 2 doc), 0 failures; 6 pre-existing ignores requiring large remote pack fixtures.
  • 17 dedicated BLAKE3 tests cover official vectors, canonical object hashing, pack/idx round-trips, cross-kind rejection, protocol negotiation, cache-spill namespaces, and byte-identical legacy rkyv archives from 0.8.7.