aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--xbmc/Application.cpp1
-rw-r--r--xbmc/epg/Epg.cpp21
-rw-r--r--xbmc/epg/EpgContainer.cpp44
-rw-r--r--xbmc/epg/EpgInfoTag.cpp39
-rw-r--r--xbmc/epg/EpgInfoTag.h6
-rw-r--r--xbmc/interfaces/json-rpc/PVROperations.cpp36
-rw-r--r--xbmc/interfaces/json-rpc/PlayerOperations.cpp8
-rw-r--r--xbmc/pvr/PVRManager.cpp43
-rw-r--r--xbmc/pvr/PVRManager.h28
-rw-r--r--xbmc/pvr/addons/PVRClients.cpp3
-rw-r--r--xbmc/pvr/channels/PVRChannelGroup.cpp19
-rw-r--r--xbmc/pvr/channels/PVRChannelGroupInternal.cpp3
-rw-r--r--xbmc/pvr/channels/PVRChannelGroups.cpp6
-rw-r--r--xbmc/pvr/recordings/PVRRecordings.cpp2
-rw-r--r--xbmc/pvr/timers/PVRTimerInfoTag.cpp4
-rw-r--r--xbmc/pvr/timers/PVRTimers.cpp43
-rw-r--r--xbmc/pvr/windows/GUIWindowPVRBase.cpp35
-rw-r--r--xbmc/pvr/windows/GUIWindowPVRGuide.cpp5
-rw-r--r--xbmc/utils/AlarmClock.cpp2
19 files changed, 216 insertions, 132 deletions
diff --git a/xbmc/Application.cpp b/xbmc/Application.cpp
index f2a8d41406..1570714ece 100644
--- a/xbmc/Application.cpp
+++ b/xbmc/Application.cpp
@@ -1337,6 +1337,7 @@ void CApplication::StopPVRManager()
StopPlaying();
// stop pvr manager thread and clear all pvr data
g_PVRManager.Stop();
+ g_PVRManager.Clear();
// stop epg container thread and clear all epg data
g_EpgContainer.Stop();
g_EpgContainer.Clear();
diff --git a/xbmc/epg/Epg.cpp b/xbmc/epg/Epg.cpp
index 8e7ad7cd41..2cd2921c69 100644
--- a/xbmc/epg/Epg.cpp
+++ b/xbmc/epg/Epg.cpp
@@ -292,20 +292,25 @@ std::vector<CEpgInfoTagPtr> CEpg::GetTagsBetween(const CDateTime &beginTime, con
void CEpg::AddEntry(const CEpgInfoTag &tag)
{
CEpgInfoTagPtr newTag;
- CSingleLock lock(m_critSection);
- std::map<CDateTime, CEpgInfoTagPtr>::iterator itr = m_tags.find(tag.StartAsUTC());
- if (itr != m_tags.end())
- newTag = itr->second;
- else
+ CPVRChannelPtr channel;
{
- newTag.reset(new CEpgInfoTag(this, m_pvrChannel, m_strName, m_pvrChannel ? m_pvrChannel->IconPath() : ""));
- m_tags.insert(make_pair(tag.StartAsUTC(), newTag));
+ CSingleLock lock(m_critSection);
+ std::map<CDateTime, CEpgInfoTagPtr>::iterator itr = m_tags.find(tag.StartAsUTC());
+ if (itr != m_tags.end())
+ newTag = itr->second;
+ else
+ {
+ newTag.reset(new CEpgInfoTag(this, m_pvrChannel, m_strName, m_pvrChannel ? m_pvrChannel->IconPath() : ""));
+ m_tags.insert(make_pair(tag.StartAsUTC(), newTag));
+ }
+
+ channel = m_pvrChannel;
}
if (newTag)
{
newTag->Update(tag);
- newTag->SetPVRChannel(m_pvrChannel);
+ newTag->SetPVRChannel(channel);
newTag->SetEpg(this);
newTag->SetTimer(g_PVRTimers->GetTimerForEpgTag(newTag));
newTag->SetRecording(g_PVRRecordings->GetRecordingForEpgTag(newTag));
diff --git a/xbmc/epg/EpgContainer.cpp b/xbmc/epg/EpgContainer.cpp
index 5e6a047783..85820b1a9b 100644
--- a/xbmc/epg/EpgContainer.cpp
+++ b/xbmc/epg/EpgContainer.cpp
@@ -179,18 +179,24 @@ void CEpgContainer::Start(bool bAsync)
LoadFromDB();
- CSingleLock lock(m_critSection);
- if (!m_bStop)
+ bool bStop = false;
{
- CheckPlayingEvents();
+ CSingleLock lock(m_critSection);
+ bStop = m_bStop;
+ if (!m_bStop)
+ {
+ CheckPlayingEvents();
- Create();
- SetPriority(-1);
+ Create();
+ SetPriority(-1);
- m_bStarted = true;
+ m_bStarted = true;
+ }
+ }
+ if (!bStop)
+ {
g_PVRManager.TriggerEpgsCreate();
-
CLog::Log(LOGNOTICE, "%s - EPG thread started", __FUNCTION__);
}
}
@@ -772,25 +778,37 @@ int CEpgContainer::GetEPGSearch(CFileItemList &results, const EpgSearchFilter &f
bool CEpgContainer::CheckPlayingEvents(void)
{
bool bReturn(false);
- time_t iNow;
bool bFoundChanges(false);
{
- CSingleLock lock(m_critSection);
+ time_t iNextEpgActiveTagCheck;
+ {
+ CSingleLock lock(m_critSection);
+ iNextEpgActiveTagCheck = m_iNextEpgActiveTagCheck;
+ }
+
+ time_t iNow;
CDateTime::GetCurrentDateTime().GetAsUTCDateTime().GetAsTime(iNow);
- if (iNow >= m_iNextEpgActiveTagCheck)
+ if (iNow >= iNextEpgActiveTagCheck)
{
for (const auto &epgEntry : m_epgs)
bFoundChanges = epgEntry.second->CheckPlayingEvent() || bFoundChanges;
- CDateTime::GetCurrentDateTime().GetAsUTCDateTime().GetAsTime(m_iNextEpgActiveTagCheck);
- m_iNextEpgActiveTagCheck += g_advancedSettings.m_iEpgActiveTagCheckInterval;
+
+ CDateTime::GetCurrentDateTime().GetAsUTCDateTime().GetAsTime(iNextEpgActiveTagCheck);
+ iNextEpgActiveTagCheck += g_advancedSettings.m_iEpgActiveTagCheckInterval;
/* pvr tags always start on the full minute */
if (g_PVRManager.IsStarted())
- m_iNextEpgActiveTagCheck -= m_iNextEpgActiveTagCheck % 60;
+ iNextEpgActiveTagCheck -= iNextEpgActiveTagCheck % 60;
bReturn = true;
}
+
+ if (bReturn)
+ {
+ CSingleLock lock(m_critSection);
+ m_iNextEpgActiveTagCheck = iNextEpgActiveTagCheck;
+ }
}
if (bFoundChanges)
diff --git a/xbmc/epg/EpgInfoTag.cpp b/xbmc/epg/EpgInfoTag.cpp
index d69b469eca..44c97e9939 100644
--- a/xbmc/epg/EpgInfoTag.cpp
+++ b/xbmc/epg/EpgInfoTag.cpp
@@ -340,18 +340,22 @@ int CEpgInfoTag::GetDuration(void) const
return end - start > 0 ? end - start : 3600;
}
-std::string CEpgInfoTag::Title(bool bOverrideParental /* = false */) const
+bool CEpgInfoTag::IsParentalLocked() const
{
- std::string strTitle;
- bool bParentalLocked(false);
-
+ CPVRChannelPtr channel;
{
CSingleLock lock(m_critSection);
- if (m_pvrChannel)
- bParentalLocked = g_PVRManager.IsParentalLocked(m_pvrChannel);
+ channel = m_pvrChannel;
}
- if (!bOverrideParental && bParentalLocked)
+ return channel && g_PVRManager.IsParentalLocked(channel);
+}
+
+std::string CEpgInfoTag::Title(bool bOverrideParental /* = false */) const
+{
+ std::string strTitle;
+
+ if (!bOverrideParental && IsParentalLocked())
strTitle = g_localizeStrings.Get(19266); // parental locked
else if (m_strTitle.empty() && !CSettings::GetInstance().GetBool(CSettings::SETTING_EPG_HIDENOINFOAVAILABLE))
strTitle = g_localizeStrings.Get(19055); // no information available
@@ -365,11 +369,8 @@ std::string CEpgInfoTag::PlotOutline(bool bOverrideParental /* = false */) const
{
std::string retVal;
- {
- CSingleLock lock(m_critSection);
- if (bOverrideParental || !m_pvrChannel || !g_PVRManager.IsParentalLocked(m_pvrChannel))
- retVal = m_strPlotOutline;
- }
+ if (bOverrideParental || !IsParentalLocked())
+ retVal = m_strPlotOutline;
return retVal;
}
@@ -378,11 +379,8 @@ std::string CEpgInfoTag::Plot(bool bOverrideParental /* = false */) const
{
std::string retVal;
- {
- CSingleLock lock(m_critSection);
- if (bOverrideParental || !m_pvrChannel || !g_PVRManager.IsParentalLocked(m_pvrChannel))
- retVal = m_strPlot;
- }
+ if (bOverrideParental || !IsParentalLocked())
+ retVal = m_strPlot;
return retVal;
}
@@ -391,11 +389,8 @@ std::string CEpgInfoTag::OriginalTitle(bool bOverrideParental /* = false */) con
{
std::string retVal;
- {
- CSingleLock lock(m_critSection);
- if (bOverrideParental || !m_pvrChannel || !g_PVRManager.IsParentalLocked(m_pvrChannel))
- retVal = m_strOriginalTitle;
- }
+ if (bOverrideParental || !IsParentalLocked())
+ retVal = m_strOriginalTitle;
return retVal;
}
diff --git a/xbmc/epg/EpgInfoTag.h b/xbmc/epg/EpgInfoTag.h
index cabc86c7de..945d6e8d37 100644
--- a/xbmc/epg/EpgInfoTag.h
+++ b/xbmc/epg/EpgInfoTag.h
@@ -170,6 +170,12 @@ namespace EPG
int GetDuration(void) const;
/*!
+ * @brief Check whether this event is parental locked.
+ * @return True if whether this event is parental locked, false otherwise.
+ */
+ bool IsParentalLocked() const;
+
+ /*!
* @brief Get the title of this event.
* @param bOverrideParental True to override parental control, false check it.
* @return The title.
diff --git a/xbmc/interfaces/json-rpc/PVROperations.cpp b/xbmc/interfaces/json-rpc/PVROperations.cpp
index 941f71d750..0ebca7547f 100644
--- a/xbmc/interfaces/json-rpc/PVROperations.cpp
+++ b/xbmc/interfaces/json-rpc/PVROperations.cpp
@@ -62,8 +62,8 @@ JSONRPC_STATUS CPVROperations::GetChannelGroups(const std::string &method, ITran
if (!g_PVRManager.IsStarted())
return FailedToExecute;
- CPVRChannelGroupsContainer *channelGroupContainer = g_PVRChannelGroups;
- if (channelGroupContainer == NULL)
+ CPVRChannelGroupsContainerPtr channelGroupContainer = g_PVRChannelGroups;
+ if (!channelGroupContainer)
return FailedToExecute;
CPVRChannelGroups *channelGroups = channelGroupContainer->Get(parameterObject["channeltype"].asString().compare("radio") == 0);
@@ -85,8 +85,8 @@ JSONRPC_STATUS CPVROperations::GetChannelGroupDetails(const std::string &method,
if (!g_PVRManager.IsStarted())
return FailedToExecute;
- CPVRChannelGroupsContainer *channelGroupContainer = g_PVRChannelGroups;
- if (channelGroupContainer == NULL)
+ CPVRChannelGroupsContainerPtr channelGroupContainer = g_PVRChannelGroups;
+ if (!channelGroupContainer)
return FailedToExecute;
CPVRChannelGroupPtr channelGroup;
@@ -109,8 +109,8 @@ JSONRPC_STATUS CPVROperations::GetChannels(const std::string &method, ITransport
if (!g_PVRManager.IsStarted())
return FailedToExecute;
- CPVRChannelGroupsContainer *channelGroupContainer = g_PVRChannelGroups;
- if (channelGroupContainer == NULL)
+ CPVRChannelGroupsContainerPtr channelGroupContainer = g_PVRChannelGroups;
+ if (!channelGroupContainer)
return FailedToExecute;
CPVRChannelGroupPtr channelGroup;
@@ -137,8 +137,8 @@ JSONRPC_STATUS CPVROperations::GetChannelDetails(const std::string &method, ITra
if (!g_PVRManager.IsStarted())
return FailedToExecute;
- CPVRChannelGroupsContainer *channelGroupContainer = g_PVRChannelGroups;
- if (channelGroupContainer == NULL)
+ CPVRChannelGroupsContainerPtr channelGroupContainer = g_PVRChannelGroups;
+ if (!channelGroupContainer)
return FailedToExecute;
CPVRChannelPtr channel = channelGroupContainer->GetChannelById((int)parameterObject["channelid"].asInteger());
@@ -155,8 +155,8 @@ JSONRPC_STATUS CPVROperations::GetBroadcasts(const std::string &method, ITranspo
if (!g_PVRManager.IsStarted())
return FailedToExecute;
- CPVRChannelGroupsContainer *channelGroupContainer = g_PVRManager.ChannelGroups();
- if (channelGroupContainer == NULL)
+ CPVRChannelGroupsContainerPtr channelGroupContainer = g_PVRManager.ChannelGroups();
+ if (!channelGroupContainer)
return FailedToExecute;
CPVRChannelPtr channel = channelGroupContainer->GetChannelById((int)parameterObject["channelid"].asInteger());
@@ -214,8 +214,8 @@ JSONRPC_STATUS CPVROperations::Record(const std::string &method, ITransportLayer
}
else if (channel.isInteger())
{
- CPVRChannelGroupsContainer *channelGroupContainer = g_PVRManager.ChannelGroups();
- if (channelGroupContainer == NULL)
+ CPVRChannelGroupsContainerPtr channelGroupContainer = g_PVRManager.ChannelGroups();
+ if (!channelGroupContainer)
return FailedToExecute;
pChannel = channelGroupContainer->GetChannelById((int)channel.asInteger());
@@ -307,7 +307,7 @@ JSONRPC_STATUS CPVROperations::GetTimers(const std::string &method, ITransportLa
if (!g_PVRManager.IsStarted())
return FailedToExecute;
- CPVRTimers* timers = g_PVRTimers;
+ CPVRTimersPtr timers = g_PVRTimers;
if (!timers)
return FailedToExecute;
@@ -324,7 +324,7 @@ JSONRPC_STATUS CPVROperations::GetTimerDetails(const std::string &method, ITrans
if (!g_PVRManager.IsStarted())
return FailedToExecute;
- CPVRTimers* timers = g_PVRTimers;
+ CPVRTimersPtr timers = g_PVRTimers;
if (!timers)
return FailedToExecute;
@@ -387,7 +387,9 @@ JSONRPC_STATUS CPVROperations::DeleteTimer(const std::string &method, ITransport
if (!g_PVRManager.IsStarted())
return FailedToExecute;
- CPVRTimers* timers = g_PVRTimers;
+ CPVRTimersPtr timers = g_PVRTimers;
+ if (!timers)
+ return FailedToExecute;
CPVRTimerInfoTagPtr timer = timers->GetById(parameterObject["timerid"].asInteger());
if (!timer)
@@ -444,7 +446,7 @@ JSONRPC_STATUS CPVROperations::GetRecordings(const std::string &method, ITranspo
if (!g_PVRManager.IsStarted())
return FailedToExecute;
- CPVRRecordings* recordings = g_PVRRecordings;
+ CPVRRecordingsPtr recordings = g_PVRRecordings;
if (!recordings)
return FailedToExecute;
@@ -461,7 +463,7 @@ JSONRPC_STATUS CPVROperations::GetRecordingDetails(const std::string &method, IT
if (!g_PVRManager.IsStarted())
return FailedToExecute;
- CPVRRecordings* recordings = g_PVRRecordings;
+ CPVRRecordingsPtr recordings = g_PVRRecordings;
if (!recordings)
return FailedToExecute;
diff --git a/xbmc/interfaces/json-rpc/PlayerOperations.cpp b/xbmc/interfaces/json-rpc/PlayerOperations.cpp
index 4827bbb598..e192b54d0b 100644
--- a/xbmc/interfaces/json-rpc/PlayerOperations.cpp
+++ b/xbmc/interfaces/json-rpc/PlayerOperations.cpp
@@ -571,8 +571,8 @@ JSONRPC_STATUS CPlayerOperations::Open(const std::string &method, ITransportLaye
if (!g_PVRManager.IsStarted())
return FailedToExecute;
- CPVRChannelGroupsContainer *channelGroupContainer = g_PVRChannelGroups;
- if (channelGroupContainer == NULL)
+ CPVRChannelGroupsContainerPtr channelGroupContainer = g_PVRChannelGroups;
+ if (!channelGroupContainer)
return FailedToExecute;
CPVRChannelPtr channel = channelGroupContainer->GetChannelById((int)parameterObject["item"]["channelid"].asInteger());
@@ -596,8 +596,8 @@ JSONRPC_STATUS CPlayerOperations::Open(const std::string &method, ITransportLaye
if (!g_PVRManager.IsStarted())
return FailedToExecute;
- CPVRRecordings *recordingsContainer = g_PVRRecordings;
- if (recordingsContainer == NULL)
+ CPVRRecordingsPtr recordingsContainer = g_PVRRecordings;
+ if (!recordingsContainer)
return FailedToExecute;
CFileItemPtr fileItem = recordingsContainer->GetById((int)parameterObject["item"]["recordingid"].asInteger());
diff --git a/xbmc/pvr/PVRManager.cpp b/xbmc/pvr/PVRManager.cpp
index 4013b2c787..b0fffccba1 100644
--- a/xbmc/pvr/PVRManager.cpp
+++ b/xbmc/pvr/PVRManager.cpp
@@ -77,6 +77,7 @@ using KODI::MESSAGING::HELPERS::DialogResponse;
CPVRManager::CPVRManager(void) :
CThread("PVRManager"),
+ m_addons(new CPVRClients),
m_triggerEvent(true),
m_currentFile(NULL),
m_database(NULL),
@@ -88,15 +89,12 @@ CPVRManager::CPVRManager(void) :
m_isChannelPreview(false)
{
CAnnouncementManager::GetInstance().AddAnnouncer(this);
- m_addons.reset(new CPVRClients);
}
CPVRManager::~CPVRManager(void)
{
CSettings::GetInstance().UnregisterCallback(this);
CAnnouncementManager::GetInstance().RemoveAnnouncer(this);
- Stop();
- m_addons.reset();
CLog::Log(LOGDEBUG,"PVRManager - destroyed");
}
@@ -138,6 +136,30 @@ CPVRManager &CPVRManager::GetInstance()
return CServiceBroker::GetPVRManager();
}
+CPVRChannelGroupsContainerPtr CPVRManager::ChannelGroups(void) const
+{
+ CSingleLock lock(m_critSection);
+ return m_channelGroups;
+}
+
+CPVRRecordingsPtr CPVRManager::Recordings(void) const
+{
+ CSingleLock lock(m_critSection);
+ return m_recordings;
+}
+
+CPVRTimersPtr CPVRManager::Timers(void) const
+{
+ CSingleLock lock(m_critSection);
+ return m_timers;
+}
+
+CPVRClientsPtr CPVRManager::Clients(void) const
+{
+ // note: m_addons is const (only set/reset in ctor/dtor). no need for a lock here.
+ return m_addons;
+}
+
void CPVRManager::OnSettingChanged(const CSetting *setting)
{
if (setting == NULL)
@@ -221,7 +243,7 @@ void CPVRManager::OnSettingAction(const CSetting *setting)
}
}
-void CPVRManager::Cleanup(void)
+void CPVRManager::Clear(void)
{
CSingleLock lock(m_critSection);
@@ -248,14 +270,12 @@ void CPVRManager::Cleanup(void)
}
HideProgressDialog();
-
- SetState(ManagerStateStopped);
}
void CPVRManager::ResetProperties(void)
{
CSingleLock lock(m_critSection);
- Cleanup();
+ Clear();
m_channelGroups.reset(new CPVRChannelGroupsContainer);
m_recordings.reset(new CPVRRecordings);
@@ -341,8 +361,7 @@ void CPVRManager::Stop(void)
if (m_database->IsOpen())
m_database->Close();
- /* unload all data */
- Cleanup();
+ SetState(ManagerStateStopped);
}
CPVRManager::ManagerState CPVRManager::GetState(void) const
@@ -724,7 +743,7 @@ void CPVRManager::ResetDatabase(bool bResetEPGOnly /* = false */)
CLog::Log(LOGNOTICE,"PVRManager - %s - restarting the PVRManager", __FUNCTION__);
m_database->Open();
- Cleanup();
+
Start();
pDlgProgress->SetPercentage(100);
@@ -1893,8 +1912,10 @@ bool CPVRManager::CreateChannelEpgs(void)
if (EpgsCreated())
return true;
+ bool bEpgsCreated = m_channelGroups->CreateChannelEpgs();
+
CSingleLock lock(m_critSection);
- m_bEpgsCreated = m_channelGroups->CreateChannelEpgs();
+ m_bEpgsCreated = bEpgsCreated;
return m_bEpgsCreated;
}
diff --git a/xbmc/pvr/PVRManager.h b/xbmc/pvr/PVRManager.h
index 56561e094e..9a3863cb04 100644
--- a/xbmc/pvr/PVRManager.h
+++ b/xbmc/pvr/PVRManager.h
@@ -51,12 +51,16 @@ namespace PVR
{
class CPVRClient;
class CPVRClients;
+ typedef std::shared_ptr<CPVRClients> CPVRClientsPtr;
class CPVRChannel;
typedef std::shared_ptr<CPVRChannel> CPVRChannelPtr;
class CPVRChannelGroupsContainer;
+ typedef std::shared_ptr<CPVRChannelGroupsContainer> CPVRChannelGroupsContainerPtr;
class CPVRChannelGroup;
class CPVRRecordings;
+ typedef std::shared_ptr<CPVRRecordings> CPVRRecordingsPtr;
class CPVRTimers;
+ typedef std::shared_ptr<CPVRTimers> CPVRTimersPtr;
class CPVRTimerInfoTag;
typedef std::shared_ptr<CPVRTimerInfoTag> CPVRTimerInfoTagPtr;
class CPVRGUIInfo;
@@ -130,25 +134,25 @@ private:
* @brief Get the channel groups container.
* @return The groups container.
*/
- CPVRChannelGroupsContainer *ChannelGroups(void) const { return m_channelGroups.get(); }
+ CPVRChannelGroupsContainerPtr ChannelGroups(void) const;
/*!
* @brief Get the recordings container.
* @return The recordings container.
*/
- CPVRRecordings *Recordings(void) const { return m_recordings.get(); }
+ CPVRRecordingsPtr Recordings(void) const;
/*!
* @brief Get the timers container.
* @return The timers container.
*/
- CPVRTimers *Timers(void) const { return m_timers.get(); }
+ CPVRTimersPtr Timers(void) const;
/*!
* @brief Get the timers container.
* @return The timers container.
*/
- CPVRClients *Clients(void) const { return m_addons.get(); }
+ CPVRClientsPtr Clients(void) const;
/*!
* @brief Init PVRManager.
@@ -161,14 +165,14 @@ private:
void Reinit(void);
/*!
- * @brief Stop the PVRManager and destroy all objects it created.
+ * @brief Stop the PVRManager.
*/
void Stop(void);
/*!
- * @brief Delete PVRManager's objects.
+ * @brief Destroy PVRManager's objects.
*/
- void Cleanup(void);
+ void Clear(void);
/*!
* @brief Get the TV database.
@@ -661,11 +665,11 @@ private:
/** @name containers */
//@{
- std::unique_ptr<CPVRChannelGroupsContainer> m_channelGroups; /*!< pointer to the channel groups container */
- std::unique_ptr<CPVRRecordings> m_recordings; /*!< pointer to the recordings container */
- std::unique_ptr<CPVRTimers> m_timers; /*!< pointer to the timers container */
- std::unique_ptr<CPVRClients> m_addons; /*!< pointer to the pvr addon container */
- std::unique_ptr<CPVRGUIInfo> m_guiInfo; /*!< pointer to the guiinfo data */
+ CPVRChannelGroupsContainerPtr m_channelGroups; /*!< pointer to the channel groups container */
+ CPVRRecordingsPtr m_recordings; /*!< pointer to the recordings container */
+ CPVRTimersPtr m_timers; /*!< pointer to the timers container */
+ const CPVRClientsPtr m_addons; /*!< pointer to the pvr addon container */
+ std::unique_ptr<CPVRGUIInfo> m_guiInfo; /*!< pointer to the guiinfo data */
//@}
CCriticalSection m_critSectionTriggers; /*!< critical section for triggered updates */
diff --git a/xbmc/pvr/addons/PVRClients.cpp b/xbmc/pvr/addons/PVRClients.cpp
index 7e89c3f062..a524f1097c 100644
--- a/xbmc/pvr/addons/PVRClients.cpp
+++ b/xbmc/pvr/addons/PVRClients.cpp
@@ -198,6 +198,9 @@ bool CPVRClients::HasEnabledClients(void) const
bool CPVRClients::StopClient(AddonPtr client, bool bRestart)
{
+ /* stop playback */
+ CApplicationMessenger::GetInstance().SendMsg(TMSG_MEDIA_STOP);
+
CSingleLock lock(m_critSection);
int iId = GetClientId(client);
PVR_CLIENT mappedClient;
diff --git a/xbmc/pvr/channels/PVRChannelGroup.cpp b/xbmc/pvr/channels/PVRChannelGroup.cpp
index c1201fba8f..1c96b53a8e 100644
--- a/xbmc/pvr/channels/PVRChannelGroup.cpp
+++ b/xbmc/pvr/channels/PVRChannelGroup.cpp
@@ -555,10 +555,11 @@ PVR_CHANNEL_GROUP_SORTED_MEMBERS CPVRChannelGroup::GetMembers(void) const
int CPVRChannelGroup::GetMembers(CFileItemList &results, bool bGroupMembers /* = true */) const
{
+ const CPVRChannelGroup* channels = bGroupMembers ? this : g_PVRChannelGroups->GetGroupAll(m_bRadio).get();
int iOrigSize = results.Size();
- CSingleLock lock(m_critSection);
- const CPVRChannelGroup* channels = bGroupMembers ? this : g_PVRChannelGroups->GetGroupAll(m_bRadio).get();
+ CSingleLock lock(channels->m_critSection);
+
for (PVR_CHANNEL_GROUP_SORTED_MEMBERS::const_iterator it = channels->m_sortedMembers.begin(); it != channels->m_sortedMembers.end(); ++it)
{
if (bGroupMembers || !IsGroupMember((*it).channel))
@@ -606,16 +607,17 @@ bool CPVRChannelGroup::AddAndUpdateChannels(const CPVRChannelGroup &channels, bo
{
bool bReturn(false);
bool bPreventSortAndRenumber(PreventSortAndRenumber());
- CSingleLock lock(m_critSection);
+ const CPVRChannelGroupPtr groupAll(g_PVRChannelGroups->GetGroupAll(m_bRadio));
SetPreventSortAndRenumber();
/* go through the channel list and check for new channels.
channels will only by updated in CPVRChannelGroupInternal to prevent dupe updates */
+ CSingleLock lock(channels.m_critSection);
for (PVR_CHANNEL_GROUP_MEMBERS::const_iterator it = channels.m_members.begin(); it != channels.m_members.end(); ++it)
{
/* check whether this channel is known in the internal group */
- const PVRChannelGroupMember& existingChannel(g_PVRChannelGroups->GetGroupAll(m_bRadio)->GetByUniqueID(it->first));
+ const PVRChannelGroupMember& existingChannel(groupAll->GetByUniqueID(it->first));
if (!existingChannel.channel)
continue;
@@ -640,11 +642,14 @@ bool CPVRChannelGroup::AddAndUpdateChannels(const CPVRChannelGroup &channels, bo
bool CPVRChannelGroup::RemoveDeletedChannels(const CPVRChannelGroup &channels)
{
bool bReturn(false);
+ CPVRChannelGroups *groups = g_PVRChannelGroups->Get(m_bRadio);
+
CSingleLock lock(m_critSection);
/* check for deleted channels */
for (PVR_CHANNEL_GROUP_SORTED_MEMBERS::iterator it = m_sortedMembers.begin(); it != m_sortedMembers.end();)
{
+ CSingleLock lock(channels.m_critSection);
if (channels.m_members.find((*it).channel->StorageId()) == channels.m_members.end())
{
/* channel was not found */
@@ -659,7 +664,7 @@ bool CPVRChannelGroup::RemoveDeletedChannels(const CPVRChannelGroup &channels)
/* remove this channel from all non-system groups if this is the internal group */
if (IsInternalGroup())
{
- g_PVRChannelGroups->Get(m_bRadio)->RemoveFromAllGroups((*it).channel);
+ groups->RemoveFromAllGroups((*it).channel);
/* since it was not found in the internal group, it was deleted from the backend */
group.channel->Delete();
@@ -761,6 +766,8 @@ bool CPVRChannelGroup::RemoveFromGroup(const CPVRChannelPtr &channel)
bool CPVRChannelGroup::AddToGroup(const CPVRChannelPtr &channel, int iChannelNumber /* = 0 */)
{
+ const CPVRChannelGroupPtr groupAll(g_PVRChannelGroups->GetGroupAll(m_bRadio));
+
CSingleLock lock(m_critSection);
bool bReturn(false);
@@ -772,7 +779,7 @@ bool CPVRChannelGroup::AddToGroup(const CPVRChannelPtr &channel, int iChannelNum
const PVRChannelGroupMember& realChannel(IsInternalGroup() ?
GetByUniqueID(channel->StorageId()) :
- g_PVRChannelGroups->GetGroupAll(m_bRadio)->GetByUniqueID(channel->StorageId()));
+ groupAll->GetByUniqueID(channel->StorageId()));
if (realChannel.channel)
{
diff --git a/xbmc/pvr/channels/PVRChannelGroupInternal.cpp b/xbmc/pvr/channels/PVRChannelGroupInternal.cpp
index eb00a59bb7..a7baacfdf5 100644
--- a/xbmc/pvr/channels/PVRChannelGroupInternal.cpp
+++ b/xbmc/pvr/channels/PVRChannelGroupInternal.cpp
@@ -160,7 +160,6 @@ bool CPVRChannelGroupInternal::AddToGroup(const CPVRChannelPtr &channel, int iCh
bool CPVRChannelGroupInternal::RemoveFromGroup(const CPVRChannelPtr &channel)
{
- CSingleLock lock(m_critSection);
assert(channel.get());
if (!IsGroupMember(channel))
@@ -174,6 +173,8 @@ bool CPVRChannelGroupInternal::RemoveFromGroup(const CPVRChannelPtr &channel)
return false;
}
+ CSingleLock lock(m_critSection);
+
/* switch the hidden flag */
if (!channel->IsHidden())
{
diff --git a/xbmc/pvr/channels/PVRChannelGroups.cpp b/xbmc/pvr/channels/PVRChannelGroups.cpp
index 06e23a2c55..4cd9e1ccf6 100644
--- a/xbmc/pvr/channels/PVRChannelGroups.cpp
+++ b/xbmc/pvr/channels/PVRChannelGroups.cpp
@@ -518,6 +518,7 @@ bool CPVRChannelGroups::DeleteGroup(const CPVRChannelGroup &group)
}
bool bFound(false);
+ CPVRChannelGroupPtr playingGroup;
// delete the group in this container
{
@@ -529,7 +530,7 @@ bool CPVRChannelGroups::DeleteGroup(const CPVRChannelGroup &group)
// update the selected group in the gui if it's deleted
CPVRChannelGroupPtr selectedGroup = GetSelectedGroup();
if (selectedGroup && *selectedGroup == group)
- g_PVRManager.SetPlayingGroup(GetGroupAll());
+ playingGroup = GetGroupAll();
it = m_groups.erase(it);
bFound = true;
@@ -541,6 +542,9 @@ bool CPVRChannelGroups::DeleteGroup(const CPVRChannelGroup &group)
}
}
+ if (playingGroup)
+ g_PVRManager.SetPlayingGroup(playingGroup);
+
if (group.GroupID() > 0)
{
// delete the group from the database
diff --git a/xbmc/pvr/recordings/PVRRecordings.cpp b/xbmc/pvr/recordings/PVRRecordings.cpp
index 7e840da89c..9cab2e8990 100644
--- a/xbmc/pvr/recordings/PVRRecordings.cpp
+++ b/xbmc/pvr/recordings/PVRRecordings.cpp
@@ -164,9 +164,9 @@ void CPVRRecordings::Update(void)
lock.Enter();
m_bIsUpdating = false;
- g_PVRManager.SetChanged();
lock.Leave();
+ g_PVRManager.SetChanged();
g_PVRManager.NotifyObservers(ObservableMessageRecordings);
g_PVRManager.PublishEvent(RecordingsInvalidated);
}
diff --git a/xbmc/pvr/timers/PVRTimerInfoTag.cpp b/xbmc/pvr/timers/PVRTimerInfoTag.cpp
index 70715900e7..096c0ea1fa 100644
--- a/xbmc/pvr/timers/PVRTimerInfoTag.cpp
+++ b/xbmc/pvr/timers/PVRTimerInfoTag.cpp
@@ -1015,8 +1015,10 @@ CPVRChannelPtr CPVRTimerInfoTag::ChannelTag(void) const
CPVRChannelPtr CPVRTimerInfoTag::UpdateChannel(void)
{
+ const CPVRChannelPtr channel(g_PVRChannelGroups->Get(m_bIsRadio)->GetGroupAll()->GetByUniqueID(m_iClientChannelUid, m_iClientId));
+
CSingleLock lock(m_critSection);
- m_channel = g_PVRChannelGroups->Get(m_bIsRadio)->GetGroupAll()->GetByUniqueID(m_iClientChannelUid, m_iClientId);
+ m_channel = channel;
return m_channel;
}
diff --git a/xbmc/pvr/timers/PVRTimers.cpp b/xbmc/pvr/timers/PVRTimers.cpp
index e486128cdf..dba374b316 100644
--- a/xbmc/pvr/timers/PVRTimers.cpp
+++ b/xbmc/pvr/timers/PVRTimers.cpp
@@ -166,7 +166,7 @@ bool CPVRTimers::UpdateEntries(const CPVRTimers &timers, const std::vector<int>
bChanged = true;
existingTimer->ResetChildState();
- if (bStateChanged && g_PVRManager.IsStarted())
+ if (bStateChanged)
{
std::string strMessage;
existingTimer->GetNotificationText(strMessage);
@@ -202,12 +202,9 @@ bool CPVRTimers::UpdateEntries(const CPVRTimers &timers, const std::vector<int>
bChanged = true;
bAddedOrDeleted = true;
- if (g_PVRManager.IsStarted())
- {
- std::string strMessage;
- newTimer->GetNotificationText(strMessage);
- timerNotifications.push_back(std::make_pair(newTimer->m_iClientId, strMessage));
- }
+ std::string strMessage;
+ newTimer->GetNotificationText(strMessage);
+ timerNotifications.push_back(std::make_pair(newTimer->m_iClientId, strMessage));
CLog::Log(LOGDEBUG,"PVRTimers - %s - added timer %d on client %d",
__FUNCTION__, (*timerIt)->m_iClientIndex, (*timerIt)->m_iClientId);
@@ -246,8 +243,7 @@ bool CPVRTimers::UpdateEntries(const CPVRTimers &timers, const std::vector<int>
CLog::Log(LOGDEBUG,"PVRTimers - %s - deleted timer %d on client %d",
__FUNCTION__, timer->m_iClientIndex, timer->m_iClientId);
- if (g_PVRManager.IsStarted())
- timerNotifications.push_back(std::make_pair(timer->m_iClientId, timer->GetDeletedNotificationText()));
+ timerNotifications.push_back(std::make_pair(timer->m_iClientId, timer->GetDeletedNotificationText()));
ClearEpgTagTimer(timer);
@@ -323,24 +319,27 @@ bool CPVRTimers::UpdateEntries(const CPVRTimers &timers, const std::vector<int>
if (bChanged)
{
UpdateChannels();
- g_PVRManager.SetChanged();
lock.Leave();
+ g_PVRManager.SetChanged();
g_PVRManager.NotifyObservers(bAddedOrDeleted ? ObservableMessageTimersReset : ObservableMessageTimers);
- /* queue notifications / fill eventlog */
- for (const auto &entry : timerNotifications)
+ if (g_PVRManager.IsStarted())
{
- if (CSettings::GetInstance().GetBool(CSettings::SETTING_PVRRECORD_TIMERNOTIFICATIONS))
- CGUIDialogKaiToast::QueueNotification(CGUIDialogKaiToast::Info, g_localizeStrings.Get(19166), entry.second);
+ /* queue notifications / fill eventlog */
+ for (const auto &entry : timerNotifications)
+ {
+ if (CSettings::GetInstance().GetBool(CSettings::SETTING_PVRRECORD_TIMERNOTIFICATIONS))
+ CGUIDialogKaiToast::QueueNotification(CGUIDialogKaiToast::Info, g_localizeStrings.Get(19166), entry.second);
- std::string strName;
- g_PVRClients->GetClientAddonName(entry.first, strName);
+ std::string strName;
+ g_PVRClients->GetClientAddonName(entry.first, strName);
- std::string strIcon;
- g_PVRClients->GetClientAddonIcon(entry.first, strIcon);
+ std::string strIcon;
+ g_PVRClients->GetClientAddonIcon(entry.first, strIcon);
- CEventLog::GetInstance().Add(EventPtr(new CNotificationEvent(strName, entry.second, strIcon, EventLevel::Information)));
+ CEventLog::GetInstance().Add(EventPtr(new CNotificationEvent(strName, entry.second, strIcon, EventLevel::Information)));
+ }
}
}
@@ -642,6 +641,7 @@ bool CPVRTimers::GetDirectory(const std::string& strPath, CFileItemList &items)
bool CPVRTimers::DeleteTimersOnChannel(const CPVRChannelPtr &channel, bool bDeleteTimerRules /* = true */, bool bCurrentlyActiveOnly /* = false */)
{
bool bReturn = false;
+ bool bChanged = false;
{
CSingleLock lock(m_critSection);
@@ -657,12 +657,15 @@ bool CPVRTimers::DeleteTimersOnChannel(const CPVRChannelPtr &channel, bool bDele
{
CLog::Log(LOGDEBUG,"PVRTimers - %s - deleted timer %d on client %d", __FUNCTION__, (*timerIt)->m_iClientIndex, (*timerIt)->m_iClientId);
bReturn = (*timerIt)->DeleteFromClient(true) || bReturn;
- g_PVRManager.SetChanged();
+ bChanged = true;
}
}
}
}
+ if (bChanged)
+ g_PVRManager.SetChanged();
+
g_PVRManager.NotifyObservers(ObservableMessageTimersReset);
return bReturn;
diff --git a/xbmc/pvr/windows/GUIWindowPVRBase.cpp b/xbmc/pvr/windows/GUIWindowPVRBase.cpp
index 71e9d6230c..a0943c1188 100644
--- a/xbmc/pvr/windows/GUIWindowPVRBase.cpp
+++ b/xbmc/pvr/windows/GUIWindowPVRBase.cpp
@@ -104,17 +104,20 @@ void CGUIWindowPVRBase::UpdateSelectedItemPath()
void CGUIWindowPVRBase::RegisterObservers(void)
{
- CSingleLock lock(m_critSection);
g_PVRManager.RegisterObserver(this);
+
+ CSingleLock lock(m_critSection);
if (m_channelGroup)
m_channelGroup->RegisterObserver(this);
};
void CGUIWindowPVRBase::UnregisterObservers(void)
{
- CSingleLock lock(m_critSection);
- if (m_channelGroup)
- m_channelGroup->UnregisterObserver(this);
+ {
+ CSingleLock lock(m_critSection);
+ if (m_channelGroup)
+ m_channelGroup->UnregisterObserver(this);
+ }
g_PVRManager.UnregisterObserver(this);
};
@@ -428,18 +431,26 @@ CPVRChannelGroupPtr CGUIWindowPVRBase::GetChannelGroup(void)
void CGUIWindowPVRBase::SetChannelGroup(const CPVRChannelGroupPtr &group)
{
- CSingleLock lock(m_critSection);
if (!group)
return;
- if (m_channelGroup != group)
+ CPVRChannelGroupPtr channelGroup;
{
- if (m_channelGroup)
- m_channelGroup->UnregisterObserver(this);
- m_channelGroup = group;
- // we need to register the window to receive changes from the new group
- m_channelGroup->RegisterObserver(this);
- g_PVRManager.SetPlayingGroup(m_channelGroup);
+ CSingleLock lock(m_critSection);
+ if (m_channelGroup != group)
+ {
+ if (m_channelGroup)
+ m_channelGroup->UnregisterObserver(this);
+ m_channelGroup = group;
+ // we need to register the window to receive changes from the new group
+ m_channelGroup->RegisterObserver(this);
+ channelGroup = m_channelGroup;
+ }
+ }
+
+ if (channelGroup)
+ {
+ g_PVRManager.SetPlayingGroup(channelGroup);
Update(GetDirectoryPath());
}
}
diff --git a/xbmc/pvr/windows/GUIWindowPVRGuide.cpp b/xbmc/pvr/windows/GUIWindowPVRGuide.cpp
index 44bb4120b4..93e875c94f 100644
--- a/xbmc/pvr/windows/GUIWindowPVRGuide.cpp
+++ b/xbmc/pvr/windows/GUIWindowPVRGuide.cpp
@@ -42,7 +42,6 @@ using namespace EPG;
CGUIWindowPVRGuide::CGUIWindowPVRGuide(bool bRadio) :
CGUIWindowPVRBase(bRadio, bRadio ? WINDOW_RADIO_GUIDE : WINDOW_TV_GUIDE, "MyPVRGuide.xml"),
- m_refreshTimelineItemsThread(new CPVRRefreshTimelineItemsThread(this)),
m_cachedChannelGroup(new CPVRChannelGroup)
{
m_bRefreshTimelineItems = false;
@@ -106,12 +105,14 @@ void CGUIWindowPVRGuide::OnDeinitWindow(int nextWindowID)
void CGUIWindowPVRGuide::StartRefreshTimelineItemsThread()
{
StopRefreshTimelineItemsThread();
+ m_refreshTimelineItemsThread.reset(new CPVRRefreshTimelineItemsThread(this));
m_refreshTimelineItemsThread->Create();
}
void CGUIWindowPVRGuide::StopRefreshTimelineItemsThread()
{
- m_refreshTimelineItemsThread->StopThread(false);
+ if (m_refreshTimelineItemsThread)
+ m_refreshTimelineItemsThread->StopThread(false);
}
void CGUIWindowPVRGuide::Notify(const Observable &obs, const ObservableMessage msg)
diff --git a/xbmc/utils/AlarmClock.cpp b/xbmc/utils/AlarmClock.cpp
index 065673604a..2e941724ad 100644
--- a/xbmc/utils/AlarmClock.cpp
+++ b/xbmc/utils/AlarmClock.cpp
@@ -125,7 +125,7 @@ void CAlarmClock::Stop(const std::string& strName, bool bSilent /* false */)
}
else
{
- CApplicationMessenger::GetInstance().SendMsg(TMSG_EXECUTE_BUILT_IN, -1, -1, nullptr, iter->second.m_strCommand);
+ CApplicationMessenger::GetInstance().PostMsg(TMSG_EXECUTE_BUILT_IN, -1, -1, nullptr, iter->second.m_strCommand);
if (iter->second.m_loop)
{
iter->second.watch.Reset();