What’s the perfect API?

I was skimming a rant by someone on arstechnica about how badly messed up Win32 APIs are and how superior everything else is, when this paragraph grabbed my attention:

The reason must be that no one in Microsoft actually gives a damn. Each group develops their own UI widgets in their own style and they simply don’t care that it’s a total mess. They don’t care that I have to learn new ways of doing the same task just because they couldn’t be bothered to do things the same way as other applications. I’m not saying, for example, that they shouldn’t have introduced the ribbon concept in Office 2007, because it seems to work pretty well, and I can believe that it really is a better UI model. But they should have taken stock of what they were doing and made it a system-wide UI device. New widgets and UI models do crop up from time to time, but they should be rare, and when they do appear, Microsoft should make them general so that everyone can use them.

The article/post contained a lot of conjecture and fact-less information up to that point, and had strayed into the Vista-bashing camp that so many love when that paragraph smacked me. It’s where I went from having very little respect for the author to near zero. I mean seriously — how could you honestly write that no one cares at Microsoft? Not a single person? Right. There are some misguided teams and products at Microsoft from time to time (and some great products that are canceled), and maybe some products that he or I don’t agree with, but come on — there’s plenty of people who want to produce a product that others will use and enjoy (or at least find useful)! Does the author of that article honestly think, Microsoft employees get up in the morning, and think to themselves, I couldn’t care less about my future or any of my customers — I’ll go do the least amount of work I can to get my job done — and produce something barely adequate.

I frequently see someone posting, “I’m joining Microsoft … so that I can not make a difference and not care!”

A few other zingers from the post…

If you develop software for a living, and were to say something to me in an interview like this:

Another example; Win32 has a function for getting the size of a file. File sizes on Windows are limited to 2^64 bytes, and so they need a 64-bit integer to be expressed easily. But the API call to get the size of a file doesn’t give you a 64-bit value. Instead, it gives you a pair of 32-bit values that have to be combined in a particular way. For 32-bit Windows, that’s sort of understandable; 32-bit Windows is, well, 32-bit, so you might not expect to be able to use 64-bit integers. But if you use the same API in 64-bit Windows, it still gives you the pair of numbers, rather than just a nice simple 64-bit number. While this made some kind of sense on 32-bit Windows, it makes no sense at all on 64-bit Windows, since 64-bit Windows can, by definition, use 64-bit numbers.

It shows such an immaturity of what it takes to do long term programming (not just one-off programming for hobbies) and API maintenance that you’d be a “no-hire.” Dude, do you seriously want to conditionalize all of your code just so you can recompile on 64 bit Windows? Do you want a new API just for that? Seriously, what’s the gain?

So clearly, …

So Windows is just a disaster to write programs for. It’s miserable. It’s quite nice if you want to use the same techniques you learned 15 years ago and not bother to change how you do, well, anything, but for anyone else it’s all pain. I thought before that Microsoft cared about people like me. But it doesn’t. And it makes programming on Windows painful. Microsoft is great at backwards compatibility—you can take really old programs and compile and run them on a brand new Windows—but terrible at design and terrible at providing a good experience.

He applauds OSX at some point — coming to the conclusion that the Mac OSX APIs are genius … never mind the fact that Apple had to start over from scratch and every application needed to be rewritten (and the fact that the whole thing was inspired by the NeXT OpenStep). Maybe they are wonderful — I’ve only dabbled (but seriously, Objective C??!?). Microsoft could have done that too — but when you have the market share Microsoft has — can you truly afford to do that? No way. Hundreds of millions of people every day use legacy software on modern Windows operating systems because Microsoft made the difficult choice to keep supporting them.

As the author goes on to say, it causes the internals of Windows to be less than completely desirable as it is forced to maintain a level of compatibility with old APIs and peculiarities of older versions of Windows. Are there people working at Microsoft right now who would love to just start fresh with a clean slate? Abso-freakin-lutely. But, business needs often come first in the world of making money. Microsoft was able to keep existing products running because of the design of their OS and APIs made it possible. Apple couldn’t with OS 9 and earlier when upgrading. When they can completely virtualize a Win32 process seamlessly — then they can start fresh.

Taken alone, these are all fairly minor things. Put together, the interface is just completely shambolic. It looks amateurish. The quirks of each new interface have to be learned anew. This slap-dash approach to look-and-feel gives the impression of a platform that no one really cares about.

The author seems to believe that everyone at Microsoft should just work together and produce products at the same time on the same ship schedules — as every one should contribute the “whole” and produce things that are only good for the masses. They aren’t allowed to innovate on their own or produce something unique or better than another team. “Just stick the widget into the OS … we’ll ship when you’re ready … and we’ll happily adapt to any changes that any other team needs to make.”

If the author had chosen to research and provide facts, better understand the development environments, platform capabilities, and stick to a point, it might have been a mildly interesting read — but alas, he did not. It got my blood boiling …, hence my post. Maybe Microsoft, who couldn’t care less according the author, will nonetheless contact him to get feedback on how to build the perfect API. Clearly it can’t ever have a backwards-compatibility layer or object model … so it just has to be perfect right out the door. :-P

What is the perfect API? For rich or a reach application? Give it a little thought right now. What comes to your mind right away?

14 Comments

  1. First point – fair enough – I think it’s harsh to say that no one at MS cares. In fact, I first learnt the point about having dialogue buttons as verbs, rather than OK/Cancel, from someone who’d been on the design team for Excel.

    The problem is the gap between best practice, and actual practice. Most companies fall down on that step, because it requires strong management support.

    >”applauds OSX at some point — coming to the conclusion >that the Mac OSX APIs are genius … never mind the fact >that Apple had to start over from scratch and every >application needed to be rewritten”

    Not so much ‘never mind the fact’ as that being the precise thing that has given Apple an advantage – that they bet the future on Cocoa rather than Carbon (the legacy API roughly equivalent to Win32 that allowed porting OS 9 apps to OS X).

    Note also the growing talk about what comes ‘after Java’, which was once presented as the final programming language.

    Perhaps we need to take a lesson from this – that languages and APIs have a life span, but that is OK because software does too. Perhaps a business dependent on a custom DOS application written in the mid-80s, is not being run that efficiently, or effectively.

    As it happens, other vendors, like Oracle or Sun’s Solaris, pull support for legacy APIs – you typically get a window of support for previous, current, and next versions, and it is up to you as a vendor to keep up, or stop and die. Usually what drives you to upgrade is that there is some really good reason to do so.

    What degree of backward compatibility do we actually need??
    At what point do we start paying for a level that we don’t need??
    And at what point do we start paying for it indirectly?

    >But seriously, Objective C??!?
    Never really understand people’s problem there, other than unfamiliarity. I’m an ADA developer myself, so I find Obj-C syntax as baffling as most people, but conceptually it seemed elegant, and complaining about syntax is often like complaining about foreign languages.

    Q. Do you think Apple would be delivering better apps, faster, if they had, say, stuck wholly with C++?

  2. JulesLt — great comment. I don’t disagree that Apple has an advantage — I wonder how long it will last though? (How old is the current programming model? I’m not familiar enough with the specifics.)

    I think it’s fair to say that if Microsoft hadn’t maintained compatibility that it’s unlikely they would have the market share they enjoy right now.

    Working for an ISV, I know that enterprises want a high degree of backward compatibility from release to release — it’s a challenge to sunset any particular version or technology.

    Objective C — Developers can probably adapt to any language if they really want to. I doubt that Apple would be less successful if they had stuck with C++ — I know I would have tried my hand at development more seriously if they had stuck with C++ as the primary development language, just so I didn’t have to learn one more language. I know it’s possible to use other languages, but Objective C certainly is the one that is encouraged. I’m not sure I entirely understand anymore why they felt it necessary to use a unique dialect of C…

    I like .NET — it’s a platform that has grown over the years and clearly can adapt to new platforms (WPF over WinForms, Silverlight). Maybe the platform isn’t perfect — but that can be fixed, and a new abstraction/API can be created for whatever new innovations Microsoft invents.

  3. Kevin — every platform does have trade-offs. What are you willing to overlook (or not) for trade-offs?

  4. Well, Nextstep dates from the early 90s – it was one of the first strict MVC frameworks – and the decision to use Obj-C for that must have been made slightly earlier.

    At that point in time, C++ was still also a young language, and Obj-C was actually more compatible with ANSI C than C++ (i.e. it was a strict extension to C).

    The conceptual implementation of OO in Obj-C was also better – it is closer to Smalltalk – whereas C++ (and by extension Java) compromised OO in favour of performance. At the time, that was a fair trade-off – NextStep only ran on workstation class machines around the $10,000 price point, whereas C++ apps could run on anything. There was no ‘C++ runtime’ that they ran in.

    On the downside, that also means shared libraries rather than shared components and objects.

    I think that is the particular strength of Cocoa – the late (runtime rather than compile time) binding makes it easy for existing applications to share components, or pick up new O/S features without recompilation – for example, the standard text class was extended under Tiger to include Spotlight/Google search options, and under Leopard a grammar checker.

    My understanding from the debate around the Java bridge, and the more recent Python and Ruby bridges, is that it’s easier to build a bridge to a more dynamic language, than to a less dynamic one – in much the same way that it is easier to call C from C++ than the other way round.

    I do wonder about your first question – given the origins of Cocoa and Obj-C date back 15 years, I do wonder what a new clean API based around those 15 years of experience would look like.

    Anyway, that’s getting away from the API debate!

  5. Point 1: It’s called hyperbole. Yes, I’m sure that there are individuals within MS who do care. Maybe even a lot of them. But I’ll tell you this: creating a good, consistent, clean UI is clearly not a priority at MS. Reinvention and duplication is not an occasional anomaly. It is the norm. The Windows Vista UI Guidelines, for example, are probably some of the most thorough MS has ever come up with. And yet… and yet Windows Vista itself does not conform with its own guidelines. Not just in a few places, either. The non-conformance is *everywhere*. The Vista UI Guidelines in a number of places use real Vista screenshots as *examples of what not to do*.

    It may well be that people near the bottom of the totem pole care about this kind of thing, but it’s also clear that people at the top–people who make decisions–do not. There is no-one within the company saying “This application’s UI is needlessly non-standard; it reinvents this, this, and this, it’s a pain for users and it’s a pain for maintenance–go fix it”. It just isn’t seen as a priority.

    Point 2: “Dude, do you seriously want to conditionalize all of your code just so you can recompile on 64 bit Windows? Do you want a new API just for that? Seriously, what’s the gain?”. No, I don’t want that. And I think it shows an incredible lack of imagination on your part that you think that’s the only alternative.

    What I would like to see is a clean 64-bit API, and a 32-bit compatibility library, so I could write 32-bit apps against a workalike of the 64-bit API. This isn’t unprecedented, at all; Microsoft created the Unicode layer for Windows 9x, so that programs could be written to use (NT’s preferred) Unicode APIs against the (narrow char/multibyte) Windows 9x family. Apple produced CarbonLib to allow programs to use Mac OS X’s (semi-modern) Carbon APIs on (legacy) MacOS 9. This isn’t a totally outlandish, never-seen-before concept. It’s something that both Apple and MS have done to ease transitions.

    Point 3: It is precisely because Apple to such an extent started with a clean slate that Apple has been able to be much better on keeping APIs clean and powerful. Apple is also willing to deprecate and remove things, which MS never does. This is particularly upsetting in .NET. .NET, unlike Windows proper, has a pretty good versioning mechanism built-in. SxS installation, rolling forward dependencies on minor version changes, that’s all there already. There’s no reason to keep everything old and deprecated hanging around for ever with .NET, and yet that’s the road they’re going down anyway.

    Point 4: No, they don’t need to all ship on the same schedule. But you are mistaken if you think that their development is “innovat[ion]” or producing something “unique”. The no-menu thing in WMP, Explorer, IE, WLM, Photo Gallery, etc.–that’s not unique. It’s just coded a bunch of different times. That’s not providing any advantage to any user. It’s not even providing any advantage to MS (because it’s just that much more code to maintain). The reason MS is doing that is simply because there’s no co-ordination between divisions. The left hand is totally clueless about the right hand.

    Now, maybe we could let that slide for stuff like WLM, which is a separate download anyway (though I still think first party apps should do a lot better than MS’s do). But for the things that *all ship together on the Vista DVD* to suffer this same reinvention and inconsistency? That stuff *already* has the same ship schedule. It’s *already* being combined into a single release. It is *not* asking a lot for it to be even slightly consistent.

  6. DrPizza — thanks for the comments. But I fail to see how any of this actually addresses some of the hard issues — like running a business and trying to make money — which is what their shareholders want.

    It’s not a lack of imagination that I have (if you knew me, you’d never suggest that) — it’s the knowledge and first hand experience of the hard truth of doing software development and trying to make money — sometimes you have to ship, even when it’s not what you wanted. You are absolutely underestimating the power of enterprise on Microsoft’s ship and design schedule. The enterprise plays a HUGE role in their every-day decisions. I know for sure — as I have worked there.

    How much time do think it would take to create a new 64 bit API with a compatibility layer for 32 bit? And how much testing would it require, by both Microsoft and 3rd parties? I can’t fathom it — it’s so high.

    What do you want from a 64 bit API anyway? What’s the real issue? If you use .NET, you’d normally not have to worry (unless doing PInvokes). Microsoft maintains a level of compatibility, even with .NET to make it easier to upgrade. If they didn’t, you’d find developers wouldn’t upgrade. The amount of effort required would exceed their schedules, the perceived benefit may be limited, etc.

    The harsh truth is that it’s Microsoft’s customers and developers who are preventing them from moving forward. Look at the number of people who are clinging to XP. How can they move the OS forward if people refuse to change? Imagine if they made a huge jump and all of their favorite software stopped working. It’s just not a simple problem to solve. There is no right answer.

    Again, thanks for your comments.

  7. “DrPizza — thanks for the comments. But I fail to see how any of this actually addresses some of the hard issues — like running a business and trying to make money — which is what their shareholders want. ”
    If I were an MS shareholder, I would be extremely dissatisfied at (a) Windows Vista (b) the failure of the share price to move upwards. I don’t think MS *is* delivering what its shareholders want. And I don’t think it *can* because it is so hamstrung by backwards compatibility.

    I think Vista is the best Windows ever, and it’s the OS I use most of the time (by far). But it took more than *five years* from the release of XP to get there. And there’s no way that Vista is five years of improvement over XP. It’s no wonder that home and business users alike are saying “You know what? XP is good enough. Vista’s not offering anything worthwhile; it’s just bigger, slower, and spuriously different”. There *are* good things about Vista (though many of them not obviously visible; I wrote at length about them at Ars), but there’s very little that’ll make someone who’s of two minds think “gosh, I really must have that”.

    MS’s slavish adherence to backwards compatibility–and they *way* in which that BC is achieved–is preventing MS from giving value to its shareholders.

    “It’s not a lack of imagination that I have (if you knew me, you’d never suggest that) — it’s the knowledge and first hand experience of the hard truth of doing software development and trying to make money — sometimes you have to ship, even when it’s not what you wanted. You are absolutely underestimating the power of enterprise on Microsoft’s ship and design schedule. The enterprise plays a HUGE role in their every-day decisions. I know for sure — as I have worked there. ”
    Sure. But that’s kind of missing the point, I think.

    There are ways to provide backwards compatibility that do not hamstring future development. The most obvious thing is *version your libraries*. It’s OK to freeze an old library and introduce a new one. That doesn’t break old applications, and equally, it doesn’t cripple new ones. But MS doesn’t do that, which makes its development much, much harder. Any time MS *does* try to introduce a new feature, MS has to make sure that it doesn’t upset old programs. Why? Because the new feature has to be shoehorned in amongst the old stuff.

    This approach simply doesn’t scale well, as MS has discovered on countless previous occasions.

    I’m not claiming versioning is a panacea; if the change is big enough it can be very difficult to continue to support the old versions, no matter how good your intentions are (although we have good solutions for that, too–virtualization). But it would provide a hell of a lot more flexibility than MS currently has.

    “How much time do think it would take to create a new 64 bit API with a compatibility layer for 32 bit? And how much testing would it require, by both Microsoft and 3rd parties? I can’t fathom it — it’s so high. ”
    How much time? Less than it took to deliver Vista, that’s for sure.

    “What do you want from a 64 bit API anyway? What’s the real issue?”
    I want to write 64-bit applications.

    “If you use .NET, you’d normally not have to worry (unless doing PInvokes).”
    That’s unfortunately not true. .NET is, unfortunately, 32-bit. Oh, sure, if you run a .NET program on 64-bit Windows it’ll create a 64-bit process. But you can’t, say, allocate an array that’s more than 2^31 elements long. This is annoying, to say the least; I’d like to, for example, work with large image files, and the ability to create 4 GiB byte arrays would make my coding *considerably* simpler. You can take a look for yourself if you don’t believe me; load up mscorlib.dll from the Framework64 directory and take a look at System.Array.LongLength. It just casts the signed 32-bit Length property to long. To deal with these large images, I’d have to do some kind of a chunking mechanism. That’s a huge amount of extra complexity.

    With native code, I don’t have an issue. I can just create a 4 GiB array. I’m not saying I would necessarily want to do things this way–although it probably *is* the most efficient way on large-memory systems–but it’d be nice to have the option. To compound the annoyance, .NET doesn’t even have a good memory-mapped file mechanism (MMFs are another good way of handling large data structures). If I want to create lots of little objects (i.e. more than 4 GiB worth of them), I suspect .NET would be good enough, but if I want to create a few huge objects, it actually kind of falls down.

    And then there’s all the things that I just can’t access in .NET anyway. Like DirectShow, or Media Foundation, or Core Audio. These are off-limits whether 32- or 64-bit, because they just don’t exist in .NET. P/Invoke is quite good if I want to bring a couple of C API calls into the .NET world, but it’s pretty grim if I want to bring whole APIs with complex data structures over. C++/CLI is a much better option, because it lets me eschew the .NET things entirely. I can ignore .NET Collections and arrays and ValueTypes and just use the C and C++ things directly.

    “Microsoft maintains a level of compatibility, even with .NET to make it easier to upgrade. If they didn’t, you’d find developers wouldn’t upgrade. The amount of effort required would exceed their schedules, the perceived benefit may be limited, etc. ”
    I don’t agree. I think .NET provides pretty good infrastructure to support MS making breaking changes (especially if they have one version where things are deprecated and a second to remove them; this gives developers plenty of advance notice and opportunity to get their house in order). With .NET’s versioning, breaking changes will only break applications that are *actively maintained* (and hence rebuilt against the latest libraries). They won’t break legacy applications. To me (and the enterprise development I have done), that seems like a more than acceptable compromise.

    “The harsh truth is that it’s Microsoft’s customers and developers who are preventing them from moving forward. Look at the number of people who are clinging to XP. How can they move the OS forward if people refuse to change? Imagine if they made a huge jump and all of their favorite software stopped working. It’s just not a simple problem to solve. There is no right answer.”
    The reason that people are clinging to XP is because Vista simply isn’t that big a leap (in spite of its extended gestation). A key reason that it’s not a big leap is because its development was so restricted by backwards compatibility.

  8. Versioning is a tough nut to crack. I don’t honestly know if that would help or hurt them — if they had 3 or 4 different versions of the WinAPI for example — would they be hampered by the sheer magnitude of keeping things aligned and supported?

    MMF’s rock. They still haven’t created a wrapper for them … bummer. I wrote one a few years ago, but I’d much rather it just be part of the core .NET framework.

    A 4GB image file?! Wow! What kind of file is it? Video comes to mind, but you said image, and I’m curious as to what file type it is now …. :)

  9. “Versioning is a tough nut to crack. I don’t honestly know if that would help or hurt them — if they had 3 or 4 different versions of the WinAPI for example — would they be hampered by the sheer magnitude of keeping things aligned and supported?”
    I think some parts will be easier than others. An example of something that should be fairly easy is the various control libraries there are. Although these are dependent quite heavily on the mechanics of User32 (WndProcs, window messages, all that jazz), they should have zero kernel dependencies, and should be independent of any other parts of Windows. It would seem quite feasible to freeze and version these.

    Things would get a bit more tricky if we were talking something more ambitious–a wholesale replacement (rather than merely a tidying up) of User32 with something good, say–so that would require more effort (one might envisage a User32-workalike layer written to sit on top of WPF, say) but I think could still ultimately be achieved.

    Please don’t get me wrong: I’m not suggesting that this would *eliminate* the issues MS faces. Rather, I’m suggesting that it would give them greater scope to move forward without jeopardizing their legacy, by compartmentalizing and isolating it. And I find it incredibly frustrating that even though MS has good infrastructure for this with .NET, it’s not being used.

    “A 4GB image file?! Wow! What kind of file is it? Video comes to mind, but you said image, and I’m curious as to what file type it is now”
    Oh, for work we get all kinds of huge TIFFs that we would like to manipulate in certain ways (typically convert them to other formats so that their file sizes are a bit smaller…). Standard TIFF is in principle good for up to 4 GiB (though many implementations are restricted to signed 32-bit, i.e. 2 GiB), and there are proposed extensions for 64-bit TIFFs, BigTIFF, and there are certainly applications for such files. Again, this is not to say that creating a bloody great array to hold all the image data is necessarily the best approach to use for such files (especially as they can easily outstrip any reasonably likely amount of memory), but even if you’re dividing the images into chunks, you’ll often want chunks as big as possible.

  10. I hope MS is seriously investigating virtualization as a solution to backward compatibility.

    I think I’ll probe some contacts at MS regarding 64-bit .NET. I may not be able to blog about them (due to NDAs), but you’ve got me curious.

  11. “I hope MS is seriously investigating virtualization as a solution to backward compatibility.”
    The big problem with virtualization is getting a streamlined experience for the user. Although we see attempts to do this with e.g. Parallels, VMware, VirtualBox, which can stick a virtual Windows window onto your actual desktop, the integration is still a long way off 100%. It’s also quite a heavyweight solution; you don’t want to have to boot up a VM each time you run a legacy program, especially since that “legacy” program could have been built and compiled a few minutes ago!

    Certainly, virtualization has a role; Win16 needs virtualization these days (no Win16 is available on 64-bit Windows), but we’re really not in a position where we could say, for example, “virtualize all Win32 apps”.

    “I think I’ll probe some contacts at MS regarding 64-bit .NET. I may not be able to blog about them (due to NDAs), but you’ve got me curious.”
    Well, it depends on what you want to do with “64-bit”. Sure, you can create a lot of objects (it is a 64-bit process, after all), it’s just that I’d like to create huge objects instead of lots of objects.

    I do think they should have been forward-looking and made array sizes use ‘long’ rather than ‘int’. Sure, it’d take a hit on 32-bit systems. I don’t care; even in 2002 it was obvious that the days of 32-bit were numbered. Look to the future, not to the past.

Comments are closed.