Thread control & (unmanaged) blocking call

  • Thread starter Thread starter Magne Ryholt
  • Start date Start date
M

Magne Ryholt

Consider a worker thread calls (PInvoke) ReadFile synchronously on a handle
created with (PInvoke) CreateFile("COM1:"...) with timeouts set to
*infinite*.
The ReadFile should read one byte, but the serial line is "dead" and it
never times out.

Then I want to stop this worker thread in a controlled manner, without
stopping the application.
(It will be stopped if it is a background thread and the application is
terminated, at least with my simple single-appdomain application)

Is it possible to force the return of the ReadFile by e.g. setting other
timeouts (which would normally make the ReadFile to return immediately), so
the worker thread may handle AbortException or similar ?
CancelIO() only works by the request-issuing thread, and it is stuck
CloseHandle() actually is a blocking call itself when called from another
thread than the handle-creating thread (I beleive).

If not, Is it at all possible to stop (by brute force) this worker thread ?
(Thread.Abort() doesn't work on thread blocked in umnaged code, neither does
Thread.Interrupt()
(In unmanaged code this would be possible e.g. TerminateThread(), I beleive)
 
Magne Ryholt said:
Consider a worker thread calls (PInvoke) ReadFile synchronously on a
handle created with (PInvoke) CreateFile("COM1:"...) with timeouts set to
*infinite*.
The ReadFile should read one byte, but the serial line is "dead" and it
never times out.
Once you get a HANDLE from CreateFile, you can wrap the handle in a
System.IO.FileStream.

Then you can use the FileStream.BeginRead etc non-blocking calls.

David
 
Thanks David
Yes, I know (one can even "construct" the handle as part of the constructor
for FileStream: FileStream stream = new FileStream(CreateFile(..)..)

In more general terms, is it possible to "get out of" a umnanaged blocking
call (any blocking call, not just the given example with ReadFile), or to
destroy a thread which is blocked by such a call ?
 
No, there is no safe way. You can always call Kernel32's TerminateThread
API, but this is dangerous practice in non managed applications, in a
managed environment it's a definitive NO NO, unless you terminate your
application in which case there's no need to call TerminateThread anyway.

Willy.
 
Back
Top