Skip to content

Commit

Permalink
Added packed big array API (#68)
Browse files Browse the repository at this point in the history
  • Loading branch information
toots authored Oct 21, 2024
1 parent f204643 commit 2bca90a
Show file tree
Hide file tree
Showing 13 changed files with 91 additions and 13 deletions.
6 changes: 6 additions & 0 deletions CHANGES
Original file line number Diff line number Diff line change
@@ -1,3 +1,9 @@
1.2.1 (unreleased)
======
* Fixed plane size when allocating big array planes in `swscale`.
* Added packed big array API to `swscale` where all planes are alloacted in
on contiguous memory region.

1.2.0 (2024-09-24)
=====
* Removed unused `Av.write_audio_frame`/`Av.write_video_frame`.
Expand Down
2 changes: 1 addition & 1 deletion dune-project
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
(lang dune 3.6)

(name ffmpeg)
(version 1.2.0)
(version 1.2.1)
(source (github savonet/ocaml-ffmpeg))
(license LGPL-2.1-only)
(authors "The Savonet Team <[email protected]>")
Expand Down
2 changes: 1 addition & 1 deletion ffmpeg-av.opam
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
# This file is generated by dune, edit dune-project instead
opam-version: "2.0"
version: "1.2.0"
version: "1.2.1"
synopsis: "Bindings for the ffmpeg libraries -- top-level helpers"
maintainer: ["Romain Beauxis <[email protected]>"]
authors: ["The Savonet Team <[email protected]>"]
Expand Down
2 changes: 1 addition & 1 deletion ffmpeg-avcodec.opam
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
# This file is generated by dune, edit dune-project instead
opam-version: "2.0"
version: "1.2.0"
version: "1.2.1"
synopsis: "Bindings for the ffmpeg avcodec library"
maintainer: ["Romain Beauxis <[email protected]>"]
authors: ["The Savonet Team <[email protected]>"]
Expand Down
2 changes: 1 addition & 1 deletion ffmpeg-avdevice.opam
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
# This file is generated by dune, edit dune-project instead
opam-version: "2.0"
version: "1.2.0"
version: "1.2.1"
synopsis: "Bindings for the ffmpeg avdevice library"
maintainer: ["Romain Beauxis <[email protected]>"]
authors: ["The Savonet Team <[email protected]>"]
Expand Down
2 changes: 1 addition & 1 deletion ffmpeg-avfilter.opam
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
# This file is generated by dune, edit dune-project instead
opam-version: "2.0"
version: "1.2.0"
version: "1.2.1"
synopsis: "Bindings for the ffmpeg avfilter library"
maintainer: ["Romain Beauxis <[email protected]>"]
authors: ["The Savonet Team <[email protected]>"]
Expand Down
2 changes: 1 addition & 1 deletion ffmpeg-avutil.opam
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
# This file is generated by dune, edit dune-project instead
opam-version: "2.0"
version: "1.2.0"
version: "1.2.1"
synopsis: "Bindings for the ffmpeg avutil libraries"
maintainer: ["Romain Beauxis <[email protected]>"]
authors: ["The Savonet Team <[email protected]>"]
Expand Down
2 changes: 1 addition & 1 deletion ffmpeg-swresample.opam
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
# This file is generated by dune, edit dune-project instead
opam-version: "2.0"
version: "1.2.0"
version: "1.2.1"
synopsis: "Bindings for the ffmpeg swresample library"
maintainer: ["Romain Beauxis <[email protected]>"]
authors: ["The Savonet Team <[email protected]>"]
Expand Down
2 changes: 1 addition & 1 deletion ffmpeg-swscale.opam
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
# This file is generated by dune, edit dune-project instead
opam-version: "2.0"
version: "1.2.0"
version: "1.2.1"
synopsis: "Bindings for the ffmpeg swscale library"
maintainer: ["Romain Beauxis <[email protected]>"]
authors: ["The Savonet Team <[email protected]>"]
Expand Down
2 changes: 1 addition & 1 deletion ffmpeg.opam
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
# This file is generated by dune, edit dune-project instead
opam-version: "2.0"
version: "1.2.0"
version: "1.2.1"
synopsis: "Bindings for the ffmpeg libraries"
maintainer: ["Romain Beauxis <[email protected]>"]
authors: ["The Savonet Team <[email protected]>"]
Expand Down
9 changes: 8 additions & 1 deletion swscale/swscale.ml
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ type planes = (data * int) array
external scale : t -> planes -> int -> int -> planes -> int -> unit
= "ocaml_swscale_scale_byte" "ocaml_swscale_scale"

type vector_kind = Ba | Frm | Str
type vector_kind = PackedBa | Ba | Frm | Str

module type VideoData = sig
type t
Expand All @@ -34,6 +34,13 @@ module BigArray = struct
let vk = Ba
end

module PackedBigArray = struct
type plane = { plane_size : int; stride : int }
type t = { data : data; planes : plane array }

let vk = PackedBa
end

module Frame = struct
type t = video frame

Expand Down
12 changes: 10 additions & 2 deletions swscale/swscale.mli
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ val scale : t -> planes -> int -> int -> planes -> int -> unit

(**/**)

type vector_kind = Ba | Frm | Str
type vector_kind = PackedBa | Ba | Frm | Str

(**/**)

Expand Down Expand Up @@ -68,13 +68,21 @@ module Make (I : VideoData) (O : VideoData) : sig
val convert : t -> I.t -> O.t
end

(** Unsigned 8 bit bigarray. *)
(** Unsigned 8 bit bigarray split by planes. *)
module BigArray : sig
type t = planes

val vk : vector_kind
end

(** Unsigned 8 bit bigarray in a single packed array.. *)
module PackedBigArray : sig
type plane = { plane_size : int; stride : int }
type t = { data : data; planes : plane array }

val vk : vector_kind
end

(** Video frame. *)
module Frame : sig
type t = video frame
Expand Down
59 changes: 58 additions & 1 deletion swscale/swscale_stubs.c
Original file line number Diff line number Diff line change
Expand Up @@ -158,7 +158,7 @@ CAMLprim value ocaml_swscale_scale_byte(value *argv, int argn) {

/***** Contexts *****/

typedef enum _vector_kind { Ba, Frm, Str } vector_kind;
typedef enum _vector_kind { PackedBa, Ba, Frm, Str } vector_kind;

struct video_t {
int width;
Expand Down Expand Up @@ -235,6 +235,27 @@ static int get_in_pixels_ba(sws_t *sws, value *in_vector) {
CAMLreturnT(int, nb_planes);
}

static int get_in_pixels_packed_ba(sws_t *sws, value *in_vector) {
CAMLparam0();
CAMLlocal1(v);
uint8_t *data = Caml_ba_data_val(Field(*in_vector, 0));
int i, nb_planes = Wosize_val(Field(*in_vector, 1));
int stride, plane_size, offset = 0;

for (i = 0; i < nb_planes && i < 4; i++) {
v = Field(Field(*in_vector, 1), i);
plane_size = Int_val(Field(v, 0));
stride = Int_val(Field(v, 1));

sws->in.slice[i] = data + offset;
sws->in.stride[i] = stride;

offset += plane_size;
}

CAMLreturnT(int, nb_planes);
}

static int alloc_out_frame(sws_t *sws, value *out_vect, value *tmp) {
int ret;
AVFrame *frame = av_frame_alloc();
Expand Down Expand Up @@ -325,6 +346,38 @@ static int alloc_out_ba(sws_t *sws, value *out_vect, value *tmp) {
return 0;
}

static int alloc_out_packed_ba(sws_t *sws, value *out_vect, value *tmp) {
int i, offset = 0;
intnat out_size = 0;
uint8_t *data;

for (i = 0; i < sws->out.nb_planes; i++)
out_size += sws->out.plane_sizes[i];

out_size += 16;

*out_vect = caml_alloc_tuple(2);
Store_field(
*out_vect, 0,
caml_ba_alloc(CAML_BA_C_LAYOUT | CAML_BA_UINT8, 1, NULL, &out_size));
Store_field(*out_vect, 1, caml_alloc_tuple(sws->out.nb_planes));

data = Caml_ba_data_val(Field(*out_vect, 0));

for (i = 0; i < sws->out.nb_planes; i++) {
*tmp = caml_alloc_tuple(2);
Store_field(*tmp, 0, Val_int(sws->out.plane_sizes[i]));
Store_field(*tmp, 1, Val_int(sws->out.stride[i]));

Store_field(Field(*out_vect, 1), i, *tmp);

sws->out.slice[i] = data + offset;
offset += sws->out.plane_sizes[i];
}

return 0;
}

CAMLprim value ocaml_swscale_convert(value _sws, value _in_vector) {
CAMLparam2(_sws, _in_vector);
CAMLlocal2(out_vect, tmp);
Expand Down Expand Up @@ -436,6 +489,8 @@ CAMLprim value ocaml_swscale_create(value flags_, value in_vector_kind_,
} else if (in_vector_kind == Str) {
sws->get_in_pixels = get_in_pixels_string;
sws->in.owns_data = 1;
} else if (in_vector_kind == PackedBa) {
sws->get_in_pixels = get_in_pixels_packed_ba;
} else {
sws->get_in_pixels = get_in_pixels_ba;
}
Expand All @@ -446,6 +501,8 @@ CAMLprim value ocaml_swscale_create(value flags_, value in_vector_kind_,
sws->alloc_out = alloc_out_string;
sws->copy_out = copy_out_string;
sws->out.owns_data = 1;
} else if (out_vect_kind == PackedBa) {
sws->alloc_out = alloc_out_packed_ba;
} else {
sws->alloc_out = alloc_out_ba;
}
Expand Down

0 comments on commit 2bca90a

Please sign in to comment.