MythTV  master
mythavutil.cpp
Go to the documentation of this file.
1 //
2 // mythavutil.cpp
3 // MythTV
4 //
5 // Created by Jean-Yves Avenard on 28/06/2014.
6 // Copyright (c) 2014 Bubblestuff Pty Ltd. All rights reserved.
7 //
8 
9 #include "mythframe.h"
10 #include "mythavutil.h"
11 #include "mythcorecontext.h"
12 #include "mythconfig.h"
13 extern "C" {
14 #include "libswscale/swscale.h"
15 #include "libavfilter/avfilter.h"
16 #include "libavcodec/avcodec.h"
17 #include "libavfilter/buffersrc.h"
18 #include "libavfilter/buffersink.h"
19 #include "libavutil/imgutils.h"
20 #include "libavformat/avformat.h"
21 }
22 #include <QMutexLocker>
23 
25 {
26  switch (type)
27  {
28  case FMT_YV12: return AV_PIX_FMT_YUV420P;
29  case FMT_YUV420P9: return AV_PIX_FMT_YUV420P9;
30  case FMT_YUV420P10: return AV_PIX_FMT_YUV420P10;
31  case FMT_YUV420P12: return AV_PIX_FMT_YUV420P12;
32  case FMT_YUV420P14: return AV_PIX_FMT_YUV420P14;
33  case FMT_YUV420P16: return AV_PIX_FMT_YUV420P16;
34  case FMT_NV12: return AV_PIX_FMT_NV12;
35  case FMT_P010: return AV_PIX_FMT_P010;
36  case FMT_P016: return AV_PIX_FMT_P016;
37  case FMT_YUV422P: return AV_PIX_FMT_YUV422P;
38  case FMT_YUV422P9: return AV_PIX_FMT_YUV422P9;
39  case FMT_YUV422P10: return AV_PIX_FMT_YUV422P10;
40  case FMT_YUV422P12: return AV_PIX_FMT_YUV422P12;
41  case FMT_YUV422P14: return AV_PIX_FMT_YUV422P14;
42  case FMT_YUV422P16: return AV_PIX_FMT_YUV422P16;
43  case FMT_YUV444P: return AV_PIX_FMT_YUV444P;
44  case FMT_YUV444P9: return AV_PIX_FMT_YUV444P9;
45  case FMT_YUV444P10: return AV_PIX_FMT_YUV444P10;
46  case FMT_YUV444P12: return AV_PIX_FMT_YUV444P12;
47  case FMT_YUV444P14: return AV_PIX_FMT_YUV444P14;
48  case FMT_YUV444P16: return AV_PIX_FMT_YUV444P16;
49  case FMT_RGB24: return AV_PIX_FMT_RGB24;
50  case FMT_BGRA: return AV_PIX_FMT_BGRA; // NOLINT(bugprone-branch-clone)
51  case FMT_RGB32: return AV_PIX_FMT_RGB32;
52  case FMT_ARGB32: return AV_PIX_FMT_ARGB;
53  case FMT_RGBA32: return AV_PIX_FMT_RGBA;
54  case FMT_YUY2: return AV_PIX_FMT_UYVY422;
55  case FMT_VDPAU: return AV_PIX_FMT_VDPAU;
56  case FMT_VTB: return AV_PIX_FMT_VIDEOTOOLBOX;
57  case FMT_VAAPI: return AV_PIX_FMT_VAAPI;
58  case FMT_MEDIACODEC: return AV_PIX_FMT_MEDIACODEC;
59  case FMT_NVDEC: return AV_PIX_FMT_CUDA;
60  case FMT_DXVA2: return AV_PIX_FMT_DXVA2_VLD;
61  case FMT_MMAL: return AV_PIX_FMT_MMAL;
62  case FMT_DRMPRIME: return AV_PIX_FMT_DRM_PRIME;
63  case FMT_NONE: break;
64  }
65  return AV_PIX_FMT_NONE;
66 }
67 
69 {
70  switch (fmt)
71  {
72  case AV_PIX_FMT_YUVJ420P:
73  case AV_PIX_FMT_YUV420P: return FMT_YV12;
74  case AV_PIX_FMT_YUV420P9: return FMT_YUV420P9;
75  case AV_PIX_FMT_YUV420P10: return FMT_YUV420P10;
76  case AV_PIX_FMT_YUV420P12: return FMT_YUV420P12;
77  case AV_PIX_FMT_YUV420P14: return FMT_YUV420P14;
78  case AV_PIX_FMT_YUV420P16: return FMT_YUV420P16;
79  case AV_PIX_FMT_NV12: return FMT_NV12;
80  case AV_PIX_FMT_P010: return FMT_P010;
81  case AV_PIX_FMT_P016: return FMT_P016;
82  case AV_PIX_FMT_YUVJ422P:
83  case AV_PIX_FMT_YUV422P: return FMT_YUV422P;
84  case AV_PIX_FMT_YUV422P9: return FMT_YUV422P9;
85  case AV_PIX_FMT_YUV422P10: return FMT_YUV422P10;
86  case AV_PIX_FMT_YUV422P12: return FMT_YUV422P12;
87  case AV_PIX_FMT_YUV422P14: return FMT_YUV422P14;
88  case AV_PIX_FMT_YUV422P16: return FMT_YUV422P16;
89  case AV_PIX_FMT_YUVJ444P:
90  case AV_PIX_FMT_YUV444P: return FMT_YUV444P;
91  case AV_PIX_FMT_YUV444P9: return FMT_YUV444P9;
92  case AV_PIX_FMT_YUV444P10: return FMT_YUV444P10;
93  case AV_PIX_FMT_YUV444P12: return FMT_YUV444P12;
94  case AV_PIX_FMT_YUV444P14: return FMT_YUV444P14;
95  case AV_PIX_FMT_YUV444P16: return FMT_YUV444P16;
96  case AV_PIX_FMT_UYVY422: return FMT_YUY2;
97  case AV_PIX_FMT_RGB24: return FMT_RGB24;
98  case AV_PIX_FMT_ARGB: return FMT_ARGB32;
99  case AV_PIX_FMT_RGBA: return FMT_RGBA32;
100  case AV_PIX_FMT_BGRA: return FMT_BGRA;
101  case AV_PIX_FMT_CUDA: return FMT_NVDEC;
102  case AV_PIX_FMT_MMAL: return FMT_MMAL;
103  case AV_PIX_FMT_VDPAU: return FMT_VDPAU;
104  case AV_PIX_FMT_VIDEOTOOLBOX: return FMT_VTB;
105  case AV_PIX_FMT_VAAPI: return FMT_VAAPI;
106  case AV_PIX_FMT_DXVA2_VLD: return FMT_DXVA2;
107  case AV_PIX_FMT_MEDIACODEC: return FMT_MEDIACODEC;
108  case AV_PIX_FMT_DRM_PRIME: return FMT_DRMPRIME;
109  default: break;
110  }
111  return FMT_NONE;
112 }
113 
114 QString DeinterlacerName(MythDeintType Deint, bool DoubleRate, VideoFrameType Format)
115 {
116  MythDeintType deint = GetDeinterlacer(Deint);
117  QString result = DoubleRate ? "2x " : "";
118  if (Deint & DEINT_CPU)
119  {
120  result += "CPU ";
121  switch (deint)
122  {
123  case DEINT_HIGH: return result + "Yadif";
124  case DEINT_MEDIUM: return result + "Linearblend";
125  case DEINT_BASIC: return result + "Onefield";
126  default: break;
127  }
128  }
129  else if (Deint & DEINT_SHADER)
130  {
131  result += "GLSL ";
132  switch (deint)
133  {
134  case DEINT_HIGH: return result + "Kernel";
135  case DEINT_MEDIUM: return result + "Linearblend";
136  case DEINT_BASIC: return result + "Onefield";
137  default: break;
138  }
139  }
140  else if (Deint & DEINT_DRIVER)
141  {
142  switch (Format)
143  {
144  case FMT_MEDIACODEC: return "MediaCodec";
145  case FMT_DRMPRIME: return result + "EGL Onefield";
146  case FMT_VDPAU:
147  result += "VDPAU ";
148  switch (deint)
149  {
150  case DEINT_HIGH: return result + "Advanced";
151  case DEINT_MEDIUM: return result + "Temporal";
152  case DEINT_BASIC: return result + "Basic";
153  default: break;
154  }
155  break;
156  case FMT_NVDEC:
157  result += "NVDec ";
158  switch (deint)
159  {
160  case DEINT_HIGH:
161  case DEINT_MEDIUM: return result + "Adaptive";
162  case DEINT_BASIC: return result + "Basic";
163  default: break;
164  }
165  break;
166  case FMT_VAAPI:
167  result += "VAAPI ";
168  switch (deint)
169  {
170  case DEINT_HIGH: return result + "Compensated";
171  case DEINT_MEDIUM: return result + "Adaptive";
172  case DEINT_BASIC: return result + "Basic";
173  default: break;
174  }
175  break;
176  default: break;
177  }
178  }
179  return "None";
180 }
181 
183 {
184  if (DEINT_NONE == Deint)
185  return QString("None");
186  QString result;
187  if (Deint & DEINT_BASIC) result = "Basic";
188  else if (Deint & DEINT_MEDIUM) result = "Medium";
189  else if (Deint & DEINT_HIGH) result = "High";
190  if (Deint & DEINT_CPU) result += "|CPU";
191  if (Deint & DEINT_SHADER) result += "|GLSL";
192  if (Deint & DEINT_DRIVER) result += "|DRIVER";
193  return result;
194 }
195 
196 int AVPictureFill(AVFrame *pic, const VideoFrame *frame, AVPixelFormat fmt)
197 {
198  if (fmt == AV_PIX_FMT_NONE)
199  {
200  fmt = FrameTypeToPixelFormat(frame->codec);
201  }
202 
203  av_image_fill_arrays(pic->data, pic->linesize, frame->buf,
204  fmt, frame->width, frame->height, IMAGE_ALIGN);
205  pic->data[1] = frame->buf + frame->offsets[1];
206  pic->data[2] = frame->buf + frame->offsets[2];
207  pic->linesize[0] = frame->pitches[0];
208  pic->linesize[1] = frame->pitches[1];
209  pic->linesize[2] = frame->pitches[2];
210  return static_cast<int>(GetBufferSize(frame->codec, frame->width, frame->height));
211 }
212 
214 {
215 public:
216  explicit MythAVCopyPrivate(bool uswc)
217  : m_copyctx(new MythUSWCCopy(4096, !uswc)) {}
218 
220  {
221  if (m_swsctx)
222  {
223  sws_freeContext(m_swsctx);
224  }
225  delete m_copyctx;
226  }
227 
228  MythAVCopyPrivate(const MythAVCopyPrivate &) = delete; // not copyable
229  MythAVCopyPrivate &operator=(const MythAVCopyPrivate &) = delete; // not copyable
230 
231  int SizeData(int _width, int _height, AVPixelFormat _fmt)
232  {
233  if (_width == m_width && _height == m_height && _fmt == m_format)
234  {
235  return m_size;
236  }
237  m_size = av_image_get_buffer_size(_fmt, _width, _height, IMAGE_ALIGN);
238  m_width = _width;
239  m_height = _height;
240  m_format = _fmt;
241  return m_size;
242  }
243 
244  SwsContext *m_swsctx {nullptr};
246  int m_width {0};
247  int m_height {0};
248  int m_size {0};
249  AVPixelFormat m_format {AV_PIX_FMT_NONE};
250 };
251 
253 {
254 }
255 
257 {
258  delete d;
259 }
260 
261 void MythAVCopy::FillFrame(VideoFrame *frame, const AVFrame *pic, int pitch,
262  int width, int height, AVPixelFormat pix_fmt)
263 {
264  int size = av_image_get_buffer_size(pix_fmt, width, height, IMAGE_ALIGN);
265 
266  if (pix_fmt == AV_PIX_FMT_YUV420P)
267  {
268  int chroma_pitch = pitch >> 1;
269  int chroma_height = height >> 1;
270  int offsets[3] =
271  { 0,
272  pitch * height,
273  pitch * height + chroma_pitch * chroma_height };
274  int pitches[3] = { pitch, chroma_pitch, chroma_pitch };
275 
276  init(frame, FMT_YV12, pic->data[0], width, height, size, pitches, offsets);
277  }
278  else if (pix_fmt == AV_PIX_FMT_NV12)
279  {
280  int offsets[3] = { 0, pitch * height, 0 };
281  int pitches[3] = { pitch, pitch, 0 };
282 
283  init(frame, FMT_NV12, pic->data[0], width, height, size, pitches, offsets);
284  }
285 }
286 
287 int MythAVCopy::Copy(AVFrame *dst, AVPixelFormat dst_pix_fmt,
288  const AVFrame *src, AVPixelFormat pix_fmt,
289  int width, int height)
290 {
291  if ((pix_fmt == AV_PIX_FMT_YUV420P || pix_fmt == AV_PIX_FMT_NV12) &&
292  (dst_pix_fmt == AV_PIX_FMT_YUV420P))
293  {
294  VideoFrame framein {};
295  VideoFrame frameout {};
296 
297  FillFrame(&framein, src, width, width, height, pix_fmt);
298  FillFrame(&frameout, dst, width, width, height, dst_pix_fmt);
299 
300  d->m_copyctx->copy(&frameout, &framein);
301  return frameout.size;
302  }
303 
304  int new_width = width;
305 #if ARCH_ARM
306  // The ARM build of FFMPEG has a bug that if sws_scale is
307  // called with source and dest sizes the same, and
308  // formats as shown below, it causes a bus error and the
309  // application core dumps. To avoid this I make a -1
310  // difference in the new width, causing it to bypass
311  // the code optimization which is failing.
312  if (pix_fmt == AV_PIX_FMT_YUV420P
313  && dst_pix_fmt == AV_PIX_FMT_BGRA)
314  new_width = width - 1;
315 #endif
316  d->m_swsctx = sws_getCachedContext(d->m_swsctx, width, height, pix_fmt,
317  new_width, height, dst_pix_fmt,
318  SWS_FAST_BILINEAR, nullptr, nullptr, nullptr);
319  if (d->m_swsctx == nullptr)
320  {
321  return -1;
322  }
323 
324  sws_scale(d->m_swsctx, src->data, src->linesize,
325  0, height, dst->data, dst->linesize);
326 
327  return d->SizeData(width, height, dst_pix_fmt);
328 }
329 
331 {
332  if ((src->codec == FMT_YV12 || src->codec == FMT_NV12) &&
333  (dst->codec == FMT_YV12))
334  {
335  d->m_copyctx->copy(dst, src);
336  return dst->size;
337  }
338 
339  AVFrame srcpic;
340  AVFrame dstpic;
341 
342  AVPictureFill(&srcpic, src);
343  AVPictureFill(&dstpic, dst);
344 
345  return Copy(&dstpic, FrameTypeToPixelFormat(dst->codec),
346  &srcpic, FrameTypeToPixelFormat(src->codec),
347  src->width, src->height);
348 }
349 
350 int MythAVCopy::Copy(AVFrame *pic, const VideoFrame *frame,
351  unsigned char *buffer, AVPixelFormat fmt)
352 {
354  unsigned char *sbuf = buffer ? buffer : CreateBuffer(type, frame->width, frame->height);
355 
356  if (!sbuf)
357  {
358  return 0;
359  }
360 
361  AVFrame pic_in;
362  AVPixelFormat fmt_in = FrameTypeToPixelFormat(frame->codec);
363 
364  AVPictureFill(&pic_in, frame, fmt_in);
365  av_image_fill_arrays(pic->data, pic->linesize, sbuf, fmt, frame->width, frame->height, IMAGE_ALIGN);
366  return Copy(pic, fmt, &pic_in, fmt_in, frame->width, frame->height);
367 }
368 
369 int MythAVCopy::Copy(VideoFrame *frame, const AVFrame *pic, AVPixelFormat fmt)
370 {
371  if (fmt == AV_PIX_FMT_NV12 || fmt == AV_PIX_FMT_YUV420P)
372  {
373  VideoFrame framein {};
374  FillFrame(&framein, pic, frame->width, frame->width, frame->height, fmt);
375  return Copy(frame, &framein);
376  }
377 
378  AVFrame frame_out;
379  AVPixelFormat fmt_out = FrameTypeToPixelFormat(frame->codec);
380 
381  AVPictureFill(&frame_out, frame, fmt_out);
382  return Copy(&frame_out, fmt_out, pic, fmt, frame->width, frame->height);
383 }
384 
386  int width, int height, float ar)
387  : m_pixfmt(pixfmt)
388  , m_width(width)
389  , m_height(height)
390  , m_ar(ar)
391 {
392  if (Flush() < 0)
393  {
394  m_errored = true;
395  }
396 }
397 
399 {
400  if (m_errored)
401  {
402  return -1;
403  }
404  if (src)
405  {
406  memcpy(m_filterFrame->data, src->data, sizeof(src->data));
407  memcpy(m_filterFrame->linesize, src->linesize, sizeof(src->linesize));
408  m_filterFrame->width = m_width;
409  m_filterFrame->height = m_height;
410  m_filterFrame->format = m_pixfmt;
411  }
412  int res = av_buffersrc_add_frame(m_bufferSrcCtx, m_filterFrame);
413  if (res < 0)
414  {
415  return res;
416  }
417  res = av_buffersink_get_frame(m_bufferSinkCtx, m_filterFrame);
418  if (res < 0)
419  {
420  return res;
421  }
422 
423  av_image_copy(dst->data, dst->linesize,
424  (const uint8_t **)((AVFrame*)m_filterFrame)->data,
425  (const int*)((AVFrame*)m_filterFrame)->linesize,
427 
428  av_frame_unref(m_filterFrame);
429 
430  return 0;
431 }
432 
434 {
435  if (m_errored)
436  {
437  return -1;
438  }
439  if (!m_filterGraph && Flush() < 0)
440  {
441  return -1;
442  }
443  int res = Deinterlace(dst, src);
444  if (res == AVERROR(EAGAIN))
445  {
446  res = Deinterlace(dst, nullptr);
447  // We have drained the filter, we need to recreate it on the next run.
448  avfilter_graph_free(&m_filterGraph);
449  }
450  return res;
451 }
452 
454 {
455  if (m_filterGraph)
456  {
457  avfilter_graph_free(&m_filterGraph);
458  }
459 
460  m_filterGraph = avfilter_graph_alloc();
461  if (!m_filterGraph)
462  {
463  return -1;
464  }
465 
466  AVFilterInOut *inputs = nullptr;
467  AVFilterInOut *outputs = nullptr;
468  AVRational ar = av_d2q(m_ar, 100000);
469  QString args = QString("buffer=video_size=%1x%2:pix_fmt=%3:time_base=1/1:pixel_aspect=%4/%5[in];"
470  "[in]yadif[out];[out] buffersink")
471  .arg(m_width).arg(m_height).arg(m_pixfmt).arg(ar.num).arg(ar.den);
472  int res = avfilter_graph_parse2(m_filterGraph, args.toLatin1().data(), &inputs, &outputs);
473  while (true)
474  {
475  if (res < 0 || inputs || outputs)
476  {
477  break;
478  }
479  res = avfilter_graph_config(m_filterGraph, nullptr);
480  if (res < 0)
481  {
482  break;
483  }
484  if (!(m_bufferSrcCtx = avfilter_graph_get_filter(m_filterGraph, "Parsed_buffer_0")))
485  {
486  break;
487  }
488  if (!(m_bufferSinkCtx = avfilter_graph_get_filter(m_filterGraph, "Parsed_buffersink_2")))
489  {
490  break;
491  }
492  return 0;
493  }
494  avfilter_inout_free(&inputs);
495  avfilter_inout_free(&outputs);
496  return -1;
497 }
498 
500 {
501  if (m_filterGraph)
502  {
503  avfilter_graph_free(&m_filterGraph);
504  }
505 }
506 
508 {
510 }
511 
512 AVCodecContext *MythCodecMap::getCodecContext(const AVStream *stream,
513  const AVCodec *pCodec, bool nullCodec)
514 {
515  QMutexLocker lock(&m_mapLock);
516  AVCodecContext *avctx = m_streamMap.value(stream, nullptr);
517  if (!avctx)
518  {
519  if (stream == nullptr || stream->codecpar == nullptr)
520  return nullptr;
521  if (nullCodec)
522  pCodec = nullptr;
523  else
524  {
525  if (!pCodec)
526  pCodec = avcodec_find_decoder(stream->codecpar->codec_id);
527  if (!pCodec)
528  {
529  LOG(VB_GENERAL, LOG_WARNING,
530  QString("avcodec_find_decoder fail for %1").arg(stream->codecpar->codec_id));
531  return nullptr;
532  }
533  }
534  avctx = avcodec_alloc_context3(pCodec);
535  if (avcodec_parameters_to_context(avctx, stream->codecpar) < 0)
536  avcodec_free_context(&avctx);
537  if (avctx)
538  {
539  avctx->pkt_timebase = stream->time_base;
540  m_streamMap.insert(stream, avctx);
541  }
542  }
543  return avctx;
544 }
545 
546 AVCodecContext *MythCodecMap::hasCodecContext(const AVStream *stream)
547 {
548  return m_streamMap.value(stream, nullptr);
549 }
550 
554 void MythCodecMap::freeCodecContext(const AVStream *stream)
555 {
556  QMutexLocker lock(&m_mapLock);
557  AVCodecContext *avctx = m_streamMap.take(stream);
558  if (avctx)
559  {
560  if (avctx->internal)
561  avcodec_flush_buffers(avctx);
562  avcodec_free_context(&avctx);
563  }
564 }
565 
567 {
568  QMutexLocker lock(&m_mapLock);
569  QMap<const AVStream*, AVCodecContext*>::iterator i = m_streamMap.begin();
570  while (i != m_streamMap.end()) {
571  const AVStream *stream = i.key();
572  ++i;
573  freeCodecContext(stream);
574  }
575 }
int pitches[3]
Y, U, & V pitches.
Definition: mythframe.h:160
MythAVFrame m_filterFrame
Definition: mythavutil.h:184
unsigned char * buf
Definition: mythframe.h:139
int Copy(VideoFrame *dst, const VideoFrame *src)
Definition: mythavutil.cpp:330
virtual ~MythAVCopy()
Definition: mythavutil.cpp:256
int SizeData(int _width, int _height, AVPixelFormat _fmt)
Definition: mythavutil.cpp:231
VideoFrameType codec
Definition: mythframe.h:138
endian dependent format, ARGB or BGRA
Definition: mythframe.h:36
struct AVFrame AVFrame
AVPixelFormat FrameTypeToPixelFormat(VideoFrameType type)
Convert VideoFrameType into FFmpeg's PixelFormat equivalent and vice-versa.
Definition: mythavutil.cpp:24
VideoFrameType PixelFormatToFrameType(AVPixelFormat fmt)
Definition: mythavutil.cpp:68
VideoFrameType
Definition: mythframe.h:23
static void FillFrame(VideoFrame *frame, const AVFrame *pic, int pitch, int width, int height, AVPixelFormat pix_fmt)
Definition: mythavutil.cpp:261
QMap< const AVStream *, AVCodecContext * > m_streamMap
Definition: mythavutil.h:96
void freeCodecContext(const AVStream *stream)
Definition: mythavutil.cpp:554
QMutex m_mapLock
Definition: mythavutil.h:97
MythDeintType
Definition: mythframe.h:120
QString DeinterlacerName(MythDeintType Deint, bool DoubleRate, VideoFrameType Format)
Return a user friendly description of the given deinterlacer.
Definition: mythavutil.cpp:114
MythAVCopyPrivate & operator=(const MythAVCopyPrivate &)=delete
AVFilterGraph * m_filterGraph
Definition: mythavutil.h:183
int AVPictureFill(AVFrame *pic, const VideoFrame *frame, AVPixelFormat fmt)
AVPictureFill Initialise AVFrame pic with content from VideoFrame frame.
Definition: mythavutil.cpp:196
AVFilterContext * m_bufferSrcCtx
Definition: mythavutil.h:186
void copy(VideoFrame *dst, const VideoFrame *src)
Definition: mythframe.cpp:629
MythAVCopyPrivate(bool uswc)
Definition: mythavutil.cpp:216
AVCodecContext * getCodecContext(const AVStream *stream, const AVCodec *pCodec=nullptr, bool nullCodec=false)
Definition: mythavutil.cpp:512
static const uint16_t * d
int DeinterlaceSingle(AVFrame *dst, const AVFrame *src)
Definition: mythavutil.cpp:433
MythAVCopyPrivate * d
Definition: mythavutil.h:140
QString DeinterlacerPref(MythDeintType Deint)
Definition: mythavutil.cpp:182
SwsContext * m_swsctx
Definition: mythavutil.cpp:244
static unsigned char * CreateBuffer(VideoFrameType Type, int Width, int Height)
Definition: mythframe.h:688
int Deinterlace(AVFrame *dst, const AVFrame *src)
Definition: mythavutil.cpp:398
static void init(VideoFrame *vf, VideoFrameType _codec, unsigned char *_buf, int _width, int _height, int _size, const int *p=nullptr, const int *o=nullptr, float _aspect=-1.0F, double _rate=-1.0F, int _aligned=MYTH_WIDTH_ALIGNMENT)
Definition: mythframe.h:231
AVCodecContext * hasCodecContext(const AVStream *stream)
Definition: mythavutil.cpp:546
AVFilterContext * m_bufferSinkCtx
Definition: mythavutil.h:185
MythPictureDeinterlacer(AVPixelFormat pixfmt, int width, int height, float ar=1.0F)
Definition: mythavutil.cpp:385
MythUSWCCopy * m_copyctx
Definition: mythavutil.cpp:245
#define LOG(_MASK_, _LEVEL_, _STRING_)
Definition: mythlogging.h:41
AVPixelFormat m_format
Definition: mythavutil.cpp:249
int offsets[3]
Y, U, & V offsets.
Definition: mythframe.h:161
AVPixelFormat m_pixfmt
Definition: mythavutil.h:187
int height
Definition: mythframe.h:142
void freeAllCodecContexts()
Definition: mythavutil.cpp:566
MythAVCopy(bool USWC=true)
Definition: mythavutil.cpp:252
static size_t GetBufferSize(VideoFrameType Type, int Width, int Height, int Aligned=MYTH_WIDTH_ALIGNMENT)
Definition: mythframe.h:657
MythDeintType GetDeinterlacer(MythDeintType Option)
Definition: mythframe.cpp:867