But it sounds like you are stuck in a synchronous I/O model. You have to
consider using async I/O, and pumping LOTS of I/O requests down, because
IoStartNextPacket (or its KMDF equivalent) is actually very fast.
Even TIME_CRITICAL threads have response time issues, and can be preempted
by file system threads. In addition, the Balance Set Manager can promote a
lower-priority thread to TIME_CRITICAL and give it a double timeslice if it
feels like it, so you are competing with an unknown and unknowable set of
threads. File system threads and other kernel threads are likely to preempt
you, and starting in Vista, there is something called the Multimedia
Scheduler Service which allows you to have user threads running up to
priority 26. You can take advantage of this service to get higher
priorities for your app threads, or you can be a victim of it.
In cases like this, I use async I/O and tend to use one or more threads
connected to an I/O Completion Port to handle the responses, but that’s just
my preferred application architecture. For high-performance devices,
synchronous I/O is a dead-end design; I’ve seen it fail consistently, and
therefore I don’t touch it or even acknowlege its existence in such cases.
In using asynch I/O for high performance devices, I usually parameterize the
number of I/O operations I’m going to queue up, so I can tune the
performance once the app is running. In one app, 40 failed, and 50 worked.
In another app, 8 failed and 10 worked. Which is why it should be a tunable
parameter.
Key here is that if you have not tried the async I/O approach, or considered
any of the other optimization strategies I suggested, you should not be
redesigning the interface to let apps touch registers on the device.
joe
-----Original Message-----
From: xxxxx@lists.osr.com
[mailto:xxxxx@lists.osr.com] On Behalf Of Michael Wade
Sent: Tuesday, December 14, 2010 7:20 PM
To: Windows System Software Devs Interest List
Subject: Re:[ntdev] The good old Sharing Memory between Driver and User,
with a twist
No. The main target thread, as you call it, does an ioctl that doesn’t
complete until an interrupt from the card is received. The process is
running at REALTIME_PRIORITY_CLASS and the main thread at tpTimeCritical. I
believe that this is the highest priority that a user thread can run at. We
have done much analysis of interrupt response time, ring transition
overhead, PCI bus overhead/throughput, etc. There is a very large amount of
data that needs to be exchanged between the hardware and the software in a
very short period of time. Transferring the data back and forth to the
kernel is not necessary, does not really give us any benefit and complicates
the design. Windows is most definitely not a real time operating system.
It is, however, the most popular OS right now, and the most familar to our
customers. So when the decision was made to go to Windows (back in Win NT
3.5) we knew that we had to work within the constraints of a non-real time
OS as best we could. As I said, this device is never communicated with by
any other user, so I don’t really see the benefit of implementing ioctl
calls to get/set memory on the PCI card. Whether drivers should or should
not share memory with user space is a very old argument, and I believe it
depends on the specifics of the situation. Just my two cents.
Thanks,
Michael
On Tue, 14 Dec 2010 19:01:12 -0500 (EST), xxxxx@hotmail.com wrote:
> When we tried doing either Read/Write or Ioctl the overhead just killed
us.
What about CPU starvation??? It never occurred to you to think that the
target thread, probably, just did not have a chance to process data or send
it to the device because it did not have a chance to get to the CPU???
Anton Bassov
NTDEV is sponsored by OSR
For our schedule of WDF, WDM, debugging and other seminars visit:
http://www.osr.com/seminars
To unsubscribe, visit the List Server section of OSR Online at
http://www.osronline.com/page.cfm?name=ListServer
–
This message has been scanned for viruses and dangerous content by
MailScanner, and is believed to be clean.