Imagine, if you will, a scene where Rear Admiral Grace Hopper is speaking to a Darth Vader-like character on whose chest is written the word COBOL. She says to this Vader-like creation, “I am your mother!” And, imagine in the same scene, that Darth-ish force-wielder saying to a well-trained, armed Jedi wearing a “HLASM” nametag, “I am your father!”
For a long time, I used to think of COBOL and IBM High Level Assembler (HLASM) language for the mainframe as twins separated at birth, and part of me still thinks that way, given their amazing similarities in functionality, perspective and style. Of course, either way, Grace Hopper deserves credit for being a matriarch of this line.
But I have begun to enjoy the perspective that, in some ways, IBM’s mainframe assembler is actually descended from a third-generation programming language—a complete reversal of the “natural order” of things.
In terms of sheer chronology, it’s easy to make the case that COBOL, developed in 1959, could be old enough to “father” HLASM, which had its nascence in 1992. 33-year-olds have kids all the time. It gets more challenging, though, when I point out that the essential family similarity has its basis in the 360 architecture (announced in 1964), not just the linguistic expression of it. Then again, we are talking computers, so five years is more than enough for a generation. After all, programs spawn child processes in generations that can last nanoseconds.
What is clear to me, in any case, is that they’re both descended from the same thinking: the kind that emerged from countless generations of business, academic, military and government best practices. This kind of thinking has continued to show its solidity for well over half a century of business computing now, while other, more binary-styled platforms, have taken over the consumer electronics computing niches.
Wait: “Binary-styled”? What do I mean by that? Or what am I contrasting it with?
Decimal: The “D” in EBCDIC. After all, like COBOL, the System/360 mainframe was designed to “think” the same way that people do business: with displayable characters, including decimal digits. And it was designed to do it at a very large scale, in a very structured manner.
Two Sides of the Same Coin
Bill Gates is credited with observing that automating an inefficient process won’t make it efficient.
On the other side of that coin, automating an efficient process will tend to retain those efficiencies, along with backwards compatibility with the original processes that have been automated.
Of course, when you’re optimizing computing to squeeze every last consumer bit and CPU cycle of functionality out of a commodity hobby computer, you have to let go of a few things. As a result, the smaller platforms that became today’s UNIX, LINUX, Windows, Apple and others, were created with a simpler, more binary orientation that didn’t go out of the way to adhere to costly scruples such as Decimal math (or security, or reliability, etc.).
The mainframe, however, held firm to the same principles that were used to design the also-business-oriented COBOL.
The System/360 architecture and instruction set were born, with wonderful decimal and packed decimal behaviors that were the default for any business application, making it possible to eyeball the data on disk or in memory and see exactly how much the numbers were. Likewise, COBOL also preferred these formats.
In other words, the mainframe instructions were designed to think just like COBOL. That even includes interestingly quirky things like a destructive move, where you have two blocks of data that overlap, and you move the first onto the second, resulting in a repeating of the initial contents across the entire block of data. In COBOL, you’d do that with a REDEFINES and a MOVE. In mainframe assembler, you’d follow similar steps, and use the Move Character Long (or one of its more powerful siblings) to “zero out” a bunch of memory in a single stroke.
But COBOL’s designers wanted it to be “self-documenting,” and as a result, it’s more English-like than the original machine and assembly languages (manifested in IBM’s Basic Assembly Language) of System/360, even though they thought similarly. In that sense, the two are like twins—one of whom became a manager and the other a systems programmer.
The Birth of a Syntacticized Assembler
They say it’s the thought that counts. And over the years, even with the advent of second-and-a-half generation languages like C and Programming Language/Systems—IBM’s internal mainframe systems language—Assembler just wouldn’t die, and instead it began to grow and take on more and more human characteristics.
It was thus that IBM’s HLASM emerged: a “Syntacticized Assembler”—isn’t that what C was trying to be?—that allowed high-level language concepts to flood into a language that had so far settled for mnemonics, branch-and-link routines and macros. But that (System/)zebra hadn’t changed its stripes—just tailored them to suit a bigger-picture approach.
And so the business data moved, in vaster and vaster chunks, faster and faster, as the mainframe took on the mantle of processing the world economy. And much of its application programming was in COBOL and COBOL-like fourth-generation languages. But if you looked at the code with the eyes of an Assembler programmer, it didn’t take long to see how close to the underlying architecture the COBOL verbs were.
Don’t believe me? Next time you compile a COBOL program, take a look at the Assembler output that precedes the final steps before a load module is created. You may imagine hearing Darth COBOL saying, “look! I am your father!”—or at least think, “that’s a chip off the old control block.”
Reg Harbeck has been working in IT and mainframes for more than 25 years, and is very involved in the mainframe culture and ecosystem, particularly with the SHARE Board and zNextGen and Security projects. He may be reached at Reg@Harbeck.ca.