From ffee27b79ef09dfc64a2ae75876c579272a7ffc5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Daniel=20Gl=C3=B6ckner?= Date: Fri, 3 Mar 2023 10:29:09 +0100 Subject: [PATCH] Add units for FFmpeg 6.0 --- configure.ac | 4 +- src/lib/ffmpeg-6.0/avcodec.pas | 257 ++++++++++++++++++++++++++++++ src/lib/ffmpeg-6.0/avformat.pas | 114 +++++++++++++ src/lib/ffmpeg-6.0/avio.pas | 47 ++++++ src/lib/ffmpeg-6.0/avutil.pas | 186 +++++++++++++++++++++ src/lib/ffmpeg-6.0/rational.pas | 32 ++++ src/lib/ffmpeg-6.0/swresample.pas | 61 +++++++ src/lib/ffmpeg-6.0/swscale.pas | 53 ++++++ 8 files changed, 753 insertions(+), 1 deletion(-) create mode 100644 src/lib/ffmpeg-6.0/avcodec.pas create mode 100644 src/lib/ffmpeg-6.0/avformat.pas create mode 100644 src/lib/ffmpeg-6.0/avio.pas create mode 100644 src/lib/ffmpeg-6.0/avutil.pas create mode 100644 src/lib/ffmpeg-6.0/rational.pas create mode 100644 src/lib/ffmpeg-6.0/swresample.pas create mode 100644 src/lib/ffmpeg-6.0/swscale.pas diff --git a/configure.ac b/configure.ac index 0b8ca0cdc..f402d0f63 100644 --- a/configure.ac +++ b/configure.ac @@ -298,7 +298,9 @@ AC_SUBST_DEFINE(HAVE_SWRESAMPLE, $libswresample_HAVE) # map avutil library version to ffmpeg version AC_MSG_CHECKING([version of ffmpeg]) # the order is ([avutil], [avcodec], [avformat], [swscale], [swresample]) -if FFMPEG_LIBS_COMPATIBLE([57017100], [59018100], [59016100], [6004100], [4003100]); then +if FFMPEG_LIBS_COMPATIBLE([58002100], [60003100], [60003100], [7001100], [4010100]); then + FFMPEG_VERSION="6.0" +elif FFMPEG_LIBS_COMPATIBLE([57017100], [59018100], [59016100], [6004100], [4003100]); then FFMPEG_VERSION="5.0" elif FFMPEG_LIBS_COMPATIBLE([56014100], [58018100], [58012100], [5001100], [3001100]); then FFMPEG_VERSION="4.0" diff --git a/src/lib/ffmpeg-6.0/avcodec.pas b/src/lib/ffmpeg-6.0/avcodec.pas new file mode 100644 index 000000000..d69a7eede --- /dev/null +++ b/src/lib/ffmpeg-6.0/avcodec.pas @@ -0,0 +1,257 @@ +unit avcodec; + +{$IFDEF FPC} + {$MODE DELPHI} + {$PACKENUM 4} (* use 4-byte enums *) + {$PACKRECORDS C} (* C/C++-compatible record packing *) +{$ELSE} + {$MINENUMSIZE 4} (* use 4-byte enums *) +{$ENDIF} + +{$IFDEF DARWIN} + {$linklib libavcodec} +{$ENDIF} + +interface + +uses + ctypes, + avutil, + rational, + SysUtils, + UConfig; + +const + (* Supported version by this header *) + LIBAVCODEC_MAX_VERSION_MAJOR = 60; + LIBAVCODEC_MAX_VERSION_MINOR = 3; + LIBAVCODEC_MAX_VERSION_RELEASE = 100; + LIBAVCODEC_MAX_VERSION = (LIBAVCODEC_MAX_VERSION_MAJOR * VERSION_MAJOR) + + (LIBAVCODEC_MAX_VERSION_MINOR * VERSION_MINOR) + + (LIBAVCODEC_MAX_VERSION_RELEASE * VERSION_RELEASE); + + (* Min. supported version by this header *) + LIBAVCODEC_MIN_VERSION_MAJOR = 60; + LIBAVCODEC_MIN_VERSION_MINOR = 0; + LIBAVCODEC_MIN_VERSION_RELEASE = 100; + LIBAVCODEC_MIN_VERSION = (LIBAVCODEC_MIN_VERSION_MAJOR * VERSION_MAJOR) + + (LIBAVCODEC_MIN_VERSION_MINOR * VERSION_MINOR) + + (LIBAVCODEC_MIN_VERSION_RELEASE * VERSION_RELEASE); + +(* Check if linked versions are supported *) +{$IF (LIBAVCODEC_VERSION < LIBAVCODEC_MIN_VERSION)} + {$MESSAGE Error 'Linked version of libavcodec is too old!'} +{$IFEND} + +(* Check if linked version is supported *) +{$IF (LIBAVCODEC_VERSION > LIBAVCODEC_MAX_VERSION)} + {$MESSAGE Error 'Linked version of libavcodec is not yet supported!'} +{$IFEND} + +const + FF_BUG_AUTODETECT = 1; +type + TAVCodecID = ( + AV_CODEC_ID_NONE + ); + PAVPacket = ^TAVPacket; + TAVPacket = record + we_do_not_use_buf: pointer; + pts: cint64; + we_do_not_use_dts: cint64; + data: PByteArray; + size: cint; + stream_index: cint; + flags: cint; + we_do_not_use_side_data: pointer; + we_do_not_use_side_data_elems: cint; + we_do_not_use_duration: cint64; + we_do_not_use_pos: cint64; + we_do_not_use_opaque: pointer; + we_do_not_use_opaque_ref: pointer; + we_do_not_use_time_base: TAVRational; + end; + PAVPacketList = ^TAVPacketList; + TAVPacketList = record + pkt: TAVPacket; + next: ^TAVPacketList; + end; + PAVCodecDescriptor = ^TAVCodecDescriptor; + TAVCodecDescriptor = record + we_do_not_use_id: TAVCodecID; + we_do_not_use_type: TAVMediaType; + name: ^AnsiChar; + long_name: ^AnsiChar; + do_not_instantiate_this_record: incomplete_record; + end; + PAVCodecParameters = ^TAVCodecParameters; + TAVCodecParameters = record + codec_type: TAVMediaType; + codec_id: TAVCodecID; + do_not_instantiate_this_record: incomplete_record; + end; + PAVCodecContext = ^TAVCodecContext; + PPAVCodecContext = ^PAVCodecContext; + PAVCodec = ^TAVCodec; + TAVCodec = record + name: ^AnsiChar; + we_do_not_use_long_name: ^AnsiChar; + type_: TAVMediaType; + id: TAVCodecID; + we_do_not_use_capabilities: cint; + we_do_not_use_max_lowres: cuint8; + we_do_not_use_supported_framerates: ^TAVRational; + pix_fmts: ^TAVPixelFormat; + do_not_instantiate_this_record: incomplete_record; + end; + TAVCodecContext = record + we_do_not_use_av_class: pointer; + we_do_not_use_log_level_offset: cint; + codec_type: TAVMediaType; + codec: ^TAVCodec; + codec_id: TAVCodecID; + we_do_not_use_codec_tag: cuint; + we_do_not_use_priv_data: pointer; + we_do_not_use_internal: pointer; + we_do_not_use_opaque: pointer; + we_do_not_use_bit_rate: cint64; + we_do_not_use_bit_rate_tolerance: cint; + we_do_not_use_global_quality: cint; + we_do_not_use_compression_level: cint; + we_do_not_use_flags: cint; + we_do_not_use_flags2: cint; + we_do_not_use_extradata: pcuint8; + we_do_not_use_extradata_size: cint; + time_base: TAVRational; + we_do_not_use_ticks_per_frame: cint; + we_do_not_use_delay: cint; + width: cint; + height: cint; + we_do_not_use_coded_width: cint; + we_do_not_use_coded_height: cint; + we_do_not_use_gop_size: cint; + pix_fmt: TAVPixelFormat; + we_do_not_use_draw_horiz_band: cfunctionpointer; + get_format: function(s: PAVCodecContext; fmt: PAVPixelFormat): TAVPixelFormat; cdecl; + we_do_not_use_max_b_frames: cint; + we_do_not_use_b_quant_factor: cfloat; + we_do_not_use_b_quant_offset: cfloat; + we_do_not_use_has_b_frames: cint; + we_do_not_use_i_quant_factor: cfloat; + we_do_not_use_i_quant_offset: cfloat; + we_do_not_use_lumi_masking: cfloat; + we_do_not_use_temporal_cplx_masking: cfloat; + we_do_not_use_spatial_cplx_masking: cfloat; + we_do_not_use_p_masking: cfloat; + we_do_not_use_dark_masking: cfloat; + we_do_not_use_slice_count: cint; + we_do_not_use_slice_offset: pcint; + sample_aspect_ratio: TAVRational; + we_do_not_use_me_cmp: cint; + we_do_not_use_me_sub_cmp: cint; + we_do_not_use_mb_cmp: cint; + we_do_not_use_ildct_cmp: cint; + we_do_not_use_dia_size: cint; + we_do_not_use_last_predictor_count: cint; + we_do_not_use_me_pre_cmp: cint; + we_do_not_use_pre_dia_size: cint; + we_do_not_use_me_subpel_quality: cint; + we_do_not_use_me_range: cint; + we_do_not_use_slice_flags: cint; + we_do_not_use_mb_decision: cint; + we_do_not_use_intra_matrix: pcuint16; + we_do_not_use_inter_matrix: pcuint16; + we_do_not_use_intra_dc_precision: cint; + we_do_not_use_skip_top: cint; + we_do_not_use_skip_bottom: cint; + we_do_not_use_mb_lmin: cint; + we_do_not_use_mb_lmax: cint; + we_do_not_use_bidir_refine: cint; + we_do_not_use_keyint_min: cint; + we_do_not_use_refs: cint; + we_do_not_use_mv0_threshold: cint; + we_do_not_use_color_primaries: cenum; + we_do_not_use_color_trc: cenum; + we_do_not_use_colorspace: cenum; + we_do_not_use_color_range: cenum; + we_do_not_use_chroma_sample_location: cenum; + we_do_not_use_slices: cint; + we_do_not_use_field_order: cenum; + sample_rate: cint; + channels: cint; + sample_fmt: TAVSampleFormat; + we_do_not_use_frame_size: cint; + we_do_not_use_frame_number: cint; + we_do_not_use_block_align: cint; + we_do_not_use_cutoff: cint; + channel_layout: cuint64; + request_channel_layout: cuint64; + we_do_not_use_audio_service_type: cenum; + request_sample_fmt: TAVSampleFormat; + we_do_not_use_get_buffer2: cfunctionpointer; + we_do_not_use_qcompress: cfloat; + we_do_not_use_qblur: cfloat; + we_do_not_use_qmin: cint; + we_do_not_use_qmax: cint; + we_do_not_use_max_qdiff: cint; + we_do_not_use_rc_buffer_size: cint; + we_do_not_use_rc_override_count: cint; + we_do_not_use_rc_override: pointer; + we_do_not_use_rc_max_rate: cint64; + we_do_not_use_rc_min_rate: cint64; + we_do_not_use_rc_max_available_vbv_use: cfloat; + we_do_not_use_rc_min_vbv_overflow_use: cfloat; + we_do_not_use_rc_initial_buffer_occupancy: cint; + we_do_not_use_trellis: cint; + we_do_not_use_stats_out: pcchar; + we_do_not_use_stats_in: pcchar; + workaround_bugs: cint; + we_do_not_use_strict_std_compliance: cint; + we_do_not_use_error_concealment: cint; + debug: cint; + we_do_not_use_err_recognition: cint; + we_do_not_use_reordered_opaque: cint64; + we_do_not_use_hwaccel: pointer; + we_do_not_use_hwaccel_context: pointer; + we_do_not_use_error: array [0..AV_NUM_DATA_POINTERS-1] of cuint64; + we_do_not_use_dct_algo: cint; + we_do_not_use_idct_algo: cint; + we_do_not_use_bits_per_coded_sample: cint; + we_do_not_use_bits_per_raw_sample: cint; + we_do_not_use_lowres: cint; + thread_count: cint; + we_do_not_use_thread_type: cint; + we_do_not_use_active_thread_type: cint; + we_do_not_use_execute: cfunctionpointer; + we_do_not_use_execute2: cfunctionpointer; + we_do_not_use_nsse_weight: cint; + we_do_not_use_profile: cint; + we_do_not_use_level: cint; + we_do_not_use_skip_loop_filter: cenum; + we_do_not_use_skip_idct: cenum; + we_do_not_use_skip_frame: cenum; + we_do_not_use_subtitle_header: pcuint8; + we_do_not_use_subtitle_header_size: cint; + we_do_not_use_initial_padding: cint; + framerate: TAVRational; + do_not_instantiate_this_record: incomplete_record; + end; +function av_packet_ref(dst: PAVPacket; src: PAVPacket): cint; cdecl; external av__codec; +procedure av_packet_unref(pkt: PAVPacket); cdecl; external av__codec; +procedure av_init_packet(var pkt: TAVPacket); cdecl; external av__codec; deprecated; +function avcodec_version(): cuint; cdecl; external av__codec; +function av_codec_is_decoder(codec: PAVCodec): cint; cdecl; external av__codec; +function av_codec_iterate(opaque: ppointer): PAVCodec; cdecl; external av__codec; +function avcodec_find_decoder(id: TAVCodecID): PAVCodec; cdecl; external av__codec; +function avcodec_find_decoder_by_name(name: PAnsiChar): PAVCodec; cdecl; external av__codec; +function avcodec_descriptor_get(id: TAVCodecID): PAVCodecDescriptor; cdecl; external av__codec; +function avcodec_open2(avctx: PAVCodecContext; codec: PAVCodec; options: PPAVDictionary): cint; cdecl; external av__codec; +function avcodec_close(avctx: PAVCodecContext): cint; cdecl; external av__codec; +procedure avcodec_flush_buffers(avctx: PAVCodecContext); cdecl; external av__codec; +function avcodec_receive_frame(avctx: PAVCodecContext; frame: PAVFrame): cint; cdecl; external av__codec; +function avcodec_send_packet(avctx: PAVCodecContext; avpkt: PAVPacket): cint; cdecl; external av__codec; +function avcodec_alloc_context3(codec: PAVCodec): PAVCodecContext; cdecl; external av__codec; +procedure avcodec_free_context(avctx: PPAVCodecContext); cdecl; external av__codec; +function avcodec_parameters_to_context(codec: PAVCodecContext; par: PAVCodecParameters): cint; cdecl; external av__codec; +implementation +end. diff --git a/src/lib/ffmpeg-6.0/avformat.pas b/src/lib/ffmpeg-6.0/avformat.pas new file mode 100644 index 000000000..66041b1e2 --- /dev/null +++ b/src/lib/ffmpeg-6.0/avformat.pas @@ -0,0 +1,114 @@ +unit avformat; + +{$IFDEF FPC} + {$MODE DELPHI} + {$PACKENUM 4} (* use 4-byte enums *) + {$PACKRECORDS C} (* C/C++-compatible record packing *) +{$ELSE} + {$MINENUMSIZE 4} (* use 4-byte enums *) +{$ENDIF} + +{$IFDEF DARWIN} + {$linklib libavformat} +{$ENDIF} + +interface + +uses + ctypes, + avcodec, + avio, + avutil, + rational, + UConfig; + +const + (* Max. supported version by this header *) + LIBAVFORMAT_MAX_VERSION_MAJOR = 60; + LIBAVFORMAT_MAX_VERSION_MINOR = 3; + LIBAVFORMAT_MAX_VERSION_RELEASE = 100; + LIBAVFORMAT_MAX_VERSION = (LIBAVFORMAT_MAX_VERSION_MAJOR * VERSION_MAJOR) + + (LIBAVFORMAT_MAX_VERSION_MINOR * VERSION_MINOR) + + (LIBAVFORMAT_MAX_VERSION_RELEASE * VERSION_RELEASE); + + (* Min. supported version by this header *) + LIBAVFORMAT_MIN_VERSION_MAJOR = 60; + LIBAVFORMAT_MIN_VERSION_MINOR = 0; + LIBAVFORMAT_MIN_VERSION_RELEASE = 100; + LIBAVFORMAT_MIN_VERSION = (LIBAVFORMAT_MIN_VERSION_MAJOR * VERSION_MAJOR) + + (LIBAVFORMAT_MIN_VERSION_MINOR * VERSION_MINOR) + + (LIBAVFORMAT_MIN_VERSION_RELEASE * VERSION_RELEASE); + +(* Check if linked versions are supported *) +{$IF (LIBAVFORMAT_VERSION < LIBAVFORMAT_MIN_VERSION)} + {$MESSAGE Error 'Linked version of libavformat is too old!'} +{$IFEND} + +(* Check if linked versions are supported *) +{$IF (LIBAVFORMAT_VERSION > LIBAVFORMAT_MAX_VERSION)} + {$MESSAGE Error 'Linked version of libavformat is not yet supported!'} +{$IFEND} + +const + AVFMT_FLAG_GENPTS = 1; + AVSEEK_FLAG_ANY = 4; + AVSEEK_FLAG_BACKWARD = 1; +type + PAVInputFormat = ^TAVInputFormat; + PAVStream = ^TAVStream; + PPAVStream = ^PAVStream; + PAVFormatContext = ^TAVFormatContext; + PPAVFormatContext = ^PAVFormatContext; + TAVFormatContext = record + we_do_not_use_av_class: pointer; + iformat: PAVInputFormat; + we_do_not_use_oformat: pointer; + we_do_not_use_priv_data: pointer; + pb: ^TAVIOContext; + we_do_not_use_ctx_flags: cint; + nb_streams: cuint; + streams: PPAVStream; + url: ^AnsiChar; + start_time: cint64; + duration: cint64; + we_do_not_use_bit_rate: cint64; + we_do_not_use_packet_size: cuint; + we_do_not_use_max_delay: cint; + flags: cint; + do_not_instantiate_this_record: incomplete_record; + end; + TAVStream = record + we_do_not_use_av_class: pointer; + we_do_not_use_index: cint; + we_do_not_use_id: cint; + codecpar: ^TAVCodecParameters; + we_do_not_use_priv_data: pointer; + time_base: TAVRational; + start_time: cint64; + we_do_not_use_duration: cint64; + we_do_not_use_nb_frames: cint64; + we_do_not_use_disposition: cint; + we_do_not_use_discard: cenum; + we_do_not_use_sample_aspect_ratio: TAVRational; + we_do_not_use_metadata: PAVDictionary; + we_do_not_use_avg_frame_rate: TAVRational; + we_do_not_use_attached_pic: TAVPacket; + we_do_not_use_side_data: pointer; + we_do_not_use_nb_side_data: cint; + we_do_not_use_event_flags: cint; + r_frame_rate: TAVRational; + do_not_instantiate_this_record: incomplete_record; + end; + TAVInputFormat = record + name: ^AnsiChar; + do_not_instantiate_this_record: incomplete_record; + end; +function avformat_alloc_context(): PAVFormatContext; cdecl; external av__format; +function avformat_open_input(ps: PPAVFormatContext; url: PAnsiChar; fmt: PAVInputFormat; options: PPAVDictionary): cint; cdecl; external av__format; +procedure avformat_close_input(s: PPAVFormatContext); cdecl; external av__format; +function avformat_version(): cuint; cdecl; external av__format; +function avformat_find_stream_info(ic: PAVFormatContext; options: PPAVDictionary): cint; cdecl; external av__format; +function av_read_frame(s: PAVFormatContext; var pkt: TAVPacket): cint; cdecl; external av__format; +function av_seek_frame(s: PAVFormatContext; stream_index: cint; timestamp: cint64; flags: cint): cint; cdecl; external av__format; +implementation +end. diff --git a/src/lib/ffmpeg-6.0/avio.pas b/src/lib/ffmpeg-6.0/avio.pas new file mode 100644 index 000000000..bb0ba1de3 --- /dev/null +++ b/src/lib/ffmpeg-6.0/avio.pas @@ -0,0 +1,47 @@ +unit avio; + +{$IFDEF FPC} + {$MODE DELPHI} + {$PACKENUM 4} (* use 4-byte enums *) + {$PACKRECORDS C} (* C/C++-compatible record packing *) +{$ELSE} + {$MINENUMSIZE 4} (* use 4-byte enums *) +{$ENDIF} + +{$IFDEF DARWIN} + {$linklib libavformat} +{$ENDIF} + +interface + +uses + ctypes, + avutil, + SysUtils, + UConfig; +const + AVSEEK_SIZE = 65536; +type + PAVIOContext = ^TAVIOContext; + TAVIOContext = record + we_do_not_use_av_class: pointer; + buffer: ^cuchar; + we_do_not_use_buffer_size: cint; + we_do_not_use_buf_ptr: pcuchar; + we_do_not_use_buf_end: pcuchar; + opaque: pointer; + we_do_not_use_read_packet: cfunctionpointer; + we_do_not_use_write_packet: cfunctionpointer; + we_do_not_use_seek: cfunctionpointer; + pos: cint64; + eof_reached: cint; + error: cint; + do_not_instantiate_this_record: incomplete_record; + end; + TReadWriteFunc = function(opaque: pointer; buf: pbytearray; buf_size: cint): cint; cdecl; + TSeekFunc = function(opaque: pointer; offset: cint64; whence: cint): cint64; cdecl; +function avio_alloc_context(buffer: pcuint8; buffer_size: cint; write_flag: cint; opaque: pointer; read_packet: TReadWriteFunc; write_packet: TReadWriteFunc; seek: TSeekFunc): PAVIOContext; cdecl; external av__format; +function avio_feof(s: PAVIOContext): cint; cdecl; external av__format; +function avio_size(s: PAVIOContext): cint64; cdecl; external av__format; +implementation +end. diff --git a/src/lib/ffmpeg-6.0/avutil.pas b/src/lib/ffmpeg-6.0/avutil.pas new file mode 100644 index 000000000..55878a02d --- /dev/null +++ b/src/lib/ffmpeg-6.0/avutil.pas @@ -0,0 +1,186 @@ +unit avutil; + +{$IFDEF FPC} + {$MODE DELPHI} + {$MODESWITCH ADVANCEDRECORDS} + {$PACKENUM 4} (* use 4-byte enums *) + {$PACKRECORDS C} (* C/C++-compatible record packing *) +{$ELSE} + {$MINENUMSIZE 4} (* use 4-byte enums *) +{$ENDIF} + +{$IFDEF DARWIN} + {$linklib libavutil} +{$ENDIF} + +interface + +uses + ctypes, + rational, + {$IFDEF UNIX} + BaseUnix, + {$ENDIF} + SysUtils, + UConfig; + + +const + (* Max. supported version by this header *) + LIBAVUTIL_MAX_VERSION_MAJOR = 58; + LIBAVUTIL_MAX_VERSION_MINOR = 2; + LIBAVUTIL_MAX_VERSION_RELEASE = 100; + LIBAVUTIL_MAX_VERSION = (LIBAVUTIL_MAX_VERSION_MAJOR * VERSION_MAJOR) + + (LIBAVUTIL_MAX_VERSION_MINOR * VERSION_MINOR) + + (LIBAVUTIL_MAX_VERSION_RELEASE * VERSION_RELEASE); + + (* Min. supported version by this header *) + LIBAVUTIL_MIN_VERSION_MAJOR = 57; + LIBAVUTIL_MIN_VERSION_MINOR = 17; + LIBAVUTIL_MIN_VERSION_RELEASE = 100; + LIBAVUTIL_MIN_VERSION = (LIBAVUTIL_MIN_VERSION_MAJOR * VERSION_MAJOR) + + (LIBAVUTIL_MIN_VERSION_MINOR * VERSION_MINOR) + + (LIBAVUTIL_MIN_VERSION_RELEASE * VERSION_RELEASE); + +(* Check if linked versions are supported *) +{$IF (LIBAVUTIL_VERSION < LIBAVUTIL_MIN_VERSION)} + {$MESSAGE Error 'Linked version of libavutil is too old!'} +{$IFEND} + +{$IF (LIBAVUTIL_VERSION > LIBAVUTIL_MAX_VERSION)} + {$MESSAGE Error 'Linked version of libavutil is not yet supported!'} +{$IFEND} + +type + (* + * We use this record as the last element of records that are not supposed + * to be allocated by pascal code either because the declaration of the + * record has never been completed or because FFmpeg does the allocation + * internally. + * + * The exceed_stack array has been declared as 10MB array because the default + * soft stack limit on Linux is less than that. So every time someone tries + * to allocate this structure on the stack, it will crash unless the soft + * limit has been raised. + * + * The existence of a constructor will cause Free Pascal to issue a warning + * if an element of this type has been created without calling the + * constructor. + *) + incomplete_record = record + exceed_stack: array [0..10000000] of byte; + constructor Never_Call(dummy: integer); + end; + +type + (* + * The C standard allows for function pointers to have a different size than + * data pointers. In practice the size differs only on exotic architectures. + *) + cfunctionpointer = procedure;cdecl; + (* + * Here we assume that the size of an enum is the same regardless of the + * values it needs to hold. This is not always the case. The AMD64 System V + * ABI says: + * + * C++ and some implementations of C permit enums larger than an int. + * The underlying type is bumped to an unsigned int, long int or + * unsigned long int, in that order. + * + * Apart from that there are systems where the default enum size is smaller + * than an int. But these are unlikely to run FFmpeg. + * + * So don't use this type to replace enums that don't fit into 32 bits. + *) + cenum = cint; + +const + AVERROR_EOF = -(ord('E') or (ord('O') shl 8) or (ord('F') shl 16) or (ord(' ') shl 24)); + AV_LOG_FATAL = 8; + AV_NOPTS_VALUE = -9223372036854775808; + AV_NUM_DATA_POINTERS = 8; + AV_TIME_BASE = 1000000; +{$IFDEF UNIX} + EAGAIN = ESysEAGAIN; +{$ELSE} + EAGAIN = 11; +{$ENDIF} + +type + TAVSampleFormat = ( + AV_SAMPLE_FMT_U8, + AV_SAMPLE_FMT_S16, + AV_SAMPLE_FMT_S32, + AV_SAMPLE_FMT_FLT, + AV_SAMPLE_FMT_DBL + ); + PAVPixelFormat = ^TAVPixelFormat; + TAVPixelFormat = ( + AV_PIX_FMT_RGB24 = 2, + AV_PIX_FMT_BGR24, + AV_PIX_FMT_RGBA = 26, + AV_PIX_FMT_BGRA = 28 + ); + TAVMediaType = ( + AVMEDIA_TYPE_VIDEO, + AVMEDIA_TYPE_AUDIO + ); + ppcuint8 = ^pcuint8; + PAVFrame = ^TAVFrame; + PPAVFrame = ^PAVFrame; + TAVFrame = record + data: array [0..AV_NUM_DATA_POINTERS-1] of ^cuint8; + linesize: array [0..AV_NUM_DATA_POINTERS-1] of cint; + extended_data: ^pcuint8; + we_do_not_use_width: cint; + we_do_not_use_height: cint; + nb_samples: cint; + we_do_not_use_format: cint; + we_do_not_use_key_frame: cint; + we_do_not_use_pict_type: cenum; + we_do_not_use_sample_aspect_ratio: TAVRational; + pts: cint64; + pkt_dts: cint64; + we_do_not_use_time_base: TAVRational; + we_do_not_use_coded_picture_number: cint; + we_do_not_use_display_picture_number: cint; + we_do_not_use_quality: cint; + we_do_not_use_opaque: pointer; + repeat_pict: cint; + do_not_instantiate_this_record: incomplete_record; + end; + PAVDictionary = ^TAVDictionary; + PPAVDictionary = ^PAVDictionary; + TAVDictionary = record + do_not_instantiate_this_record: incomplete_record; + end; +procedure av_free(ptr: pointer); cdecl; external av__util; +procedure av_freep(ptr: pointer); cdecl; external av__util; +function av_malloc(size: csize_t): pointer; cdecl; external av__util; +function avutil_version(): cuint; cdecl; external av__util; +function av_frame_alloc(): PAVFrame; cdecl; external av__util; +procedure av_frame_free(frame: PPAVFrame); cdecl; external av__util; +function av_image_alloc(pointers: ppcuint8; linesizes: pcint; w: cint; h: cint; pix_fmt: TAVPixelFormat; align: cint): cint; cdecl; external av__util; +function AVERROR(e: cint): cint; {$IFDEF HasInline}inline;{$ENDIF} +function av_opt_set_int(obj: pointer; name: PAnsiChar; val: cint64; search_flags: cint): cint; cdecl; external av__util; +function av_opt_set_channel_layout(obj: pointer; name: PAnsiChar; ch_layout: cint64; search_flags: cint): cint; cdecl; external av__util; +function av_opt_set_sample_fmt(obj: pointer; name: PAnsiChar; fmt: TAVSampleFormat; search_flags: cint): cint; cdecl; external av__util; +function av_samples_alloc(var audio_data: pcuint8; linesize: pcint; nb_channels: cint; nb_samples: cint; sample_fmt: TAVSampleFormat; align: cint): cint; cdecl; external av__util; +function av_get_packed_sample_fmt(sample_fmt: TAVSampleFormat): TAVSampleFormat; cdecl; external av__util; +function av_get_bytes_per_sample(sample_fmt: TAVSampleFormat): cint; cdecl; external av__util; +procedure av_log_set_level(level: cint); cdecl; external av__util; +implementation +function AVERROR(e: cint): cint; {$IFDEF HasInline}inline;{$ENDIF} +begin + if EAGAIN < 0 then + AVERROR := e + else + AVERROR := -e; +end; + +constructor incomplete_record.Never_Call(dummy: integer); +begin + abort; +end; + +end. diff --git a/src/lib/ffmpeg-6.0/rational.pas b/src/lib/ffmpeg-6.0/rational.pas new file mode 100644 index 000000000..46c6ccba8 --- /dev/null +++ b/src/lib/ffmpeg-6.0/rational.pas @@ -0,0 +1,32 @@ +unit rational; + +{$IFDEF FPC} + {$MODE DELPHI} + {$PACKENUM 4} (* use 4-byte enums *) + {$PACKRECORDS C} (* C/C++-compatible record packing *) +{$ELSE} + {$MINENUMSIZE 4} (* use 4-byte enums *) +{$ENDIF} + +interface + +uses + ctypes; +type + TAVRational = record + num: csint; + den: csint; + end; +function av_q2d(a: TAVRational): cdouble; {$IFDEF HasInline}inline;{$ENDIF} +function av_inv_q(q: TAVRational): TAVRational; {$IFDEF HasInline}inline;{$ENDIF} +implementation +function av_q2d(a: TAVRational): cdouble; {$IFDEF HasInline}inline;{$ENDIF} +begin + av_q2d := a.num / a.den; +end; +function av_inv_q(q: TAVRational): TAVRational; {$IFDEF HasInline}inline;{$ENDIF} +begin + av_inv_q.num := q.den; + av_inv_q.den := q.num; +end; +end. diff --git a/src/lib/ffmpeg-6.0/swresample.pas b/src/lib/ffmpeg-6.0/swresample.pas new file mode 100644 index 000000000..1637a4e4e --- /dev/null +++ b/src/lib/ffmpeg-6.0/swresample.pas @@ -0,0 +1,61 @@ +unit swresample; + +{$IFDEF FPC} + {$MODE DELPHI} + {$PACKENUM 4} (* use 4-byte enums *) + {$PACKRECORDS C} (* C/C++-compatible record packing *) +{$ELSE} + {$MINENUMSIZE 4} (* use 4-byte enums *) +{$ENDIF} + +{$IFDEF DARWIN} + {$linklib libswresample} +{$ENDIF} + +interface + +uses + ctypes, + avutil, + UConfig; + +const + (* Supported version by this header *) + LIBSWRESAMPLE_MAX_VERSION_MAJOR = 4; + LIBSWRESAMPLE_MAX_VERSION_MINOR = 10; + LIBSWRESAMPLE_MAX_VERSION_RELEASE = 100; + LIBSWRESAMPLE_MAX_VERSION = (LIBSWRESAMPLE_MAX_VERSION_MAJOR * VERSION_MAJOR) + + (LIBSWRESAMPLE_MAX_VERSION_MINOR * VERSION_MINOR) + + (LIBSWRESAMPLE_MAX_VERSION_RELEASE * VERSION_RELEASE); + + (* Min. supported version by this header *) + LIBSWRESAMPLE_MIN_VERSION_MAJOR = 0; + LIBSWRESAMPLE_MIN_VERSION_MINOR = 15; + LIBSWRESAMPLE_MIN_VERSION_RELEASE = 100; + LIBSWRESAMPLE_MIN_VERSION = (LIBSWRESAMPLE_MIN_VERSION_MAJOR * VERSION_MAJOR) + + (LIBSWRESAMPLE_MIN_VERSION_MINOR * VERSION_MINOR) + + (LIBSWRESAMPLE_MIN_VERSION_RELEASE * VERSION_RELEASE); + +(* Check if linked versions are supported *) +{$IF (LIBSWRESAMPLE_VERSION < LIBSWRESAMPLE_MIN_VERSION)} + {$MESSAGE Error 'Linked version of libswresample is too old!'} +{$IFEND} + +(* Check if linked version is supported *) +{$IF (LIBSWRESAMPLE_VERSION > LIBSWRESAMPLE_MAX_VERSION)} + {$MESSAGE Error 'Linked version of libswresample is not yet supported!'} +{$IFEND} + +type + PSwrContext = ^TSwrContext; + PPSwrContext = ^PSwrContext; + TSwrContext = record + do_not_instantiate_this_record: incomplete_record; + end; +function swr_alloc(): PSwrContext; cdecl; external sw__resample; +function swr_alloc_set_opts(s: PSwrContext; out_ch_layout: cint64; out_sample_fmt: TAVSampleFormat; out_sample_rate: cint; in_ch_layout: cint64; in_sample_fmt: TAVSampleFormat; in_sample_rate: cint; log_offset: cint; log_ctx: pointer): PSwrContext; cdecl; external sw__resample; +function swr_init(s: PSwrContext): cint; cdecl; external sw__resample; +procedure swr_free(s: PPSwrContext); cdecl; external sw__resample; +function swr_convert(s: PSwrContext; var out: pcuint8; out_count: cint; var in_: pcuint8; in_count: cint): cint; cdecl; external sw__resample; +implementation +end. diff --git a/src/lib/ffmpeg-6.0/swscale.pas b/src/lib/ffmpeg-6.0/swscale.pas new file mode 100644 index 000000000..07e2d157b --- /dev/null +++ b/src/lib/ffmpeg-6.0/swscale.pas @@ -0,0 +1,53 @@ +unit swscale; + +{$IFDEF FPC} + {$MODE DELPHI} + {$PACKENUM 4} (* use 4-byte enums *) + {$PACKRECORDS C} (* C/C++-compatible record packing *) +{$ELSE} + {$MINENUMSIZE 4} (* use 4-byte enums *) +{$ENDIF} + +{$IFDEF DARWIN} + {$linklib libswscale} +{$ENDIF} + +interface + +uses + ctypes, + avutil, + UConfig; + +const + (* Max. supported version by this header *) + LIBSWSCALE_MAX_VERSION_MAJOR = 7; + LIBSWSCALE_MAX_VERSION_MINOR = 1; + LIBSWSCALE_MAX_VERSION_RELEASE = 100; + LIBSWSCALE_MAX_VERSION = (LIBSWSCALE_MAX_VERSION_MAJOR * VERSION_MAJOR) + + (LIBSWSCALE_MAX_VERSION_MINOR * VERSION_MINOR) + + (LIBSWSCALE_MAX_VERSION_RELEASE * VERSION_RELEASE); + +(* Check if linked versions are supported *) +{$IF (LIBSWSCALE_VERSION > LIBSWSCALE_MAX_VERSION)} + {$MESSAGE Error 'Linked version of libswscale is not yet supported!'} +{$IFEND} + + +const + SWS_FAST_BILINEAR = 1; +type + PSwsContext = ^TSwsContext; + TSwsContext = record + do_not_instantiate_this_record: incomplete_record; + end; + PSwsFilter = ^TSwsFilter; + TSwsFilter = record + do_not_instantiate_this_record: incomplete_record; + end; +function swscale_version(): cuint; cdecl; external sw__scale; +function sws_isSupportedInput(pix_fmt: TAVPixelFormat): cint; cdecl; external sw__scale; +function sws_scale(c: PSwsContext; srcSlice: ppcuint8; srcStride: pcint; srcSliceY: cint; srcSliceH: cint; dst: ppcuint8; dstStride: pcint): cint; cdecl; external sw__scale; +function sws_getContext(srcW: cint; srcH: cint; srcFormat: TAVPixelFormat; dstW: cint; dstH: cint; dstFormat: TAVPixelFormat; flags: cint; srcFilter: PSwsFilter; dstFilter: PSwsFilter; param: pcdouble): PSwsContext; cdecl; external sw__scale; +implementation +end.