The Importance of Terminology's Quality
John W Kennedy
jwkenne at attglobal.net
Mon Jul 21 00:29:25 CEST 2008
Robert Maas, http://tinyurl.com/uh3t wrote:
>>>> ... the "thunks" were necessary at the machine-language level to
>>>> /implement/ ALGOL 60, but they could not be expressed /in/ ALGOL.
>>> Ah, thanks for the clarification. Is that info in the appropriate
>>> WikiPedia page? If not, maybe you would edit it in?
>> From: John W Kennedy <jwke... at attglobal.net>
>> It is explained s.v. "thunk", which is referenced from "ALGOL
>> 60". The ALGOL "pass-by-name" argument/parameter matching was
>> perhaps the most extreme example ever of a language feature that
>> was "elegant" but insane. What it meant, in effect, was that,
>> unless otherwise marked, every argument was passed as two closures,
>> one that returned a fresh evaluation of the expression given as the
>> argument, which was called every time the parameter was read, and
>> one that set the argument to a new value, which was called every
>> time the parameter was set.
> Wow! All these years when I occasionally heard of a "thunk" I never
> was told, until now, what it really meant. Thanks for the info!!
> Followup question #1: I assume these are lexical closures in the
> environment of the point of the call, right?
Yes. (Actually, subprogram calls are first described as working like
macro expansions, but then the specification adds that there must be
magic fixups so that variable names are resolved in point-of-call
At this point in the history of computing, the conceptual distinction
between subprograms and macros was not at all clear. It was quite
possible to have "macros" that generated an out-of-line subprogram once
and then generated calling code the first time and every time thereafter
(it was a way of life on systems without linkage editors or linking
loaders), and it was also quite possible to refer to in-line macro
expansions as "subprograms". I suspect that the triumph of FORTRAN may
have had something to do with cleaning up the terminological mess by the
Into the 60s, indeed, there were still machines being made that had no
instruction comparable to the mainframe BASx/BALx family, or to Intel's
CALL. You had to do a subprogram call by first overwriting the last
instruction of what you were calling with a branch instruction that
would return back to you.
> Followup question #2: For simple arithmetic expressions, I can
> possibly understand how the UPDATE closure might be implemeted
> (expressed in Lisp to make the intent clear):
> Call form: MyFunction(X+2);
> GET closure: (+ closedX 2)
> UPDATE closure: (lambda (newval) (setf closedX (- newval 2))
> Thus from inside MyFunction where formal parameter Arg1 is bound
> to actual parameter X+2, after doing Arg1 := 7; X will have the
> value 5 so that calling Arg1 will return 7 as expected, right?
> But if the actual argument is something complicated, especially if
> it makes a nested function call, how can that possibly be
It was forbidden. In the formal definition of ALGOL 60, there was no
such thing as an external subprogram (except for non-ALGOL code, which
was treated as magic), so the whole program was supposed to be one
compile. Therefore, a theoretical compiler could verify that any
parameter used as an LHS was always matched with an argument that was a
variable. (However, a "thunk" was still required to evaluate any array
index and, possibly, to convert between REAL and INTEGER variables.)
Many actual compilers /did/ support separate complication as a language
extension -- I suppose they had to use run-time checking.
John W. Kennedy
"Compact is becoming contract,
Man only earns and pays."
-- Charles Williams. "Bors to Elayne: On the King's Coins"
More information about the Python-list