[Bf-blender-cvs] [0b03785] master: Make Blender compilable with FFmpeg-3.0

Sergey Sharybin noreply at git.blender.org
Tue Feb 16 12:35:00 CET 2016


Commit: 0b03785eb5d46dfc053d7f8ef4924219fe7759c5
Author: Sergey Sharybin
Date:   Tue Feb 16 12:32:42 2016 +0100
Branches: master
https://developer.blender.org/rB0b03785eb5d46dfc053d7f8ef4924219fe7759c5

Make Blender compilable with FFmpeg-3.0

While it's not something we'll be using for the official release,
it's nice to support new libraries at least on "it compiles" level,
so it's not that many frustrated developers around.

Nexyon, please have a look into Audaspace changes :)

===================================================================

M	intern/audaspace/ffmpeg/AUD_FFMPEGReader.cpp
M	intern/audaspace/ffmpeg/AUD_FFMPEGWriter.cpp
M	intern/ffmpeg/ffmpeg_compat.h
M	source/blender/blenkernel/intern/writeffmpeg.c
M	source/blender/imbuf/intern/anim_movie.c
M	source/blender/imbuf/intern/indexer.c

===================================================================

diff --git a/intern/audaspace/ffmpeg/AUD_FFMPEGReader.cpp b/intern/audaspace/ffmpeg/AUD_FFMPEGReader.cpp
index ff2c526..e9eea19 100644
--- a/intern/audaspace/ffmpeg/AUD_FFMPEGReader.cpp
+++ b/intern/audaspace/ffmpeg/AUD_FFMPEGReader.cpp
@@ -58,9 +58,9 @@ int AUD_FFMPEGReader::decode(AVPacket& packet, AUD_Buffer& buffer)
 		got_frame = 0;
 
 		if(!frame)
-			frame = avcodec_alloc_frame();
+			frame = av_frame_alloc();
 		else
-			avcodec_get_frame_defaults(frame);
+			av_frame_unref(frame);
 
 		read_length = avcodec_decode_audio4(m_codecCtx, frame, &got_frame, &packet);
 		if(read_length < 0)
diff --git a/intern/audaspace/ffmpeg/AUD_FFMPEGWriter.cpp b/intern/audaspace/ffmpeg/AUD_FFMPEGWriter.cpp
index 4ee99c7..3f95ac7 100644
--- a/intern/audaspace/ffmpeg/AUD_FFMPEGWriter.cpp
+++ b/intern/audaspace/ffmpeg/AUD_FFMPEGWriter.cpp
@@ -202,7 +202,7 @@ AUD_FFMPEGWriter::AUD_FFMPEGWriter(std::string filename, AUD_DeviceSpecs specs,
 			m_frame = av_frame_alloc();
 			if (!m_frame)
 				AUD_THROW(AUD_ERROR_FFMPEG, codec_error);
-			avcodec_get_frame_defaults(m_frame);
+			av_frame_unref(m_frame);
 			m_frame->linesize[0]    = m_input_size * samplesize;
 			m_frame->format         = m_codecCtx->sample_fmt;
 			m_frame->nb_samples     = m_input_size;
@@ -224,7 +224,9 @@ AUD_FFMPEGWriter::AUD_FFMPEGWriter(std::string filename, AUD_DeviceSpecs specs,
 				if(avio_open(&m_formatCtx->pb, filename.c_str(), AVIO_FLAG_WRITE))
 					AUD_THROW(AUD_ERROR_FILE, file_error);
 
-				avformat_write_header(m_formatCtx, NULL);
+				if(avformat_write_header(m_formatCtx, NULL) < 0) {
+					throw;
+				}
 			}
 			catch(AUD_Exception&)
 			{
diff --git a/intern/ffmpeg/ffmpeg_compat.h b/intern/ffmpeg/ffmpeg_compat.h
index ac4da5b..b591032 100644
--- a/intern/ffmpeg/ffmpeg_compat.h
+++ b/intern/ffmpeg/ffmpeg_compat.h
@@ -446,4 +446,205 @@ AVRational av_get_r_frame_rate_compat(const AVStream *stream)
 #  define FFMPEG_HAVE_DEPRECATED_FLAGS2
 #endif
 
+/* Since FFmpeg-1.1 this constant have AV_ prefix. */
+#if LIBAVUTIL_VERSION_INT < AV_VERSION_INT(52, 13, 100)
+#  define AV_PIX_FMT_BGR32 PIX_FMT_BGR32
+#  define AV_PIX_FMT_YUV422P PIX_FMT_YUV422P
+#  define AV_PIX_FMT_BGRA PIX_FMT_BGRA
+#  define AV_PIX_FMT_ARGB PIX_FMT_ARGB
+#  define AV_PIX_FMT_RGBA PIX_FMT_RGBA
+#endif
+
+/* New API from FFmpeg-2.0 which soon became recommended one. */
+#if LIBAVUTIL_VERSION_INT < AV_VERSION_INT(52, 38, 100)
+#  define av_frame_alloc avcodec_alloc_frame
+#  define av_frame_free avcodec_free_frame
+#  define av_frame_unref avcodec_get_frame_defaults
+#endif
+
+#if LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(57, 24, 102)
+
+/* NOTE: The code in this block are from FFmpeg 2.6.4, which is licensed by LGPL. */
+
+#define MAX_NEG_CROP 1024
+
+extern const uint8_t ff_crop_tab[256 + 2 * MAX_NEG_CROP];
+
+/* filter parameters: [-1 4 2 4 -1] // 8 */
+FFMPEG_INLINE
+void deinterlace_line(uint8_t *dst,
+                      const uint8_t *lum_m4, const uint8_t *lum_m3,
+                      const uint8_t *lum_m2, const uint8_t *lum_m1,
+                      const uint8_t *lum,
+                      int size)
+{
+	const uint8_t *cm = ff_crop_tab + MAX_NEG_CROP;
+	int sum;
+
+	for(;size > 0;size--) {
+		sum = -lum_m4[0];
+		sum += lum_m3[0] << 2;
+		sum += lum_m2[0] << 1;
+		sum += lum_m1[0] << 2;
+		sum += -lum[0];
+		dst[0] = cm[(sum + 4) >> 3];
+		lum_m4++;
+		lum_m3++;
+		lum_m2++;
+		lum_m1++;
+		lum++;
+		dst++;
+	}
+}
+
+FFMPEG_INLINE
+void deinterlace_line_inplace(uint8_t *lum_m4, uint8_t *lum_m3,
+                              uint8_t *lum_m2, uint8_t *lum_m1,
+                              uint8_t *lum, int size)
+{
+	const uint8_t *cm = ff_crop_tab + MAX_NEG_CROP;
+	int sum;
+
+	for(;size > 0;size--) {
+		sum = -lum_m4[0];
+		sum += lum_m3[0] << 2;
+		sum += lum_m2[0] << 1;
+		lum_m4[0]=lum_m2[0];
+		sum += lum_m1[0] << 2;
+		sum += -lum[0];
+		lum_m2[0] = cm[(sum + 4) >> 3];
+		lum_m4++;
+		lum_m3++;
+		lum_m2++;
+		lum_m1++;
+		lum++;
+	}
+}
+
+/* deinterlacing : 2 temporal taps, 3 spatial taps linear filter. The
+   top field is copied as is, but the bottom field is deinterlaced
+   against the top field. */
+FFMPEG_INLINE
+void deinterlace_bottom_field(uint8_t *dst, int dst_wrap,
+                              const uint8_t *src1, int src_wrap,
+                              int width, int height)
+{
+	const uint8_t *src_m2, *src_m1, *src_0, *src_p1, *src_p2;
+	int y;
+
+	src_m2 = src1;
+	src_m1 = src1;
+	src_0=&src_m1[src_wrap];
+	src_p1=&src_0[src_wrap];
+	src_p2=&src_p1[src_wrap];
+	for(y=0;y<(height-2);y+=2) {
+		memcpy(dst,src_m1,width);
+		dst += dst_wrap;
+		deinterlace_line(dst,src_m2,src_m1,src_0,src_p1,src_p2,width);
+		src_m2 = src_0;
+		src_m1 = src_p1;
+		src_0 = src_p2;
+		src_p1 += 2*src_wrap;
+		src_p2 += 2*src_wrap;
+		dst += dst_wrap;
+	}
+	memcpy(dst,src_m1,width);
+	dst += dst_wrap;
+	/* do last line */
+	deinterlace_line(dst,src_m2,src_m1,src_0,src_0,src_0,width);
+}
+
+FFMPEG_INLINE
+int deinterlace_bottom_field_inplace(uint8_t *src1, int src_wrap,
+                                     int width, int height)
+{
+	uint8_t *src_m1, *src_0, *src_p1, *src_p2;
+	int y;
+	uint8_t *buf = (uint8_t *)av_malloc(width);
+	if (!buf)
+		return AVERROR(ENOMEM);
+
+	src_m1 = src1;
+	memcpy(buf,src_m1,width);
+	src_0=&src_m1[src_wrap];
+	src_p1=&src_0[src_wrap];
+	src_p2=&src_p1[src_wrap];
+	for(y=0;y<(height-2);y+=2) {
+		deinterlace_line_inplace(buf,src_m1,src_0,src_p1,src_p2,width);
+		src_m1 = src_p1;
+		src_0 = src_p2;
+		src_p1 += 2*src_wrap;
+		src_p2 += 2*src_wrap;
+	}
+	/* do last line */
+	deinterlace_line_inplace(buf,src_m1,src_0,src_0,src_0,width);
+	av_free(buf);
+	return 0;
+}
+
+#ifdef __GNUC__
+#  pragma GCC diagnostic push
+#  pragma GCC diagnostic ignored "-Wdeprecated-declarations"
+#endif
+
+FFMPEG_INLINE
+int avpicture_deinterlace(AVPicture *dst, const AVPicture *src,
+                          enum AVPixelFormat pix_fmt, int width, int height)
+{
+	int i, ret;
+
+	if (pix_fmt != AV_PIX_FMT_YUV420P &&
+	    pix_fmt != AV_PIX_FMT_YUVJ420P &&
+	    pix_fmt != AV_PIX_FMT_YUV422P &&
+	    pix_fmt != AV_PIX_FMT_YUVJ422P &&
+	    pix_fmt != AV_PIX_FMT_YUV444P &&
+	    pix_fmt != AV_PIX_FMT_YUV411P &&
+	    pix_fmt != AV_PIX_FMT_GRAY8)
+		return -1;
+	if ((width & 3) != 0 || (height & 3) != 0)
+		return -1;
+
+	for(i=0;i<3;i++) {
+		if (i == 1) {
+			switch(pix_fmt) {
+			case AV_PIX_FMT_YUVJ420P:
+			case AV_PIX_FMT_YUV420P:
+				width >>= 1;
+				height >>= 1;
+				break;
+			case AV_PIX_FMT_YUV422P:
+			case AV_PIX_FMT_YUVJ422P:
+				width >>= 1;
+				break;
+			case AV_PIX_FMT_YUV411P:
+				width >>= 2;
+				break;
+			default:
+				break;
+			}
+			if (pix_fmt == AV_PIX_FMT_GRAY8) {
+				break;
+			}
+		}
+		if (src == dst) {
+			ret = deinterlace_bottom_field_inplace(dst->data[i],
+			                                       dst->linesize[i],
+			                                       width, height);
+			if (ret < 0)
+				return ret;
+		} else {
+			deinterlace_bottom_field(dst->data[i],dst->linesize[i],
+			                         src->data[i], src->linesize[i],
+			                         width, height);
+		}
+	}
+	return 0;
+}
+
+#ifdef __GNUC__
+#  pragma GCC diagnostic pop
+#endif
+
+#endif
+
 #endif
diff --git a/source/blender/blenkernel/intern/writeffmpeg.c b/source/blender/blenkernel/intern/writeffmpeg.c
index 35fd94d..edeccf4 100644
--- a/source/blender/blenkernel/intern/writeffmpeg.c
+++ b/source/blender/blenkernel/intern/writeffmpeg.c
@@ -138,8 +138,8 @@ static int write_audio_frame(FFMpegContext *context)
 	context->audio_time += (double) context->audio_input_samples / (double) c->sample_rate;
 
 #ifdef FFMPEG_HAVE_ENCODE_AUDIO2
-	frame = avcodec_alloc_frame();
-	avcodec_get_frame_defaults(frame);
+	frame = av_frame_alloc();
+	av_frame_unref(frame);
 	frame->pts = context->audio_time / av_q2d(c->time_base);
 	frame->nb_samples = context->audio_input_samples;
 	frame->format = c->sample_fmt;
@@ -172,7 +172,7 @@ static int write_audio_frame(FFMpegContext *context)
 	}
 
 	if (!got_output) {
-		avcodec_free_frame(&frame);
+		av_frame_free(&frame);
 		return 0;
 	}
 #else
@@ -202,7 +202,7 @@ static int write_audio_frame(FFMpegContext *context)
 		if (av_interleaved_write_frame(context->outfile, &pkt) != 0) {
 			fprintf(stderr, "Error writing audio packet!\n");
 			if (frame)
-				avcodec_free_frame(&frame);
+				av_frame_free(&frame);
 			return -1;
 		}
 
@@ -210,7 +210,7 @@ static int write_audio_frame(FFMpegContext *context)
 	}
 
 	if (frame)
-		avcodec_free_frame(&frame);
+		av_frame_free(&frame);
 
 	return 0;
 }
@@ -224,7 +224,7 @@ static AVFrame *alloc_picture(int pix_fmt, int width, int height)
 	int size;
 	
 	/* allocate space for the struct */
-	f = avcodec_alloc_frame();
+	f = av_frame_alloc();
 	if (!f) return NULL;
 	size = avpicture_get_size(pix_fmt, width, height);
 	/* allocate the actual picture buffer */
@@ -363,8 +363,8 @@ static AVFrame *generate_video_frame(FFMpegContext *context, uint8_t *pixels, Re
 	int height = c->height;
 	AVFrame *rgb_frame;
 
-	if (c->pix_fmt != PIX_FMT_BGR32) {
-		rgb_frame = alloc_picture(PIX_FMT_BGR32, width, height);
+	if (c->pix_fmt != AV_PIX_FMT_BGR32) {
+		rgb_frame = alloc_picture(AV_PIX_FMT_BGR32, width, height);
 		if (!rgb_frame) {
 			BKE_report(reports, RPT_ERROR, "Could not allocate temporary frame");
 			return NULL;
@@ -414,14 +414,14 @@ static AVFrame *generate_video_frame(FFMpegContext *context, uint8_t *pixels, Re
 		}
 	}
 
-	if (c->pix_fmt != PIX_FMT_BGR32) {
+	if (c->pix_fmt != AV_PIX_FMT_BGR32) {
 		sws_scale(context->img_convert_ctx, (const uint8_t *const *) rgb_frame->data,
 		          rgb_frame->linesize, 0, c->height,
 		          context->current_frame->data, context->current_frame->linesize);
 		delete_picture(rgb_frame);
 	}
 
-	context->current_frame->format = PIX_FMT_BGR32;
+	context->current_frame->format = AV_PIX_FMT_BGR32;
 	context->current_frame->width = width;
 	context->current_frame->height = height;
 
@@ -586,12 +586,12 @@ static AVStream *alloc_video_stream(FFMpegContext *context, RenderData *rd, int
 	}
 	else {
 		/* makes HuffYUV happy ... */
-		c->pix_fmt = PIX_FMT_YUV422P;
+		c->pix_fmt = AV_PIX_FMT_YUV422P;
 	}
 
 	if (context->ffmpeg_type == FFMPEG_XVID) {
 		

@@ Diff output truncated at 10240 characters. @@




More information about the Bf-blender-cvs mailing list