|
dev
newsgroups
|
|||||||||||||||||||||||
|
|||||||||||||||||||||||
Unhandled Exception in Windows ServiceI need to know if the AppDomain.UnhandledException event can be handled using a Windows Service. I've create a Windows Service that uses the Exception Handling Applilcation Block and there are certain exceptoions that I want bubbled up as unhandled exceptions so in the Main method I add a method for handling Unhandled Exceptions. The code never seems to get hit. Doing some research, I remember that the UnhandledException event is specific to one app domain. When the ServiceBase.Run(ServiceBase[]) method is called, I am assuming each servicebase is created in its own app domain. So for kicks I added the UnhandledException assignment to both the service constructor and the OnStart method, neither of which seems to have worked either. Does this even work from a Windows Service? Please advise. Thanks, The Man From SQL Hi,
Thanks for your post! Yes, based on my test, the AppDomain.UnhandledException event is not called, if the exception is generated in Windows Service application. I suspect this is caused by special feature of Windows Service, I will perform some deeper research on it and try to find out the root cause. I will update you ASAP. Thanks. Best regards, Jeffrey Tan Microsoft Online Community Support ================================================== Get notification to my posts through email? Please refer to http://msdn.microsoft.com/subscriptions/managednewsgroups/default.aspx#notif ications. Note: The MSDN Managed Newsgroup support offering is for non-urgent issues where an initial response from the community or a Microsoft Support Engineer within 1 business day is acceptable. Please note that each follow up response may take approximately 2 business days as the support professional working with you may need further investigation to reach the most efficient resolution. The offering is not appropriate for situations that require urgent, real-time or phone-based interactions or complex project analysis and dump analysis issues. Issues of this nature are best handled working with a dedicated Microsoft Support Engineer by contacting Microsoft Customer Support Services (CSS) at http://msdn.microsoft.com/subscriptions/support/default.aspx. ================================================== This posting is provided "AS IS" with no warranties, and confers no rights. Jeffrey,
Thanks so much for your quick response. I look forward to any insights you can offer. TheManFromSQL Hi,
I still did not get any insight regarding this issue yet, I will try to give it a consulting with the CLR team. Thanks for your patient! Best regards, Jeffrey Tan Microsoft Online Community Support ================================================== Get notification to my posts through email? Please refer to http://msdn.microsoft.com/subscriptions/managednewsgroups/default.aspx#notif ications. Note: The MSDN Managed Newsgroup support offering is for non-urgent issues where an initial response from the community or a Microsoft Support Engineer within 1 business day is acceptable. Please note that each follow up response may take approximately 2 business days as the support professional working with you may need further investigation to reach the most efficient resolution. The offering is not appropriate for situations that require urgent, real-time or phone-based interactions or complex project analysis and dump analysis issues. Issues of this nature are best handled working with a dedicated Microsoft Support Engineer by contacting Microsoft Customer Support Services (CSS) at http://msdn.microsoft.com/subscriptions/support/default.aspx. ================================================== This posting is provided "AS IS" with no warranties, and confers no rights. Hi,
Sorry for letting you wait. I finally found out the root cause. The OnStop method of ServiceBase is triggerred by ServiceBase.DeferredStop method. Using Reflector, we can see the source code like this: private unsafe void DeferredStop() { fixed (NativeMethods.SERVICE_STATUS* service_statusRef1 = &this.status) { int num1 = this.status.currentState; this.status.checkPoint = 0; this.status.waitHint = 0; this.status.currentState = 3; NativeMethods.SetServiceStatus(this.statusHandle, service_statusRef1); try { this.OnStop(); this.WriteEventLogEntry(Res.GetString("StopSuccessful")); this.status.currentState = 1; NativeMethods.SetServiceStatus(this.statusHandle, service_statusRef1); } catch (StackOverflowException) { throw; } catch (OutOfMemoryException) { throw; } catch (ThreadAbortException) { throw; } catch (Exception exception1) { this.WriteEventLogEntry(Res.GetString("StopFailed", new object[] { exception1.ToString() }), EventLogEntryType.Error); this.status.currentState = num1; } } } As you can see, the DeferredStop method catched all the exceptions, so the exception in the OnStop method will not trigger our AppDomain.UnhandledException event. So was DeferredPause for OnPause method. Hope this helps. Best regards, Jeffrey Tan Microsoft Online Community Support ================================================== Get notification to my posts through email? Please refer to http://msdn.microsoft.com/subscriptions/managednewsgroups/default.aspx#notif ications. Note: The MSDN Managed Newsgroup support offering is for non-urgent issues where an initial response from the community or a Microsoft Support Engineer within 1 business day is acceptable. Please note that each follow up response may take approximately 2 business days as the support professional working with you may need further investigation to reach the most efficient resolution. The offering is not appropriate for situations that require urgent, real-time or phone-based interactions or complex project analysis and dump analysis issues. Issues of this nature are best handled working with a dedicated Microsoft Support Engineer by contacting Microsoft Customer Support Services (CSS) at http://msdn.microsoft.com/subscriptions/support/default.aspx. ================================================== This posting is provided "AS IS" with no warranties, and confers no rights. Hi Jeffrey,
Thanks so much for your diligence. This might answer my question after all. One more question: the exception I am encountering actually doesn't occur in the OnStop method or the OnShutDown method. It occurs in a thread pool thread spawned when my timer.elapsed event is called. Would the thread exception cause DeferredStop to be called? Thanks again for your help, TheManFromSql ""Jeffrey Tan[MSFT]"" wrote: Show quote > Hi, > > Sorry for letting you wait. > > I finally found out the root cause. The OnStop method of ServiceBase is > triggerred by ServiceBase.DeferredStop method. Using Reflector, we can see > the source code like this: > > private unsafe void DeferredStop() > { > fixed (NativeMethods.SERVICE_STATUS* service_statusRef1 = > &this.status) > { > int num1 = this.status.currentState; > this.status.checkPoint = 0; > this.status.waitHint = 0; > this.status.currentState = 3; > NativeMethods.SetServiceStatus(this.statusHandle, > service_statusRef1); > try > { > this.OnStop(); > this.WriteEventLogEntry(Res.GetString("StopSuccessful")); > this.status.currentState = 1; > NativeMethods.SetServiceStatus(this.statusHandle, > service_statusRef1); > } > catch (StackOverflowException) > { > throw; > } > catch (OutOfMemoryException) > { > throw; > } > catch (ThreadAbortException) > { > throw; > } > catch (Exception exception1) > { > this.WriteEventLogEntry(Res.GetString("StopFailed", new > object[] { exception1.ToString() }), EventLogEntryType.Error); > this.status.currentState = num1; > } > } > } > As you can see, the DeferredStop method catched all the exceptions, so the > exception in the OnStop method will not trigger our > AppDomain.UnhandledException event. So was DeferredPause for OnPause > method. > > Hope this helps. > > Best regards, > Jeffrey Tan > Microsoft Online Community Support > ================================================== > Get notification to my posts through email? Please refer to > http://msdn.microsoft.com/subscriptions/managednewsgroups/default.aspx#notif > ications. > > Note: The MSDN Managed Newsgroup support offering is for non-urgent issues > where an initial response from the community or a Microsoft Support > Engineer within 1 business day is acceptable. Please note that each follow > up response may take approximately 2 business days as the support > professional working with you may need further investigation to reach the > most efficient resolution. The offering is not appropriate for situations > that require urgent, real-time or phone-based interactions or complex > project analysis and dump analysis issues. Issues of this nature are best > handled working with a dedicated Microsoft Support Engineer by contacting > Microsoft Customer Support Services (CSS) at > http://msdn.microsoft.com/subscriptions/support/default.aspx. > ================================================== > This posting is provided "AS IS" with no warranties, and confers no rights. > > Hi,
I assume you are using System.Timers.Timer component. In this component, Timer.Elapsed event is triggered by System.Timers.Timer.MyTimerCallback method. It is this method that catches all the exceptions, below is the source code comes from Reflector: private void MyTimerCallback(object state) { if (state == this.cookie) { if (!this.autoReset) { this.enabled = false; } Timer.FILE_TIME file_time1 = new Timer.FILE_TIME(); Timer.GetSystemTimeAsFileTime(ref file_time1); ElapsedEventArgs args1 = new ElapsedEventArgs(file_time1.ftTimeLow, file_time1.ftTimeHigh); try { if (this.onIntervalElapsed != null) { if ((this.SynchronizingObject != null) && this.SynchronizingObject.InvokeRequired) { this.SynchronizingObject.BeginInvoke(this.onIntervalElapsed, new object[] { this, args1 }); } else { this.onIntervalElapsed(this, args1); } } } catch (Exception) { } } } So AppDomain.UnhandledException is not fired at all. Hope this helps. Best regards, Jeffrey Tan Microsoft Online Community Support ================================================== Get notification to my posts through email? Please refer to http://msdn.microsoft.com/subscriptions/managednewsgroups/default.aspx#notif ications. Note: The MSDN Managed Newsgroup support offering is for non-urgent issues where an initial response from the community or a Microsoft Support Engineer within 1 business day is acceptable. Please note that each follow up response may take approximately 2 business days as the support professional working with you may need further investigation to reach the most efficient resolution. The offering is not appropriate for situations that require urgent, real-time or phone-based interactions or complex project analysis and dump analysis issues. Issues of this nature are best handled working with a dedicated Microsoft Support Engineer by contacting Microsoft Customer Support Services (CSS) at http://msdn.microsoft.com/subscriptions/support/default.aspx. ================================================== This posting is provided "AS IS" with no warranties, and confers no rights. Jeffrey,
That does answer my question fully, yes. Thanks again for your help. ""Jeffrey Tan[MSFT]"" wrote: Show quote > Hi, > > I assume you are using System.Timers.Timer component. In this component, > Timer.Elapsed event is triggered by System.Timers.Timer.MyTimerCallback > method. It is this method that catches all the exceptions, below is the > source code comes from Reflector: > > private void MyTimerCallback(object state) > { > if (state == this.cookie) > { > if (!this.autoReset) > { > this.enabled = false; > } > Timer.FILE_TIME file_time1 = new Timer.FILE_TIME(); > Timer.GetSystemTimeAsFileTime(ref file_time1); > ElapsedEventArgs args1 = new > ElapsedEventArgs(file_time1.ftTimeLow, file_time1.ftTimeHigh); > try > { > if (this.onIntervalElapsed != null) > { > if ((this.SynchronizingObject != null) && > this.SynchronizingObject.InvokeRequired) > { > > this.SynchronizingObject.BeginInvoke(this.onIntervalElapsed, new object[] { > this, args1 }); > } > else > { > this.onIntervalElapsed(this, args1); > } > } > } > catch (Exception) > { > } > } > } > So AppDomain.UnhandledException is not fired at all. > > Hope this helps. > > Best regards, > Jeffrey Tan > Microsoft Online Community Support > ================================================== > Get notification to my posts through email? Please refer to > http://msdn.microsoft.com/subscriptions/managednewsgroups/default.aspx#notif > ications. > > Note: The MSDN Managed Newsgroup support offering is for non-urgent issues > where an initial response from the community or a Microsoft Support > Engineer within 1 business day is acceptable. Please note that each follow > up response may take approximately 2 business days as the support > professional working with you may need further investigation to reach the > most efficient resolution. The offering is not appropriate for situations > that require urgent, real-time or phone-based interactions or complex > project analysis and dump analysis issues. Issues of this nature are best > handled working with a dedicated Microsoft Support Engineer by contacting > Microsoft Customer Support Services (CSS) at > http://msdn.microsoft.com/subscriptions/support/default.aspx. > ================================================== > This posting is provided "AS IS" with no warranties, and confers no rights. > > Hi Jeffery,
I had exactly the same question. I tried to follow along but found that when I used reflector the code that I reviewed looks like it does in deed throw the caught exception. I am reflecting on v2.0.50727. Most likely code has changed from previous revision. Either way I'm still not receiving the event for AppDomain.CurrentDomain.UnhandledException. I am registering for the event in the constructor of the service. Thanks for your help, Terry private unsafe void DeferredStop() { fixed (NativeMethods.SERVICE_STATUS* service_statusRef1 = &this.status) { int num1 = this.status.currentState; this.status.checkPoint = 0; this.status.waitHint = 0; this.status.currentState = 3; NativeMethods.SetServiceStatus(this.statusHandle, service_statusRef1); try { this.OnStop(); this.WriteEventLogEntry(Res.GetString("StopSuccessful")); this.status.currentState = 1; NativeMethods.SetServiceStatus(this.statusHandle, service_statusRef1); if (this.isServiceHosted) { try { AppDomain.Unload(AppDomain.CurrentDomain); } catch (CannotUnloadAppDomainException exception1) { this.WriteEventLogEntry(Res.GetString("FailedToUnloadAppDomain", new object[] { AppDomain.CurrentDomain.FriendlyName, exception1.Message }), EventLogEntryType.Error); } } } catch (Exception exception2) { this.status.currentState = num1; NativeMethods.SetServiceStatus(this.statusHandle, service_statusRef1); this.WriteEventLogEntry(Res.GetString("StopFailed", new object[] { exception2.ToString() }), EventLogEntryType.Error); throw; } catch { this.status.currentState = num1; NativeMethods.SetServiceStatus(this.statusHandle, service_statusRef1); this.WriteEventLogEntry(Res.GetString("StopFailed", new object[] { string.Empty }), EventLogEntryType.Error); throw; } } } |
|||||||||||||||||||||||