package: shotdetect Version: 1.0.86-6 The source code of shotdetect is incompatible with the current version of FFmpeg 7, leading to a crash when trying to compile against it. The attached patch fixes the issues, allowing successful compilation.
I am using Ubuntu 24.04 and Debian Unstable.
diff -Nru shotdetect-1.0.86.orig/src/film.cpp shotdetect-1.0.86/src/film.cpp --- shotdetect-1.0.86.orig/src/film.cpp 2024-09-11 12:04:16.621965453 -0400 +++ shotdetect-1.0.86/src/film.cpp 2024-09-11 18:18:09.827384029 -0400 @@ -18,6 +18,7 @@ #include "film.h" #include "graph.h" extern "C" { +#include <libavutil/imgutils.h> #include <libswscale/swscale.h> } #define DEBUG @@ -143,10 +144,13 @@ /* Video metadata */ if (videoStream != -1) { - this->height = int (pFormatCtx->streams[videoStream]->codec->height); - this->width = int (pFormatCtx->streams[videoStream]->codec->width); + this->height = int (pFormatCtx->streams[videoStream]->codecpar->height); + this->width = int (pFormatCtx->streams[videoStream]->codecpar->width); this->fps = av_q2d (pFormatCtx->streams[videoStream]->avg_frame_rate); - avcodec_string (buf, sizeof (buf), pFormatCtx->streams[videoStream]->codec, 0); + AVCodecContext *pCodecCtx_temp; + avcodec_parameters_to_context (pCodecCtx_temp, pFormatCtx->streams[videoStream]->codecpar); + avcodec_string (buf, sizeof (buf), pCodecCtx_temp, 0); + avcodec_free_context(&pCodecCtx_temp); this->codec.video = buf; } else @@ -162,7 +166,7 @@ { avcodec_string (buf, sizeof (buf), pCodecCtxAudio, 0); this->codec.audio = buf; - this->nchannel = pCodecCtxAudio->channels; + this->nchannel = pCodecCtxAudio->ch_layout.nb_channels; this->samplerate = pCodecCtxAudio->sample_rate; } else @@ -210,7 +214,6 @@ /* * Register all formats and codecs */ - av_register_all (); if( ! ( pFormatCtx = avformat_alloc_context() ) || (avformat_open_input (&pFormatCtx, input_path.c_str (), NULL, NULL) != 0) ) @@ -238,7 +241,7 @@ */ for (int j = 0; j < pFormatCtx->nb_streams; j++) { - switch (pFormatCtx->streams[j]->codec->codec_type) + switch (pFormatCtx->streams[j]->codecpar->codec_type) { case AVMEDIA_TYPE_VIDEO: videoStream = j; @@ -266,8 +269,9 @@ init_xml (xml_audio); } - pCodecCtxAudio = pFormatCtx->streams[audioStream]->codec; - pCodecAudio = avcodec_find_decoder (pCodecCtxAudio->codec_id); + avcodec_parameters_to_context (pCodecCtxAudio, pFormatCtx->streams[audioStream]->codecpar); + const AVCodec * local_codec_Audio = avcodec_find_decoder (pCodecCtxAudio->codec_id); + pCodecAudio = const_cast<AVCodec *>(local_codec_Audio); if (pCodecAudio == NULL) return -1; // Codec not found @@ -281,8 +285,9 @@ */ if (videoStream != -1) { - pCodecCtx = pFormatCtx->streams[videoStream]->codec; - pCodec = avcodec_find_decoder (pCodecCtx->codec_id); + avcodec_parameters_to_context (pCodecCtx, pFormatCtx->streams[videoStream]->codecpar); + const AVCodec * local_codec = avcodec_find_decoder (pCodecCtx->codec_id); + pCodec = const_cast<AVCodec *>(local_codec); if (pCodec == NULL) return -1; // Codec not found @@ -299,7 +304,7 @@ /* * Determine required buffer size and allocate buffer */ - numBytes = avpicture_get_size (AV_PIX_FMT_RGB24, width, height); + numBytes = av_image_get_buffer_size (AV_PIX_FMT_RGB24, width, height, 1); buffer = (uint8_t *) malloc (sizeof (uint8_t) * numBytes); buffer2 = (uint8_t *) malloc (sizeof (uint8_t) * numBytes); @@ -307,10 +312,11 @@ /* * Assign appropriate parts of buffer to image planes in pFrameRGB */ - avpicture_fill ((AVPicture *) pFrameRGB, buffer, AV_PIX_FMT_RGB24, width, height); - - avpicture_fill ((AVPicture *) pFrameRGBprev, buffer2, AV_PIX_FMT_RGB24, width, height); + av_image_fill_arrays(pFrameRGB->data, pFrameRGB->linesize, + buffer, AV_PIX_FMT_RGB24, width, height, 1); + av_image_fill_arrays(pFrameRGBprev->data, pFrameRGBprev->linesize, + buffer2, AV_PIX_FMT_RGB24, width, height, 1); /* * Mise en place du premier plan @@ -335,15 +341,15 @@ { if (packet.stream_index == videoStream) { - AVPacket avpkt; - av_init_packet(&avpkt); - avpkt.data = packet.data; - avpkt.size = packet.size; - // + AVPacket *avpkt = av_packet_alloc(); + avpkt->data = packet.data; + avpkt->size = packet.size; + // // HACK for CorePNG to decode as normal PNG by default // same method used by ffmpeg - avpkt.flags = AV_PKT_FLAG_KEY; - avcodec_decode_video2(pCodecCtx, pFrame, &frameFinished, &avpkt); + avpkt->flags = AV_PKT_FLAG_KEY; + avcodec_send_packet(pCodecCtx,avpkt); + avcodec_receive_frame(pCodecCtx,pFrame); if (frameFinished) { @@ -404,7 +410,7 @@ * Free the packet that was allocated by av_read_frame */ if (packet.data != NULL) - av_free_packet (&packet); + av_packet_unref (&packet); } if (videoStream != -1) @@ -440,7 +446,7 @@ av_frame_free (&pFrameRGB); av_frame_free (&pFrame); av_frame_free (&pFrameRGBprev); - avcodec_close (pCodecCtx); + avcodec_free_context(&pCodecCtx); } /* * Close the codec @@ -449,7 +455,7 @@ { /* Close the XML file */ if (audio_set) close_xml (); - avcodec_close (pCodecCtxAudio); + avcodec_free_context(&pCodecCtxAudio); } /* @@ -496,14 +502,13 @@ ptr = packet.data; len = packet.size; - AVPacket avpkt; - av_init_packet(&avpkt); + AVPacket *avpkt = av_packet_alloc(); while (len > 0) { - avpkt.data = ptr; - avpkt.size = len; - len1 = avcodec_decode_audio4 (pCodecCtxAudio, frame, &got_output, &avpkt); - + avpkt->data = ptr; + avpkt->size = len; + avcodec_send_packet (pCodecCtxAudio,avpkt); + len1 = avcodec_receive_frame (pCodecCtxAudio, frame); if (len1 < 0) { @@ -524,12 +529,12 @@ if (av_sample_fmt_is_planar(pCodecCtxAudio->sample_fmt)) { left = (int16_t*)frame->data[0]; - right = (pCodecCtxAudio->channels > 1) ? (int16_t*)frame->data[1] : left; + right = (pCodecCtxAudio->ch_layout.nb_channels > 1) ? (int16_t*)frame->data[1] : left; block_align = 1; } else { left = (int16_t*)frame->data[0]; - right = (pCodecCtxAudio->channels > 1) ? left + 1 : left; - block_align = pCodecCtxAudio->channels; + right = (pCodecCtxAudio->ch_layout.nb_channels > 1) ? left + 1 : left; + block_align = pCodecCtxAudio->ch_layout.nb_channels; } samples += frame->nb_samples; @@ -594,3 +599,4 @@ this->shot_set = false; } +