Skip to content

sidx encode: reference_size bit 31 bleeds into reference_type; SAP fields silently truncated #189

Description

@kixelated

src/sidx.rs:104-107:

let reference_type_and_size: u32 = match reference.reference_type {
    true => 0x8000_0000 | reference.reference_size,
    false => reference.reference_size,
};

SegmentReference.reference_size is a public u32, but the wire field is 31 bits (ISO/IEC 14496-12 §8.16.3). With reference_type: false and a reference_size that has bit 31 set, the encoded stream has the reference_type bit set: decoding yields reference_type: true with the truncated size — decode(encode(x)) != x, and the output claims a segment-index reference instead of a media reference. Following the crate's own convention for reference_count a few lines up (sidx.rs:97-101), out-of-range values should produce an Error rather than corrupt adjacent bits.

Milder variants in the same loop: sap_type (& 0b111) and sap_delta_time (& 0x0FFF_FFFF) are silently truncated instead of erroring, so out-of-range values also round-trip unequal — though at least they can't corrupt neighboring fields.

(Version selection for earliest_presentation_time/first_offset, the starts_with_sap bit, and the capped preallocation were all checked and are correct.)

Found during an extensive automated correctness review (Claude Code); verified against the current main sources.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions