[Interest] Threading Question
Jason Kretzer
Jason at gocodigo.com
Thu Oct 9 13:05:40 CEST 2014
Ack! You are correct.
I guess I would do something like this to remedy that:
in the main:
BackgroundTaskManager::init();
QThread *thread = new QThread();
connect(thread, SIGNAL(started()), BackgroundTaskManager::instance(), SLOT(startTimer()));
BackgroundTaskManager::instance()->moveToThread(thread);
thread->start();
where the SLOT startTimer would instantiate that QTimer that was previously in the constructor.
correct?
-Jason
On Oct 9, 2014, at 6:46 AM, interest-bounces+jason=gocodigo.com at qt-project.org wrote:
>
> On Thursday 09 October 2014 03:32:20 Jason Kretzer wrote:
>> Thanks for the response.
>>
>> Yeah, I have placed qDebug() just before and just after the emit. The one
>> before always prints, the one after never does except in the following
>> case. If I change the connection to QueuedConnection, then the qDebug
>> right after does print, the rest of the function does return and the next
>> iteration of the while loop does start. However, in the slot, as soon as
>> it starts to execute, the loop literally stops executing at another spot.
>> This leads to the same condition, the mutex is never released.
>>
>> The idea is that the BackgroundClass just be executing on its own while the
>> main thread (Thread A) is off doing what it does.
>>
>> Is it possible that the program flow of BackgroundClass is being pulled back
>> into the main thread when the slot starts executing and is thus waiting its
>> turn?
>>
>> -Jason
>>
>> On Oct 9, 2014, at 12:11 AM, interest-bounces+jason=gocodigo.com at qt-
> project.org wrote:
>>> Two suggestions:
>>> 1) add qDebug-s around the "emit someSignal();" line to see whether it
>>> returns or not, hanging somewhere in validateResult();
>>> 2) try to explicitly specify the Qt::QueuedConnection type for the
>>> someSignal() connection — if it helps, then the [most likely] cause is
>>> Qt choosing wrong connection type.
>>>
>>> And, as always, a minimal compilable example would be nice. :)
>>>
>>> On 10/09/2014 07:53 AM, Jason Kretzer wrote:
>>>> Addendum at the bottom…
>>>>
>>>> On Oct 8, 2014, at 11:42 PM, Jason Kretzer <Jason at gocodigo.com> wrote:
>>>>> I am a bit confused on threading.
>>>>>
>>>>> Lets say I have Thread A — which is where the program is started — has
>>>>> main(), etc.
>>>>>
>>>>> Inside of main() I instantiate a class called BackgroundClass and I move
>>>>> it to another thread (Thread B).>>>
>>>>> BackgroundClass::init();
>>>>>
>>>>> QThread *thread = new QThread();
>>>>> BackgroundClass::instance()->moveToThread(thread);
>>>>> thread->start();
>>>>>
>>>>> Inside of BackgroundClass in the constructor, I start a QTimer that is
>>>>> supposed to go off every 5minutes and call the runTasks function when
>>>>> it does. QTimer* timer = new QTimer(this);
>
> And in _which_ thread does this happen? I would guess the constructor is
> running in the main thread. So you create the timer there, too.
> Later you move your BackgroundClass to the other thread, but the timer stays
> where it was created.
>
>>>>>
>>>>> connect(timer, SIGNAL(timeout()), this, SLOT(runTasks()));
>>>>> timer->start(FIVE_MINS);
>>>>>
>>>>> I put a qDebug in the runTasks function to ensure that it is a different
>>>>> thread than the main thread (Thread A). qDebug() << "Running tasks...
>>>>> -- Thread ID: " << QThread::currentThreadId(); //inside runTasks
>>>>>
>>>>> This always shows a different ID than the main thread.
>>>>>
>>>>>
>>>>> Back in the main thread (Thread A), I instantiate another class AFTER
>>>>> the BackgroundClass instantiation.
>>>>>
>>>>> WorkManager::init();
>>>>>
>>>>> this is not moved to a separate thread so, I assume it stays in Thread
>>>>> A.
>>>>>
>>>>> In the constructor of WorkManager, I connect Signals from
>>>>> BackgroundClass to Slots in WorkManager like so.
>>>>>
>>>>> connect(BackgroundTaskManager::instance(), SIGNAL(someSignal()),
>>>>> instance(), SLOT(restartWorker()));
>>>>>
>>>>> When the BackgroundClass finishes a task, it emits the someSignal.
>>>>>
>>>>>> From what I can tell, as soon as the someSignal is emitted, the
>>>>>> restartWorker slot is called and the rest of the code that is
>>>>>> immediately after that does not execute. For example, above, the
>>>>>> runTasks function is supposed to run several tasks in a while loop.
>>>>>> To make sure this loop is thread safe, so it can be the only thing
>>>>>> running those tasks I put a mutex around the while loop. At the end
>>>>>> of the runTask function, the someSignal is emitted the result is set,
>>>>>> and then it is returned.>>>
>>>>> if (!mutex.tryLock()) {
>>>>>
>>>>> qDebug() << "Previous instance of RunTasks still running...";
>>>>> return;
>>>>>
>>>>> }
>>>>>
>>>>> while(moreTasks) {
>>>>>
>>>>> bool result = runTask(t);
>>>>>
>>>>> updateDatabase(t, result);
>>>>>
>>>>> }
>>>>> mutex.unlock();
>>>>>
>>>>>
>>>>> Unforturnately, the runTask method never returns, it appears that the
>>>>> restartWorker is called immediately upon someSignal being emitted.
>>>>>
>>>>> So, I say all that to ask, why does the rest of the code not execute?
>>>>> Obviously, I am doing something wrong, but I am not sure where the flaw
>>>>> is. Would anyone be so kind as to point me in the right direction?>>
>>>> ADDENDUM:
>>>> Since the runTask method never returns, the mutex is never released. So,
>>>> it stalls because the mutext is not released.
>>>>
>>>> Also, just to clarify, the end of runTask, looks like this:
>>>> …
>>>> ...
>>>> emit someSignal();
>>>> result = validateResult(); //last second validation
>>>> return result;
>>>> }
>>>>
>>>>
>>>> -Jason
>>>
>>> -----
>>> No virus found in this message.
>>> Checked by AVG - www.avg.com
>>> Version: 2014.0.4765 / Virus Database: 4015/8233 - Release Date: 09/18/14
>>> Internal Virus Database is out of
>>> date.<signature.asc>_______________________________________________
>>> Interest mailing list
>>> Interest at qt-project.org
>>> http://lists.qt-project.org/mailman/listinfo/interest
>>
>> _______________________________________________
>> Interest mailing list
>> Interest at qt-project.org
>> http://lists.qt-project.org/mailman/listinfo/interest
>
> _______________________________________________
> Interest mailing list
> Interest at qt-project.org
> http://lists.qt-project.org/mailman/listinfo/interest
More information about the Interest
mailing list