[TUHS] C declarations.

Bakul Shah bakul at bitblocks.com
Sun May 14 16:48:20 AEST 2017

So the problem was your assumptions didn't match IBM's! Most likely the FORTRAN standard /allowed/ pass by value/result instead of pass by ref.

None of the changes I suggested in my previous email (that focused on arrays in C) would have required a GC or heap. It would've increased programmer convenience and reduced bugs though! 

> On May 13, 2017, at 11:12 PM, Steve Johnson <scj at yaccman.com> wrote:
> I can't resist jumping in here.   My main point is that system coding is a rather different beast than most application programming.  An operating system must be able to handle memory allocation requests from a user without knowing any details of what is requested.  Dennis explicitly left out a heap and garbage collection code in C because he didn't want OS code to be burdened with it.  Similarly with a "real" string type (with concatenation, etc.).
> An example that speaks to me is that of creating a symbol table.  This isn't kernel programming, but consider what is needed:
> A structure that holds the individual table entries
> A tree of lookup tables that reflects the scoping rules of the language -- several tables might need to be searched to find an entry
> A function that looks up a name in a scope, returns the entry if it's defined, and adds a new entry in the appropriate scope if it isn't there yet.
> Statistically a majority of the calls do not change the symbol table, but some do, and you can't tell in advance.  And in the same way, many of the possible scopes where a variable might reside need not be searched.
> So how much of this table should we copy into the lookup function?  The answer seems obvious to me -- none of it...
> Before Unix, Dennis and I and several other people worked on a symbolic algebra system written in FORTRAN.  Dennis wrote a dynamic storage allocator, which was a real feat in FORTRAN, complete with garbage collector.  The goal was to have the program work on the 6 major manufacturers' FORTRANs.  We got it up and running on many of the systems, but did not have easy access to OS 360.   Finally, we were granted the third shift on the OS 360, and ran our program (that had become rather solid by this time...).   It was a disaster -- the brogram ran for a few second and then the OS dies and could not be restarted (turns out the core dump area allotted on the disc was not big enough to hold our program).  
> The problem turned out to be that the IBM compiler did copy in/copy out argument passing, while all the other compilers passed by reference.  If you passed in an argument  that was dynamically allocated, and the system did a garbage collection, all the elements that were still live were moved around but kept their contents intact... until the function returned, and tried to copy the changed value out where that block used to be at the time of the call.
> It took us about 6 months to rewrite the system so we didn't do that -- we had to allocate everything that would be needed first, then do the work, and then free things...
> None of us were fans of copy in/copy out after that experience...
> Steve
> ----- Original Message -----
> From: "Bakul Shah" <bakul at bitblocks.com>
> To:"Lawrence Stewart" <stewart at serissa.com>
> Cc:"tuhs" <tuhs at minnie.tuhs.org>
> Sent:Sat, 13 May 2017 21:24:11 -0700
> Subject:Re: [TUHS] C declarations.
> On Sat, 13 May 2017 21:59:57 EDT Lawrence Stewart <stewart at serissa.com> wrote:
> >
> > * - But I have never been able to remember the syntax for function pointers. > I always "man qsort" to refresh my memory.
> The way I remember:
> given *x[] or *x(), x /sticks/ to the /right/ first. Thus
> int *x[];	// x is array of ptr to int
> int *x();	// x is a function returning ptr to int
> If you don't want a var to stick to its right, separate using
> using parentheses.
> int (*x)[];	// x is a ptr to array of ints
> int (*x)();	// x is a ptr to function returning int
> int *(*x)[];	// x is a ptr to array of ptrs to int
> This sort of also works for multiple variables in one declaration. Given
> int *x, y;	// * /sticks/ to the right (x) first, so not available for y.
> Now if they'd allowed parenthesizing the type, as in
> (int *)x, y;
> we would see that both x & y are of type int *. That would've also allowed
> declaring multiple vars in one declaration where the previous rule applies!
> (int*)(*f,*g)();
> Part of the confusion is * is tacked on at the front while []
> & () at the back of a variable. Someone (Chandy?) had
> proposed unifying this syntax but it didn't go anywhere. I
> think the author used @ in a suffix place though I don't
> recall any other details. But if you put the var all the way
> to the right and read a declaration right to left, it works:
> int*[] x	// x is a array of ptr to ints
> int() f	// f is a function returning it
> int*()* f	// f is a ptr to function returning ptr to int
> int*()* f,g	// f & g are ptrs to function returning ptr to int
> This is only slightly weird if you are used to the current syntax
> but you can easily retrain yourself.
> IMHO, where evolution of C, Scheme and most programming
> languages goes wrong is doing evolutionary design by
> committee. Most users grasp what is easier to use vs what is
> hard but they don't have the aesthetic sense or imagination or
> training to make things simple. And in large groups popularity
> or force of personality or some other irrelevant attribute
> wins not aesthetics. Language evolution IMHO must be done by
> benevolent dictatorship or a guild of like minded people who
> have worked together for a long time! Go seems to have
> adapted that style....

-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://minnie.tuhs.org/pipermail/tuhs/attachments/20170513/46d94d99/attachment-0001.html>

More information about the TUHS mailing list