🚀 go-pugleaf

RetroBBS NetNews Server

Inspired by RockSolid Light RIP Retro Guy

Article View: borland.public.cppbuilder.nativeapi
Article #22

Re: Multi-threading...

#22
From: Bob Gonder
Date: Sun, 20 Jul 2008 17:02
96 lines
3386 bytes
Carl Danley wrote:

>DWORD WINAPI Thread2(LPVOID Param)
>{
> //code here
> ShowMessage("test2");
> //terminate Thread
> TerminateThread(Thread, false);
> return 0;
>}

<Help>
TerminateThread is a dangerous function that should
only be used in the most extreme cases.</Help>

TerminateThread is used OUTSIDE the thread to terminate it with prejudice.
You should never ever use it inside the thread.
ExitThread() or just plain return 0 are sufficient.

> Thread = CreateThread(0, 0, ThreadA, Form1->Handle, CREATE_SUSPENDED, &Id);

The error you are getting is from the threads having
the Form1 handle, but Form1 going away before they do.
Your Form1 should be waiting for these threads
to terminate before self destructing.

BOOL Terminating;

void SomeStartupFunc(void)
{
	Terminating = FALSE;
	Thread1 = CreateThread(...);
	Thread2 = CreateThread(...);
}
void _fastcall Form1::OnClose(...)
{
	Terminating = TRUE;
	if( WAIT_FAILED == WaitforSingleObject(Thread1,2000) )
		TerminateThread(Thread1,0);
	CloseHandle(Thread1);
	if( WAIT_FAILED == WaitforSingleObject(Thread2,100) )
		TerminateThread(Thread2,0);
	CloseHandle(Thread2);
}
DWORD Thread1(...)
{
	while( ! Terminating )
	{
	};
	{ Close any open resources. };
	return 0;
}
The trick then comes in the thread.
It must not be in a hard-wait.
If it is in a wait, it can be perhaps up
to half of the 2000 specified in the OnClose.

Another trick, is if the thread is using WaitFor...()
you can CreateEvent and have the thread
WaitForMultipleObjects, including the new event.

BOOL	Terminating;
HANDLE	TerminatingEvent;

void SomeStartupFunc(void)
{
	Terminating = FALSE;
	TerminatingEvent = CreateEvent(0,TRUE,FALSE,NULL);
	Thread1 = CreateThread(...);
	Thread2 = CreateThread(...);
}
void _fastcall Form1::OnClose(...)
{
	Terminating = TRUE;
	SetEvent(TerminatingEvent);
	if( WAIT_FAILED == WaitforSingleObject(Thread1,2000) )
		TerminateThread(Thread1,0);
	CloseHandle(Thread1);
	if( WAIT_FAILED == WaitforSingleObject(Thread2,100) )
		TerminateThread(Thread2,0);
	CloseHandle(Thread2);
	CloseHandle(TerminatingEvent);
}
DWORD Thread1(...)
{
	while( ! Terminating )
	{	HANDLE	WaitHandles[2];
		WaitHandle[0] = whatever I'm waiting for;
		WaitHandle[1] = TerminatingEvent;
		if( WaitForMultipleObjects( 2, WaitHandles,FALSE,INFINITE)
			== WAIT_OBJECT_0 )
		{ Handle whatever I'm supposed to be doing }
	};
	{ Close any open resources. };
	return 0;
}
Technical Details
Message-ID: <g8o684tvboeu25bfol5rpb9ssq6oaqosmb@4ax.com>
Path: arc1-ca.pugleaf.net!g2news1.google.com!news3.google.com!feeder.news-service.com!newsfeed.freenet.de!newsfeed00.sul.t-online.de!newsfeed01.sul.t-online.de!t-online.de!newsgroups.borland.com!not-for-mail
References: <4882cf55$1@newsgroups.borland.com>

Show Full Headers
Complete Article Headers
X-Google-Thread: 10cc67,b069f0aa9205a142
X-Google-Attributes: gid10cc67,domainid0,public,usenet
X-Google-Language: ENGLISH,ASCII-7-bit
From: Bob Gonder <none@nowhere.invalid>
Newsgroups: borland.public.cppbuilder.nativeapi
Subject: Re: Multi-threading...
Date: Sun, 20 Jul 2008 10:02:49 -0700
Message-ID: <g8o684tvboeu25bfol5rpb9ssq6oaqosmb@4ax.com>
References: <4882cf55$1@newsgroups.borland.com>
X-Newsreader: Forte Agent 1.93/32.576 English (American)
MIME-Version: 1.0
Content-Type: text/plain; charset=us-ascii
Content-Transfer-Encoding: 7bit
NNTP-Posting-Host: 67.77.144.209
X-Trace: newsgroups.borland.com 1216573365 67.77.144.209 (20 Jul 2008 10:02:45 -0700)
Lines: 98
Path: arc1-ca.pugleaf.net!g2news1.google.com!news3.google.com!feeder.news-service.com!newsfeed.freenet.de!newsfeed00.sul.t-online.de!newsfeed01.sul.t-online.de!t-online.de!newsgroups.borland.com!not-for-mail