[Date Prev][Date Next] [Thread Prev][Thread Next] [Date Index] [Thread Index]

Bug#1081485: Fix compilation of shotdetect against ffmpeg 7



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;
 
 }
+

Reply to: