简体   繁体   中英

How to ensure saving of application state on crash c#

I am very new to c# programming, so that in mind:

I have an in-memory data object with data I need to save the information when(if) my application were to crash OR closed. Is there a way to do this deterministically or reliably?

I have been looking at destructors

~MyObjectName(){}

finalizers and Dispose(),

but as far as I understand none of these will do reliably what I want?

Currently I am using the destructor, and it works when I am closing the program, but this doesn't mean it will work on crashing, or always.

Should I be looking at events as well?

There is no 100% reliable mechanism that you can use to save data (or do anything else for that matter) when a process (any process, not just a .Net process) terminates - most processes can be terminated at any point using the "End Process" option in the task manager, when this happens the process is immediately killed. As a more extreme example the power cord could be pulled out the back of the machine.

If its not 100% necessary that this data object be up-to-date and saved once the process is killed then the AppDomain.UnhandledException Event may suffice.

If its absolutely 100% necessary that this be the case then you need to be continuously saving this information as the process is running - there is absolutely no guarentee that you will get a chance to do it at a later date. This is how databases operate, no transaction returns until some record of the change has been recorded to disk in some format (eg a transaction log). This is what the D stands for in ACID .

I believe you are looking for catching unhandled exceptions? something like this:

static void Main()
{
  Application.EnableVisualStyles();
  Application.SetCompatibleTextRenderingDefault(false);

  Application.ThreadException += new ThreadExceptionEventHandler(Application_ThreadException);
  AppDomain.CurrentDomain.UnhandledException += new UnhandledExceptionEventHandler(CurrentDomain_UnhandledException);

  Application.Run(new Form1());
}

static void Application_ThreadException(object sender, ThreadExceptionEventArgs e)
{
  MessageBox.Show(e.Exception.Message, "Unhandled Thread Exception");
  // here you can log the exception ...
}

static void CurrentDomain_UnhandledException(object sender, UnhandledExceptionEventArgs e)
{
  MessageBox.Show((e.ExceptionObject as Exception).Message, "Unhandled UI Exception");
  // here you can log the exception ...
}

This example shows how to manage all exceptions that haven't been caught in the try-catch sections (in Windows Forms application).

The UnhandledException event handles uncaught exceptions thrown from the main UI thread. The ThreadException event handles uncaught exceptions thrown from non-UI threads.

You can achieve this with windbg.

  1. Keep a breakpoint in zwterminateprocess method in windbg. This method will be called when your application exits.
  2. when the breakpoint is reached , use !dumpheap -type MyObjectName to get the address of your object
  3. Use !dumpobject "address of MyObjectName" to know the values inside the object

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM