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. QTimer seems to just stop
QtWS25 Last Chance

QTimer seems to just stop

Scheduled Pinned Locked Moved Solved General and Desktop
19 Posts 6 Posters 4.1k Views
  • 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.
  • K Kent-Dorfman
    21 Mar 2019, 23:24

    @acs-sharp said in QTimer seems to just stop:

    Then, the timeout handler apparently sees no more timeout() signals.

    3600ish timeouts and then nothing? It's entirely possible that there is a resource leak, but you need to do a lot investigating first. Memory usage over the life of the program? Putting a QTimer into its own project that does nothing except output a counter value, and then see if it behaves similarly?

    Post the substance of your timeout() slot.

    A Offline
    A Offline
    acs-sharp
    wrote on 22 Mar 2019, 14:48 last edited by
    #5

    @Kent-Dorfman said in QTimer seems to just stop:

    @acs-sharp said in QTimer seems to just stop:

    Then, the timeout handler apparently sees no more timeout() signals.

    3600ish timeouts and then nothing? It's entirely possible that there is a resource leak,

    Interesting. The resource leak angle seems worth pursuing. Would I be naive in thinking that if memory ran out I'd get a warning message, or at least a segfault?

    Are there Qt functions for monitoring resources it manages? (I don't have access to the usual C tools, e.g. valgrind, in this environment.)

    1 Reply Last reply
    0
    • A acs-sharp
      21 Mar 2019, 23:26

      @SGaist said in QTimer seems to just stop:

      Do you have your device going to sleep ?

      No--its incapable of this :-)

      Do you have any other application doing something ?

      There are other applications on the system though afaict they are sleeping most of the time.

      What are you doing in the slot connected to that timer ?

      It updates displayed content in various widgets (labels,spinbox, LCDNumber,, ComboBox). I've looked over these for anything that might block (no obvious candidates), and tried commenting them out one by one, but the problem persists. The data (array of integers) it accesses does not entail I/O, but it is memory shared with another thread--the slot handler reads only.

      J Online
      J Online
      JonB
      wrote on 22 Mar 2019, 19:51 last edited by JonB
      #6

      @acs-sharp
      You talk about multiple threads. If the thread with the timer doesn't hit its event loop your timer doesn't fire. Or if your thread gets blocked, perhaps waiting on the other one. Just saying.

      Thought: Assuming your OS allows a second timer, create a QTimer timer2 alongside your timer. It's sole job is log the https://doc.qt.io/qt-5/qtimer.html#remainingTime-prop of your actual timer. See how that behaves doing its logging, does it continue or seem to stop too? See what it reports for real timer's remainingTime when that finally seems to stop ticking?

      A 1 Reply Last reply 22 Mar 2019, 23:40
      1
      • J JonB
        22 Mar 2019, 19:51

        @acs-sharp
        You talk about multiple threads. If the thread with the timer doesn't hit its event loop your timer doesn't fire. Or if your thread gets blocked, perhaps waiting on the other one. Just saying.

        Thought: Assuming your OS allows a second timer, create a QTimer timer2 alongside your timer. It's sole job is log the https://doc.qt.io/qt-5/qtimer.html#remainingTime-prop of your actual timer. See how that behaves doing its logging, does it continue or seem to stop too? See what it reports for real timer's remainingTime when that finally seems to stop ticking?

        A Offline
        A Offline
        acs-sharp
        wrote on 22 Mar 2019, 23:40 last edited by
        #7

        @JonB said in QTimer seems to just stop:

        @acs-sharp
        You talk about multiple threads. If the thread with the timer doesn't hit its event loop your timer doesn't fire. Or if your thread gets blocked, perhaps waiting on the other one. Just saying.

        That hypothesis has indeed worried me, however I disconnected the two threads but the problem persists.

        Thought: Assuming your OS allows a second timer, create a QTimer timer2 alongside your timer. It's sole job is log the https://doc.qt.io/qt-5/qtimer.html#remainingTime-prop of your actual timer. See how that behaves doing its logging, does it continue or seem to stop too? See what it reports for real timer's remainingTime when that finally seems to stop ticking?

        That was an interesting experiment--thanks for the suggestion. Both timers stop on the same second (~4280). Timer 2 last states that timer1 has 994 remaining; we never hear from either timer after that. I would suppose, "oh, something is blocking the event loop", but the buttons on the window continue to work after the timers stop, which would seem inconsistent with a blocked event loop, no? Could the QTimer instance's memory be getting clobbered thereby stopping the timer(s)? I will try rearranging their position in RAM....

        J 1 Reply Last reply 23 Mar 2019, 09:10
        0
        • A acs-sharp
          22 Mar 2019, 23:40

          @JonB said in QTimer seems to just stop:

          @acs-sharp
          You talk about multiple threads. If the thread with the timer doesn't hit its event loop your timer doesn't fire. Or if your thread gets blocked, perhaps waiting on the other one. Just saying.

          That hypothesis has indeed worried me, however I disconnected the two threads but the problem persists.

          Thought: Assuming your OS allows a second timer, create a QTimer timer2 alongside your timer. It's sole job is log the https://doc.qt.io/qt-5/qtimer.html#remainingTime-prop of your actual timer. See how that behaves doing its logging, does it continue or seem to stop too? See what it reports for real timer's remainingTime when that finally seems to stop ticking?

          That was an interesting experiment--thanks for the suggestion. Both timers stop on the same second (~4280). Timer 2 last states that timer1 has 994 remaining; we never hear from either timer after that. I would suppose, "oh, something is blocking the event loop", but the buttons on the window continue to work after the timers stop, which would seem inconsistent with a blocked event loop, no? Could the QTimer instance's memory be getting clobbered thereby stopping the timer(s)? I will try rearranging their position in RAM....

          J Online
          J Online
          JonB
          wrote on 23 Mar 2019, 09:10 last edited by JonB
          #8

          @acs-sharp
          That's about what I kind of expected. It's telling us something, but I'm not sure what! Next steps:

          • I'm not quite sure if you can do this, but can you now move timer2 into its own thread and see how it behaves? It probably doesn't need to log timer1's remaining time, because you know what happens to that, it can probably just log itself. You want to know whether that keeps ticking after timer1 stops?

          • It might be time to try @Kent-Dorfman's suggestion: just a standalone project/executable which does nothing but logs a timer, if that too stops then...?

          • Let's be clear: you say you have two threads. Does your timer1 run in the same thread as your GUI (which you say remains responsive), or does it run in the other thread??

          A 1 Reply Last reply 23 Mar 2019, 19:37
          0
          • J JonB
            23 Mar 2019, 09:10

            @acs-sharp
            That's about what I kind of expected. It's telling us something, but I'm not sure what! Next steps:

            • I'm not quite sure if you can do this, but can you now move timer2 into its own thread and see how it behaves? It probably doesn't need to log timer1's remaining time, because you know what happens to that, it can probably just log itself. You want to know whether that keeps ticking after timer1 stops?

            • It might be time to try @Kent-Dorfman's suggestion: just a standalone project/executable which does nothing but logs a timer, if that too stops then...?

            • Let's be clear: you say you have two threads. Does your timer1 run in the same thread as your GUI (which you say remains responsive), or does it run in the other thread??

            A Offline
            A Offline
            acs-sharp
            wrote on 23 Mar 2019, 19:37 last edited by
            #9

            @JonB said in QTimer seems to just stop:

            • I'm not quite sure if you can do this, but can you now move timer2 into its own thread and see how it behaves? It probably doesn't need to log timer1's remaining time, because you know what happens to that, it can probably just log itself. You want to know whether that keeps ticking after timer1 stops?

            I think I managed this:

            class TimerThread : public QThread
            {
                Q_OBJECT
                void run() override
                {
                    QTimer  qtimer2 {this};
                    qDebug("TimerThread starting...");
                    QObject::connect( &qtimer2, SIGNAL(timeout()), this,
                                     SLOT(timer2Update()) );
                    qtimer2.start(1000);  // start timer2
                    //
                    exec();               // start even loop
                    qDebug("TimerThread exits!");
                }
            private slots:
                void timer2Update();
            };
            

            An instance of TimerThread is created and started in the constructor for the main window. (Hope that is what you proposed. The timeout handler prints a message on the console every second. It stops at the same time as the timer in the main UI thread.

            • It might be time to try @Kent-Dorfman's suggestion: just a standalone project/executable which does nothing but logs a timer, if that too stops then...?

            Agreed. It will be a bit of work, but feasible. However if anybody has a brilliant hypothesis that would short-circuit that, I'd be really pleased ;-)

            • Let's be clear: you say you have two threads. Does your timer1 run in the same thread as your GUI (which you say remains responsive), or does it run in the other thread??

            Yes, timer1 runs in the same thread as the GUI, which does remain responsive. It is created in the MainWindow ctor.

            J 1 Reply Last reply 23 Mar 2019, 19:41
            1
            • A acs-sharp
              23 Mar 2019, 19:37

              @JonB said in QTimer seems to just stop:

              • I'm not quite sure if you can do this, but can you now move timer2 into its own thread and see how it behaves? It probably doesn't need to log timer1's remaining time, because you know what happens to that, it can probably just log itself. You want to know whether that keeps ticking after timer1 stops?

              I think I managed this:

              class TimerThread : public QThread
              {
                  Q_OBJECT
                  void run() override
                  {
                      QTimer  qtimer2 {this};
                      qDebug("TimerThread starting...");
                      QObject::connect( &qtimer2, SIGNAL(timeout()), this,
                                       SLOT(timer2Update()) );
                      qtimer2.start(1000);  // start timer2
                      //
                      exec();               // start even loop
                      qDebug("TimerThread exits!");
                  }
              private slots:
                  void timer2Update();
              };
              

              An instance of TimerThread is created and started in the constructor for the main window. (Hope that is what you proposed. The timeout handler prints a message on the console every second. It stops at the same time as the timer in the main UI thread.

              • It might be time to try @Kent-Dorfman's suggestion: just a standalone project/executable which does nothing but logs a timer, if that too stops then...?

              Agreed. It will be a bit of work, but feasible. However if anybody has a brilliant hypothesis that would short-circuit that, I'd be really pleased ;-)

              • Let's be clear: you say you have two threads. Does your timer1 run in the same thread as your GUI (which you say remains responsive), or does it run in the other thread??

              Yes, timer1 runs in the same thread as the GUI, which does remain responsive. It is created in the MainWindow ctor.

              J Online
              J Online
              JonB
              wrote on 23 Mar 2019, 19:41 last edited by JonB
              #10

              @acs-sharp

              It stops at the same time as the timer in the main UI thread.

              Now, if only we knew what that was telling us...! :)

              It does not necessarily matter about creating a separate application with a timer. It is time(!) now for you to simply change your current timer to only log to file, not "perform some regular display updates" (nor access that shared array). Does that too stop, or was it only because of the display updates it has been performing?

              A 1 Reply Last reply 24 Mar 2019, 17:15
              2
              • J JonB
                23 Mar 2019, 19:41

                @acs-sharp

                It stops at the same time as the timer in the main UI thread.

                Now, if only we knew what that was telling us...! :)

                It does not necessarily matter about creating a separate application with a timer. It is time(!) now for you to simply change your current timer to only log to file, not "perform some regular display updates" (nor access that shared array). Does that too stop, or was it only because of the display updates it has been performing?

                A Offline
                A Offline
                acs-sharp
                wrote on 24 Mar 2019, 17:15 last edited by
                #11

                @JonB said in QTimer seems to just stop:

                @acs-sharp

                It stops at the same time as the timer in the main UI thread.

                It does not necessarily matter about creating a separate application with a timer. It is time(!) now for you to simply change your current timer to only log to file, not "perform some regular display updates" (nor access that shared array). Does that too stop, or was it only because of the display updates it has been performing?

                Done. The original timer now only increments a static variable counter and prints its value to stderr (every 5th count). It does not touch any shared memory or perform any display updates or anything else. But, timeout events still stop--and, at about the same number of ticks: (4280+/-5, 1hr 11min).

                Well, what if I run the clock faster: update at 200ms instead of 1sec? It still stops at about the same wall clock time (1hr 10min), even thought the number of timeout events processed is 5x higher. My conclusion is that it is not the timeout event processing that is killing the clock(s). But something is killing them, and it appears to be tied to wall-clock time.

                I am tempted to add a button that will try to restart the timer when pressed.

                1 Reply Last reply
                0
                • C Offline
                  C Offline
                  Christian Ehrlicher
                  Lifetime Qt Champion
                  wrote on 24 Mar 2019, 17:56 last edited by
                  #12

                  Please show us the complete code - where does TimerThread live? I would guess in the main thread which means timer2Update() is also executed in 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

                  1 Reply Last reply
                  1
                  • H Offline
                    H Offline
                    hskoglund
                    wrote on 24 Mar 2019, 18:40 last edited by hskoglund
                    #13

                    Hi, could the stop be due to a 2^32 wraparound? Because 4294967296 (2^32) microseconds is 4295 seconds.

                    J 1 Reply Last reply 24 Mar 2019, 18:47
                    5
                    • H hskoglund
                      24 Mar 2019, 18:40

                      Hi, could the stop be due to a 2^32 wraparound? Because 4294967296 (2^32) microseconds is 4295 seconds.

                      J Online
                      J Online
                      JonB
                      wrote on 24 Mar 2019, 18:47 last edited by JonB
                      #14

                      @hskoglund

                      Hi, could the stop be due to a 2^32 wraparound? Because 4294967296 (2^32) microseconds is 4295 seconds.

                      It might have been nice if you'd quoted it in minutes, I had to go use calc! 71 minutes, and OP says it works for about an hour, then specifically 1:10, very good spot! But where do you think this happening? I can't see that QTimer stops working, the docs would say so....

                      @acs-sharp
                      Is there anything in your code which could be sensitive to this? You are 32-bit....
                      You said at the beginning:

                      Using Qt 5.8.0 on Genode, x86_32.

                      I know nothing, what is "Genode"? If it's some embedded system(??), does it have its own clock being leveraged by Qt which might wrap??

                      H K 2 Replies Last reply 24 Mar 2019, 19:19
                      1
                      • J JonB
                        24 Mar 2019, 18:47

                        @hskoglund

                        Hi, could the stop be due to a 2^32 wraparound? Because 4294967296 (2^32) microseconds is 4295 seconds.

                        It might have been nice if you'd quoted it in minutes, I had to go use calc! 71 minutes, and OP says it works for about an hour, then specifically 1:10, very good spot! But where do you think this happening? I can't see that QTimer stops working, the docs would say so....

                        @acs-sharp
                        Is there anything in your code which could be sensitive to this? You are 32-bit....
                        You said at the beginning:

                        Using Qt 5.8.0 on Genode, x86_32.

                        I know nothing, what is "Genode"? If it's some embedded system(??), does it have its own clock being leveraged by Qt which might wrap??

                        H Offline
                        H Offline
                        hskoglund
                        wrote on 24 Mar 2019, 19:19 last edited by
                        #15

                        @JonB Google thinks it's from Germany https://www.genode-labs.com

                        About 32-bit overflows, actually the Qt docs mentions it can happen for QElapsedTimer

                        A 1 Reply Last reply 26 Mar 2019, 18:06
                        4
                        • J Online
                          J Online
                          JonB
                          wrote on 24 Mar 2019, 19:27 last edited by
                          #16

                          @acs-sharp
                          Right! In view of the above: At present you QTimer::start() and leave it to tick forever. Now, for a test, at some point before 71 minutes make your code stop that timer and completely restart it, or delete it and create a new one, or whatever. Do you no longer stop getting timeouts after 71 minutes? It's a workaround, if not a resolution :)

                          A 1 Reply Last reply 29 Mar 2019, 20:08
                          1
                          • J JonB
                            24 Mar 2019, 18:47

                            @hskoglund

                            Hi, could the stop be due to a 2^32 wraparound? Because 4294967296 (2^32) microseconds is 4295 seconds.

                            It might have been nice if you'd quoted it in minutes, I had to go use calc! 71 minutes, and OP says it works for about an hour, then specifically 1:10, very good spot! But where do you think this happening? I can't see that QTimer stops working, the docs would say so....

                            @acs-sharp
                            Is there anything in your code which could be sensitive to this? You are 32-bit....
                            You said at the beginning:

                            Using Qt 5.8.0 on Genode, x86_32.

                            I know nothing, what is "Genode"? If it's some embedded system(??), does it have its own clock being leveraged by Qt which might wrap??

                            K Offline
                            K Offline
                            Kent-Dorfman
                            wrote on 24 Mar 2019, 21:32 last edited by
                            #17

                            @JonB said in QTimer seems to just stop:

                            I know nothing, what is "Genode"? If it's some embedded system(??), does it have its own clock being leveraged by Qt which might wrap??

                            I'm pretty sure this is what the OP was refering to...
                            https://en.wikipedia.org/wiki/Geode_(processor)

                            1 Reply Last reply
                            0
                            • H hskoglund
                              24 Mar 2019, 19:19

                              @JonB Google thinks it's from Germany https://www.genode-labs.com

                              About 32-bit overflows, actually the Qt docs mentions it can happen for QElapsedTimer

                              A Offline
                              A Offline
                              acs-sharp
                              wrote on 26 Mar 2019, 18:06 last edited by
                              #18

                              @hskoglund said in QTimer seems to just stop:

                              @JonB Google thinks it's from Germany https://www.genode-labs.com

                              About 32-bit overflows, actually the Qt docs mentions it can happen for QElapsedTimer

                              Aha! That's a really intriguing theory--with an obvious workaround to try.
                              I will pursue this, and report back here, hopefully with data useful to others.

                              Also, you have the right Genode: https://genode.org/
                              There is no actual OS as such underneath the application I'm debugging, just a seL4 microkernel and some peer components.

                              1 Reply Last reply
                              0
                              • J JonB
                                24 Mar 2019, 19:27

                                @acs-sharp
                                Right! In view of the above: At present you QTimer::start() and leave it to tick forever. Now, for a test, at some point before 71 minutes make your code stop that timer and completely restart it, or delete it and create a new one, or whatever. Do you no longer stop getting timeouts after 71 minutes? It's a workaround, if not a resolution :)

                                A Offline
                                A Offline
                                acs-sharp
                                wrote on 29 Mar 2019, 20:08 last edited by
                                #19

                                @JonB said in QTimer seems to just stop:

                                @acs-sharp
                                Right! In view of the above: At present you QTimer::start() and leave it to tick forever. Now, for a test, at some point before 71 minutes make your code stop that timer and completely restart it, or delete it and create a new one, or whatever. Do you no longer stop getting timeouts after 71 minutes? It's a workaround, if not a resolution :)

                                Good workaround discovered. Thanks to all who responded for your help on this!

                                Starting and stopping the QTimer did not help, nor did operating it in one-shot mode. However replacing it with a native periodic timer did prove to be a good workaround--it just emits a signal that is handled by the window. Experimentally, the gist of the QTimer-based code seems to work correctly in Linux, so I'm guessing the conjecture that the underlying clock source port has a limitation, e.g. counter word size, is most likely correct. I will take this up with the vendor anon.

                                1 Reply Last reply
                                1

                                14/19

                                24 Mar 2019, 18:47

                                • Login

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