How Can I DeviceIoControl in less than 10 milliseconds?

Tech Tip: Click here to run a free scan for Windows Errors and optimize PC performance



The following is code snippet inside a thread that first waits on an
incoming data from a socket (not shown here), then attempts to
immediately write it to my device.

The entire sequence (wait for buffer full, then DeviceIoControl, then
GetOverlappedResult) should take no more than 10 milliseconds.


//////////////////// BEGIN SNIPPET /////////////////////////
ResetEvent(context->ahEvents[OVERLAPPEDWRITE]);

int na;
DWORD numBytesRead = 0;
BOOL rc = DeviceIoControl(hDevice,
DIOC_WRITE,
buffer, buflen, // in/write
&na, sizeof(na), // out/read
&numBytesRead,
&(context->overlapped));
if (!rc)
{
if (GetLastError() == ERROR_IO_PENDING)
{
// Wait for write to complete
DWORD dw = WaitForMultipleObjects(2,
context->ahEvents,
FALSE,
INFINITE);
{
if (dw == WAIT_OBJECT_0+1) // overlapped i/o event
{
rc = GetOverlappedResult(hDevice,
&(context->overlapped),
&numBytesRead,
FALSE);
if (!rc)
HandleLE(GetLastError(), "GetOverlappedResult()");
}
else // thread stop event or error
{
HandleLE(GetLastError(), "WaitForMultipleObjects()");

if (CancelIo(hDevice) == 0) // cancel pending write
HandleLE(GetLastError(), "CancelIo()");
}
}
}
else
HandleLE(GetLastError(), "DeviceIoControl not/O pending");
}
\\\\\\\\\\\\\\\\\\\ END SNIPPET \\\\\\\\\\\\\\\\\\\\\\\\\


My problem is that the above snippet (not even including the preceding
socket handling) *sometimes* takes MUCH longer than 10 milliseconds...
sometimes even more than 200 milliseconds!

Further diagnostics and measurements revealed that this time is not
spent in DeviceIoControl() and not in GetOverlappedResult() but rather
in WaitForMultipleObjects().

My (current) conclusion is that this is due to preemption.

Intuitively it seems that, in order for "my socket handling sequence"
to take less than 10ms, WaitForMultipleObjects (and thus
GetOverlappedResult) should move elsewhere (possibly to another
thread?)

If so, how do I do that? It seems insane to track dynamically variable
number of overlapped events...

Also, the way I have been using overlapped I/O as depicted above gives
me no benefit over blocking I/O. So, what am I doing wrong? How can
overlapped I/O be used the way it was intended to be used?

Thanks,
Chris
.



Relevant Pages

  • RE: Server socket problems
    ... This article explains the difference between a socket's overlapped I/O ... When a socket is created, by default it is a blocking socket. ... socket will perform an overlapped I/O operation. ... On Windows NT, you can specify NULL as the ...
    (microsoft.public.win2000.networking)
  • Re: WSASend()
    ... There's a glaring error in the sample code - the socket is not ... overlapped I/O is so you can service multiple sockets efficiently. ... > data to the client until the client disconnects. ...
    (microsoft.public.win32.programmer.networks)
  • Re: WSARecv call blocking when using overlapped I/O
    ... That's because Win9x doesn't feature overlapped I/O. ... Alexander Nickolov ... >> You need an overlapped socket for overlapped I/O. ... >> Microsoft MVP, MCSD ...
    (microsoft.public.win32.programmer.networks)
  • Re: Related to LSP
    ... when i am trying to create a socket on port 5101 it is giving me ... IFS Model is and how it is related to Overlapped I/O.. ... OVerlapped I/O: One creates a separate thread for each socket created ... "An LSP cannot create socket handles that are true IFS handles since ...
    (microsoft.public.win32.programmer.networks)
  • Re: Related to LSP
    ... when i am trying to create a socket on port 5101 it is giving me ... IFS Model is and how it is related to Overlapped I/O.. ... OVerlapped I/O: One creates a separate thread for each socket created ... "An LSP cannot create socket handles that are true IFS handles since ...
    (microsoft.public.win32.programmer.networks)