Fixed a channel switching logic bug (Thanks to REELcoder).

This commit is contained in:
Rolf Ahrenberg 2020-01-03 23:02:52 +02:00
parent a3fa5865f3
commit 826dea4ba8
3 changed files with 26 additions and 6 deletions

View File

@ -211,3 +211,5 @@ VDR Plugin 'satip' Revision History
2019-XX-XX: Version 2.4.1 2019-XX-XX: Version 2.4.1
- Added an option to enable/disable frontend reuse. - Added an option to enable/disable frontend reuse.
- Added a preliminary ATSC support.
- Fixed a channel switching logic bug (Thanks to REELcoder).

24
tuner.c
View File

@ -25,6 +25,8 @@ cSatipTuner::cSatipTuner(cSatipDeviceIf &deviceP, unsigned int packetLenP)
rtcpM(*this), rtcpM(*this),
streamAddrM(""), streamAddrM(""),
streamParamM(""), streamParamM(""),
lastAddrM(""),
lastParamM(""),
tnrParamM(""), tnrParamM(""),
streamPortM(SATIP_DEFAULT_RTSP_PORT), streamPortM(SATIP_DEFAULT_RTSP_PORT),
currentServerM(NULL, deviceP.GetId(), 0), currentServerM(NULL, deviceP.GetId(), 0),
@ -34,6 +36,7 @@ cSatipTuner::cSatipTuner(cSatipDeviceIf &deviceP, unsigned int packetLenP)
keepAliveM(), keepAliveM(),
statusUpdateM(), statusUpdateM(),
pidUpdateCacheM(), pidUpdateCacheM(),
setupTimeoutM(-1),
sessionM(""), sessionM(""),
currentStateM(tsIdle), currentStateM(tsIdle),
internalStateM(), internalStateM(),
@ -192,8 +195,6 @@ bool cSatipTuner::Open(void)
cMutexLock MutexLock(&mutexM); cMutexLock MutexLock(&mutexM);
debug1("%s [device %d]", __PRETTY_FUNCTION__, deviceIdM); debug1("%s [device %d]", __PRETTY_FUNCTION__, deviceIdM);
RequestState(tsSet, smExternal);
// return always true // return always true
return true; return true;
} }
@ -203,7 +204,8 @@ bool cSatipTuner::Close(void)
cMutexLock MutexLock(&mutexM); cMutexLock MutexLock(&mutexM);
debug1("%s [device %d]", __PRETTY_FUNCTION__, deviceIdM); debug1("%s [device %d]", __PRETTY_FUNCTION__, deviceIdM);
RequestState(tsRelease, smExternal); if (setupTimeoutM.TimedOut())
RequestState(tsRelease, smExternal);
// return always true // return always true
return true; return true;
@ -219,10 +221,15 @@ bool cSatipTuner::Connect(void)
tnrParamM = ""; tnrParamM = "";
// Just retune // Just retune
if (streamIdM >= 0) { if (streamIdM >= 0) {
if (!strcmp(*streamParamM, *lastParamM)) {
debug1("%s Identical parameters [device %d]", __PRETTY_FUNCTION__, deviceIdM);
return true;
}
cString uri = cString::sprintf("%sstream=%d?%s", *connectionUri, streamIdM, *streamParamM); cString uri = cString::sprintf("%sstream=%d?%s", *connectionUri, streamIdM, *streamParamM);
debug1("%s Retuning [device %d]", __PRETTY_FUNCTION__, deviceIdM); debug1("%s Retuning [device %d]", __PRETTY_FUNCTION__, deviceIdM);
if (rtspM.Play(*uri)) { if (rtspM.Play(*uri)) {
keepAliveM.Set(timeoutM); keepAliveM.Set(timeoutM);
lastParamM = streamParamM;
return true; return true;
} }
} }
@ -240,6 +247,7 @@ bool cSatipTuner::Connect(void)
currentServerM = nextServerM; currentServerM = nextServerM;
nextServerM.Reset(); nextServerM.Reset();
} }
lastAddrM = connectionUri;
currentServerM.Attach(); currentServerM.Attach();
return true; return true;
} }
@ -257,8 +265,8 @@ bool cSatipTuner::Disconnect(void)
cMutexLock MutexLock(&mutexM); cMutexLock MutexLock(&mutexM);
debug1("%s [device %d]", __PRETTY_FUNCTION__, deviceIdM); debug1("%s [device %d]", __PRETTY_FUNCTION__, deviceIdM);
if (!isempty(*streamAddrM) && (streamIdM >= 0)) { if (!isempty(*lastAddrM) && (streamIdM >= 0)) {
cString uri = cString::sprintf("%sstream=%d", *GetBaseUrl(*streamAddrM, streamPortM), streamIdM); cString uri = cString::sprintf("%sstream=%d", *lastAddrM, streamIdM);
rtspM.Teardown(*uri); rtspM.Teardown(*uri);
// some devices requires a teardown for TCP connection also // some devices requires a teardown for TCP connection also
rtspM.Reset(); rtspM.Reset();
@ -447,7 +455,13 @@ bool cSatipTuner::SetSource(cSatipServer *serverP, const int transponderP, const
if (nextServerM.IsQuirk(cSatipServer::eSatipQuirkForcePilot) && strstr(parameterP, "msys=dvbs2") && !strstr(parameterP, "plts=")) if (nextServerM.IsQuirk(cSatipServer::eSatipQuirkForcePilot) && strstr(parameterP, "msys=dvbs2") && !strstr(parameterP, "plts="))
streamParamM = rtspM.RtspUnescapeString(*cString::sprintf("%s&plts=on", parameterP)); streamParamM = rtspM.RtspUnescapeString(*cString::sprintf("%s&plts=on", parameterP));
// Reconnect // Reconnect
if (!isempty(*lastAddrM)) {
cString connectionUri = GetBaseUrl(*streamAddrM, streamPortM);
if (strcmp(*connectionUri, *lastAddrM))
RequestState(tsRelease, smInternal);
}
RequestState(tsSet, smExternal); RequestState(tsSet, smExternal);
setupTimeoutM.Set(eSetupTimeoutMs);
} }
} }
else { else {

View File

@ -88,7 +88,8 @@ private:
eConnectTimeoutMs = 5000, // in milliseconds eConnectTimeoutMs = 5000, // in milliseconds
eIdleCheckTimeoutMs = 15000, // in milliseconds eIdleCheckTimeoutMs = 15000, // in milliseconds
eTuningTimeoutMs = 20000, // in milliseconds eTuningTimeoutMs = 20000, // in milliseconds
eMinKeepAliveIntervalMs = 30000 // in milliseconds eMinKeepAliveIntervalMs = 30000, // in milliseconds
eSetupTimeoutMs = 2000 // in milliseconds
}; };
enum eTunerState { tsIdle, tsRelease, tsSet, tsTuned, tsLocked }; enum eTunerState { tsIdle, tsRelease, tsSet, tsTuned, tsLocked };
enum eStateMode { smInternal, smExternal }; enum eStateMode { smInternal, smExternal };
@ -101,6 +102,8 @@ private:
cSatipRtcp rtcpM; cSatipRtcp rtcpM;
cString streamAddrM; cString streamAddrM;
cString streamParamM; cString streamParamM;
cString lastAddrM;
cString lastParamM;
cString tnrParamM; cString tnrParamM;
int streamPortM; int streamPortM;
cSatipTunerServer currentServerM; cSatipTunerServer currentServerM;
@ -110,6 +113,7 @@ private:
cTimeMs keepAliveM; cTimeMs keepAliveM;
cTimeMs statusUpdateM; cTimeMs statusUpdateM;
cTimeMs pidUpdateCacheM; cTimeMs pidUpdateCacheM;
cTimeMs setupTimeoutM;
cString sessionM; cString sessionM;
eTunerState currentStateM; eTunerState currentStateM;
cVector<eTunerState> internalStateM; cVector<eTunerState> internalStateM;