Delphi - What happens to a non-running (but terminated) thread when an application exits?

I have a multi-threaded application, and I have a little problem when the application ends: I can terminate the thread correctly by calling the TThread.Terminate method in the TThread.Terminate event handler, but it takes some time to complete, and therefore I can’t free up memory ( by the TThread.Free method TThread.Free ) Unfortunately, for some other reason, I must have the TThread.FreeOnTerminate property TThread.FreeOnTerminate to false, so the thread object will not be automatically destroyed after the thread finishes.

My question is probably a little silly, and I should have known this for a long time, but is this normal and the thread will be destroyed automatically (since the application just ends), or is it a problem and the memory will be “lost”? Thanks so much for the explanation.

+4
source share
5 answers

You must wait for the thread to complete before starting the process by shutting down the rest of your application, otherwise shared resources may be released under your feet, which can lead to a series of access violations. After you wait for the thread to complete, you can free it. In fact, this is what the TThread destructor TThread for you.

If there are no shared resources, then I am sure that he will die on his own. Even if a thread terminates after the main thread, all that is required is that all your threads terminate to complete the program. Any memory associated with the stream object will simply be cleared and returned to the OS with everything else.

BUT , be careful! If your thread takes some time to exit, it can cause the zombie process to sit without a graphical interface. This is why it is very important to frequently check the Terminated flag in the flow path and exit the flow.

N @

+6
source

Your question is not stupid or simple - read the MSDN article . In general, if you want to be safe, you better wait until the background thread completes before exiting the application.

+3
source

When the process ends, the OS will return all the allocated memory and close all open descriptors. You do not need to worry about MEMORY *), which occurs in the special case of closing the application. OS will also close all your open handles **), at least theoretically. All that has been taken into account may be safe for you to simply terminate your thread (using TerminateThread (MyThread.Handle) ) from your form destructor before destroying other shared resources. Ask yourself the following questions:

  • What does a stream do? Is it safe to terminate it at any time? Example. If a stream writes to disk, it is unsafe to simply kill it, because you can write files to disk in an inconsistent state.
  • Are you using any resources that are not automatically released by Windows? Can't come up with a good example here ...

If you are safe with both, you can use TerminateThread and not wait for the thread to terminate naturally. A safer approach can be combined, perhaps you should give the thread the chance to naturally terminate, and if it does not exit in 5 seconds, force it to stop.

*) I'm talking about memory, you can only prove a leak at the end of the process, for example, a leak that you kill, preventing them from closing correctly or global singleton classes that you are not freeing. All other unaccounted memory must be tracked and corrected, because this is an error.

**) Unfortunately, Windows is not an error. Example. Anyone who has been working with serial devices on the Windows platform knows how easy it is to get a serial device in a “locked” state, requiring a reboot so that it works again. Technically, this is also Handle, which completes the processing of the application that blocked it, should unlock it.

0
source

Eventually, the thread will end and Windows will clear the remaining memory. However, you can just wait for the thread to finish, because that is exactly what Windows will do anyway. Perhaps your application has shut down because all windows can be closed / hidden, but the application process will not be completed until all threads have ended ...

0
source

why don’t you increase the variable when creating the stream, but on the destroy event, wait until the stream ends, reduce the value of the variable and just execute Application.processmessages on applicationterminate?

why is your thread not freeonterminate = true? all shared resources can be processed in a critical section.

Best wishes,

0
source

Source: https://habr.com/ru/post/1315156/


All Articles