type t = { data : bytes; len : int; mutable byte_idx : int; mutable bit_idx : int } let of_bytes b = { data = b; len = Bytes.length b; byte_idx = 0; bit_idx = 0 } let byte_pos t = t.byte_idx let bit_pos t = t.bit_idx let has_more t = t.byte_idx < t.len || (t.byte_idx = t.len && t.bit_idx <> 0) let available_bits t = (t.len - t.byte_idx) * 8 - t.bit_idx let read_bits t n = if n <= 0 then 0 else begin if n > 31 then invalid_arg "read_bits: n too large"; if available_bits t < n then invalid_arg "read_bits: not enough bits"; let acc = ref 0 in for _ = 1 to n do if t.byte_idx >= t.len then invalid_arg "read_bits: out of data"; let byte = Char.code (Bytes.get t.data t.byte_idx) in let bit_pos = 7 - t.bit_idx in let bit = (byte lsr bit_pos) land 1 in acc := (!acc lsl 1) lor bit; if t.bit_idx = 7 then (t.byte_idx <- t.byte_idx + 1; t.bit_idx <- 0) else t.bit_idx <- t.bit_idx + 1 done; !acc end let peek_bits t n = let saved_b = t.byte_idx in let saved_bit = t.bit_idx in let v = read_bits t n in t.byte_idx <- saved_b; t.bit_idx <- saved_bit; v