vdr-plugin-softhddevice-drm-gles 1.6.2
softhddevice.h
Go to the documentation of this file.
1// SPDX-License-Identifier: AGPL-3.0-or-later
2
13#ifndef __SOFTHDDEVICE_H
14#define __SOFTHDDEVICE_H
15
16#if __cplusplus < 201703L
17#error "C++17 or higher is required"
18#endif
19
20#include <atomic>
21#include <mutex>
22
23extern "C"
24{
25#include <libavcodec/avcodec.h>
26}
27
28#include <vdr/device.h>
29#include <vdr/osd.h>
30#include <vdr/status.h>
31
32#include "config.h"
33#include "event.h"
34#include "jittertracker.h"
35#include "pes.h"
36
37class cAudioDecoder;
38class cDvbSpuDecoder;
39class cPipHandler;
40class cPipReceiver;
41class cSpuDecoder;
42class cSoftHdAudio;
43class cSoftHdGrab;
45class cVideoRender;
46class cVideoStream;
47
53// State machine definitions
54// Implementing C++17 visitor pattern
55
56template<class... Ts>
57struct overload : Ts... { using Ts::operator()...; };
58template<class... Ts> overload(Ts...) -> overload<Ts...>;
59
67
68inline const char* EventToString(const Event& e) {
69 return std::visit(overload{
70 [](const PlayEvent&) -> const char* { return "PlayEvent"; },
71 [](const PauseEvent&) -> const char* { return "PauseEvent"; },
72 [](const StopEvent&) -> const char* { return "StopEvent"; },
73 [](const TrickSpeedEvent&) -> const char* { return "TrickSpeedEvent"; },
74 [](const StillPictureEvent&) -> const char* { return "StillPictureEvent"; },
75 [](const DetachEvent&) -> const char* { return "DetachEvent"; },
76 [](const AttachEvent&) -> const char* { return "AttachEvent"; },
77 [](const BufferUnderrunEvent& e) -> const char* { return e.type == AUDIO ? "BufferUnderrunEvent: Audio" : "BufferUnderrunEvent: Video"; },
78 [](const BufferingThresholdReachedEvent&) -> const char* { return "BufferingThresholdReachedEvent"; },
79 [](const PipEvent&) -> const char* { return "PipEvent"; },
80 [](const ScheduleResyncAtPtsMsEvent&) -> const char* { return "ScheduleResyncAtPtsMsEvent"; },
81 [](const ResyncEvent&) -> const char* { return "ResyncEvent"; },
82 }, e);
83}
84
85inline const char* StateToString(State s) {
86 switch(s) {
87 case State::STOP: return "STOP";
88 case State::BUFFERING: return "BUFFERING";
89 case State::PLAY: return "PLAY";
90 case State::TRICK_SPEED: return "TRICK_SPEED";
91 case State::DETACHED: return "DETACHED";
92 }
93 return "Unknown";
94}
95
102
106class cSoftHdDevice : public cDevice, public IEventReceiver, public cStatus {
107public:
109 virtual ~cSoftHdDevice(void);
110
111 //
112 // virtual cDevice
113 //
114protected:
115 virtual void MakePrimaryDevice(bool);
116 virtual void ChannelSwitch(const cDevice *, int, bool);
117
118public:
119 virtual cString DeviceName(void) const { return "softhddevice-drm-gles"; }
120 virtual bool HasDecoder(void) const;
121
122 // SPU facilities
123 virtual cSpuDecoder * GetSpuDecoder(void);
124
125 // player facilities
126 virtual bool CanReplay(void) const;
127 virtual bool SetPlayMode(ePlayMode);
128 virtual int PlayVideo(const uchar *, int);
129 virtual int PlayAudio(const uchar *, int, uchar);
130 virtual int64_t GetSTC(void);
131 virtual cRect CanScaleVideo(const cRect &, int taCenter);
132 virtual void ScaleVideo(const cRect & = cRect::Null);
133 virtual void TrickSpeed(int, bool);
134 virtual void Clear(void);
135 virtual void Play(void);
136 virtual void Freeze(void);
137 virtual void StillPicture(const uchar *, int);
138 virtual bool Poll(cPoller &, int = 0);
139 virtual bool Flush(int = 0);
140
141 // Image Grab facilities
142 virtual uchar *GrabImage(int &, bool, int, int, int);
143
144 // video format facilities
146 virtual void SetVideoFormat(bool);
147 virtual void GetVideoSize(int &, int &, double &);
148 virtual void GetOsdSize(int &, int &, double &);
149
150 // track facilities
151 virtual void SetAudioTrackDevice(eTrackType);
152
153 // audio facilities
154 virtual int GetAudioChannelDevice(void);
155 virtual void SetAudioChannelDevice(int);
156 virtual void SetVolumeDevice(int);
157 virtual void SetDigitalAudioDevice(bool);
158
159 //
160 // wrapped by cPluginSoftHdDevice
161 //
162 const char *CommandLineHelp(void); // wrapped by cPluginSoftHdDevice::CommandLineHelp()
163 int ProcessArgs(int, char *[]); // wrapped by cPluginSoftHdDevice::ProcessArgs()
164 int Start(void);
165 void Stop(void);
166
167 //
168 // cSoftHdDevice public methods
169 //
170 cSoftHdConfig *Config(void) { return m_pConfig; };
172 cVideoRender *Render(void) { return m_pRender; };
173 cSoftHdAudio *Audio(void) { return m_pAudio; };
174
175 void SetDisableDeint(void);
176 void SetDecoderNeedsIFrame(void);
177 void SetParseH264Dimensions(void);
178 void SetDecoderFallbackToSw(bool);
179 void SetEnableHdr(bool);
180
181 // osd
182#ifdef USE_GLES
183 int MaxSizeGPUImageCache(void);
184 int OglOsdIsDisabled(void);
185 void SetDisableOglOsd(void);
186 void SetEnableOglOsd(void);
187#endif
188 void OsdClose(void);
189 void OsdDrawARGB(int, int, int, int, int, const uint8_t *, int, int);
190 void SetScreenSize(int, int, double);
191
192 // audio
195 void SetPassthroughMask(int);
196 void ResetChannelId(void);
197
198 // Logging, statistics
199 void GetStats(int *, int *, int *);
200 std::chrono::steady_clock::time_point GetChannelSwitchStartTime(void) { return m_channelSwitchStartTime; };
201 std::chrono::steady_clock::time_point GetChannelSwitchFirstPacketTime(void) { return m_dataReceivedTime; };
202
203 // Mediaplayer
206 int PlayAudioPkts(AVPacket *);
207 int PlayVideoPkts(AVPacket *);
208
209 // detach/ attach
210 void Detach(void);
211 void Attach(void);
212 bool IsDetached(void) const;
213 void ResetOsdProvider(void) { m_pOsdProvider = nullptr; }
214 bool IsOsdProviderSet(void) const { return m_pOsdProvider != nullptr; }
215
218
219 // pip wrapper functions
220 bool PipIsEnabled(void);
221 void PipEnable(void);
222 void PipDisable(void);
223 void PipToggle(void);
224 void PipChannelChange(int);
225 void PipChannelSwap(bool);
226 void PipSwapPosition(void);
227 void PipSetSize(void);
228 void SetRenderPipSize(void);
229 void SetRenderPipActive(bool);
230
231 // pip functions
232 int PlayPipVideo(const uchar *, int);
235 void ResetPipStream(void);
237
238private:
239 static constexpr int MIN_BUFFER_FILL_LEVEL_THRESHOLD_MS = 450;
240
241 std::atomic<State> m_state = DETACHED;
242 std::mutex m_eventMutex;
243 bool m_needsMakePrimary = false;
255 std::chrono::steady_clock::time_point m_channelSwitchStartTime;
256 std::chrono::steady_clock::time_point m_dataReceivedTime;
257
258 std::atomic<PlaybackMode> m_playbackMode = NONE;
261
265 mutable std::mutex m_mutex;
266 std::mutex m_sizeMutex;
267 std::atomic<bool> m_receivedAudio = false;
268 std::atomic<bool> m_receivedVideo = false;
270 bool m_drmCanDisplayPip = true;
271 bool m_disablePip = false;
272 int m_volume = 0;
273
277
278 bool m_forceDetached = false;
279
280 int PlayVideoInternal(cVideoStream *, cReassemblyBufferVideo *, const uchar *, int, bool);
281 void FlushAudio(void);
282 void OnEventReceived(const Event&);
283 void HandleStillPicture(const uchar *data, int size);
286
288
289 // State machine
290 void SetState(State);
292 void OnLeavingState(State);
293};
294
297#endif
Event Receiver.
Definition event.h:85
Audio Decoder.
Definition codec_audio.h:81
Jitter Tracker.
PiP Stream Handler.
Definition pipreceiver.h:51
Receiver for PiP Stream.
Definition pipreceiver.h:29
Audio Stream Reassembly Buffer.
Definition pes.h:166
Video Stream Reassembly Buffer.
Definition pes.h:137
Audio Interface.
Definition audio.h:46
Plugin Configuration.
Definition config.h:29
int ConfigVideoAudioDelayMs
config audio delay
Definition config.h:43
Output Device Implementation.
cReassemblyBufferVideo m_videoReassemblyBuffer
video pes reassembly buffer
bool m_pipUseAlt
use alternative pip position
cReassemblyBufferVideo m_pipReassemblyBuffer
pip pes reassembly buffer
cVideoStream * m_pPipStream
pointer to pip video stream
static constexpr int MIN_BUFFER_FILL_LEVEL_THRESHOLD_MS
min buffering threshold in ms
int m_volume
track the volume in the device (for attach)
cSoftOsdProvider * m_pOsdProvider
pointer to cSoftOsdProvider object
cVideoStream * m_pVideoStream
pointer to main video stream
cReassemblyBufferAudio m_audioReassemblyBuffer
audio pes reassembly buffer
std::atomic< bool > m_receivedAudio
flag if audio packets have been received
cDvbSpuDecoder * m_pSpuDecoder
pointer to spu decoder
bool IsOsdProviderSet(void) const
bool UsePip(void)
std::mutex m_mutex
mutex to lock the state machine
cPipHandler * m_pPipHandler
pointer to pip handler
int GetVideoAudioDelayMs(void)
double m_screenRefreshRateHz
std::chrono::steady_clock::time_point m_dataReceivedTime
timestamp, when the first audio or video data after a channel switch arrives in Play*()
std::atomic< State > m_state
current plugin state, normal plugin start sets detached state
cAudioDecoder * m_pAudioDecoder
pointer to cAudioDecoder object
void SetDrmCanDisplayPip(bool canDisplay)
cVideoRender * m_pRender
pointer to cVideoRender object
cSoftHdGrab * m_pGrab
pointer to grabber object
bool m_needsMakePrimary
cSoftHdAudio * m_pAudio
pointer to cSoftHdAudio object
std::chrono::steady_clock::time_point GetChannelSwitchFirstPacketTime(void)
cSoftHdConfig * m_pConfig
pointer to cSoftHdConfig object
void ResetOsdProvider(void)
bool m_disablePip
true, if pip was disabled by the user
cVideoRender * Render(void)
cVideoStream * VideoStream(void)
std::chrono::steady_clock::time_point m_channelSwitchStartTime
timestamp, when VDR triggered a channel switch
std::mutex m_sizeMutex
mutex to lock screen size (which is accessed by different threads)
std::chrono::steady_clock::time_point GetChannelSwitchStartTime(void)
std::atomic< bool > m_receivedVideo
flag if video packets have been received
cJitterTracker m_audioJitterTracker
audio jitter tracker
virtual cString DeviceName(void) const
std::mutex m_eventMutex
mutex to protect event queue
cSoftHdConfig * Config(void)
bool m_forceDetached
start the plugin in detached state
int GetMinBufferFillLevelThresholdMs(void)
int m_audioChannelID
current audio channel ID
cJitterTracker m_videoJitterTracker
video jitter tracker
bool m_drmCanDisplayPip
true, if the drm device is able to display a pip video
std::atomic< PlaybackMode > m_playbackMode
current playback mode
bool IsVideoOnlyPlayback(void)
cSoftHdAudio * Audio(void)
void ToggleRenderPipPosition(void)
Grabbing Processor.
Definition grab.h:79
Plugin OSD provider.
Video Renderer.
Video Input Stream.
Definition videostream.h:57
Plugin Configuration Header File.
State Machine and Event Header File.
std::variant< PlayEvent, PauseEvent, StopEvent, TrickSpeedEvent, StillPictureEvent, DetachEvent, AttachEvent, BufferUnderrunEvent, BufferingThresholdReachedEvent, PipEvent, ScheduleResyncAtPtsMsEvent, ResyncEvent > Event
Definition event.h:80
@ AUDIO
Definition event.h:27
void SetState(State)
Sets the device into the given state.
void OsdDrawARGB(int, int, int, int, int, const uint8_t *, int, int)
Draw an OSD pixmap.
void Stop(void)
Called by VDR when the plugin is stopped.
void PipChannelSwap(bool)
void FlushAudio(void)
Clear all audio data from the decoder and ringbuffer.
void PipSwapPosition(void)
virtual void StillPicture(const uchar *, int)
Display the given I-frame as a still picture.
void PipSetSize(void)
int MaxSizeGPUImageCache(void)
Get the maximum GPU image cache size.
void SetRenderPipSize(void)
Wrapper functions for cVideoRender and cPipHandler.
PlaybackMode
void OnEnteringState(State)
Actions to be performed when entering a state.
int Start(void)
Called by VDR when the plugin is started.
void SetEnableOglOsd(void)
Enables OpenGL/ES Osd.
virtual void GetVideoSize(int &, int &, double &)
Get the video size.
const char * EventToString(const Event &e)
int PlayAudioPkts(AVPacket *)
Play an audio packet.
virtual void GetOsdSize(int &, int &, double &)
Returns the width, height and aspect ratio the OSD.
void SetEnableHdr(bool)
Enable HDR display mode.
void SetRenderPipActive(bool)
void GetStats(int *, int *, int *)
Get statistics from the renderer.
void ResetChannelId(void)
Reset the channel ID (restarts audio)
virtual bool CanReplay(void) const
Return true if this device can currently start a replay session.
virtual void SetDigitalAudioDevice(bool)
virtual bool HasDecoder(void) const
Tells whether this device has an MPEG decoder.
virtual void Clear(void)
Clears all video and audio data from the device.
void OnEventReceived(const Event &)
Event handler for playback state transitions.
void Detach(void)
Detach the device.
State
virtual int PlayVideo(const uchar *, int)
Play a video packet of the main videostream.
void ResetPipStream(void)
Resets pip stream and render pipeline.
void OnLeavingState(State)
Actions to be performed when leaving a state.
virtual bool SetPlayMode(ePlayMode)
Sets the device into the given play mode.
void SetAudioCodec(enum AVCodecID, AVCodecParameters *, AVRational)
Open an audio codec.
virtual void Play(void)
Sets the device into play mode (after a previous trick mode, or pause)
bool IsBufferingThresholdReached(void)
Check if the buffering threshold has been reached.
virtual void SetAudioChannelDevice(int)
const char * CommandLineHelp(void)
Return command line help string.
int OglOsdIsDisabled(void)
Is the OpenGL/ES osd disabled?
int PlayPipVideo(const uchar *, int)
Play a video packet of the pip videostream.
virtual void ChannelSwitch(const cDevice *, int, bool)
Monitor a channel switch triggered by VDR (cStatus::ChannelSwitch())
virtual cRect CanScaleVideo(const cRect &, int taCenter)
Ask the output, if it can scale video.
virtual void SetVolumeDevice(int)
Sets the audio volume on this device (Volume = 0...255).
virtual int64_t GetSTC(void)
Gets the current System Time Counter, which can be used to synchronize audio, video and subtitles.
virtual bool Flush(int=0)
Flush the device output buffers.
bool IsDetached(void) const
Returns true, if the device is detached.
virtual void TrickSpeed(int, bool)
Sets the device into a mode where replay is done slower.
void SetDecoderFallbackToSw(bool)
Force the decoder to fallback to software if the hardware decoder fails after the configured amount o...
virtual int PlayAudio(const uchar *, int, uchar)
Play an audio packet.
void PipToggle(void)
bool PipIsEnabled(void)
Returns true, if pip is currently enabled.
void SetDecoderNeedsIFrame(void)
Forces the h264 decoder to wait for an I-Frame to start.
int PlayVideoInternal(cVideoStream *, cReassemblyBufferVideo *, const uchar *, int, bool)
Play a video packet.
virtual int GetAudioChannelDevice(void)
int PlayVideoPkts(AVPacket *)
Play a video packet.
void SetScreenSize(int, int, double)
Set the screen size.
const char * StateToString(State s)
int GetBufferFillLevelThresholdMs()
Returns the buffer fill level threshold in milliseconds.
void HandleStillPicture(const uchar *data, int size)
The still picture data received from VDR can contain multiple PES packets.
virtual void SetVideoDisplayFormat(eVideoDisplayFormat)
Sets the video display format.
virtual void Freeze(void)
Puts the device into "freeze frame" mode.
void SetParseH264Dimensions(void)
Parse the h264 stream width and height before starting the decoder.
void SetDisableOglOsd(void)
Disables OpenGL/ES Osd (called from setup menu or conf)
virtual ~cSoftHdDevice(void)
Destroy the device.
void PipDisable(void)
virtual void SetVideoFormat(bool)
Set the video format.
virtual void MakePrimaryDevice(bool)
Informs a device that it will be the primary device.
void SetVideoCodec(enum AVCodecID, AVCodecParameters *, AVRational)
Open a video codec.
void PipEnable(void)
void SetPassthroughMask(int)
Set the passthrough mask (called from setup menu or conf)
void SetDisableDeint(void)
Disables deinterlacer (called from setup menu or conf)
virtual uchar * GrabImage(int &, bool, int, int, int)
Grabs the currently visible screen image.
virtual cSpuDecoder * GetSpuDecoder(void)
Get the device SPU decoder.
virtual void SetAudioTrackDevice(eTrackType)
void OsdClose(void)
Close the OSD.
int64_t GetFirstAudioPtsMsToPlay()
Calculate the first audio PTS that should be played during synchronized playback.
virtual void ScaleVideo(const cRect &=cRect::Null)
Scale the currently shown video.
int64_t GetFirstVideoPtsMsToPlay()
int ProcessArgs(int, char *[])
Process the command line arguments.
void PipChannelChange(int)
virtual bool Poll(cPoller &, int=0)
Return true if the device itself or any of the file handles in poller is ready for further action.
void Attach(void)
Attach the device again.
@ AUDIO_AND_VIDEO
@ VIDEO_ONLY
@ AUDIO_ONLY
@ NONE
@ PLAY
@ STOP
@ BUFFERING
@ TRICK_SPEED
@ DETACHED
Jitter Tracking of Incoming Packets Header File.
PES Packet Parser Header File.