Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • World
  • Users
  • Groups
Skins
  • Light
  • Cerulean
  • Cosmo
  • Flatly
  • Journal
  • Litera
  • Lumen
  • Lux
  • Materia
  • Minty
  • Morph
  • Pulse
  • Sandstone
  • Simplex
  • Sketchy
  • Spacelab
  • United
  • Yeti
  • Zephyr
  • Dark
  • Cyborg
  • Darkly
  • Quartz
  • Slate
  • Solar
  • Superhero
  • Vapor

  • Default (No Skin)
  • No Skin
Collapse
Code Project
  1. Home
  2. General Programming
  3. C#
  4. Timer trouble -timer "dies"

Timer trouble -timer "dies"

Scheduled Pinned Locked Moved C#
questiondatabasedebuggingperformancehelp
8 Posts 4 Posters 0 Views 1 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.
  • E Offline
    E Offline
    EnkelIk
    wrote on last edited by
    #1

    Hi all. I have a implemented a Window Service which includes a timer. The timer "ticks" every five minutes, and writes an entry to a database plus enters a line into an eventlog. Unfortunatelly this timer does not seem fully reliable as the service occasionally just stop writing to both the database and the eventlog. Sometimes this happens when it has been running for just a few hours, other times when it has been going for several days. Is there a known limitation in timers? Or is there some internal or external event that might cause the timer to stop? Since the timer does not 'die' at the same tick each time it is very hard to try to debug or something. The code snippets below is pretty straight forward, I hope you can follow it and that it may give you some clue as to what is going wrong here. Do you think it would help to implement a second timer that executes say every ten hours, which creates a new instance of the first timer? That of course would leave me at the mercy of the second timer and in the case where an external event causes the first timer to stop it will most certainly also cause the second timer to stop... Thanks /EnkelIk public class MyService : System.ServiceProcess.ServiceBase { private Timer vscTimer=null; public MyService() { // This call is required by the Windows.Forms Component Designer. InitializeComponent(); //Create eventlog if(!System.Diagnostics.EventLog.SourceExists("MyServiceLogSource")) System.Diagnostics.EventLog.CreateEventSource("MyServiceLogSource","MyServiceLog"); eventLog.Source = "MyServiceLogSource"; eventLog.Log="MyServiceLog"; double interval=300000; vscTimer = new Timer(interval); vscTimer.Elapsed += new ElapsedEventHandler( this.ServiceTimer_Tick ); } ... [ Auto generated code for initializing and disposing process ] ... /// /// Set things in motion so your service can do its work. /// protected override void OnStart(string[] args) { //Start timer vscTimer.AutoReset=true; vscTimer.Enabled=true; vscTimer.Start(); } private void ServiceTimer_Tick(object sender, System.Timers.ElapsedEventArgs e) { this.vscTimer.Stop(); eventLog.WriteEntry("Timer event!"); [Write to database] //Tried to do something about the huge memory consumption... GC.Collect(); //Restart timer this.vscTimer.Start(); } }

    L H 2 Replies Last reply
    0
    • E EnkelIk

      Hi all. I have a implemented a Window Service which includes a timer. The timer "ticks" every five minutes, and writes an entry to a database plus enters a line into an eventlog. Unfortunatelly this timer does not seem fully reliable as the service occasionally just stop writing to both the database and the eventlog. Sometimes this happens when it has been running for just a few hours, other times when it has been going for several days. Is there a known limitation in timers? Or is there some internal or external event that might cause the timer to stop? Since the timer does not 'die' at the same tick each time it is very hard to try to debug or something. The code snippets below is pretty straight forward, I hope you can follow it and that it may give you some clue as to what is going wrong here. Do you think it would help to implement a second timer that executes say every ten hours, which creates a new instance of the first timer? That of course would leave me at the mercy of the second timer and in the case where an external event causes the first timer to stop it will most certainly also cause the second timer to stop... Thanks /EnkelIk public class MyService : System.ServiceProcess.ServiceBase { private Timer vscTimer=null; public MyService() { // This call is required by the Windows.Forms Component Designer. InitializeComponent(); //Create eventlog if(!System.Diagnostics.EventLog.SourceExists("MyServiceLogSource")) System.Diagnostics.EventLog.CreateEventSource("MyServiceLogSource","MyServiceLog"); eventLog.Source = "MyServiceLogSource"; eventLog.Log="MyServiceLog"; double interval=300000; vscTimer = new Timer(interval); vscTimer.Elapsed += new ElapsedEventHandler( this.ServiceTimer_Tick ); } ... [ Auto generated code for initializing and disposing process ] ... /// /// Set things in motion so your service can do its work. /// protected override void OnStart(string[] args) { //Start timer vscTimer.AutoReset=true; vscTimer.Enabled=true; vscTimer.Start(); } private void ServiceTimer_Tick(object sender, System.Timers.ElapsedEventArgs e) { this.vscTimer.Stop(); eventLog.WriteEntry("Timer event!"); [Write to database] //Tried to do something about the huge memory consumption... GC.Collect(); //Restart timer this.vscTimer.Start(); } }

      L Offline
      L Offline
      Lost User
      wrote on last edited by
      #2

      Dear EnkelIk, i have the same broblem with dieing the timers so you should use the timer of threading try System.Threading.Timer this class is beter that the standered one you can create it by using call back function it is good one so try it Mhmoud Rawas ------------ Software Eng.

      E 1 Reply Last reply
      0
      • E EnkelIk

        Hi all. I have a implemented a Window Service which includes a timer. The timer "ticks" every five minutes, and writes an entry to a database plus enters a line into an eventlog. Unfortunatelly this timer does not seem fully reliable as the service occasionally just stop writing to both the database and the eventlog. Sometimes this happens when it has been running for just a few hours, other times when it has been going for several days. Is there a known limitation in timers? Or is there some internal or external event that might cause the timer to stop? Since the timer does not 'die' at the same tick each time it is very hard to try to debug or something. The code snippets below is pretty straight forward, I hope you can follow it and that it may give you some clue as to what is going wrong here. Do you think it would help to implement a second timer that executes say every ten hours, which creates a new instance of the first timer? That of course would leave me at the mercy of the second timer and in the case where an external event causes the first timer to stop it will most certainly also cause the second timer to stop... Thanks /EnkelIk public class MyService : System.ServiceProcess.ServiceBase { private Timer vscTimer=null; public MyService() { // This call is required by the Windows.Forms Component Designer. InitializeComponent(); //Create eventlog if(!System.Diagnostics.EventLog.SourceExists("MyServiceLogSource")) System.Diagnostics.EventLog.CreateEventSource("MyServiceLogSource","MyServiceLog"); eventLog.Source = "MyServiceLogSource"; eventLog.Log="MyServiceLog"; double interval=300000; vscTimer = new Timer(interval); vscTimer.Elapsed += new ElapsedEventHandler( this.ServiceTimer_Tick ); } ... [ Auto generated code for initializing and disposing process ] ... /// /// Set things in motion so your service can do its work. /// protected override void OnStart(string[] args) { //Start timer vscTimer.AutoReset=true; vscTimer.Enabled=true; vscTimer.Start(); } private void ServiceTimer_Tick(object sender, System.Timers.ElapsedEventArgs e) { this.vscTimer.Stop(); eventLog.WriteEntry("Timer event!"); [Write to database] //Tried to do something about the huge memory consumption... GC.Collect(); //Restart timer this.vscTimer.Start(); } }

        H Offline
        H Offline
        Heath Stewart
        wrote on last edited by
        #3

        Several things: if you read the documentation for Start and Stop, they are exactly the same as passing true and false to the Timer.Enabled property, respectively. Don't do both because it's a waste of CPU time. Second, it is recommended that you don't use GC.Collect. Instead, dispose of the objects in your "[Write to database]" block that implement IDisposable. Finally: exception handling and stopping / starting timers. What's probably happening is that since you're stopping the timer, writing to the event log, and then performing database functions - which can be volatile - and then starting the timer again, if an exception were to be thrown your time would not be started again! Instead, put your database calls in a try-catch and gracefully catch all exceptions, or add this.vscTimer.Start() to a finally block of a try-catch-finally or try-finally (exceptions are still thrown in the latter block, but finally is always executed regardless of success. You should also enable auto-logging on the Windows Service by setting ServiceBase.AutoLog to true (of course, your service inherits ServiceBase, so you can set this property on yourself, too). One more option: don't stop the timer! If you don't stop it, even if the database code throws an exception, the timer will keep running. Besides, lets say all the database code takes 2 seconds and you run this code every 10 minutes. That means that you're shifting time about 4.8 minutes per day! Just let it run, man! :)

        -----BEGIN GEEK CODE BLOCK----- Version: 3.21 GCS/G/MU d- s: a- C++++ UL@ P++(+++) L+(--) E--- W+++ N++ o+ K? w++++ O- M(+) V? PS-- PE Y++ PGP++ t++@ 5 X+++ R+@ tv+ b(-)>b++ DI++++ D+ G e++>+++ h---* r+++ y+++ -----END GEEK CODE BLOCK-----

        X E 2 Replies Last reply
        0
        • H Heath Stewart

          Several things: if you read the documentation for Start and Stop, they are exactly the same as passing true and false to the Timer.Enabled property, respectively. Don't do both because it's a waste of CPU time. Second, it is recommended that you don't use GC.Collect. Instead, dispose of the objects in your "[Write to database]" block that implement IDisposable. Finally: exception handling and stopping / starting timers. What's probably happening is that since you're stopping the timer, writing to the event log, and then performing database functions - which can be volatile - and then starting the timer again, if an exception were to be thrown your time would not be started again! Instead, put your database calls in a try-catch and gracefully catch all exceptions, or add this.vscTimer.Start() to a finally block of a try-catch-finally or try-finally (exceptions are still thrown in the latter block, but finally is always executed regardless of success. You should also enable auto-logging on the Windows Service by setting ServiceBase.AutoLog to true (of course, your service inherits ServiceBase, so you can set this property on yourself, too). One more option: don't stop the timer! If you don't stop it, even if the database code throws an exception, the timer will keep running. Besides, lets say all the database code takes 2 seconds and you run this code every 10 minutes. That means that you're shifting time about 4.8 minutes per day! Just let it run, man! :)

          -----BEGIN GEEK CODE BLOCK----- Version: 3.21 GCS/G/MU d- s: a- C++++ UL@ P++(+++) L+(--) E--- W+++ N++ o+ K? w++++ O- M(+) V? PS-- PE Y++ PGP++ t++@ 5 X+++ R+@ tv+ b(-)>b++ DI++++ D+ G e++>+++ h---* r+++ y+++ -----END GEEK CODE BLOCK-----

          X Offline
          X Offline
          Xiangyang Liu
          wrote on last edited by
          #4

          Heath, I haven't seen the code that causes this problme so I may not be making any sense here. Feel free to use your vast reserves of knowledge to correct me. ;) The .NET timer class uses the .NET built-in thread pool to execute the timer callback function. The .NET built-in thread pool has a maximum of 25 threads as the default limit. If the timer callback function got stuck (with some database operations, for example) for longer than the timer interval (5 minutes in this case), the timer callback function will be invoked by a new thread from the thread pool. If this new thread got stuck again, then another new thread from the thread pool will be used. Anyway, under some conditions, the timer can exaust all 25 threads from the thread pool. I have posted a simple example in a message after my article Creating Your Own Thread Pool In .NET[^] to demonstrate this. If there is no easy way to figure out what caused the timer callback to stuck, then the solution may be not using the .NET timer class at all or restarting the applcation when too many threads are being used to handle the timer event.[

          My articles and software tools

          ](http://hometown.aol.com/XiangYangL/)

          H 1 Reply Last reply
          0
          • X Xiangyang Liu

            Heath, I haven't seen the code that causes this problme so I may not be making any sense here. Feel free to use your vast reserves of knowledge to correct me. ;) The .NET timer class uses the .NET built-in thread pool to execute the timer callback function. The .NET built-in thread pool has a maximum of 25 threads as the default limit. If the timer callback function got stuck (with some database operations, for example) for longer than the timer interval (5 minutes in this case), the timer callback function will be invoked by a new thread from the thread pool. If this new thread got stuck again, then another new thread from the thread pool will be used. Anyway, under some conditions, the timer can exaust all 25 threads from the thread pool. I have posted a simple example in a message after my article Creating Your Own Thread Pool In .NET[^] to demonstrate this. If there is no easy way to figure out what caused the timer callback to stuck, then the solution may be not using the .NET timer class at all or restarting the applcation when too many threads are being used to handle the timer event.[

            My articles and software tools

            ](http://hometown.aol.com/XiangYangL/)

            H Offline
            H Offline
            Heath Stewart
            wrote on last edited by
            #5

            Thanks, but I don't think that was his problem. His Elapsed handler stopped the timer, ran some database code, then started the timer again after the database code completed. The database code was not wrapped in a try-catch block and if any exceptions where thrown, the timer would not be restarted. Or am I missing your point? BTW, I've read your article and found it very interesting. Good job!

            -----BEGIN GEEK CODE BLOCK----- Version: 3.21 GCS/G/MU d- s: a- C++++ UL@ P++(+++) L+(--) E--- W+++ N++ o+ K? w++++ O- M(+) V? PS-- PE Y++ PGP++ t++@ 5 X+++ R+@ tv+ b(-)>b++ DI++++ D+ G e++>+++ h---* r+++ y+++ -----END GEEK CODE BLOCK-----

            X 1 Reply Last reply
            0
            • H Heath Stewart

              Thanks, but I don't think that was his problem. His Elapsed handler stopped the timer, ran some database code, then started the timer again after the database code completed. The database code was not wrapped in a try-catch block and if any exceptions where thrown, the timer would not be restarted. Or am I missing your point? BTW, I've read your article and found it very interesting. Good job!

              -----BEGIN GEEK CODE BLOCK----- Version: 3.21 GCS/G/MU d- s: a- C++++ UL@ P++(+++) L+(--) E--- W+++ N++ o+ K? w++++ O- M(+) V? PS-- PE Y++ PGP++ t++@ 5 X+++ R+@ tv+ b(-)>b++ DI++++ D+ G e++>+++ h---* r+++ y+++ -----END GEEK CODE BLOCK-----

              X Offline
              X Offline
              Xiangyang Liu
              wrote on last edited by
              #6

              Heath Stewart wrote: Thanks, but I don't think that was his problem. You are right again. I wasn't reading the code in his post carefully. :-O Thanks.[

              My articles and software tools

              ](http://hometown.aol.com/XiangYangL/)

              1 Reply Last reply
              0
              • L Lost User

                Dear EnkelIk, i have the same broblem with dieing the timers so you should use the timer of threading try System.Threading.Timer this class is beter that the standered one you can create it by using call back function it is good one so try it Mhmoud Rawas ------------ Software Eng.

                E Offline
                E Offline
                EnkelIk
                wrote on last edited by
                #7

                Thanks. Using System.Threading.Timer plus improved error handling (try-catch) my service seems much more stable than before. Again, THANKS! /EnkelIk

                1 Reply Last reply
                0
                • H Heath Stewart

                  Several things: if you read the documentation for Start and Stop, they are exactly the same as passing true and false to the Timer.Enabled property, respectively. Don't do both because it's a waste of CPU time. Second, it is recommended that you don't use GC.Collect. Instead, dispose of the objects in your "[Write to database]" block that implement IDisposable. Finally: exception handling and stopping / starting timers. What's probably happening is that since you're stopping the timer, writing to the event log, and then performing database functions - which can be volatile - and then starting the timer again, if an exception were to be thrown your time would not be started again! Instead, put your database calls in a try-catch and gracefully catch all exceptions, or add this.vscTimer.Start() to a finally block of a try-catch-finally or try-finally (exceptions are still thrown in the latter block, but finally is always executed regardless of success. You should also enable auto-logging on the Windows Service by setting ServiceBase.AutoLog to true (of course, your service inherits ServiceBase, so you can set this property on yourself, too). One more option: don't stop the timer! If you don't stop it, even if the database code throws an exception, the timer will keep running. Besides, lets say all the database code takes 2 seconds and you run this code every 10 minutes. That means that you're shifting time about 4.8 minutes per day! Just let it run, man! :)

                  -----BEGIN GEEK CODE BLOCK----- Version: 3.21 GCS/G/MU d- s: a- C++++ UL@ P++(+++) L+(--) E--- W+++ N++ o+ K? w++++ O- M(+) V? PS-- PE Y++ PGP++ t++@ 5 X+++ R+@ tv+ b(-)>b++ DI++++ D+ G e++>+++ h---* r+++ y+++ -----END GEEK CODE BLOCK-----

                  E Offline
                  E Offline
                  EnkelIk
                  wrote on last edited by
                  #8

                  Thanks. Using System.Threading.Timer plus improved error handling (try-catch) my service seems much more stable than before. It's quite true that I have no need to stop and start the timer (even when not using the Threading timer), don't know why I got that idea. I have also with interest read Xiangyang Liu's article but I don't think that will be any serious and frequent problem in my case. Again, THANKS! /EnkelIk

                  1 Reply Last reply
                  0
                  Reply
                  • Reply as topic
                  Log in to reply
                  • Oldest to Newest
                  • Newest to Oldest
                  • Most Votes


                  • Login

                  • Don't have an account? Register

                  • Login or register to search.
                  • First post
                    Last post
                  0
                  • Categories
                  • Recent
                  • Tags
                  • Popular
                  • World
                  • Users
                  • Groups