37#include <libavcodec/avcodec.h>
38#include <libavformat/avformat.h>
39#include <libavutil/timestamp.h>
73 fd = fopen(file,
"r");
75 LOGERROR(
"videostream: %s: Can't open %s", __FUNCTION__, file);
79 character = getline(&buf, &size, fd);
98 txt_buf = (
char *) calloc(bufsize,
sizeof(
char));
99 int hardwareQuirks = 0;
101 read_size =
ReadLineFromFile(txt_buf, bufsize,
"/sys/firmware/devicetree/base/compatible");
103 free((
void *)txt_buf);
111 char *_txt_buf = (
char *) calloc(bufsize,
sizeof(
char));
112 char *_read_ptr = _txt_buf;
113 for (
size_t i = 0; i < bufsize; i++) {
114 if (memcmp(read_ptr,
"\0",
sizeof(
char))) {
115 memcpy(_read_ptr, read_ptr,
sizeof(
char));
122 LOGDEBUG2(
L_DRM,
"videostream: %s: found \"%s\", set hardware quirks", __FUNCTION__, _txt_buf);
125 if (strstr(read_ptr,
"bcm2836")) {
126 LOGDEBUG2(
L_DRM,
"videostream: %s: bcm2836 (Raspberry Pi 2 Model B) found", __FUNCTION__);
130 if (strstr(read_ptr,
"bcm2837")) {
131 LOGDEBUG2(
L_DRM,
"videostream: %s: bcm2837 (Raspberry Pi 2 Model B v1.2/ 3 Model B, Raspberry Pi 3 Compute Module 3) found", __FUNCTION__);
135 if (strstr(read_ptr,
"bcm2711")) {
136 LOGDEBUG2(
L_DRM,
"videostream: %s: bcm2711 (Raspberry Pi 4 Model B, Compute Module 4, Pi 400) found", __FUNCTION__);
140 if (strstr(read_ptr,
"bcm2712")) {
141 LOGDEBUG2(
L_DRM,
"videostream: %s: bcm2712 (Raspberry Pi 5, Compute Module 5, Pi 500) found", __FUNCTION__);
145 if (strstr(read_ptr,
"amlogic")) {
146 LOGDEBUG2(
L_DRM,
"videostream: %s: amlogic found, disable HW deinterlacer", __FUNCTION__);
153 read_size -= (strlen(read_ptr) + 1);
154 read_ptr = (
char *)&read_ptr[(strlen(read_ptr) + 1)];
156 free((
void *)_txt_buf);
157 free((
void *)txt_buf);
159 return hardwareQuirks;
171 LOGDEBUG(
"videostream %s: %s", __FUNCTION__, identifier);
195 LOGDEBUG(
"videostream %s:", __FUNCTION__);
262 av_packet_free(&avpkt);
305 LOGFATAL(
"videostream %s: %s: Could not reopen the decoder (flush)!",
m_identifier, __FUNCTION__);
316 AVFrame *frame =
nullptr;
352 if (ret != AVERROR(EAGAIN)) {
354 av_packet_free(&avpkt);
358 bool flushDecoder =
false;
374 if (ret == AVERROR_EOF || flushDecoder) {
392 *width = videoCtx->coded_width;
393 *height = videoCtx->coded_height;
394 *aspect_ratio = *width / (double)*height;
411 m_trickpkts = codecId == AV_CODEC_ID_MPEG2VIDEO ? 1 : 2;
455 if (frame->decode_error_flags || frame->flags & AV_FRAME_FLAG_CORRUPT)
477 bool useDeinterlacer =
484 LOGDEBUG(
"videostream: %s: %s: deinterlacer disabled by user configuration",
m_identifier, __FUNCTION__);
490 if (frame->format == AV_PIX_FMT_YUV420P || (frame->format == AV_PIX_FMT_DRM_PRIME && useDeinterlacer))
Audio and alsa module header file.
Some helper functions header file.
void InitAndStart(const AVCodecContext *, AVFrame *, bool)
Init and start the video filter thread.
int GetNumFramesToFilter(void)
void PushFrame(AVFrame *)
Put a frame in the buffer to be filtered.
bool IsInputBufferFull(void)
cH264Parser - H264 Parser class
void GetDimensions(int *, int *)
Get width and height from stream.
T * Pop(void)
Pop an element from the back of the queue.
bool IsEmpty(void)
Check if the queue is empty.
bool IsFull(void)
Check if the queue is full.
bool Push(T *element)
Push an element to the front of the queue.
size_t Size(void)
Get the current size of the queue.
T * Peek(void)
Get a reference to the back element.
bool ConfigDisableDeint
disable deinterlacer
cVideoDecoder - VideoDecoder class
int ReopenCodec(enum AVCodecID, AVCodecParameters *, AVRational, int)
Reopen the video decoder.
AVCodecContext * GetContext(void)
int SendPacket(const AVPacket *)
Send a video packet to be decoded.
void FlushBuffers(void)
Flush the video decoder.
int ReceiveFrame(AVFrame **)
Receive a decoded a video frame.
void Close(void)
Close video decoder.
int Open(enum AVCodecID, AVCodecParameters *, AVRational, int, int, int)
Open the video decoder.
cVideoRender - Video render class
int GetTrickForward(void)
Get the current trickspeed direction.
int GetTrickSpeed(void)
Get the current trickspeed.
cDecodingThread * m_pDecodingThread
pointer to decoding thread
bool m_interlaced
flag for interlaced stream
void GetVideoSize(int *, int *, double *)
Get video size and aspect ratio.
cFilterThread * m_pFilterThread
pointer to deinterlace filter thread
std::function< void(AVFrame *)> m_frameOutput
function to output the frame
const char * m_identifier
identifier string for logging
int64_t m_inputPts
PTS of the first packet in the input buffer.
bool m_deinterlacerDeactivated
set, if the deinterlacer shall be deactivated temporarily (used for trick speed and still picture)
int m_sentTrickPkts
how many avpkt have been sent to the decoder in trickspeed mode?
std::string m_decodingThreadName
decoding thread name string (persists for object lifetime)
void Flush(void)
Flushes the video stream by finalizing any pending data.
void StartDecoder()
Start the decoder.
void ClearVdrCoreToDecoderQueue(void)
Clears all video stream data, which is buffered to be decoded.
bool m_userDisabledDeinterlacer
set, if the user configured the deinterlace to be disabled
volatile bool m_newStream
flag for new stream
enum AVCodecID m_codecId
current codec id
bool m_checkFilterThreadNeeded
set, if we have to check, if filter thread is needed at start of playback
AVCodecParameters * m_pPar
current codec parameters
void DecodeInput(void)
Decodes a reassembled codec packet.
cQueue< cDrmBuffer > * m_pDrmBufferQueue
pointer to renderer's DRM buffer queue
cVideoStream(cVideoRender *, cQueue< cDrmBuffer > *, cSoftHdConfig *, const char *, std::function< void(AVFrame *)>)
cVideoStream constructor
void CloseDecoder(void)
Close the decoder.
int m_hardwareQuirks
hardware specific quirks
cVideoDecoder * m_pDecoder
video decoder
void Exit(void)
Exit video stream.
virtual ~cVideoStream(void)
cVideoStream destructor
void CancelFilterThread(void)
Stop filter thread.
cVideoRender * m_pRender
video renderer
int m_trickpkts
how many avpkt does the decoder need in trickspeed mode?
void RenderFrame(AVFrame *)
Render a frame.
cQueue< AVPacket > m_packets
AVPackets queue.
void ExitDecodingThread(void)
Stop decoding thread.
void FlushDecoder(void)
Flush the decoder.
void Open(AVCodecID, AVCodecParameters *=nullptr, AVRational={ .num=1,.den=90000 })
Open a video codec.
bool PushAvPacket(AVPacket *avpkt)
Pushes a pre-assembled AVPacket directly to the processing queue.
int64_t GetInputPtsMs(void)
std::string m_filterThreadName
filter thread name string (persists for object lifetime)
std::atomic< struct AVRational > m_timebase
current codec timebase
Audio decoder header file.
Video decoder header file.
Atomic wrapper macros function header file.
Logger class header file.
#define LOGFATAL
Logger macros.
Misc function header file.
static bool isInterlacedFrame(AVFrame *frame)
Check, if this is an interlaced frame.
Thread-safe queue header file.
Main plugin class header file.
Device class header file.
Rendering class header file.
#define QUIRK_CODEC_FLUSH_WORKAROUND
set, if we have to close and reopen the codec instead of avcodec_flush_buffers (rpi)
#define QUIRK_CODEC_NEEDS_EXT_INIT
set, if codec needs some infos for init (coded_width and coded_height)
#define QUIRK_NO_HW_DEINT
set, if no hw deinterlacer available
#define QUIRK_CODEC_SKIP_FIRST_FRAMES
set, if codec should skip first I-Frames
static size_t ReadLineFromFile(char *buf, size_t size, const char *file)
Helper function to read a line from a given file.
static int ReadHWPlatform(void)
Helper function to find out which platform we are on.
Videostream class header file.