6502.org Forum  Projects  Code  Documents  Tools  Forum
It is currently Thu May 09, 2024 5:32 pm

All times are UTC




Post new topic Reply to topic  [ 12 posts ] 
Author Message
PostPosted: Tue Jul 19, 2016 12:31 pm 
Offline
User avatar

Joined: Thu Dec 11, 2008 1:28 pm
Posts: 10800
Location: England
Here's a transcript of a now-unavailable video interview with Chuck Moore, from 1999.
http://www.ultratechnology.com/1xforth.htm

There are many good little quips in here. I think Chuck always comes across as having quite strong and perhaps quite extreme opinions. But interesting thoughts all the same.

Quote:
But as to stack parameters, the stacks should be shallow. On the i21 we have an on-chip stack 18 deep. This size was chosen as a number effectively infinite.


Quote:
I don't see that ELSE is as useful as the complexity it introduces would justify. You can see this in my code. I will have IF with a semicolon and then I will exit the definition at that point or continue.


Quote:
nested loops are a very dicey concept anyway. You may as well have nested definitions.


Quote:
On i21 the return stack is only 17 deep. People who are used to nesting indefinitely might get into trouble here. You shouldn't nest too deeply. It makes programs impossible to follow. You can have spaghetti code with calls just a you can with GOTOs. You have got to keep it simple.


Quote:
I have found that teaching someone Forth does not mean that he is going to be a good Forth programmer. There is something more than the formalism and syntax of Forth that has got to be embedded in your brain before you're going to be effective at what you do.


Quote:
About a thousand instructions seems about right to me to do about anything.


Quote:
The whole point of Forth was that you didn't write programs in Forth you wrote vocabularies in Forth. When you devised an application you wrote a hundred words or so that discussed the application and you used those hundred words to write a one line definition to solve the application. It is not easy to find those hundred words, but they exist, they always exist.


Quote:
I remain adamant that local variables are not only useless, they are harmful.


via Margaret Leber on gplus.


Top
 Profile  
Reply with quote  
PostPosted: Tue Jul 19, 2016 6:27 pm 
Online
User avatar

Joined: Fri Aug 30, 2002 1:09 am
Posts: 8432
Location: Southern California
Yes, he always has some interesting ideas, and fortunately he sometimes realizes one wasn't so good. I remember him saying something like "The map isn't the land," and although I don't remember the details it seems like he was saying there was something deficient about human-readable code. I think that was one he went back on.

I've mentioned here before that I did a test to see how much of the space of both stacks I used on the 6502, and came up with the most stack-intensive ap I had written and then had IRQ interrupts serviced in high-level Forth plus NMIs serviced in assembly language, and found that I used less than 20% of both stacks. 20% of 256 bytes is about 51 bytes. If it were all two-byte cells (it wasn't), that would be 25 cells, which is more than his 18. I wonder if he believes in interrupts. His number does seem to conflict with his ideas of keeping definitions super short and of factoring out things that are only used once, adding to the nest/unnest overhead, not to mention trying to give all these factors names that are any more meaningful than the code itself, and the additional memory penalty incurred by the extra headers. On an entirely different level is multitasking where a separate stack area is given to each task so a task doesn't have to completely finish its stack usage before relinquishing control, like a zero-stack-effect word.

I think he was also against the CASE structure. I cannot agree with him on that.

Nested definitions? Nested macros in assembly language are certainly useful, like if you want one macro to be able to invoke another so you don't have to spell out all the code that there's already another macro for. But isn't that similar to what Forth does all the time? A colon definition uses other colon definitions which use others, until you get down to the primitives, ie, code definitions which are always written in assembly.

I haven't used local variables so far in Forth, but I remain interested. The internals appear simple enough, but I haven't done it to know what challenges I'd run into. I did write about local variables in assembly language in the 6502 stacks treatise at http://wilsonminesco.com/stacks/loc_vars.html .

Forth is great for us obstinate free-thinkers who want to do things our own way though. We don't have to agree. It lets us make our own tools to get the job done.

_________________
http://WilsonMinesCo.com/ lots of 6502 resources
The "second front page" is http://wilsonminesco.com/links.html .
What's an additional VIA among friends, anyhow?


Top
 Profile  
Reply with quote  
PostPosted: Tue Jul 19, 2016 6:57 pm 
Offline
User avatar

Joined: Thu Dec 11, 2008 1:28 pm
Posts: 10800
Location: England
The quote about nested definitions is, I think, in a bit about loop constructs. I think he's saying that when a definition can call itself, you don't need looping. So, recursion instead of iteration, which is an idea with a pedigree. To combine recursion with a shallow stack you do need to be able to substitute a jump for the call, which he's aware of.


Top
 Profile  
Reply with quote  
PostPosted: Wed Jul 20, 2016 12:12 am 
Offline

Joined: Wed Jan 08, 2014 3:31 pm
Posts: 575
He kinda strikes me as the software industry's equivalent to Nikola Tesla. He's smart and made major contributions, but seems to say some outrageous things.

For example, traversing a large graph or forwards or backwards chaining can consume enormous amounts of stack, and even small 8 bit machines can solve such problems too. For example my junior year project was written using Inter-Lisp on my Atari 800XL to evaluate game trees. It was slow, ate half my RAM generating and evaluating tree nodes, but it worked.

Now you could use FORTH to solve such problems, but you would need a stack to hold state while you travel the tree, and I can't imagine fitting that into 18 cells.

As an aside, I wish I never sold the 800. I had a custom ROM with 80 column text, and built-in machine language monitor. I had more fun with that machine than anything since.


Top
 Profile  
Reply with quote  
PostPosted: Wed Jul 20, 2016 5:37 am 
Offline
User avatar

Joined: Thu Dec 11, 2008 1:28 pm
Posts: 10800
Location: England
Agreed - some problems have good recursive solutions, and you need an adequately deep stack for those. But in any case, you do need to know when you've reached the limit of your stack. That's the sort of thing that hardware can help with.


Top
 Profile  
Reply with quote  
PostPosted: Wed Jul 20, 2016 8:19 pm 
Offline
User avatar

Joined: Mon Apr 23, 2012 12:28 am
Posts: 760
Location: Huntsville, AL
I generally enjoy just reading threads such as this one. I tend to learn quite a bit from the back and forth discussions. However, I think that this discussion regarding Chuck Moore has gotten off track a bit, and is missing the point about stack capacity.

I believe that Mr. Moore is referring to a stack depth that allows a FORTH chip to support a broad spectrum of FORTH applications without breaking the bank by using scarce resources to implement FORTH stacks on-chip. On-chip stacks will naturally have a limit simply due to the area required to implement them. Overly deep stacks will incur area penalties and provide resources seldom used by the majority of FORTH programmers. Those area penalties will result in lower yields, increased costs, reduced number of processors on a chip/die, etc.

From a FORTH chip vendor's perspective, the penalties associated with the production of FORTH chips with seldom used resources far outweigh the effects that smaller on-chip stacks will have on FORTH programmers. In addition, the lower costs and increased number of processors on each chip/die can lead FORTH programmers to develop and utilize more efficient distributed programming solutions that don't rely on tried and true, but generally resource inefficient, solutions such as recursion.

Recursion is an elegant approach to many problems, but it relies on a very particular processor architecture element: an "infinite" depth stack. Assuming that a processor architecture or computer language supports recursion and using it to solve problems is, in my opinion, a poor choice. It is far more likely that recursion will provide the programmer employing it the opportunity to measure the processor's (or his programming environment) stack depth. It is also very likely, particularly in embedded systems with their far more resource-limited processors, to result in very poor behavior.

I generally frown on using recursion for any solutions on embedded platforms because the testing required to ensure correct behavior under all circumstances is generally never performed to an adequate level of rigor. The complexity of most applications is such that having a complete enough understanding of the ramifications of a recursive solution is insufficient to build reliable embedded systems.

I cringe and gnash my teeth whenever I hear that the solution to a particular runtime problem was to increase the stack depth. This is a very common approach to solving runtime issues in embedded systems, so I naturally shy away from approaches like recursion which invite this type of fix.

One of my favorite processors, the Inmos Transputer, only had a 3-deep, programmer-visible evaluation stack. In my current work, I use an ALU inspired by that processor, but I built my ALU to have a 5-deep evaluation stack. Professor May and the Transputer team performed many studies regarding the average depth of the evaluation stack for different programs and programming languages. On average, a 3-deep stack was sufficient, so that is how the Transputer ended up with its evaluation stack.

In my case, however, I found that I needed a 5 deep stack to pass the parameters to my common signal processing routines, and I did not have the luxury of spilling parameters into another stack like the workspace stack of the Transputer. So I upped the depth of my ALU's evaluation stack in order to minimize programmer effort for the majority applications in which my ALU would be used; in most instances, the programmers using my ALU only use 2/3 elements of the evaluation stack.

_________________
Michael A.


Top
 Profile  
Reply with quote  
PostPosted: Wed Jul 20, 2016 8:27 pm 
Offline
User avatar

Joined: Thu Dec 11, 2008 1:28 pm
Posts: 10800
Location: England
It's a fair point, embedded computing is different from general purpose computing.


Top
 Profile  
Reply with quote  
PostPosted: Wed Jul 20, 2016 8:59 pm 
Offline

Joined: Tue Jul 24, 2012 2:27 am
Posts: 672
While I haven't read this article, doesn't his general thinking trend toward the hardware Forth being used to run a user-space Forth that actually runs the applications? The depth of the hardware stack would be related to the depth the Forth environment would use in its evaluations, not the nesting depth of the user program.

_________________
WFDis Interactive 6502 Disassembler
AcheronVM: A Reconfigurable 16-bit Virtual CPU for the 6502 Microprocessor


Top
 Profile  
Reply with quote  
PostPosted: Thu Jul 21, 2016 12:50 am 
Offline

Joined: Wed Jan 08, 2014 3:31 pm
Posts: 575
I skimmed the article as I've read it before. The article is a bit dated which isn't a suprize considering it's age.

For CPU designs stack machines fell out of favor verus register machines. Register machines work better for pipelies, multiple instruction issue, out of order execution, and general bus bandwidth utilization. This is important because CPU's now generally run faster than the data bus, so the on chip cache and instruction pipeline helps the CPU run at peak performance. While the Java virtual machine is stack based, when Google implemented their Dalvik VM they also switched to a register machine with fewer but more complex instructions for similar reasons.

Also, most compiler output I've read targets the underlying hardware stack if it is present because of the greater efficiency it allows. So if your application needs a deep stack it will be better off if the underlying hardware has deep stack as well.

All that said, in a perfect world stack machines are much more elegant than register machines. The elegance of FORTH made it fairly influential for languages like PostScript, the JVM, and Open Firmware. I wish I came up with an idea half as good or influential.


Top
 Profile  
Reply with quote  
PostPosted: Thu Jul 21, 2016 5:50 pm 
Offline

Joined: Sat Dec 13, 2003 3:37 pm
Posts: 1004
you can consider stack depth as a measure of levels of abstraction in your application. Since the stack is used to demarcate those levels via word invocation.

Chuck has always appeared to me to be a pretty minimalistic guy. Witness ColorForth. So, for Chuck, perhaps a depth of 18 is abstract enough.

His point about nesting loops, I don't see Chuck as a recursive guy. You can't recurse very well with an 18 deep stack, for example, and Forth doesn't implicitly support tail call optimization ala Scheme, which make recursion a much more viable looping mechanism.


Top
 Profile  
Reply with quote  
PostPosted: Thu Jul 21, 2016 6:11 pm 
Offline
User avatar

Joined: Sun Jun 30, 2013 10:26 pm
Posts: 1928
Location: Sacramento, CA, USA
I don't pretend to be in the same league as Chuck, but the gut-feeling I got from reading this was that he had a tendency to avoid nested loops in a single word, and instead to hide the inner loops inside nested words. This is different than recursion, obviously. Similar tactics can be used with complex conditional structures, to hide some of the complexity within nested words; one or two "IF"s per word.

Am I making any sense?

Mike B.


Top
 Profile  
Reply with quote  
PostPosted: Thu Jul 21, 2016 8:05 pm 
Offline
User avatar

Joined: Thu Dec 11, 2008 1:28 pm
Posts: 10800
Location: England
(I see this as saying that Chuck does indeed optimise tail calls:
Quote:
So there is no reason to make that a call since you are never going to go anywhere afterwards so you just make that jump. In fact in all my latest Forths semicolon kind of meant either return or jump depending on the context and it's optimized in the compiler to do that. It's a very simple look back optimization that actually saves a very important resource, the return stack.

)


Top
 Profile  
Reply with quote  
Display posts from previous:  Sort by  
Post new topic Reply to topic  [ 12 posts ] 

All times are UTC


Who is online

Users browsing this forum: No registered users and 2 guests


You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot post attachments in this forum

Search for:
Jump to: