Skip to content

Commit

Permalink
Merge pull request #1649 from CastagnaIT/ck_dash_kid
Browse files Browse the repository at this point in the history
[DashTree] Improved clearkey defaultkid workaround
  • Loading branch information
CastagnaIT authored Aug 23, 2024
2 parents a1346a5 + 250130f commit 8ef1b81
Show file tree
Hide file tree
Showing 4 changed files with 58 additions and 14 deletions.
8 changes: 7 additions & 1 deletion src/Session.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -65,7 +65,7 @@ CSession::CSession(const std::string& manifestUrl) : m_manifestUrl(manifestUrl)
CSession::~CSession()
{
LOG::Log(LOGDEBUG, "CSession::~CSession()");
m_streams.clear();
DeleteStreams();
DisposeDecrypter();

if (m_adaptiveTree)
Expand All @@ -79,6 +79,12 @@ CSession::~CSession()
m_reprChooser = nullptr;
}

void SESSION::CSession::DeleteStreams()
{
LOG::Log(LOGDEBUG, "CSession::DeleteStreams()");
m_streams.clear();
}

void CSession::SetSupportedDecrypterURN(std::vector<std::string_view>& keySystems)
{
std::string decrypterPath = CSrvBroker::GetSettings().GetDecrypterPath();
Expand Down
2 changes: 2 additions & 0 deletions src/Session.h
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,8 @@ class ATTR_DLL_LOCAL CSession : public adaptive::AdaptiveStreamObserver
CSession(const std::string& manifestUrl);
virtual ~CSession();

void DeleteStreams();

/*! \brief Initialize the session
* \return True if has success, false otherwise
*/
Expand Down
21 changes: 21 additions & 0 deletions src/main.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -136,6 +136,27 @@ bool CInputStreamAdaptive::GetStream(int streamid, kodi::addon::InputstreamInfo&

if (stream)
{
// If the stream is encrypted, verify if the decrypter has been initialized
// this is important for HLS because the DRM it is initialized at later time
// so on the OpenStream, instead of CSession::Initialize->InitializePeriod->InitializeDRM
// Since kodi initialize one single stream at time, can happens that or another stream
// has been opened before this one, or another stream will be opened after this one (e.g. unencrypted)
// so if you dont delete all streams, the kodi demux reader still starts
// and a corrupted playback will starts.
// NOTE: GetStream is called by Kodi twice times, before and after OpenStream, on HLS
// the first time all streams are unencrypted because child manifest has not been downloaded
const uint16_t psshSetPos = stream->m_adStream.getRepresentation()->m_psshSetPos;
if (psshSetPos != PSSHSET_POS_DEFAULT ||
stream->m_adStream.getPeriod()->GetEncryptionState() == EncryptionState::NOT_SUPPORTED)
{
if (!m_session->GetSingleSampleDecryptor(psshSetPos))
{
LOG::Log(LOGERROR, "GetStream(%d): Decrypter for the stream not found");
m_session->DeleteStreams();
return false;
}
}

info = stream->m_info;
return true;
}
Expand Down
41 changes: 28 additions & 13 deletions src/parser/DASHTree.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1343,26 +1343,41 @@ bool adaptive::CDashTree::GetProtectionData(
//! @todo: this should not be a task of parser, moreover missing an appropriate KID extraction from mp4 box
auto& kodiProps = CSrvBroker::GetKodiProps();
ProtectionScheme ckProtScheme;
if (!protSelected && !protCommon && kodiProps.GetLicenseType() == DRM::KS_CLEARKEY)
if (kodiProps.GetLicenseType() == DRM::KS_CLEARKEY)
{
for (const ProtectionScheme& protScheme : reprProtSchemes)
std::string_view defaultKid;
if (protSelected)
defaultKid = protSelected->kid;
if (defaultKid.empty() && protCommon)
defaultKid = protCommon->kid;

if (defaultKid.empty())
{
if (!protScheme.kid.empty())
for (const ProtectionScheme& protScheme : reprProtSchemes)
{
ckProtScheme.kid = protScheme.kid;
break;
if (!protScheme.kid.empty())
{
defaultKid = protScheme.kid;
break;
}
}
}
if (ckProtScheme.kid.empty())
{
for (const ProtectionScheme& protScheme : adpProtSchemes)
if (defaultKid.empty())
{
ckProtScheme.kid = protScheme.kid;
break;
for (const ProtectionScheme& protScheme : adpProtSchemes)
{
if (!protScheme.kid.empty())
{
defaultKid = protScheme.kid;
break;
}
}
}
}
if (!ckProtScheme.kid.empty())
if (protCommon)
ckProtScheme = *protCommon;

ckProtScheme.kid = defaultKid;
protCommon = &ckProtScheme;
}
}

bool isEncrypted{false};
Expand Down

0 comments on commit 8ef1b81

Please sign in to comment.