[Interest] Does cross thread signal/slot connection order matter?

Murphy, Sean smurphy at walbro.com
Wed Jun 11 16:51:57 CEST 2014


>> I've got an object that I want to live in another thread, so in a class in my main thread I've got:
>> 
>> //  pseudo-code, may not compile
>> QThread* thread = new QThread(this);
>> myObject* foo =  new myObject();
>> foo ->moveToThread(thread);
>> thread->start();
>> 
>> But when I go to connect the signals/slots between objects in the main thread and the "foo" object, should I do that before I move that object to a different thread, or after, or does it not matter?
>> 
>> So should it be either:
>> QThread* thread = new QThread(this);
>> myObject* foo =  new myObject();
>> // make calls to connect() before calling moveToThread()
>> connect(this, SIGNAL(.),foo, SLOT(.)); // repeat as necessary for all my signal/slot connections
>> foo->moveToThread(thread);
>> thread->start();
>> 
>> Or:
>> QThread* thread = new QThread(this);
>> myObject* foo =  new myObject();
>> foo->moveToThread(thread);
>> thread->start();
>> // make calls to connect() after calling moveToThread()
>> connect(this, SIGNAL(.),foo, SLOT(.));// repeat as necessary for all my signal/slot connections
>>
>> Or even delaying the thread->start() call until after everything else:
>> QThread* thread = new QThread(this);
>> myObject* foo =  new myObject();
>> foo->moveToThread(thread);
>> // make calls to connect() after calling moveToThread() then call thread->start()
>> connect(this, SIGNAL(.),foo, SLOT(.));// repeat as necessary for all my signal/slot connections
>> thread->start();
>> 
>> I can't find any authoritative documentation that says to do it one way or the other, so either it doesn't exist or more likely, I'm not googling well.  I can find lots of docs on the merits of inheriting from QThread vs. using the moveToThread(), but the ones I've found don't address this question in detail.
>> 
> It doesn't matter. Qt::autConnection connections (the default connection type) will evaluate the thread affinity of the current thread* and the receiver at the moment of the signal emission. So, it doesn't matter if you connect first and then move, or move first and then connect, only at signal emission it is evaluated what mechanism to use (direct call, or go through the event system of the receiving thread). 

That's what I assumed, but wasn't sure.

> Note that your second example will work in this case, but may end up as a race condition if you make a connection the other way around from a signal on your worker to a slot in your current thread. If you start the thread before making the connection, you run the risk that you'll miss signals as they may be emitted before you make the connection.
>
> *) note that the current thread _may_ not match the thread affinity of the signal's object.

I do have signals going both ways so I'll make sure to not use option #2!

Thanks, 
Sean




More information about the Interest mailing list