Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. General and Desktop
  4. threads and created objects
Forum Update on Tuesday, May 27th 2025

threads and created objects

Scheduled Pinned Locked Moved Solved General and Desktop
26 Posts 4 Posters 2.9k Views 4 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • M Offline
    M Offline
    mzimmers
    wrote on 6 Oct 2020, 17:22 last edited by
    #1

    Hi all -

    I'm trying to clean up a lingering issue with an app. The app creates a second thread, into which I move my worker object:

    int main(int argc, char *argv[])
    {
        int rc;
        QApplication a(argc, argv);
        ModelDevice modelDevices(nullptr);
        ModelApScan modelApScan(nullptr);
        QThread thread(&a);
        Widget widget(&modelDevices, &modelApScan);
        Worker worker(&modelDevices);
        widget.setWorker(&worker);
        worker.setWidget(&widget);
        worker.moveToThread(&thread);
    
        QObject::connect(&widget, &Widget::quitButtonPushed, &thread, &QThread::exit);
        QObject::connect(&thread, &QThread::finished, &a, &QApplication::quit);
        QObject::connect(&thread, &QThread::started, &worker, &Worker::start);
    
        widget.show();
        thread.start();
        rc = a.exec();
        return rc;
    }
    

    The worker object creates another object:

    Worker::Worker(ModelDevice *modelDevices) : m_modelDevices(modelDevices)
    {
        m_mcastSocket = new UdpSocket(&m_addrMulticast, this);
    }
    

    The destructor for UdpSocket is this:

    UdpSocket::~UdpSocket()
    {
        m_timer.stop();
    }
    

    On the call to stop(), I get this message:

    QObject::killTimer: Timers cannot be stopped from another thread
    

    It seems to me that UdpSocket, being created in Worker::start(), should belong to the Worker thread, no? What am I doing wrong here?

    Thanks...

    1 Reply Last reply
    0
    • S Offline
      S Offline
      SGaist
      Lifetime Qt Champion
      wrote on 6 Oct 2020, 17:35 last edited by
      #2

      Hi,

      If you want everything to happen in the worker thread, allocate your Worker object on the heap and connect deleteLater to the thread finished signal.

      Interested in AI ? www.idiap.ch
      Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

      M 1 Reply Last reply 6 Oct 2020, 18:05
      3
      • C Online
        C Online
        Christian Ehrlicher
        Lifetime Qt Champion
        wrote on 6 Oct 2020, 17:55 last edited by
        #3

        @mzimmers said in threads and created objects:

        worker.setWidget(&widget);

        Why? You must not access gui from another thread than the main thread.

        Qt Online Installer direct download: https://download.qt.io/official_releases/online_installers/
        Visit the Qt Academy at https://academy.qt.io/catalog

        M 1 Reply Last reply 6 Oct 2020, 17:58
        1
        • C Christian Ehrlicher
          6 Oct 2020, 17:55

          @mzimmers said in threads and created objects:

          worker.setWidget(&widget);

          Why? You must not access gui from another thread than the main thread.

          M Offline
          M Offline
          mzimmers
          wrote on 6 Oct 2020, 17:58 last edited by mzimmers 10 Jun 2020, 18:08
          #4

          @Christian-Ehrlicher I do that so I can do things like this:

          void Worker::start()
          {
              QObject::connect(m_widget, &Widget::discoverButtonPushed, this, &Worker::sendDiscoveryRequest);
              QObject::connect(m_widget, &Widget::scanButtonPushed, this, &Worker::sendScanRequest);
          ...
          
          1 Reply Last reply
          0
          • C Online
            C Online
            Christian Ehrlicher
            Lifetime Qt Champion
            wrote on 6 Oct 2020, 18:00 last edited by
            #5

            No need to do this inside start()

            Qt Online Installer direct download: https://download.qt.io/official_releases/online_installers/
            Visit the Qt Academy at https://academy.qt.io/catalog

            M 1 Reply Last reply 6 Oct 2020, 18:02
            0
            • C Christian Ehrlicher
              6 Oct 2020, 18:00

              No need to do this inside start()

              M Offline
              M Offline
              mzimmers
              wrote on 6 Oct 2020, 18:02 last edited by
              #6

              @Christian-Ehrlicher well, it has to be done somewhere; are you suggesting it would be preferable to make the connections from the widget object?

              1 Reply Last reply
              0
              • S SGaist
                6 Oct 2020, 17:35

                Hi,

                If you want everything to happen in the worker thread, allocate your Worker object on the heap and connect deleteLater to the thread finished signal.

                M Offline
                M Offline
                mzimmers
                wrote on 6 Oct 2020, 18:05 last edited by
                #7

                @SGaist thank you; that seems to work. I'm still curious, though -- why doesn't an object created in worker::start() belong to worker? Or, am I misinterpreting the message?

                1 Reply Last reply
                0
                • C Online
                  C Online
                  Christian Ehrlicher
                  Lifetime Qt Champion
                  wrote on 6 Oct 2020, 18:08 last edited by
                  #8

                  @mzimmers said in threads and created objects:

                  why doesn't an object created in worker::start() belong to worker?

                  It's important to which thread the objects belong to. Please show the UdpSocket ctor - there I see the only reason why the UdpSocket should not be moved to the thread where you move Worker to.

                  Qt Online Installer direct download: https://download.qt.io/official_releases/online_installers/
                  Visit the Qt Academy at https://academy.qt.io/catalog

                  M 1 Reply Last reply 6 Oct 2020, 18:10
                  0
                  • S Offline
                    S Offline
                    SGaist
                    Lifetime Qt Champion
                    wrote on 6 Oct 2020, 18:10 last edited by
                    #9

                    Object belonging and thread affinity are different things.

                    The message you had was because the destruction happened in the main thread.

                    Interested in AI ? www.idiap.ch
                    Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

                    M C 3 Replies Last reply 6 Oct 2020, 18:12
                    1
                    • C Christian Ehrlicher
                      6 Oct 2020, 18:08

                      @mzimmers said in threads and created objects:

                      why doesn't an object created in worker::start() belong to worker?

                      It's important to which thread the objects belong to. Please show the UdpSocket ctor - there I see the only reason why the UdpSocket should not be moved to the thread where you move Worker to.

                      M Offline
                      M Offline
                      mzimmers
                      wrote on 6 Oct 2020, 18:10 last edited by
                      #10

                      @Christian-Ehrlicher

                      UdpSocket::UdpSocket(QHostAddress *qha, QObject *parent) :
                          QObject(parent)
                      {
                          QHostAddress *l_qha;
                          QString qs;
                      	
                          // set up addresses.
                          l_qha = qha;
                          qs = l_qha->toString();
                          m_addrMulticast.setAddress(qs);
                      
                          init();
                      
                          QObject::connect(&m_timer, &QTimer::timeout, this, &UdpSocket::checkSockets);
                          m_timer.start(3000);
                      }
                      
                      1 Reply Last reply
                      0
                      • S SGaist
                        6 Oct 2020, 18:10

                        Object belonging and thread affinity are different things.

                        The message you had was because the destruction happened in the main thread.

                        M Offline
                        M Offline
                        mzimmers
                        wrote on 6 Oct 2020, 18:12 last edited by
                        #11

                        @SGaist said in threads and created objects:

                        Object belonging and thread affinity are different things.

                        I didn't realize that, but OK.

                        The message you had was because the destruction happened in the main thread.

                        So, how is this changed by creating worker on the heap?

                        1 Reply Last reply
                        0
                        • S SGaist
                          6 Oct 2020, 18:10

                          Object belonging and thread affinity are different things.

                          The message you had was because the destruction happened in the main thread.

                          C Online
                          C Online
                          Christian Ehrlicher
                          Lifetime Qt Champion
                          wrote on 6 Oct 2020, 18:14 last edited by
                          #12

                          @SGaist said in threads and created objects:

                          The message you had was because the destruction happened in the main thread.

                          Correct, I read it the other way and thought the timer was still in the main thread and was destructed in the other thread :)

                          Qt Online Installer direct download: https://download.qt.io/official_releases/online_installers/
                          Visit the Qt Academy at https://academy.qt.io/catalog

                          1 Reply Last reply
                          0
                          • S Offline
                            S Offline
                            SGaist
                            Lifetime Qt Champion
                            wrote on 6 Oct 2020, 18:15 last edited by
                            #13

                            Your object on the stack gets destroyed at the end of the current scope.

                            Moving it on the heap gets it out of that scope, but then it's your duty to delete it properly. Which you do by connecting the deleteLater slot to the finished signal.

                            Interested in AI ? www.idiap.ch
                            Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

                            1 Reply Last reply
                            3
                            • S SGaist
                              6 Oct 2020, 18:10

                              Object belonging and thread affinity are different things.

                              The message you had was because the destruction happened in the main thread.

                              M Offline
                              M Offline
                              mzimmers
                              wrote on 7 Oct 2020, 18:53 last edited by
                              #14

                              @SGaist said in threads and created objects:

                              Object belonging and thread affinity are different things.

                              I need to pursue this a bit further. So, if I have an object (my worker object) that I move to another thread, is it true that anything created within that object prior to the move "belongs" to the original thread?

                              Specifically, my worker object has a member object m_serial. Presumably this object belongs to the original thread. After worker is moved, when this object creates something (like a QSerialPort), this "belongs" to the worker thread. When the worker thread does a write on it, I get the timer error. Is this because m_serial belongs to the original thread, but its QSerialPort belongs to the worker thread?

                              And if I have this right, is the solution that the worker thread would create its objects in start(), instead of having member objects?

                              1 Reply Last reply
                              0
                              • S Offline
                                S Offline
                                SGaist
                                Lifetime Qt Champion
                                wrote on 7 Oct 2020, 19:02 last edited by SGaist 10 Jul 2020, 19:26
                                #15

                                @mzimmers said in threads and created objects:

                                I need to pursue this a bit further. So, if I have an object (my worker object) that I move to another thread, is it true that anything created within that object prior to the move "belongs" to the original thread?

                                If it's a QObject that is properly parented, it will move with it. Note that classes like QTcpSocket must be created in the new thread. You can however pass the descriptor like shown in the threaded QTcpSocket/Server example.

                                Interested in AI ? www.idiap.ch
                                Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

                                kshegunovK M 2 Replies Last reply 7 Oct 2020, 19:04
                                1
                                • S SGaist
                                  7 Oct 2020, 19:02

                                  @mzimmers said in threads and created objects:

                                  I need to pursue this a bit further. So, if I have an object (my worker object) that I move to another thread, is it true that anything created within that object prior to the move "belongs" to the original thread?

                                  If it's a QObject that is properly parented, it will move with it. Note that classes like QTcpSocket must be created in the new thread. You can however pass the descriptor like shown in the threaded QTcpSocket/Server example.

                                  kshegunovK Offline
                                  kshegunovK Offline
                                  kshegunov
                                  Moderators
                                  wrote on 7 Oct 2020, 19:04 last edited by
                                  #16

                                  @SGaist said in threads and created objects:

                                  If it's a QObject that is properly patented, it will move with it. Note that classes like QTcoSocket must be created in the new thread. You can however pass the descriptor like shown in the threaded QTcpSocket/Server example.

                                  Actually a comment on that. Sockets that haven't been opened/bound can still be moved normally, however I agree it's a bad practice to depend on the actual implementation.

                                  Read and abide by the Qt Code of Conduct

                                  1 Reply Last reply
                                  1
                                  • S SGaist
                                    7 Oct 2020, 19:02

                                    @mzimmers said in threads and created objects:

                                    I need to pursue this a bit further. So, if I have an object (my worker object) that I move to another thread, is it true that anything created within that object prior to the move "belongs" to the original thread?

                                    If it's a QObject that is properly parented, it will move with it. Note that classes like QTcpSocket must be created in the new thread. You can however pass the descriptor like shown in the threaded QTcpSocket/Server example.

                                    M Offline
                                    M Offline
                                    mzimmers
                                    wrote on 7 Oct 2020, 19:15 last edited by
                                    #17

                                    @SGaist said in threads and created objects:

                                    If it's a QObject that is properly patented, it will move with it.

                                    This is my current creation:

                                    class Worker : public QObject
                                    {
                                        Q_OBJECT
                                    private:
                                        SerialPort m_serial;
                                    ...
                                    SerialPort::SerialPort(QObject *parent) : QObject (parent)
                                    {
                                    ...
                                    

                                    Note that classes like QTcoSocket must be created in the new thread.

                                    But not in the c'tor, correct? Because that is called prior to the thread move, so it would pertain to the original thread?

                                    1 Reply Last reply
                                    0
                                    • S Offline
                                      S Offline
                                      SGaist
                                      Lifetime Qt Champion
                                      wrote on 7 Oct 2020, 19:21 last edited by
                                      #18

                                      I fixed the typo of parented (damn autocorrect...)

                                      Yes, m_serial will not be moved.

                                      Interested in AI ? www.idiap.ch
                                      Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

                                      M 1 Reply Last reply 7 Oct 2020, 19:23
                                      2
                                      • S SGaist
                                        7 Oct 2020, 19:21

                                        I fixed the typo of parented (damn autocorrect...)

                                        Yes, m_serial will not be moved.

                                        M Offline
                                        M Offline
                                        mzimmers
                                        wrote on 7 Oct 2020, 19:23 last edited by mzimmers 10 Jul 2020, 19:23
                                        #19

                                        @SGaist said in threads and created objects:

                                        I fixed the typo of parented (damn autocorrect...

                                        Well, while you're at it..."QTcoSocket?"

                                        kshegunovK S 2 Replies Last reply 7 Oct 2020, 19:24
                                        0
                                        • M mzimmers
                                          7 Oct 2020, 19:23

                                          @SGaist said in threads and created objects:

                                          I fixed the typo of parented (damn autocorrect...

                                          Well, while you're at it..."QTcoSocket?"

                                          kshegunovK Offline
                                          kshegunovK Offline
                                          kshegunov
                                          Moderators
                                          wrote on 7 Oct 2020, 19:24 last edited by kshegunov 10 Jul 2020, 19:31
                                          #20

                                          If you want the QObjects to to be moved alongside with their parent to another thread, then you must pass them the parent. No parent, no way Qt to know whether the object's supposed to be moved.

                                          Read and abide by the Qt Code of Conduct

                                          M 1 Reply Last reply 7 Oct 2020, 19:40
                                          0

                                          1/26

                                          6 Oct 2020, 17:22

                                          • Login

                                          • Login or register to search.
                                          1 out of 26
                                          • First post
                                            1/26
                                            Last post
                                          0
                                          • Categories
                                          • Recent
                                          • Tags
                                          • Popular
                                          • Users
                                          • Groups
                                          • Search
                                          • Get Qt Extensions
                                          • Unsolved