sig
  type t
  type callbacks = {
    read : int -> string * int;
    seek : (int -> int) option;
    tell : (unit -> int) option;
  }
  type track =
      Audio_track of (string * nativeint)
    | Video_track of (string * nativeint)
  type standard_tracks = {
    mutable audio_track : Ogg_demuxer.track option;
    mutable video_track : Ogg_demuxer.track option;
  }
  type metadata = string * (string * string) list
  type audio_info = { channels : int; sample_rate : int; }
  type audio_data = float array array
  type video_plane =
      (int, Bigarray.int8_unsigned_elt, Bigarray.c_layout) Bigarray.Array1.t
  type video_format = Yuvj_420 | Yuvj_422 | Yuvj_444
  type video_info = {
    fps_numerator : int;
    fps_denominator : int;
    width : int;
    height : int;
  }
  type video_data = {
    format : Ogg_demuxer.video_format;
    frame_width : int;
    frame_height : int;
    y_stride : int;
    uv_stride : int;
    y : Ogg_demuxer.video_plane;
    u : Ogg_demuxer.video_plane;
    v : Ogg_demuxer.video_plane;
  }
  exception Invalid_stream
  exception Not_available
  exception End_of_stream
  val init : ?log:(string -> unit) -> Ogg_demuxer.callbacks -> Ogg_demuxer.t
  val init_from_file :
    ?log:(string -> unit) -> string -> Ogg_demuxer.t * Unix.file_descr
  val init_from_fd :
    ?log:(string -> unit) -> Unix.file_descr -> Ogg_demuxer.t
  val get_ogg_sync : Ogg_demuxer.t -> Ogg.Sync.t
  val reset : Ogg_demuxer.t -> unit
  val abort : Ogg_demuxer.t -> unit
  val eos : Ogg_demuxer.t -> bool
  val get_tracks : Ogg_demuxer.t -> Ogg_demuxer.track list
  val get_standard_tracks : Ogg_demuxer.t -> Ogg_demuxer.standard_tracks
  val update_standard_tracks :
    Ogg_demuxer.t -> Ogg_demuxer.standard_tracks -> unit
  val drop_track : Ogg_demuxer.t -> Ogg_demuxer.track -> unit
  val audio_info :
    Ogg_demuxer.t ->
    Ogg_demuxer.track -> Ogg_demuxer.audio_info * Ogg_demuxer.metadata
  val video_info :
    Ogg_demuxer.t ->
    Ogg_demuxer.track -> Ogg_demuxer.video_info * Ogg_demuxer.metadata
  val sample_rate : Ogg_demuxer.t -> Ogg_demuxer.track -> int * int
  val get_track_position : Ogg_demuxer.t -> Ogg_demuxer.track -> float
  val get_position : Ogg_demuxer.t -> float
  val can_seek : Ogg_demuxer.t -> bool
  val seek : ?relative:bool -> Ogg_demuxer.t -> float -> float
  val decode_audio :
    Ogg_demuxer.t ->
    Ogg_demuxer.track -> (Ogg_demuxer.audio_data -> unit) -> unit
  val decode_video :
    Ogg_demuxer.t ->
    Ogg_demuxer.track -> (Ogg_demuxer.video_data -> unit) -> unit
  type ('a, 'b) decoder = {
    name : string;
    info : unit -> 'a * Ogg_demuxer.metadata;
    decode : ('-> unit) -> unit;
    restart : Ogg.Stream.stream -> unit;
    samples_of_granulepos : Stdlib.Int64.t -> Stdlib.Int64.t;
  }
  type decoders =
      Video of
        (Ogg_demuxer.video_info, Ogg_demuxer.video_data) Ogg_demuxer.decoder
    | Audio of
        (Ogg_demuxer.audio_info, Ogg_demuxer.audio_data) Ogg_demuxer.decoder
    | Unknown
  type register_decoder =
      (Ogg.Stream.packet -> bool) *
      (Ogg.Stream.stream -> Ogg_demuxer.decoders)
  val ogg_decoders : (string, Ogg_demuxer.register_decoder) Stdlib.Hashtbl.t
end