Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

Bug inside TThread.WaitFor In Delphi 6

0 views
Skip to first unread message

Alexander

unread,
Jun 5, 2002, 11:05:30 AM6/5/02
to
Hi,

I use dxsock and I always get an error 6 Invalid Handle from windows when I
terminate my server.
This is triggered inside the function TThread.WaitFor.

I'll explain what happens.

In the main thread the function WaitFor Is Called
This will copy the handle to a variable H.
It will use this handle to call the function MsgWaitForMultipleObjects.
If the threads FreeOnTerminate is True it will free this handle.
Therefor making this handle Invalid.
Therefor resulting in the error triggered by Win32Check;

This is extremely irritating, we have made a workaround, it requires a
duplicatehandle. We have a workaround now, but I would like to see this
modified in newer versions of Delphi. I don't like me making modifications
in the source.

In order to get it working, compile this file and put the new classes.DCU in
Lib.

Kind regards

Alexander

Snip from D6 source.
var
H: THandle;
WaitResult: Cardinal;
Msg: TMsg;
begin
H := FHandle;
if GetCurrentThreadID = MainThreadID then
begin
WaitResult := 0;
repeat
{ This prevents a potential deadlock if the background thread
does a SendMessage to the foreground thread }
if WaitResult = WAIT_OBJECT_0 + 1 then
PeekMessage(Msg, 0, 0, 0, PM_NOREMOVE);
Sleep(0);
CheckSynchronize;
WaitResult := MsgWaitForMultipleObjects(1, H, False, 0,
QS_SENDMESSAGE);
Win32Check(WaitResult <> WAIT_FAILED);
until WaitResult = WAIT_OBJECT_0;
end else WaitForSingleObject(H, INFINITE);
CheckThreadError(GetExitCodeThread(H, Result));
end;

WorkAround
function TThread.WaitFor: LongWord;
{$IFDEF MSWINDOWS}
var
PH : THandle;
H: THandle;
WaitResult: Cardinal;
Msg: TMsg;
begin
PH := getCurrentProcess;
DuplicateHandle(PH, FHandle, PH, @H, 0, false, DUPLICATE_SAME_ACCESS);

if GetCurrentThreadID = MainThreadID then
begin
WaitResult := 0;
repeat
{ This prevents a potential deadlock if the background thread
does a SendMessage to the foreground thread }
if WaitResult = WAIT_OBJECT_0 + 1 then
PeekMessage(Msg, 0, 0, 0, PM_NOREMOVE);
Sleep(0);
CheckSynchronize;
WaitResult := MsgWaitForMultipleObjects(1, H, False, 0,
QS_SENDMESSAGE);
Win32Check(WaitResult <> WAIT_FAILED);
until WaitResult = WAIT_OBJECT_0;
end else WaitForSingleObject(H, INFINITE);
CheckThreadError(GetExitCodeThread(H, Result));
CloseHandle(H);
end;


Alexander

unread,
Jun 5, 2002, 11:11:58 AM6/5/02
to
Oh btw,

Not to piss anyone off,

but IMHO a guy implementing the new TThread.WaitFor, should *NOT* make such
an obvious mistake. This is a very basic thread shit.

Kind regards

Alexander


Stefan Hoffmeister

unread,
Jun 5, 2002, 12:13:52 PM6/5/02
to
: "Alexander" <amuylaer...@hotmail.com> wrote:

>I use dxsock
...


>In the main thread the function WaitFor Is Called
>This will copy the handle to a variable H.
>It will use this handle to call the function MsgWaitForMultipleObjects.
>If the threads FreeOnTerminate is True it will free this handle.
>Therefor making this handle Invalid.
>Therefor resulting in the error triggered by Win32Check;

Please tell the dxsock folks to fix their defect.

They cannot have FreeOnTerminate = true *and* call WaitFor.

Alexander

unread,
Jun 6, 2002, 3:11:48 AM6/6/02
to
After serious thinking,

This is *NOT* a bug and Stefan is right.

Kind regards

Alexander


0 new messages