• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * This file is part of FFmpeg.
3  *
4  * FFmpeg is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU Lesser General Public
6  * License as published by the Free Software Foundation; either
7  * version 2.1 of the License, or (at your option) any later version.
8  *
9  * FFmpeg is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
12  * Lesser General Public License for more details.
13  *
14  * You should have received a copy of the GNU Lesser General Public
15  * License along with FFmpeg; if not, write to the Free Software
16  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
17  */
18 
19 #include "channel_layout.h"
20 #include "avassert.h"
21 #include "buffer.h"
22 #include "common.h"
23 #include "dict.h"
24 #include "frame.h"
25 #include "imgutils.h"
26 #include "mem.h"
27 #include "samplefmt.h"
28 #include "hwcontext.h"
29 
30 #if FF_API_FRAME_GET_SET
31 MAKE_ACCESSORS(AVFrame, frame, int64_t, best_effort_timestamp)
32 MAKE_ACCESSORS(AVFrame, frame, int64_t, pkt_duration)
33 MAKE_ACCESSORS(AVFrame, frame, int64_t, pkt_pos)
34 MAKE_ACCESSORS(AVFrame, frame, int64_t, channel_layout)
35 MAKE_ACCESSORS(AVFrame, frame, int,     channels)
36 MAKE_ACCESSORS(AVFrame, frame, int,     sample_rate)
37 MAKE_ACCESSORS(AVFrame, frame, AVDictionary *, metadata)
38 MAKE_ACCESSORS(AVFrame, frame, int,     decode_error_flags)
39 MAKE_ACCESSORS(AVFrame, frame, int,     pkt_size)
40 MAKE_ACCESSORS(AVFrame, frame, enum AVColorSpace, colorspace)
41 MAKE_ACCESSORS(AVFrame, frame, enum AVColorRange, color_range)
42 #endif
43 
44 #define CHECK_CHANNELS_CONSISTENCY(frame) \
45     av_assert2(!(frame)->channel_layout || \
46                (frame)->channels == \
47                av_get_channel_layout_nb_channels((frame)->channel_layout))
48 
49 #if FF_API_FRAME_QP
50 struct qp_properties {
51     int stride;
52     int type;
53 };
54 
av_frame_set_qp_table(AVFrame * f,AVBufferRef * buf,int stride,int qp_type)55 int av_frame_set_qp_table(AVFrame *f, AVBufferRef *buf, int stride, int qp_type)
56 {
57     struct qp_properties *p;
58     AVFrameSideData *sd;
59     AVBufferRef *ref;
60 
61 FF_DISABLE_DEPRECATION_WARNINGS
62     av_buffer_unref(&f->qp_table_buf);
63 
64     f->qp_table_buf = buf;
65     f->qscale_table = buf->data;
66     f->qstride      = stride;
67     f->qscale_type  = qp_type;
68 FF_ENABLE_DEPRECATION_WARNINGS
69 
70     av_frame_remove_side_data(f, AV_FRAME_DATA_QP_TABLE_PROPERTIES);
71     av_frame_remove_side_data(f, AV_FRAME_DATA_QP_TABLE_DATA);
72 
73     ref = av_buffer_ref(buf);
74     if (!av_frame_new_side_data_from_buf(f, AV_FRAME_DATA_QP_TABLE_DATA, ref)) {
75         av_buffer_unref(&ref);
76         return AVERROR(ENOMEM);
77     }
78 
79     sd = av_frame_new_side_data(f, AV_FRAME_DATA_QP_TABLE_PROPERTIES,
80                                 sizeof(struct qp_properties));
81     if (!sd)
82         return AVERROR(ENOMEM);
83 
84     p = (struct qp_properties *)sd->data;
85     p->stride = stride;
86     p->type = qp_type;
87 
88     return 0;
89 }
90 
av_frame_get_qp_table(AVFrame * f,int * stride,int * type)91 int8_t *av_frame_get_qp_table(AVFrame *f, int *stride, int *type)
92 {
93     AVBufferRef *buf = NULL;
94 
95     *stride = 0;
96     *type   = 0;
97 
98 FF_DISABLE_DEPRECATION_WARNINGS
99     if (f->qp_table_buf) {
100         *stride = f->qstride;
101         *type   = f->qscale_type;
102         buf     = f->qp_table_buf;
103 FF_ENABLE_DEPRECATION_WARNINGS
104     } else {
105         AVFrameSideData *sd;
106         struct qp_properties *p;
107         sd = av_frame_get_side_data(f, AV_FRAME_DATA_QP_TABLE_PROPERTIES);
108         if (!sd)
109             return NULL;
110         p = (struct qp_properties *)sd->data;
111         sd = av_frame_get_side_data(f, AV_FRAME_DATA_QP_TABLE_DATA);
112         if (!sd)
113             return NULL;
114         *stride = p->stride;
115         *type   = p->type;
116         buf     = sd->buf;
117     }
118 
119     return buf ? buf->data : NULL;
120 }
121 #endif
122 
av_get_colorspace_name(enum AVColorSpace val)123 const char *av_get_colorspace_name(enum AVColorSpace val)
124 {
125     static const char * const name[] = {
126         [AVCOL_SPC_RGB]       = "GBR",
127         [AVCOL_SPC_BT709]     = "bt709",
128         [AVCOL_SPC_FCC]       = "fcc",
129         [AVCOL_SPC_BT470BG]   = "bt470bg",
130         [AVCOL_SPC_SMPTE170M] = "smpte170m",
131         [AVCOL_SPC_SMPTE240M] = "smpte240m",
132         [AVCOL_SPC_YCOCG]     = "YCgCo",
133     };
134     if ((unsigned)val >= FF_ARRAY_ELEMS(name))
135         return NULL;
136     return name[val];
137 }
138 
get_frame_defaults(AVFrame * frame)139 static void get_frame_defaults(AVFrame *frame)
140 {
141     if (frame->extended_data != frame->data)
142         av_freep(&frame->extended_data);
143 
144     memset(frame, 0, sizeof(*frame));
145 
146     frame->pts                   =
147     frame->pkt_dts               = AV_NOPTS_VALUE;
148 #if FF_API_PKT_PTS
149 FF_DISABLE_DEPRECATION_WARNINGS
150     frame->pkt_pts               = AV_NOPTS_VALUE;
151 FF_ENABLE_DEPRECATION_WARNINGS
152 #endif
153     frame->best_effort_timestamp = AV_NOPTS_VALUE;
154     frame->pkt_duration        = 0;
155     frame->pkt_pos             = -1;
156     frame->pkt_size            = -1;
157     frame->key_frame           = 1;
158     frame->sample_aspect_ratio = (AVRational){ 0, 1 };
159     frame->format              = -1; /* unknown */
160     frame->extended_data       = frame->data;
161     frame->color_primaries     = AVCOL_PRI_UNSPECIFIED;
162     frame->color_trc           = AVCOL_TRC_UNSPECIFIED;
163     frame->colorspace          = AVCOL_SPC_UNSPECIFIED;
164     frame->color_range         = AVCOL_RANGE_UNSPECIFIED;
165     frame->chroma_location     = AVCHROMA_LOC_UNSPECIFIED;
166     frame->flags               = 0;
167 }
168 
free_side_data(AVFrameSideData ** ptr_sd)169 static void free_side_data(AVFrameSideData **ptr_sd)
170 {
171     AVFrameSideData *sd = *ptr_sd;
172 
173     av_buffer_unref(&sd->buf);
174     av_dict_free(&sd->metadata);
175     av_freep(ptr_sd);
176 }
177 
wipe_side_data(AVFrame * frame)178 static void wipe_side_data(AVFrame *frame)
179 {
180     int i;
181 
182     for (i = 0; i < frame->nb_side_data; i++) {
183         free_side_data(&frame->side_data[i]);
184     }
185     frame->nb_side_data = 0;
186 
187     av_freep(&frame->side_data);
188 }
189 
av_frame_alloc(void)190 AVFrame *av_frame_alloc(void)
191 {
192     AVFrame *frame = av_mallocz(sizeof(*frame));
193 
194     if (!frame)
195         return NULL;
196 
197     frame->extended_data = NULL;
198     get_frame_defaults(frame);
199 
200     return frame;
201 }
202 
av_frame_free(AVFrame ** frame)203 void av_frame_free(AVFrame **frame)
204 {
205     if (!frame || !*frame)
206         return;
207 
208     av_frame_unref(*frame);
209     av_freep(frame);
210 }
211 
get_video_buffer(AVFrame * frame,int align)212 static int get_video_buffer(AVFrame *frame, int align)
213 {
214     const AVPixFmtDescriptor *desc = av_pix_fmt_desc_get(frame->format);
215     int ret, i, padded_height, total_size;
216     int plane_padding = FFMAX(16 + 16/*STRIDE_ALIGN*/, align);
217     ptrdiff_t linesizes[4];
218     size_t sizes[4];
219 
220     if (!desc)
221         return AVERROR(EINVAL);
222 
223     if ((ret = av_image_check_size(frame->width, frame->height, 0, NULL)) < 0)
224         return ret;
225 
226     if (!frame->linesize[0]) {
227         if (align <= 0)
228             align = 32; /* STRIDE_ALIGN. Should be av_cpu_max_align() */
229 
230         for(i=1; i<=align; i+=i) {
231             ret = av_image_fill_linesizes(frame->linesize, frame->format,
232                                           FFALIGN(frame->width, i));
233             if (ret < 0)
234                 return ret;
235             if (!(frame->linesize[0] & (align-1)))
236                 break;
237         }
238 
239         for (i = 0; i < 4 && frame->linesize[i]; i++)
240             frame->linesize[i] = FFALIGN(frame->linesize[i], align);
241     }
242 
243     for (i = 0; i < 4; i++)
244         linesizes[i] = frame->linesize[i];
245 
246     padded_height = FFALIGN(frame->height, 32);
247     if ((ret = av_image_fill_plane_sizes(sizes, frame->format,
248                                          padded_height, linesizes)) < 0)
249         return ret;
250 
251     total_size = 4*plane_padding;
252     for (i = 0; i < 4; i++) {
253         if (sizes[i] > INT_MAX - total_size)
254             return AVERROR(EINVAL);
255         total_size += sizes[i];
256     }
257 
258     frame->buf[0] = av_buffer_alloc(total_size);
259     if (!frame->buf[0]) {
260         ret = AVERROR(ENOMEM);
261         goto fail;
262     }
263 
264     if ((ret = av_image_fill_pointers(frame->data, frame->format, padded_height,
265                                       frame->buf[0]->data, frame->linesize)) < 0)
266         goto fail;
267 
268     for (i = 1; i < 4; i++) {
269         if (frame->data[i])
270             frame->data[i] += i * plane_padding;
271     }
272 
273     frame->extended_data = frame->data;
274 
275     return 0;
276 fail:
277     av_frame_unref(frame);
278     return ret;
279 }
280 
get_audio_buffer(AVFrame * frame,int align)281 static int get_audio_buffer(AVFrame *frame, int align)
282 {
283     int channels;
284     int planar   = av_sample_fmt_is_planar(frame->format);
285     int planes;
286     int ret, i;
287 
288     if (!frame->channels)
289         frame->channels = av_get_channel_layout_nb_channels(frame->channel_layout);
290 
291     channels = frame->channels;
292     planes = planar ? channels : 1;
293 
294     CHECK_CHANNELS_CONSISTENCY(frame);
295     if (!frame->linesize[0]) {
296         ret = av_samples_get_buffer_size(&frame->linesize[0], channels,
297                                          frame->nb_samples, frame->format,
298                                          align);
299         if (ret < 0)
300             return ret;
301     }
302 
303     if (planes > AV_NUM_DATA_POINTERS) {
304         frame->extended_data = av_mallocz_array(planes,
305                                           sizeof(*frame->extended_data));
306         frame->extended_buf  = av_mallocz_array((planes - AV_NUM_DATA_POINTERS),
307                                           sizeof(*frame->extended_buf));
308         if (!frame->extended_data || !frame->extended_buf) {
309             av_freep(&frame->extended_data);
310             av_freep(&frame->extended_buf);
311             return AVERROR(ENOMEM);
312         }
313         frame->nb_extended_buf = planes - AV_NUM_DATA_POINTERS;
314     } else
315         frame->extended_data = frame->data;
316 
317     for (i = 0; i < FFMIN(planes, AV_NUM_DATA_POINTERS); i++) {
318         frame->buf[i] = av_buffer_alloc(frame->linesize[0]);
319         if (!frame->buf[i]) {
320             av_frame_unref(frame);
321             return AVERROR(ENOMEM);
322         }
323         frame->extended_data[i] = frame->data[i] = frame->buf[i]->data;
324     }
325     for (i = 0; i < planes - AV_NUM_DATA_POINTERS; i++) {
326         frame->extended_buf[i] = av_buffer_alloc(frame->linesize[0]);
327         if (!frame->extended_buf[i]) {
328             av_frame_unref(frame);
329             return AVERROR(ENOMEM);
330         }
331         frame->extended_data[i + AV_NUM_DATA_POINTERS] = frame->extended_buf[i]->data;
332     }
333     return 0;
334 
335 }
336 
av_frame_get_buffer(AVFrame * frame,int align)337 int av_frame_get_buffer(AVFrame *frame, int align)
338 {
339     if (frame->format < 0)
340         return AVERROR(EINVAL);
341 
342     if (frame->width > 0 && frame->height > 0)
343         return get_video_buffer(frame, align);
344     else if (frame->nb_samples > 0 && (frame->channel_layout || frame->channels > 0))
345         return get_audio_buffer(frame, align);
346 
347     return AVERROR(EINVAL);
348 }
349 
frame_copy_props(AVFrame * dst,const AVFrame * src,int force_copy)350 static int frame_copy_props(AVFrame *dst, const AVFrame *src, int force_copy)
351 {
352     int ret, i;
353 
354     dst->key_frame              = src->key_frame;
355     dst->pict_type              = src->pict_type;
356     dst->sample_aspect_ratio    = src->sample_aspect_ratio;
357     dst->crop_top               = src->crop_top;
358     dst->crop_bottom            = src->crop_bottom;
359     dst->crop_left              = src->crop_left;
360     dst->crop_right             = src->crop_right;
361     dst->pts                    = src->pts;
362     dst->repeat_pict            = src->repeat_pict;
363     dst->interlaced_frame       = src->interlaced_frame;
364     dst->top_field_first        = src->top_field_first;
365     dst->palette_has_changed    = src->palette_has_changed;
366     dst->sample_rate            = src->sample_rate;
367     dst->opaque                 = src->opaque;
368 #if FF_API_PKT_PTS
369 FF_DISABLE_DEPRECATION_WARNINGS
370     dst->pkt_pts                = src->pkt_pts;
371 FF_ENABLE_DEPRECATION_WARNINGS
372 #endif
373     dst->pkt_dts                = src->pkt_dts;
374     dst->pkt_pos                = src->pkt_pos;
375     dst->pkt_size               = src->pkt_size;
376     dst->pkt_duration           = src->pkt_duration;
377     dst->reordered_opaque       = src->reordered_opaque;
378     dst->quality                = src->quality;
379     dst->best_effort_timestamp  = src->best_effort_timestamp;
380     dst->coded_picture_number   = src->coded_picture_number;
381     dst->display_picture_number = src->display_picture_number;
382     dst->flags                  = src->flags;
383     dst->decode_error_flags     = src->decode_error_flags;
384     dst->color_primaries        = src->color_primaries;
385     dst->color_trc              = src->color_trc;
386     dst->colorspace             = src->colorspace;
387     dst->color_range            = src->color_range;
388     dst->chroma_location        = src->chroma_location;
389 
390     av_dict_copy(&dst->metadata, src->metadata, 0);
391 
392 #if FF_API_ERROR_FRAME
393 FF_DISABLE_DEPRECATION_WARNINGS
394     memcpy(dst->error, src->error, sizeof(dst->error));
395 FF_ENABLE_DEPRECATION_WARNINGS
396 #endif
397 
398     for (i = 0; i < src->nb_side_data; i++) {
399         const AVFrameSideData *sd_src = src->side_data[i];
400         AVFrameSideData *sd_dst;
401         if (   sd_src->type == AV_FRAME_DATA_PANSCAN
402             && (src->width != dst->width || src->height != dst->height))
403             continue;
404         if (force_copy) {
405             sd_dst = av_frame_new_side_data(dst, sd_src->type,
406                                             sd_src->size);
407             if (!sd_dst) {
408                 wipe_side_data(dst);
409                 return AVERROR(ENOMEM);
410             }
411             memcpy(sd_dst->data, sd_src->data, sd_src->size);
412         } else {
413             AVBufferRef *ref = av_buffer_ref(sd_src->buf);
414             sd_dst = av_frame_new_side_data_from_buf(dst, sd_src->type, ref);
415             if (!sd_dst) {
416                 av_buffer_unref(&ref);
417                 wipe_side_data(dst);
418                 return AVERROR(ENOMEM);
419             }
420         }
421         av_dict_copy(&sd_dst->metadata, sd_src->metadata, 0);
422     }
423 
424 #if FF_API_FRAME_QP
425 FF_DISABLE_DEPRECATION_WARNINGS
426     dst->qscale_table = NULL;
427     dst->qstride      = 0;
428     dst->qscale_type  = 0;
429     av_buffer_replace(&dst->qp_table_buf, src->qp_table_buf);
430     if (dst->qp_table_buf) {
431         dst->qscale_table = dst->qp_table_buf->data;
432         dst->qstride      = src->qstride;
433         dst->qscale_type  = src->qscale_type;
434     }
435 FF_ENABLE_DEPRECATION_WARNINGS
436 #endif
437 
438     ret = av_buffer_replace(&dst->opaque_ref, src->opaque_ref);
439     ret |= av_buffer_replace(&dst->private_ref, src->private_ref);
440     return ret;
441 }
442 
av_frame_ref(AVFrame * dst,const AVFrame * src)443 int av_frame_ref(AVFrame *dst, const AVFrame *src)
444 {
445     int i, ret = 0;
446 
447     av_assert1(dst->width == 0 && dst->height == 0);
448     av_assert1(dst->channels == 0);
449 
450     dst->format         = src->format;
451     dst->width          = src->width;
452     dst->height         = src->height;
453     dst->channels       = src->channels;
454     dst->channel_layout = src->channel_layout;
455     dst->nb_samples     = src->nb_samples;
456 
457     ret = frame_copy_props(dst, src, 0);
458     if (ret < 0)
459         goto fail;
460 
461     /* duplicate the frame data if it's not refcounted */
462     if (!src->buf[0]) {
463         ret = av_frame_get_buffer(dst, 0);
464         if (ret < 0)
465             goto fail;
466 
467         ret = av_frame_copy(dst, src);
468         if (ret < 0)
469             goto fail;
470 
471         return ret;
472     }
473 
474     /* ref the buffers */
475     for (i = 0; i < FF_ARRAY_ELEMS(src->buf); i++) {
476         if (!src->buf[i])
477             continue;
478         dst->buf[i] = av_buffer_ref(src->buf[i]);
479         if (!dst->buf[i]) {
480             ret = AVERROR(ENOMEM);
481             goto fail;
482         }
483     }
484 
485     if (src->extended_buf) {
486         dst->extended_buf = av_mallocz_array(sizeof(*dst->extended_buf),
487                                        src->nb_extended_buf);
488         if (!dst->extended_buf) {
489             ret = AVERROR(ENOMEM);
490             goto fail;
491         }
492         dst->nb_extended_buf = src->nb_extended_buf;
493 
494         for (i = 0; i < src->nb_extended_buf; i++) {
495             dst->extended_buf[i] = av_buffer_ref(src->extended_buf[i]);
496             if (!dst->extended_buf[i]) {
497                 ret = AVERROR(ENOMEM);
498                 goto fail;
499             }
500         }
501     }
502 
503     if (src->hw_frames_ctx) {
504         dst->hw_frames_ctx = av_buffer_ref(src->hw_frames_ctx);
505         if (!dst->hw_frames_ctx) {
506             ret = AVERROR(ENOMEM);
507             goto fail;
508         }
509     }
510 
511     /* duplicate extended data */
512     if (src->extended_data != src->data) {
513         int ch = src->channels;
514 
515         if (!ch) {
516             ret = AVERROR(EINVAL);
517             goto fail;
518         }
519         CHECK_CHANNELS_CONSISTENCY(src);
520 
521         dst->extended_data = av_malloc_array(sizeof(*dst->extended_data), ch);
522         if (!dst->extended_data) {
523             ret = AVERROR(ENOMEM);
524             goto fail;
525         }
526         memcpy(dst->extended_data, src->extended_data, sizeof(*src->extended_data) * ch);
527     } else
528         dst->extended_data = dst->data;
529 
530     memcpy(dst->data,     src->data,     sizeof(src->data));
531     memcpy(dst->linesize, src->linesize, sizeof(src->linesize));
532 
533     return 0;
534 
535 fail:
536     av_frame_unref(dst);
537     return ret;
538 }
539 
av_frame_clone(const AVFrame * src)540 AVFrame *av_frame_clone(const AVFrame *src)
541 {
542     AVFrame *ret = av_frame_alloc();
543 
544     if (!ret)
545         return NULL;
546 
547     if (av_frame_ref(ret, src) < 0)
548         av_frame_free(&ret);
549 
550     return ret;
551 }
552 
av_frame_unref(AVFrame * frame)553 void av_frame_unref(AVFrame *frame)
554 {
555     int i;
556 
557     if (!frame)
558         return;
559 
560     wipe_side_data(frame);
561 
562     for (i = 0; i < FF_ARRAY_ELEMS(frame->buf); i++)
563         av_buffer_unref(&frame->buf[i]);
564     for (i = 0; i < frame->nb_extended_buf; i++)
565         av_buffer_unref(&frame->extended_buf[i]);
566     av_freep(&frame->extended_buf);
567     av_dict_free(&frame->metadata);
568 #if FF_API_FRAME_QP
569 FF_DISABLE_DEPRECATION_WARNINGS
570     av_buffer_unref(&frame->qp_table_buf);
571 FF_ENABLE_DEPRECATION_WARNINGS
572 #endif
573 
574     av_buffer_unref(&frame->hw_frames_ctx);
575 
576     av_buffer_unref(&frame->opaque_ref);
577     av_buffer_unref(&frame->private_ref);
578 
579     get_frame_defaults(frame);
580 }
581 
av_frame_move_ref(AVFrame * dst,AVFrame * src)582 void av_frame_move_ref(AVFrame *dst, AVFrame *src)
583 {
584     av_assert1(dst->width == 0 && dst->height == 0);
585     av_assert1(dst->channels == 0);
586 
587     *dst = *src;
588     if (src->extended_data == src->data)
589         dst->extended_data = dst->data;
590     memset(src, 0, sizeof(*src));
591     get_frame_defaults(src);
592 }
593 
av_frame_is_writable(AVFrame * frame)594 int av_frame_is_writable(AVFrame *frame)
595 {
596     int i, ret = 1;
597 
598     /* assume non-refcounted frames are not writable */
599     if (!frame->buf[0])
600         return 0;
601 
602     for (i = 0; i < FF_ARRAY_ELEMS(frame->buf); i++)
603         if (frame->buf[i])
604             ret &= !!av_buffer_is_writable(frame->buf[i]);
605     for (i = 0; i < frame->nb_extended_buf; i++)
606         ret &= !!av_buffer_is_writable(frame->extended_buf[i]);
607 
608     return ret;
609 }
610 
av_frame_make_writable(AVFrame * frame)611 int av_frame_make_writable(AVFrame *frame)
612 {
613     AVFrame tmp;
614     int ret;
615 
616     if (!frame->buf[0])
617         return AVERROR(EINVAL);
618 
619     if (av_frame_is_writable(frame))
620         return 0;
621 
622     memset(&tmp, 0, sizeof(tmp));
623     tmp.format         = frame->format;
624     tmp.width          = frame->width;
625     tmp.height         = frame->height;
626     tmp.channels       = frame->channels;
627     tmp.channel_layout = frame->channel_layout;
628     tmp.nb_samples     = frame->nb_samples;
629 
630     if (frame->hw_frames_ctx)
631         ret = av_hwframe_get_buffer(frame->hw_frames_ctx, &tmp, 0);
632     else
633         ret = av_frame_get_buffer(&tmp, 0);
634     if (ret < 0)
635         return ret;
636 
637     ret = av_frame_copy(&tmp, frame);
638     if (ret < 0) {
639         av_frame_unref(&tmp);
640         return ret;
641     }
642 
643     ret = av_frame_copy_props(&tmp, frame);
644     if (ret < 0) {
645         av_frame_unref(&tmp);
646         return ret;
647     }
648 
649     av_frame_unref(frame);
650 
651     *frame = tmp;
652     if (tmp.data == tmp.extended_data)
653         frame->extended_data = frame->data;
654 
655     return 0;
656 }
657 
av_frame_copy_props(AVFrame * dst,const AVFrame * src)658 int av_frame_copy_props(AVFrame *dst, const AVFrame *src)
659 {
660     return frame_copy_props(dst, src, 1);
661 }
662 
av_frame_get_plane_buffer(AVFrame * frame,int plane)663 AVBufferRef *av_frame_get_plane_buffer(AVFrame *frame, int plane)
664 {
665     uint8_t *data;
666     int planes, i;
667 
668     if (frame->nb_samples) {
669         int channels = frame->channels;
670         if (!channels)
671             return NULL;
672         CHECK_CHANNELS_CONSISTENCY(frame);
673         planes = av_sample_fmt_is_planar(frame->format) ? channels : 1;
674     } else
675         planes = 4;
676 
677     if (plane < 0 || plane >= planes || !frame->extended_data[plane])
678         return NULL;
679     data = frame->extended_data[plane];
680 
681     for (i = 0; i < FF_ARRAY_ELEMS(frame->buf) && frame->buf[i]; i++) {
682         AVBufferRef *buf = frame->buf[i];
683         if (data >= buf->data && data < buf->data + buf->size)
684             return buf;
685     }
686     for (i = 0; i < frame->nb_extended_buf; i++) {
687         AVBufferRef *buf = frame->extended_buf[i];
688         if (data >= buf->data && data < buf->data + buf->size)
689             return buf;
690     }
691     return NULL;
692 }
693 
av_frame_new_side_data_from_buf(AVFrame * frame,enum AVFrameSideDataType type,AVBufferRef * buf)694 AVFrameSideData *av_frame_new_side_data_from_buf(AVFrame *frame,
695                                                  enum AVFrameSideDataType type,
696                                                  AVBufferRef *buf)
697 {
698     AVFrameSideData *ret, **tmp;
699 
700     if (!buf)
701         return NULL;
702 
703     if (frame->nb_side_data > INT_MAX / sizeof(*frame->side_data) - 1)
704         return NULL;
705 
706     tmp = av_realloc(frame->side_data,
707                      (frame->nb_side_data + 1) * sizeof(*frame->side_data));
708     if (!tmp)
709         return NULL;
710     frame->side_data = tmp;
711 
712     ret = av_mallocz(sizeof(*ret));
713     if (!ret)
714         return NULL;
715 
716     ret->buf = buf;
717     ret->data = ret->buf->data;
718     ret->size = buf->size;
719     ret->type = type;
720 
721     frame->side_data[frame->nb_side_data++] = ret;
722 
723     return ret;
724 }
725 
av_frame_new_side_data(AVFrame * frame,enum AVFrameSideDataType type,buffer_size_t size)726 AVFrameSideData *av_frame_new_side_data(AVFrame *frame,
727                                         enum AVFrameSideDataType type,
728                                         buffer_size_t size)
729 {
730     AVFrameSideData *ret;
731     AVBufferRef *buf = av_buffer_alloc(size);
732     ret = av_frame_new_side_data_from_buf(frame, type, buf);
733     if (!ret)
734         av_buffer_unref(&buf);
735     return ret;
736 }
737 
av_frame_get_side_data(const AVFrame * frame,enum AVFrameSideDataType type)738 AVFrameSideData *av_frame_get_side_data(const AVFrame *frame,
739                                         enum AVFrameSideDataType type)
740 {
741     int i;
742 
743     for (i = 0; i < frame->nb_side_data; i++) {
744         if (frame->side_data[i]->type == type)
745             return frame->side_data[i];
746     }
747     return NULL;
748 }
749 
frame_copy_video(AVFrame * dst,const AVFrame * src)750 static int frame_copy_video(AVFrame *dst, const AVFrame *src)
751 {
752     const uint8_t *src_data[4];
753     int i, planes;
754 
755     if (dst->width  < src->width ||
756         dst->height < src->height)
757         return AVERROR(EINVAL);
758 
759     if (src->hw_frames_ctx || dst->hw_frames_ctx)
760         return av_hwframe_transfer_data(dst, src, 0);
761 
762     planes = av_pix_fmt_count_planes(dst->format);
763     for (i = 0; i < planes; i++)
764         if (!dst->data[i] || !src->data[i])
765             return AVERROR(EINVAL);
766 
767     memcpy(src_data, src->data, sizeof(src_data));
768     av_image_copy(dst->data, dst->linesize,
769                   src_data, src->linesize,
770                   dst->format, src->width, src->height);
771 
772     return 0;
773 }
774 
frame_copy_audio(AVFrame * dst,const AVFrame * src)775 static int frame_copy_audio(AVFrame *dst, const AVFrame *src)
776 {
777     int planar   = av_sample_fmt_is_planar(dst->format);
778     int channels = dst->channels;
779     int planes   = planar ? channels : 1;
780     int i;
781 
782     if (dst->nb_samples     != src->nb_samples ||
783         dst->channels       != src->channels ||
784         dst->channel_layout != src->channel_layout)
785         return AVERROR(EINVAL);
786 
787     CHECK_CHANNELS_CONSISTENCY(src);
788 
789     for (i = 0; i < planes; i++)
790         if (!dst->extended_data[i] || !src->extended_data[i])
791             return AVERROR(EINVAL);
792 
793     av_samples_copy(dst->extended_data, src->extended_data, 0, 0,
794                     dst->nb_samples, channels, dst->format);
795 
796     return 0;
797 }
798 
av_frame_copy(AVFrame * dst,const AVFrame * src)799 int av_frame_copy(AVFrame *dst, const AVFrame *src)
800 {
801     if (dst->format != src->format || dst->format < 0)
802         return AVERROR(EINVAL);
803 
804     if (dst->width > 0 && dst->height > 0)
805         return frame_copy_video(dst, src);
806     else if (dst->nb_samples > 0 && dst->channels > 0)
807         return frame_copy_audio(dst, src);
808 
809     return AVERROR(EINVAL);
810 }
811 
av_frame_remove_side_data(AVFrame * frame,enum AVFrameSideDataType type)812 void av_frame_remove_side_data(AVFrame *frame, enum AVFrameSideDataType type)
813 {
814     int i;
815 
816     for (i = frame->nb_side_data - 1; i >= 0; i--) {
817         AVFrameSideData *sd = frame->side_data[i];
818         if (sd->type == type) {
819             free_side_data(&frame->side_data[i]);
820             frame->side_data[i] = frame->side_data[frame->nb_side_data - 1];
821             frame->nb_side_data--;
822         }
823     }
824 }
825 
av_frame_side_data_name(enum AVFrameSideDataType type)826 const char *av_frame_side_data_name(enum AVFrameSideDataType type)
827 {
828     switch(type) {
829     case AV_FRAME_DATA_PANSCAN:         return "AVPanScan";
830     case AV_FRAME_DATA_A53_CC:          return "ATSC A53 Part 4 Closed Captions";
831     case AV_FRAME_DATA_STEREO3D:        return "Stereo 3D";
832     case AV_FRAME_DATA_MATRIXENCODING:  return "AVMatrixEncoding";
833     case AV_FRAME_DATA_DOWNMIX_INFO:    return "Metadata relevant to a downmix procedure";
834     case AV_FRAME_DATA_REPLAYGAIN:      return "AVReplayGain";
835     case AV_FRAME_DATA_DISPLAYMATRIX:   return "3x3 displaymatrix";
836     case AV_FRAME_DATA_AFD:             return "Active format description";
837     case AV_FRAME_DATA_MOTION_VECTORS:  return "Motion vectors";
838     case AV_FRAME_DATA_SKIP_SAMPLES:    return "Skip samples";
839     case AV_FRAME_DATA_AUDIO_SERVICE_TYPE:          return "Audio service type";
840     case AV_FRAME_DATA_MASTERING_DISPLAY_METADATA:  return "Mastering display metadata";
841     case AV_FRAME_DATA_CONTENT_LIGHT_LEVEL:         return "Content light level metadata";
842     case AV_FRAME_DATA_GOP_TIMECODE:                return "GOP timecode";
843     case AV_FRAME_DATA_S12M_TIMECODE:               return "SMPTE 12-1 timecode";
844     case AV_FRAME_DATA_SPHERICAL:                   return "Spherical Mapping";
845     case AV_FRAME_DATA_ICC_PROFILE:                 return "ICC profile";
846 #if FF_API_FRAME_QP
847     case AV_FRAME_DATA_QP_TABLE_PROPERTIES:         return "QP table properties";
848     case AV_FRAME_DATA_QP_TABLE_DATA:               return "QP table data";
849 #endif
850     case AV_FRAME_DATA_DYNAMIC_HDR_PLUS: return "HDR Dynamic Metadata SMPTE2094-40 (HDR10+)";
851     case AV_FRAME_DATA_REGIONS_OF_INTEREST: return "Regions Of Interest";
852     case AV_FRAME_DATA_VIDEO_ENC_PARAMS:            return "Video encoding parameters";
853     case AV_FRAME_DATA_SEI_UNREGISTERED:            return "H.26[45] User Data Unregistered SEI message";
854     case AV_FRAME_DATA_FILM_GRAIN_PARAMS:           return "Film grain parameters";
855     }
856     return NULL;
857 }
858 
calc_cropping_offsets(size_t offsets[4],const AVFrame * frame,const AVPixFmtDescriptor * desc)859 static int calc_cropping_offsets(size_t offsets[4], const AVFrame *frame,
860                                  const AVPixFmtDescriptor *desc)
861 {
862     int i, j;
863 
864     for (i = 0; frame->data[i]; i++) {
865         const AVComponentDescriptor *comp = NULL;
866         int shift_x = (i == 1 || i == 2) ? desc->log2_chroma_w : 0;
867         int shift_y = (i == 1 || i == 2) ? desc->log2_chroma_h : 0;
868 
869         if (desc->flags & (AV_PIX_FMT_FLAG_PAL | FF_PSEUDOPAL) && i == 1) {
870             offsets[i] = 0;
871             break;
872         }
873 
874         /* find any component descriptor for this plane */
875         for (j = 0; j < desc->nb_components; j++) {
876             if (desc->comp[j].plane == i) {
877                 comp = &desc->comp[j];
878                 break;
879             }
880         }
881         if (!comp)
882             return AVERROR_BUG;
883 
884         offsets[i] = (frame->crop_top  >> shift_y) * frame->linesize[i] +
885                      (frame->crop_left >> shift_x) * comp->step;
886     }
887 
888     return 0;
889 }
890 
av_frame_apply_cropping(AVFrame * frame,int flags)891 int av_frame_apply_cropping(AVFrame *frame, int flags)
892 {
893     const AVPixFmtDescriptor *desc;
894     size_t offsets[4];
895     int i;
896 
897     if (!(frame->width > 0 && frame->height > 0))
898         return AVERROR(EINVAL);
899 
900     if (frame->crop_left >= INT_MAX - frame->crop_right        ||
901         frame->crop_top  >= INT_MAX - frame->crop_bottom       ||
902         (frame->crop_left + frame->crop_right) >= frame->width ||
903         (frame->crop_top + frame->crop_bottom) >= frame->height)
904         return AVERROR(ERANGE);
905 
906     desc = av_pix_fmt_desc_get(frame->format);
907     if (!desc)
908         return AVERROR_BUG;
909 
910     /* Apply just the right/bottom cropping for hwaccel formats. Bitstream
911      * formats cannot be easily handled here either (and corresponding decoders
912      * should not export any cropping anyway), so do the same for those as well.
913      * */
914     if (desc->flags & (AV_PIX_FMT_FLAG_BITSTREAM | AV_PIX_FMT_FLAG_HWACCEL)) {
915         frame->width      -= frame->crop_right;
916         frame->height     -= frame->crop_bottom;
917         frame->crop_right  = 0;
918         frame->crop_bottom = 0;
919         return 0;
920     }
921 
922     /* calculate the offsets for each plane */
923     calc_cropping_offsets(offsets, frame, desc);
924 
925     /* adjust the offsets to avoid breaking alignment */
926     if (!(flags & AV_FRAME_CROP_UNALIGNED)) {
927         int log2_crop_align = frame->crop_left ? ff_ctz(frame->crop_left) : INT_MAX;
928         int min_log2_align = INT_MAX;
929 
930         for (i = 0; frame->data[i]; i++) {
931             int log2_align = offsets[i] ? ff_ctz(offsets[i]) : INT_MAX;
932             min_log2_align = FFMIN(log2_align, min_log2_align);
933         }
934 
935         /* we assume, and it should always be true, that the data alignment is
936          * related to the cropping alignment by a constant power-of-2 factor */
937         if (log2_crop_align < min_log2_align)
938             return AVERROR_BUG;
939 
940         if (min_log2_align < 5) {
941             frame->crop_left &= ~((1 << (5 + log2_crop_align - min_log2_align)) - 1);
942             calc_cropping_offsets(offsets, frame, desc);
943         }
944     }
945 
946     for (i = 0; frame->data[i]; i++)
947         frame->data[i] += offsets[i];
948 
949     frame->width      -= (frame->crop_left + frame->crop_right);
950     frame->height     -= (frame->crop_top  + frame->crop_bottom);
951     frame->crop_left   = 0;
952     frame->crop_right  = 0;
953     frame->crop_top    = 0;
954     frame->crop_bottom = 0;
955 
956     return 0;
957 }
958