I am creating numerous threads on-the-fly in Delphi 2.0. I create them suspended. The question is: How do I make the threads go away? I’ve tried Free, Terminate… nothing seems to work. The threads are simple. The Execute procedure is only three lines:
As it is now, I can’t kill a thread that’s sleeping. If I set its Terminate property to True, the thread will fall out of the Execute procedure once it has stopped sleeping, but I want to be able to kill the thing outright! If I call the Free method, I get a thread exception complaining something about the Main VCL being inSleep(some amount of time)if not Terminated then DoSomething
WaitFor (can’t recall the exact details, but that seems close!).
Here’s my application:
A user launches this application to digitize a video clip from a videotape to a digital device. As a by-product of digitizing, this application allows the user to apply “Chyrons” (a trade name for a character generator) auto-magically without user-assistance. When the user hits the big red “GO” button, all of these threads are created as suspended. (I’m leaving out the part where the programs fetches the events, and that’s where the program knows how long to make each thread sleep ? the offset from the beginning of the clip until the event occurs.)
Once the tape machine has pre-rolled and begun to roll forward, it will eventually pass the “in-point,” at which time the application places the digital box into record and then resumes all the sleeping threads. They sleep for the appropriate amount of time and then, after the sleep expires, a machine control event is stuffed out of a COM port. The threads are set to
FreeOnTerminate so that’s what they do next.
Here’s the problem: If the user hits the ABORT key (for whatever reason) the application has to toss all those threads away. If they’re in the middle of digitizing, none of the threads are suspended and some of them may have already executed. The ones that are left are all alive now, just counting down. Obviously, it won’t do to have these unwanted events ocurring, so I want to be able to tell those now unwanted threads to go away ? completely.
Right now, I’ve had to insert an “if not terminated then” statement after the sleep statement to keep it from sending things out of the COM port. Not too elegant! There are a ton of threads left hanging around until the sleep statement expires. And as you can imagine, these are sort of time-critical events. I really don’t want to have to perform ANY checking in the execute procedure, but right now it seems that I have to. Add to this that when the user hits the big red button again, all those threads are created again! (It’s obviously all dynamic. The program doesn’t know or care how many events there are. It just happily spins off a thread and doesn’t have to deal with it after that unless the user aborts in mid-run.)
Soooo…. is there a way to kill a sleeping thread? (I guess that’s the bottom line, eh?!)
Thanks for the very complete explanation of your program. Here’s my suggestion:
First of all, don’t create the threads in a suspended state, since they can’t receive messages in this state. What I would do instead is allow the threads to enter their Execute procedure. But, at the top, put a looping mechanism that checks a global Boolean value that says whether to proceed or not. Within the loop, you’ll also check another global Boolean flag that indicates an abort by the user. If that flag becomes true, you exit out of the thread entirely.
Granted, you’ll probably have to play with this. You might also check using a semaphore or mutex. In any case, I think that a looping structure is probably your best bet to approaching this problem.