As things turned out, the UDI specification turned out describe a small operating system which - at the expense of being sheer, painful hell to work on or with - made drivers binary portable. I wondered if I'd read the specs earlier while drunk (and I don't drink)! So I decided not to implement the dirty crock. Still, I had promised about 61 people (a rough estimate of how many people commented on the article) in writing, and felt some obligation to fulfill that promise. I also still thought that the idea of a portable driver interface was a good one, so I began trying to construct a better driver interface.
This driver interface needed to be small, covering only things which all drivers and operating systems truly had in common; extensible, allowing people to add hardware- or OS- specific features in a way that didn't destroy driver portability; and obedient to common sense, aiming only for source-portability in the first place. A new driver interface had to work without making implementors its beasts of burden. It needed do for driver interfacing what L4 has done for operating systems: provide a small, stable, and flexible core supporting standard functionality alongside an ecosystem of extensions and personalities.
I have tried to create such a thing, and I have named it the Extensible Driver Interface (EDI for short). EDI specifies the interface between a runtime - which abstracts operating system functionality - and a driver - which uses the facilities of the EDI runtime to abstract a useful device.
To abstract but allow extensions, a language-independent object system rests at EDI's core. EDI runtimes and drivers create instances of classes = owned by themselves or the other party - and call the methods of those objects to interact. Any driver or runtime can transparently extend any class they're already expected to implement, or add entirely new classes. Standard classes now exist for the runtime to reasonably abstract system hardware, and EDI also standardizes a class each to represent block and character devices. More devices abstracting driver functionality may come later, if necessary.
EDI also calls for a partial implementation of POSIX threading, and allows drivers to take advantage of multithreading. I'm very sorry about having to standardize this, but most systems implement some kind of threading and many drivers require it.
Note however, that for runtimes EDI standardizes only partial POSIX threading, the object system's API and several hardware-handling classes. Runtime developers implement everything as they please. This means that the EDI runtime on Microkernel System X may actually be a stub which implements EDI by shuttling messages around. It can also mean that Monolithic Kernel System Y can implement an EDI runtime by loading drivers into the kernel and letting them call directly into real kernel code. Since EDI's guarantees only source-portability of drivers, they become portable across kernel architectures.
EDI standardizes even less for drivers: only two classes. POSIX-like block and character device classes provide a baseline of abstraction over driver functionality: you can kludge just about everything into acting like one or the other. And when drivers need to provide a better interface to their functionality, they can. In a most likely typical case, adding a non-standard initialization method to the sample driver supplied with EDI will make it far more elegant. However, I leave it up to runtime and driver developers what kind of non-standard interfaces their software should accept and/or provide.
By standardizing as little as possible, EDI should give operating system and driver developers a common tongue to speak in while still allowing local variations and dialects. That has brought EDI to where it is today. You can download our (I've had much help, even if nobody else's name is on the files) attempt at headers and documentation for an Extensible Driver Interface and take a look. The tarball includes C headers and documentation in both HTML and LATEX (thank you Doxygen). It is the fourth minor revision of the third major revision, and it's time I let the internet public know about it.
Especially since it's the internet public I hope will implement and use EDI. So in hopes of strengthening the community ties among operating system developers (such as exist on the net), EDI is copyrighted to me and placed under the GNU Free Documentation License version 1.2. Take it, change it, poke it with a stick, it's free! However, implementors are also free (If words on the net can constitute legal permission, this does.) to license their EDI drivers and runtimes however they please. Just note that the few-guarantees design of EDI makes it simple to implement an EDI runtime which would log all calls to itself, helping to reverse engineer drivers.
Hey, if nVidia really wanted to they could "extend" their drivers to only run on Trusted Computing EDI Platforms or some such nonsense. That's allowed, though improbable.
Since nobody fears the open-sourcing of serial port drivers, I've put the sample driver in the public domain. I only wrote a cheap, fast, but sufficient proof-of-concept, and feel no need to hold on to any rights.
So please, every reader with a word to say, come and comment! More eyeballs are good; hands and brains even better! I especially welcome eyes and/or hands already experienced in the development of systems software. You get a free smiley face. EDI needs people to improve it - and eventually to implement it in their own systems. Indeed, you can best give feedback by explaining what EDI needs to be for you to want it implemented or (better yet) for you to implement it yourself. If that sounds like a marketing pitch, it is. I apologize for my incompetance at herding cats, or in this case operating system geeks. My country has inferior potassium.
One comment which two people have made (and which I therefore address here) is "Why don't you write the object system as a set of normal C++ classes?" The answer is language and compiler portability. Turning the entire deal into a set of C++ classes would then require the ability to declare member functions as imported from the runtime, which extremely few languages and compilers allow. Furthermore, attempting to solve that problem through a set of M$ COM-like abstract interface classes would tie the project down to a particular the implementation of virtual method tables for only one pair of language adn compiler. EDI should be only as difficult to implement as any other piece of an operating system, so it has no business requiring people to change their compiler internals in order to use it, even to make EDI's architecture much cleaner. Besides, people use C for most operating system development, and C-kernel-hackers would have to hand-build such "virtual method tables". However, all that matters to EDI now is a few function pointers passed on class declaration to EDI specifying the class's methods and a means of creating and destroying objects of that class. Programmers can actually implement those X+2 functions in practically any language that compiles to binary. However, current EDI standards assume the C calling convention, since it is the most common. That assumption can change.
About the author:
Eli Zachary Gottlieb develops his hobby kernel named Glider in his Copious Free Time while trying to get into college. Yes, he's in his senior year of high school. OSNews published an editorial of his, "The Reasons Nobody Gets Any Help" last year, which sparked his later quests into the land of device driver interface development. Flames and trolls get dumped into the Atlantic Ocean, so speak reasonably unless you want to pollute the Earth.
If you would like to see your thoughts or experiences with technology published, please consider writing an article for OSNews.