Multi-threaded (TThread) Delphi Application Will Not End

I wrote an application (using Delphi 2009) that allows the user to select a series of queries that can run on different systems. To allow simultaneous execution of queries, each query is launched in its thread using the TADOQuery object. It all works great.

The problem I am facing is trying to close the application while the request is still running (and therefore a separate thread is active). When I create each thread, I write the THandle stream to an array. When I try to close the application, if any threads are still running, I retrieve the handle of the thread and pass it to TerminateThread, which theoretically terminates the thread and allows you to close the application. However, this does not happen. The main form onClose event is fired, and it looks like the application is closing, but the process remains active, and the Delphi interface looks as if the application is still running (ie, the Run button is greyed out, debug view is active, etc. ) I don't get control back to Delphi until I finish manually (either Ctrl-F2 in Delphi, or through the task manager).

I use TerminateThread because the request can take a lot of time (several minutes when we are dealing with millions of records that are quite possible in the final user environment) and during operation, if I'm not mistaken, the thread will not be able to check the Terminated property and therefore, it won’t be able to finish itself if it was set to True until the request returns, so I cannot end the stream in the usual way (i.e. by checking the Terminated property). It may happen that the user wants to exit the application during the execution of a large request, and in this case I need the application to stop immediately (i.e. all running threads stopped immediately), and not force them to wait until all requests have finished starting , so TerminateThread would be ideal, but in fact it did not finish the thread!

Can anyone help here? Does anyone know why TerminateThread is not working correctly? Could someone suggest something to make threads executing large ADO requests stop immediately?

Thank you for your help!

+6
multithreading delphi ado
source share
3 answers

You should be able to cancel the ADO request by attaching the OnFetchProgress event and setting the Eventstatus parameter to esCancel. This should cause your request to complete and allow the thread to close the grace without resorting to using TerminateThread.

+8
source share

Instead of using threads with TADOQuery, perhaps you should consider using the asynchronous ADO options.

ADOQuery1.ExecuteOptions := [eoAsyncExecute, eoAsyncFetch, eoAsyncFetch]; 

Then, when your application closes, you can call:

 ADOQuery1.cancel; 
+6
source share

As you can read in msdn using TerminateThread is dangerous.

TerminateThread is a dangerous function that should only be used in the most extreme cases. You should call TerminateThread only if you know exactly what the target thread is and you control all the code so that the target thread can be started at the time of termination.

But it is also very effective in destroying threads. Are you sure you are right in your conclusions? Maybe the thread is killed, but another thread is still working? Maybe your pens are not pens? Could you show us some code? Or even better: a small working example that we could try for ourselves?

+5
source share

All Articles