Mail Archives: cygwin/2001/07/19/19:27:39
On Wed, 18 Jul 2001, Corinna Vinschen wrote:
> > > I'm somehow missing a
> > >
> > > CloseHandle ((HANDLE)code);
> > >
> > > at this point which at least closes the handle to the thread. Otherwise
> > > the following from MSDN is valid:
> > >
> > > The thread object remains in the system until the thread has
> > > terminated and all handles to it have been closed through a
> > > call to CloseHandle.
> > >
> > > Corinna
> >
> > That is interesting. The code variable is a local and the
> > pointer is not saved. Would this call to CloseHandle()
> > need to be done after a call to ExitThread()?
>
> No. After CreateThread() the thread is up and running. The
> handle returned by CreateThread() is just the handle for the
> parent thread to have control over the child thread. If the
> parent is not further interested in controlling the child
> it simply closes the handle immediately and forgets about
> the child thread:
>
> if ((thdl = CreateThread (...)) != NULL)
> CloseHandle (thdl):
I implemented the change you suggested and took care
of calling CloseHandle() for the handle returned by
CreateThread() or _beginthreadex(). Once the following
patch is applied to the CVS version of Tcl, it will
build with Cygwin gcc.
Index: win/tclWinThrd.c
===================================================================
RCS file: /cvsroot/tcl/tcl/win/tclWinThrd.c,v
retrieving revision 1.12
diff -u -r1.12 tclWinThrd.c
--- win/tclWinThrd.c 2001/07/16 23:30:16 1.12
+++ win/tclWinThrd.c 2001/07/19 07:15:41
@@ -131,14 +131,21 @@
int flags; /* Flags controlling behaviour of
* the new thread */
{
- unsigned long code;
+ HANDLE tHandle;
EnterCriticalSection(&joinLock);
- code = _beginthreadex(NULL, (unsigned) stackSize, proc, clientData, 0,
- (unsigned *)idPtr);
-
- if (code == 0) {
+#ifdef __CYGWIN__
+ tHandle = CreateThread(NULL, (DWORD) stackSize,
+ (LPTHREAD_START_ROUTINE) proc, (LPVOID) clientData,
+ (DWORD) 0, (LPDWORD)idPtr);
+ if (tHandle == NULL) {
+#else
+ tHandle = (HANDLE) _beginthreadex(NULL, (unsigned) stackSize,
+ proc, (void *) clientData,
+ (unsigned) 0, (unsigned *)idPtr);
+ if (tHandle == 0) {
+#endif /* CYGWIN */
LeaveCriticalSection(&joinLock);
return TCL_ERROR;
} else {
@@ -146,6 +153,7 @@
TclRememberJoinableThread (*idPtr);
}
+ CloseHandle(tHandle);
LeaveCriticalSection(&joinLock);
return TCL_OK;
}
@@ -202,7 +210,11 @@
TclSignalExitThread (Tcl_GetCurrentThread (), status);
LeaveCriticalSection(&joinLock);
- _endthreadex((DWORD)status);
+#ifdef __CYGWIN__
+ ExitThread((DWORD) status);
+#else
+ _endthreadex((unsigned) status);
+#endif /* __CYGWIN__ */
}
Of course, there may still be a problem. The reason Tcl started
using _beginthreadex() instead of CreateThread() was related
to memory that would not be deallocated after a call to
ExitThread(). Here are some docs I found on the subject.
http://support.microsoft.com/support/kb/articles/q132/0/78.asp
http://www.microsoft.com/msj/0799/win32/win320799.htm
http://technology.niagarac.on.ca/courses/comp831/win32/_beginthread.htm
http://msdn.microsoft.com/library/default.asp?url=/library/en-us/vccore98/HTML/_crt__beginthread.2c_._beginthreadex.asp
My question is, is this same memory leak problem going
to show up when using Cygwin's CreateThread() and
C library APIs?
Even if this is not going to be a problem, should
Cygwin provide the _beginthread, _beginthreadex,
_endthread, and _endthreadex methods to ease
porting existing apps that have already dealt
with this issue?
thanks
Mo DeJong
Red Hat Inc
--
Unsubscribe info: http://cygwin.com/ml/#unsubscribe-simple
Bug reporting: http://cygwin.com/bugs.html
Documentation: http://cygwin.com/docs.html
FAQ: http://cygwin.com/faq/
- Raw text -