Seite 1 von 1
Probleme mit QWaitCondition und QMutex
Verfasst: 18. März 2009 14:30
von MisterJ
Hallo,
ich habe versucht, einen Thread mit QMutex und QWaitConditon zu stoppen und dann wieder zu starten. Dabei bekomme ich aber eine access violation, wenn ich im Thread zum erstem Mal mit QMutex arbeite.
Zunächst eine Frage zu meiner Vorgehensweise:
Ist es richtig, dass ich meinem Thread einen Zeiger auf ein QMutex und ein QWaitCondition Objekt beim Erzeugen aus der aufrufenden Klasse übergebe?
Code: Alles auswählen
m_pDataThread = new DataThread(this, m_pMutex, m_pWaitCondition);
Oder muss ich in beiden Klassen eine Instanz von QMutex und QWaitCondition erzeugen?
Im Thread kommt dann bei
direkt eine Fehlermeldung:
Access violation reading location ...
Ich bitte um Rat, da ich anscheinend das Thema trotz Lesens der Dokumentation und einiger Seiten im Internet noch immer nicht zur Gänze zu durchblicken scheine.
Vielen Dank
Johannes
Verfasst: 18. März 2009 15:04
von pfid
Wenn du in beiden Threads ein Mutex Objekt hast, werden 2 Unterschiedliche Mutexe gesperrt, dementsprechend gar nichts geschützt/blockiert/angehalten (= ja, du musst das Mutex des anderen Threads übergeben).
WaitCond musst du keine mitgeben, die kannst du lokal im Thread (in der Methode... sonst wo) haben, so lang sie als Parameter das mitgegebene Mutex verwendet.
Viel zum Fehler kann man nicht sagen. Die Pointer die du mitgibst sind auch nicht 0, ja?
Verfasst: 18. März 2009 16:19
von MisterJ
Okay, jetzt habe ich keine Fehlermeldung mehr, aber er tut einfach nichts, wenn ich
ausführe.
Im DataThread ist das so verknüpft:
Johannes
Verfasst: 18. März 2009 16:22
von RHBaum
Access violation reading location ...
oder der mutex wurde nicht initialisiert (unwahrscheinlich bei QMutex)
oder der mutex wurde schon deleted (oder ausm scope gelaufen) nur dein benutzender thread hat das ned mitbekommen und nutzt den (nun ungültigen) Zeiger lustig weiter ...
Ciao ...
Verfasst: 18. März 2009 16:32
von pfid
MisterJ hat geschrieben:Okay, jetzt habe ich keine Fehlermeldung mehr, aber er tut einfach nichts, wenn ich
ausführe.
Im DataThread ist das so verknüpft:
Johannes
Also ohne Code kann man dir wirklich nicht helfen.
Läuft dein Thread? (start() ? runloop?)
Hat der Thread vor dem waitcond.wait() das Mutex gelockt? (muss er, sonst gehts nicht)
Hat der andere Thread das Mutex gelockt?
Verfasst: 18. März 2009 16:46
von MisterJ
Okay,
hier der Code:
BasisKlasse.h
BasisKlasse.cpp
Code: Alles auswählen
QMutex * m_pMutex = new QMutex;
m_pDataThread = new DataThread(this, m_pMutex);
...
m_pDataThread->start();
...
m_WaitCondition.wakeAll();
DataThread.h
DataThread.cpp
Code: Alles auswählen
DataThread::DataThread(QObject * parent, QMutex * pMutex)
: QThread(parent)
{
m_pBasisKlasse = qobject_cast<BasisKlasse*>(parent);
m_pMutex = pMutex;
...
}
void DataThread::run(void)
{
while(...) {
m_pMutex->lock();
...
m_pMutex->unlock();
m_pMutex->lock();
...
m_WaitCondition.wait(m_pMutex);
m_pMutex->unlock();
...
} // end while
}
Ich hoffe, das hilft etwas weiter.
Johannes
P.S.: Der Thread läuft bis zu dem wait aber dann nicht weiter, weil er anscheinend nicht wieder aufgeweckt wird.
Verfasst: 18. März 2009 20:16
von pfid
Okay war meinerseits unglücklich formuliert. Du musst die waitcond nicht mitgeben, um sie im thread für wait() zu benutzen. Du musst allerdings schon die waitcond mit wakeAll() aufwecken, auf der der Thread schläft. Wenn du in der basisklasse ne lokale waitcond hast, schläft auf der doch kein thread, folglich kannst du auch keinen aufwecken.
also einfach in den thread header
und das von der basisklasse aufrufen.
Verfasst: 23. März 2009 10:09
von MisterJ
Vielen Dank, jetzt funktioniert es!
