I've been on a little adventure learning about how Windows platforms deal with sounds. Now I know a couple of things from taking an Operating System class and reading this:
IO devices such as a sound card communicate with the OS through a device driver. Microsoft supplies a standard so that in kernel mode the OS can make certain system calls (in this case Win32 api calls) to make an I/O device do something. Bytes or characters are streamed to over buses to whatever port the I/O device resides in. These are interpreted by the device controller as instructions for the physical hardware.
There are OS calls to prepare audio devices and stream data to them. Actually for some reason their are 2 ways to do this: MMSystem and DirectSound. I think the reason there are 2 has something to do with gaming? Like DIrectSound was more geared toward that while MMsystem was more standard apps that need audio?
Beyond that their are also other audio APIs NOT written by microsoft for the Win32 platform. ASIO and GSIF.
How can these non Microsoft standards exist on the Windows platform? How can they possibly communicate with hardware or the OS? With something like openGL(something else I toy with), a version of Windows supports a version openGL standard and so does you GPU. BAM, easy-peasy no problems, everything checks out.
How I see it can be is:
MMsystem and/or DirectSound are not part of Win32, but there is some even lower level windows kernel driver everyone is keeping a secret because it's really ugly or
These other driver API's are built on top of the Microsoft supplied ones
Can someone please clarify? Where am I mistaken, I am missing something. I own my old OS textbook still(Modern Operating Systems 3rd Ed. by Tanenbaum) so if you want to point at something in there, go for it.
Related
I'm thinking of making a game in 8086 ASM using VGA for graphics, but before I proceed with anything I want to make sure that I can get audio into my project. I doubt PC Speaker will be sufficient.
I'm looking for a way to program music in 8086 for Windows. Is there some kind of standard in modern sound cards that I can access directly, or will I have to use the Windows API? I'm not really sure what to look for at this point, so any suggestions are welcome.
Unlike the displays, which ultimately converged to (S)VGA, soundcards never reached the same compatibility. There were different Sound Blasters, Gravis Ultrasound and others. These days the modern hardware is often incompatible with those and you cannot program them in DOS as the Sound Blaster without having a proper DOS driver or without knowing the supported memory regions, ports, formats and protocols.
I can only suggest writing such a program for a PC/DOS emulator like DosBox, which emulates Sound Blaster and (S)VGA. That should work.
Alternatively, you can just write a normal Windows program, using Win32 APIs for input, drawing and sound.
I'm creating an application that needs to use some kernel level modules, for which I've divided the app into 2: one user-level program and one kernel level program.
After reading about device drivers and walking through some tutorials, I'm a little confused.
Can there be a device driver without any specific device associated with it? Is there anything other than the device driver (kernel code or something) which works in kernel mode?
How do anti-virus programs and other such applications work in kernel mode? Is device driver the correct way or am I missing something?
Yes, device drivers can work without an actual piece of hardware (i.e. the device) attached to the machine. Just think of the different programs that emulate a connected SCSI drive (CD-ROM, whatever) for mounting ISO images. Or think about TrueCrypt, which emulates (removable) drives using containers, which are nothing more than encrypted files on your hard drive.
A word of warning, though: Driver development requires much more thought and has to be done more carefully, no shortcuts, good testing and in general expects you to know quite a good deal about the Windows driver model. Remember that faulty and poor drivers put the whole system's stability in jeopardy.
Honestly, I don't think reading a tutorial is sufficient here. You might want to at least invest in a decent book on that subject. Just my 2 cents, though.
Sorry, but the Windows Internals book is more of a general reading for the curious. I cannot recommend it if you want to engage in driver development - or at most as prerequisite reading to understand the architecture. There are plenty of other books around, although most of them are a bit older.
Depending on your goal, you may get away with one of the simpler driver models. That is not to say that driver development is trivial - in fact I second all aspects of the warning above and would even go further - but it means that you can save some of the more tedious work, if instead of writing a legacy file system filter you'd write one based on the filter manager. However, Windows XP before SP2 did not have it installed by default and Windows 2000 would require SP4+SRP+patch if I remember correctly. WDF (Windows Driver Foundation) makes writing drivers even easier, but it is not suitable for all needs.
The term device is somewhat of bad choice here. Device has a meaning in drivers as well, and it does not necessarily refer to the hardware device (as pointed out). Roughly there is a distinction between PDOs (physical device objects) and CDOs (control device objects). The latter are usually what you get to see in user mode and what can be accessed by means of CreateFile, ReadFile, WriteFile, DeviceIoControl and friends. CDOs are usually made visible to the Win32 realm by means of symbolic links (not to be confused with the file system entities of the same name). Drive letter assignments like C: are actually symbolic links to an underlying device. It depends on the driver whether that'd be a CDO or PDO. The distinction is more of a conceptual one taught as such in classes.
And that's what I would actually recommend. Take a class about Windows driver development. Having attended two seminars from OSR myself, I can highly recommend it. Those folks know what they're talking about. Oh, and sign up to their mailing lists over at OSR Online.
Use Sysinternals' WinObj to find out more about the device and driver objects and symlinks.
As for the question about AVs, yes they use file system filter drivers (briefly mentioned above). The only alternative to a full-fledged legacy FSFD is a mini-filter.
It is possible to load a special kind of DLL in kernel mode, too. But in general a driver is the way into the kernel mode and well documented as such.
Books you may want to consider (by ISBN): Most importantly "Programming the Windows Driver Model" (0735618038), "Windows NT Device Driver Development" (1578700582), "Windows NT File System Internals" (0976717514 (OSR's new edition)), "Undocumented Windows NT" (0764545698) and "Undocumented Windows 2000 Secrets" (0201721872) - and of course "Windows NT/2000 Native API Reference" (9781578701995) (classic). Although the last three more or less give you a better insight and are not strictly needed as reading for driver developers.
Anti-virus (and system recovery) software generally make use of file-system filter drivers. A device can have multiple filter drivers arranged like a stack, and any event/operation on this device has to pass through all the stacked up drivers. For example, anti-viruses install a filter driver for disk device so that they can intercept and scan all file system (read/write) operation.
As mentioned in above post, going through a good book would be a nice way to start. Also, install DDK/WDK and refer the bundled examples.
I need some advice on windows programming, MIDI and WDM. I am trying to write a small application that will sit in the sys tray and be advertised to the system as a MIDI In/Out device so that MIDI programs can send to it and it will convert the messages into a different format. I have been reading Cant's WDM book and scouring for information about writing device drivers, but don't know if I'm going down the right path.
I don't see yet how to:-
a) register my driver as MIDI capable (do I stick a ref to it in the registery and let the OS direct MIDI calls to the functionality in a dll?)
b) direct MIDI data through the my driver to my app, which is probably going to be too large to be a driver itself.
Any advice on where to start would be much appreciated.
thanks,
Pete
Windows MIDI drivers do not need to be implemented in the kernel, they can be implemented entirely in userspace as DLLs.
MSDN has some information about the functions you need to implement -
Audio Device Messages for MIDI - unfortunately it is somewhat lacking.
There used to be sample code for this kind of driver, as part of the NT4 DDK, but more recent releases of the DDK / WDK unfortunately don't include it any more.
Some better (though older) documentation and sample code can still be found after some searching:
Introduction to Multimedia Drivers (From NT4 DDK)
Sample MIDI Wine Driver for Mac OS X
Devices are enumerated (or simulated) by device drivers, not applications. What you see in the sys tray is an application icon. Hence, you will need to have both a driver and an app - you can't have one bit of compiled code acting as both.
On the driver side, you probably want to have a peek at the MSDN docs. This will answer part (a) of yopur question.
Assuming that you still would like to continue, (b) is best don by letting your application pull the data from the driver. That's far easier than the other way around - an application can trivially find a driver, but a driver has big problems finding a specific app (process)
If you are looking for a bit easier way to get started, there is a MIDI loopback driver out there, and the folks that make it also offer (or used to offer) a version of it that allows your program to communicate directly with the driver. This gives you the behavior you are looking for, where a program appears as a MIDI device. The loopback driver is at http://nerds.de/en/loopbe1.html. I don't see the developer page anymore, but if you contact them, you might be able to purchase a license to a driver that you can access directly without the loopback.
I know this probably is not the easiest thing to do, but I am trying to connect Microcontroller and PC using USB. I dont want to use internal USART of Microcontroller or USB to RS232 converted, its project indended to help me understand various principles.
So, getting the communication done from the Microcontroller side is piece of cake - I mean, when I know he protocol, its relativelly easy to implement it on Micro, becouse I am in direct control of evrything, even precise timing.
But this is not the case of PC. I am not very familiar with concept of Windows handling the devices connected. In one of my previous question I ask about how Windows works with devices thru drivers. I understood that for internal use of Windows, drivers must have some default set of functions available to OS. I mean, when OS wants to access HDD, it calls HDD driver (which is probably internal in OS), with specific "questions" so that means that HDD driver has to be written to cooperate with Windows, to have write function in the proper place to be called by the OS. Something similiar is for GPU, Even DirectX, I mean DirectX must call specific functions from drivers, so drivers must be written to work with DX. I know, many functions from WinAPI works on their own, but even "simple" window must be in the end written into framebuffer, using MMIO to adress specified by drivers. Am I right?
So, I expected that Windows have internal functions, parts of WinAPI designed to work with certain comonly used things. To call manufacturer-designed drivers. But this seems to not be entirely true becouse Windows has no way to communicate thru Paralel port. I mean, there is no function in the WinAPI to work with serial port, but there are funcions to work with HDD,GPU and so.
But now there comes the part I am getting very lost at. So, I think Windows must have some built-in functions to communicate thru USB, becouse for example it handles USB flash memory. So, is there any WinAPI function designed to let user to operate USB thru that function, or when I want to use USB myself, do I have to call desired USB-driver function myself? Becouse all you need to send to USB controller is device adress and the infromation right? I mean, I donĀ“t have to write any new drivers, am I right? Just to call WinAPI function if there is such, or directly call original USB driver. Does any of this make some sense?
To make your life easier, and avoid writing your own driver, try using the HID (Human Interface Device) API on top of USB. Although it says "Human Interface", it doesn't actually have to be for devices that a human controls. The advantage is that modern OSes already come with a HID driver and you can use sample code such as what you can find here to get started. Many microcontroller manufacturers provide suitable code for the embedded of the protocol.
Because OSes already understand HID, if you build a device using the HID interface you'll find that not only can you read from it from any OS, you may also find that many applications can already talk to your device if its communication is restricted to a small enough subset of HID. (For example, I built an input device for a music app, but amazingly I found I could literally plug it straight into a 3D animation app we use at work, running on a different OS, and have it work right away without writing a single additional line of code!)
This answer might aim you in the right direction.
The first answer here might also be helpful.
The answers to this have some actual code and links to yet other resources.
USB includes a set of stock functionality, much like supporting USB flash drives (USB Mass Storage class). The two most interesting for microcontroller interfacing are HID and CDC. CDC is easiest to use as it directly emulates an old fashioned serial port.
If you configure the microcontroller to act as a CDC device, Windows will enumerate it as a serial port, and all the old serial APIs will work on it.
My application needs to behave as a virtual joystick (imagine dragging a square with the mouse and translating that to the output of an analog joystick) and send some keystrokes over the network to another computer where the driver would receive that input.
I only need to support XP, Vista and Win7.
Maybe it can be done without writing a driver. I tried sending keystrokes with SendKey() which seemed to work but don't know how to emulate an analog joystick.
I've downloaded the VDK and been reading everything I can find on the subject but there are lots of things I still don't understand. Can you please point me in the right direction?
Should I build a kernel-mode or user-mode driver?
Can my driver act as a server for an app on the network?
Do you know good tutorials / books / samples that can help me with this.
Thanks
First of all you will have to have some kind of interface between your computer (or the network) and the joystick device that is being controlled.
If it involves making custom hardware to control the analog joystick (like it controls pneumatics or hydraulics or something, not just a pc game joystick type thing), then yes, you will almost certainly need a driver to allow a network app to move (the robot arm, or whatever) will move that joystick.
If you are able to remove the physical joystick from the equation, maybe you can write software that emulates the input of wherever the joystick used to plug into (a joystick/serial port?), or emulates it completely (a reasonably simple driver could do this). You could do it completely without writing a driver if the joystick used a standard communication interface (like RS232) because libraries exist that will handle all that and you can set up virtual COM ports that will be indistinguishable to whatever you are trying to communicate with.
The best book you can buy on driver development at the moment is Developing Drivers with the Windows Driver Foundation
Rootkits: Subverting the Windows Kernel is another great book, but doesn't cover a lot of the newer WDF stuff. It has more of a security focus but has a few awesome chapters on device drivers with fully spoonfed examples, breaking it down in a really accessible way.
If it is only over the network, probably simple socket programming should be enough.