Before we start scrabbling for case histories & reference studies to
support Ada, perhaps we should not forget what we are fighting
*against*! Here is a brief case history of a project I spent a year on:
The company I worked for at the time (which must remain nameless, to
avoid any legal complications), had a lucrative deal with another
company to develop a commercial application, but rather than invest in
doing it properly (horror!), they bought in an absolutely *crap* C
package from a Taiwanese company (I remember when the "Made In Taiwan"
label on a product was a sure-fire warning!), then thought that it could
be easily modified and extended.
To make it worse, the man who came with the package (its original
designer), and who was in technical charge, was 25 years out-of-date. To
him, everything was a macro: there were 7000 macros in the package (out
of 130K SLOC); there were macros 300 lines long; there were macros
expanding macros down to a depth of 10 or 12 levels; there were macros
which had to be defined before expanding other macros to give "unbound"
global variables to be used by them; there were macros which were
defined, undefined, and redefined in different header files - so making
the order of header file inclusion critical. MACROS MACROS MACROS!! He
wasn't happy with C, though: "I don't know why when people change
things, they make them worse. I remember when I was using BCPL, the
wonderful system of macros I had then.". Also, all data and functions
were global ("I really don't see much difference between internal
functions and external ones"), and he didn't like individual header
files (thought there should just be a few giant ones instead - was
horrified when I introduced individual ones for the new modules we
wrote!); plus there was a massively over-complex API (multiple layers
of macros, of course) to access what was a not-very-complicated data
model (he optimized this model in some places to save a single word of
storage!); plus he did all his own store management (did not trust
malloc & free) - except that his pointer arithmetic was generally wrong,
resulting in store corruption all the time. Much of the data in the
data model was densely packed, needing hand-written bit masks, and &, |
and shift operators to access it - this resulted in multitudes of macros
defining the masks and the read/set operations.
Everyone on the project except him said it was going to be a disaster
(early on, I gave the company management a 27-point list of what was
wrong, and *told* them it would be a disaster), but nothing was ever
done - so it crawled on for many months, until finally they pulled the
plug on it. It cost the company over 1M GBP, and the customer 1/2M - yet
we had all said that it could be rewritten from scratch faster and
Now, at the very least, if Ada had been used instead, we would have had
the following advantages:
1) NO macros - so we could have used a debugger to help us (you just try
getting a C debugger to single-step through macro-expansion which has
resulted in a line of source code several thousand characters long); and
everything semantically checked at its declaration (instead of endlessly
finding bugs in macros according to the context of their expansion). It
sometimes took myself and one of the other developers, working together,
a full *day* to make progress of half a dozen lines of code using the
2) interfaces between modules *required* to be complete and correct -
else it won't compile - so no regular checking with lint needed to look
for mismatches in calls.
3) bounds checking on all array access, no malloc to get blocks of raw
memory, no pointer arithmetic - so no store corruption => so no days
wasted hunting down obscure bugs causing crashes.
4) full signature checking by the compiler on calls: no passing a word
parameter which is interpreted as a flag in some circumstances, a bit
mask or a counter in others, and a pointer to a string in all the rest
(I jest not - this was in the code!).
5) representation specifications for densely-packed data, allowing the
compiler to generate all the read/write operations needed - and doing it
This alone would have saved us months of effort, even without the
benefits of using Ada's facilities to the full. Even if the code had
still been written in a C style, so many errors would have been
prohibited, and so much done for us by the compiler, that we could have
concentrated on the logic of the application domain, rather than
low-level details of programming.
In all, if the package had been in Ada, no matter how badly written, I
think there would have been some chance of saving the project; as it
was, there was no chance at all.
Of course, this being a commercial project failure, it never made the
news: the company certainly didn't issue a press announcement about it!
This was as much a management failure as a technical one: they were not
prepared to invest the money required to do it properly in the first
place (as though the 1M they threw down the drain on this one made good
financial sense!), and would not listen to the technical people like
myself who told them how bad the situation was ("But can't we just pick
up the ball and run with it?"). However, if Ada had been used instead of
C, I do not believe that the technical problems would have been so bad
as to make the success or failure of the project a management issue.
I'm thinking of writing this one up as a cautionary tale for one of the
journals - if only people would learn from stories like this!
Still, what can you do with someone who looks back wistfully to the good
old days of BCPL and thinks that C is too sophisticated?!