Skip to content
This repository
Browse code

[fix] There was a possible concurrent modification of a vector that w…

…ould corrupt the state of iterators.
  • Loading branch information...
commit 290265045b2b9c1304eca3f6609401615d410091 1 parent e4f2088
authored December 23, 2012
1  xbmc/interfaces/python/XBPyThread.cpp
@@ -98,6 +98,7 @@ XBPyThread::~XBPyThread()
98 98
       delete [] m_argv[i];
99 99
     delete [] m_argv;
100 100
   }
  101
+  g_pythonParser.FinalizeScript();
101 102
 }
102 103
 
103 104
 void XBPyThread::setSource(const CStdString &src)
40  xbmc/interfaces/python/XBPython.cpp
@@ -613,6 +613,7 @@ void XBPython::FinalizeScript()
613 613
     CLog::Log(LOGERROR, "Python script counter attempted to become negative");
614 614
   m_endtime = XbmcThreads::SystemClockMillis();
615 615
 }
  616
+
616 617
 void XBPython::Finalize()
617 618
 {
618 619
   TRACE;
@@ -656,16 +657,15 @@ void XBPython::FreeResources()
656 657
   CSingleLock lock(m_critSection);
657 658
   if (m_bInitialized)
658 659
   {
  660
+    // with the m_critSection held, we should copy the PyList so that 
  661
+    // we can operate on the values once we release it.
  662
+    PyList tmpvec = m_vecPyList;
  663
+    m_vecPyList.clear();
  664
+
  665
+    lock.Leave(); //unlock here because the python thread might lock when it exits
  666
+
659 667
     // cleanup threads that are still running
660  
-    PyList::iterator it = m_vecPyList.begin();
661  
-    while (it != m_vecPyList.end())
662  
-    {
663  
-      lock.Leave(); //unlock here because the python thread might lock when it exits
664  
-      delete it->pyThread;
665  
-      lock.Enter();
666  
-      it = m_vecPyList.erase(it);
667  
-      FinalizeScript();
668  
-    }
  668
+    tmpvec.clear(); // boost releases the XBPyThreads which, if deleted, calls FinalizeScript
669 669
   }
670 670
 }
671 671
 
@@ -688,21 +688,21 @@ void XBPython::Process()
688 688
 
689 689
   if (m_bInitialized)
690 690
   {
691  
-    PyList::iterator it = m_vecPyList.begin();
692  
-    while (it != m_vecPyList.end())
  691
+    PyList tmpvec;
  692
+    for (PyList::iterator it = m_vecPyList.begin(); it != m_vecPyList.end();)
693 693
     {
694  
-      //delete scripts which are done
695 694
       if (it->bDone)
696 695
       {
697  
-        {
698  
-          CSingleExit exit(m_critSection);
699  
-          delete it->pyThread;
700  
-        }
  696
+        tmpvec.push_back(*it);
701 697
         it = m_vecPyList.erase(it);
702  
-        FinalizeScript();
703 698
       }
704  
-      else ++it;
  699
+      else
  700
+        it++;
705 701
     }
  702
+    lock.Leave();
  703
+
  704
+    //delete scripts which are done
  705
+    tmpvec.clear(); // boost releases the XBPyThreads which, if deleted, calls FinalizeScript
706 706
 
707 707
     if(m_iDllScriptCounter == 0 && (XbmcThreads::SystemClockMillis() - m_endtime) > 10000 )
708 708
       Finalize();
@@ -753,7 +753,7 @@ int XBPython::evalFile(const CStdString &src, const std::vector<CStdString> &arg
753 753
   if (!m_bInitialized) return -1;
754 754
 
755 755
   m_nextid++;
756  
-  XBPyThread *pyThread = new XBPyThread(this, m_nextid);
  756
+  boost::shared_ptr<XBPyThread> pyThread = boost::shared_ptr<XBPyThread>(new XBPyThread(this, m_nextid));
757 757
   pyThread->setArgv(argv);
758 758
   pyThread->setAddon(addon);
759 759
   pyThread->evalFile(src);
@@ -917,7 +917,7 @@ int XBPython::evalString(const CStdString &src, const std::vector<CStdString> &a
917 917
 
918 918
   // Previous implementation would create a new thread for every script
919 919
   m_nextid++;
920  
-  XBPyThread *pyThread = new XBPyThread(this, m_nextid);
  920
+  boost::shared_ptr<XBPyThread> pyThread = boost::shared_ptr<XBPyThread>(new XBPyThread(this, m_nextid));
921 921
   pyThread->setArgv(argv);
922 922
   pyThread->evalString(src);
923 923
 
3  xbmc/interfaces/python/XBPython.h
@@ -26,6 +26,7 @@
26 26
 #include "threads/CriticalSection.h"
27 27
 #include "interfaces/IAnnouncer.h"
28 28
 #include "addons/IAddon.h"
  29
+#include "boost/shared_ptr.hpp"
29 30
 
30 31
 #include <vector>
31 32
 
@@ -33,7 +34,7 @@ typedef struct {
33 34
   int id;
34 35
   bool bDone;
35 36
   std::string strFile;
36  
-  XBPyThread *pyThread;
  37
+  boost::shared_ptr<XBPyThread> pyThread;
37 38
 }PyElem;
38 39
 
39 40
 class LibraryLoader;

0 notes on commit 2902650

Please sign in to comment.
Something went wrong with that request. Please try again.