Forth on Robots

From HBRC WIki

Jump to: navigation, search

If you do not wish to edit this page yourself please email name@gmail.com, where name is johngslater, and send me additions or changes.

Contents

The Project

This project promotes the use of Forth for robot control by implementing Forth on one or more robots. We will document things as we go to show what works and why it works.

What is Forth?

Forth is an extensible command language. The language has a dictionary of command words, where each word causes some action. Forth programs extend the command language by defining new words and inserting them in the dictionary. New words are defined as either compound (also called "high level") words using words already in the dictionary or as primitive words defined in assembly language. Think of each Forth word as a subroutine.

Forth uses a programmer visible data stack to pass subroutine parameters. Each Forth word can push words onto the stack or pop them off as it uses them. Consider the following Forth command line:

OK> 1 2 + . CR
3
OK> 

The OK> is the command prompt, and the CR means carriage return = end of line. "1" pushes a numeric 1 on the stack and "2" pushes a numeric 2 on the stack. "+" adds the top two stack elements leaving one element on the stack. "." prints the result, "3". The CR causes a new line and a new "OK> prompt.

The "1" and "2" each push an element on the stack. The "+" adds the two and pops an element from the stack, leaving the sum. The "." prints the element on the top of the stack, then pops it off.

Forth command line parsing is elegantly simple. The parser looks for names of words. These are defined as contiguous groups of ASCII characters set off from other names by white space (e.g. spaces, tabs, etc.) When it finds a name, it looks it up in the dictionary, comparing latest dictionary entries first. If it finds a match, it executes the corresponding word. If it does not find a match, the parser tries to convert the name as a number. If the conversion is successful, it places the numeric value of the converted number on the stack. If the conversion is not successful, the parser aborts with an error. That's all.

Forth was invented by Charles Moore in 1970 as a language to control the telescopes at Kitt Peak National Observatory. Charles Moore founded Forth, Inc. to commercialize Forth. Forth has been implemented on almost every computer that has been built, from the earliest microprocessors to the Cray machines. It was very effective on early satellites. The Forth Interest Group helped this proliferation of Forth by porting it to almost all microprocessors.

Forth is simple in concept and execution, but different from conventional languages. Almost all other languages except assembly are based on the model of a memory containing (global) variables and an equation that changes these variables. Fortran, Basic, Pascal, Modula, C, Python, etc. all have this basic model.

The assembly language model has a main memory and a register memory, not part of main. Assembly language instructions copy words from memory to registers, manipulate the register data and write register data back to memory.

The Forth model has a memory containing variables and a calculator-like stack for manipulating variables instead of using an equation. The stack is a small memory that works like a stack. It is commonly implemented as a small array in main memory. Forth command words get data from memory to the stack, manipulate words on the stack and put them back in memory.

What Good is Forth?

Forth is:

  • interactive - lets you directly read and control I/O devices from the keyboard
  • transparent - you can see and modify any and all of Forth from the keyboard and
  • fast - typically runs at 90% of assembly language speed,
  • small - Forth takes ~8 KBytes total for most machines,
  • tight - Forth code often takes *less* space than assembly language,
  • powerful - because of its clean extensibility.

Forth is a command language. It is good for controlling things that move and make a noise, like robots. Its interactive nature lets you directly interact with the machinery you are trying to control. You can wiggle and measure things without having to recompile, etc. This is important during test and debug where you are exploring and measuring actual performance and trying new algorithms for improving the performance. Immediate action and feedback are good.

Forth is completely transparent . You can examine and modify anything from the keyboard. It is also small enough to allow you to completely understand everything. This is a Great Comfort to anyone debugging a system. When things do not work, you need to pop the hood and look underneath. It is not good knowing it *should* work when it *doesn't* work. This is especially true for hardware systems such as robots, where the problem is likely to be a run-time problem caused by assumptions about how the system should work versus how it does work. Debug means measuring and re-thinking.

Forth is an interpreted language with incremental compile. This means interactive + fast. Forth words (i.e. subroutines) can be directly executed from the keyboard by the interpreter. It pulls in a line of text and executes one word at a time. When a new word is defined from the keyboard, the new word is compiled into a list of subroutine calls (compound word) or directly into assembly language (primitive word). Primitive words are assembly language and run at full speed. Compound words tend to run at close to assembly language speeds because they are just nests of fast calls to assembly language primitive routines. Therefore, any new word you define (which is how you program) runs at full speed when called.

Forth is small. You can get a complete Forth system in ~8 K Bytes of code on a typical uP such as an AVR or a PIC, perhaps 12 K Bytes on a 32-bit machine such as an ARM. This means that Forth can fit on almost any micro with room to spare. Also, added code tends to take up little space. Forth code can actually take *less* space than assembly language.

Forth is powerful because it is so cleanly extensible. All words are equal in terms of calling overhead, etc. By defining new words, you end up creating an application specific language (vocabulary) for efficiently capturing and implementing the abstractions of your design.


What Good is Forth for Robots?

Forth is an interactive language good for controlling things that move and make a noise, like robots. It lets you directly interact with the I/O devices that drive and sense the machinery you are trying to control. You can wiggle and measure things without having to recompile, etc. This is important during test and debug where you are exploring and measuring actual performance and trying new algorithms for improving the performance. Immediate action and feedback are good.

In debug, you are investigating how the robot works and how to make it work. You have an idea of how it *should* work, but it usually does not work as it "should". You are usually fighting hardware bugs such as sensor problems, electrical noise, motor limitations, friction, etc. So you need to instrument your machine, not just your code. Forth lets you code up test and data log programs quickly for debugging. That is why it is a popular language on the test floor.

Forth also provides speed. Forth words are compiled and run at close to assembly language speed. Some robot functions that you may want to test have to run in continuous real time. A balancing robot is a good example. Its code has to run at real time rates, or the robot falls over. You cannot slow it down or single step it. Another common example is moving wheels and arms in a coordinated way. Motors have to move together in time or you do not go where you expected, etc.

Forth usually runs 'on the bare metal', eliminating the need for an operating system. You have full control of timing and operations. Without an Operating System to run, you run a simple, tight infinite loop, and you specify all the logic and operations done within each loop.

A cheap AVR 8-bit microprocessor has a 20 MHz instruction rate. Running a Forth word takes about 10 (assembler) instructions => 0.5 usec. This means you can easily do motion control system with a 1 KHz (1000 usec) or faster update rate, with loops of several hundred words with good margin. This can be very important in robotics. For example, balancing robots need very fast response to changes in sensor readings that tell you about tilt or some obstruction you might hit.


How Can I Use Forth on My Robot?

Forth fits in an AVR Atmega328 with 32 K Bytes of flash and 2 K Bytes of RAM. It will also fit in various PICs an fits nicely in ARM devices such as the NXP 2106, etc.

Pololu sells a Stamp-like module called the Baby Orangutan with an Atmega328 for $30. The programmer costs an additional $20. It is mostly compatible with the Parallax Stamp module. You have to cut off (or not mount) about 6 pins. I (Dave) am running one on a BoeBot in place of the Stamp.


The Forth Experience - A Maker Language

Forth is a command language. It is good for controlling things that move and make a noise, like robots - a "maker" language. You have to actually use it to understand how much it can help you. "Hello, world!" is not enough. The best way is to develop code for operating or testing something like a robot. The equivalent for Forth is to blink an LED or spin a motor.

Forth is very good at letting you directly control I/O devices such as sensors and motors. All other languages (except assembly) strongly oppose this idea. The language and operating system buffer and restrict any attempt to control I/O, lest it cause the system to crash. This is an understandable for a big data center running many users, but not for controlling motors on a single machine. Direct control of I/O is mostly what robots are about.

Forth is an excellent language for debugging. And the proof of the robot engineering is in the debugging, where you can spend 90+% of your time. Forth is an interactive language, and the code-test-debug-recode cycle is very tight. You tend to develop one word at a time. As soon as you create the word, you can test it and fix it if it is not right. As a result, you are typically building new words using already tested words.

Forth code consists of a set of named subroutines called words. The code for a Forth word tends to be short. This is not a requirement nor does it require effort. It is an observation. Short words are easy to understand and test. They are often right the first time. We know from programming experience that the number of bugs tends to go up with at least the square of the size of the program. Short words reduce bugs, and the short code-test-recode loop tends to find and fix them quickly.

The code for a Forth word tends to be short because there is no penalty to short, deeply nested words. In Forth, all words (i.e., subroutines) are equal in terms of calling and using them. The calls are simple, bare calls, with parameters implicitly passed on the data stack. As far as computing theory is concerned, short, nested routines are a Good Thing.

Conventional languages like C, etc. indirectly penalize subroutines and functions. Count how many line of code you have to write to call a "Hello, world!" subroutine from Main. There is a structure to be stet up for coding and calling subroutines and functions. All call and return parameters have to be explicitly enumerated in the call and inside the subroutine as part of the call. If subroutine calls another subroutine, those parameters must be explicitly enumerated. Forth decouples the subroutine data parameters (data flow) from the subroutine call (control flow). Implicit passing is used instead of explicit enumeration.

And Forth is also a programming productivity enhancer. A typical, reasonably good programmer will usually experience a significant performance improvement as measured by debugged functions completed per day. A 5X improvement is a typical number. I (Dave Wyland) have experienced this. Now, programming productivity improvements are endlessly arguable as well as the benchmarks that support or deny them. However, if *your* own, personal productivity goes up on a project by using Forth, this is the unarguable benchmark. I will leave it to the student to discover this effect on his or her own.

Forth Project Goals

This project will implement a Web Controlled Device. Web Controlled Devices (say a robot!) have a web server on them. This allows anything with a web browser (say a cellphone!) to interact with the device.

Forth will be used to program the device, and a web page based Forth IDE will be used to program the device and interact (ie control) with it.

Current Project Goals

  • Put a Baby Orangutan B-328 Robot Controller http://www.pololu.com/catalog/product/1220 on a BoeBot (DAVE - done)
  • Install Forth on the ATmega328P of the Baby Orangutan (Dave - working on)
  • Create a web page based Integrated Development Environment (IDE) for object oriented Forth (John - working on)
  • Add a web server and wifi


Current Participants

If anyone wants to be part of this project, contact John Slater or Dave Wyland.

  • John Slater
  • Dave Wyland


Current Activities

John is learning Forth and figuring out how to implement an object oriented Forth. His IDE will then be updated.

Dave is (Aug 28,2009) fleshing out his implementation of Forth:

  • Writing to the flash memory. Looks OK, but you need to write a block of 128 bytes at a time. - Done
  • Compiling words: CONSTANT, VARIABLE, ALLOT, COLON, DOES> and SEMICOLON. - Done
  • Conditional and loop words: IF, ELSE, ENDIF, DO, LOOP, BEGIN, WHILE, UNTIL, REPEAT
  • Adding real-time support: a timer based interrupt system
  • Bring up the BOEBot.
  • Bring up the rate gyro from Pololu.


Forth Links for More Detail

These are broken out so this Wiki page does not get too long.


Forth Basics Page

This goes into more detail on how Forth works and how it is built internally.

Forth_on_Robots/Forth_Basics


Forth Dictionary Page

This page provides a dictionary/encyclopedia for the basic Forth words you need to get Forth up and running. The intent is to provide a small, grouped dictionary reference to basic Forth kernel words in a manner that is easy to follow and provides the data you need to understand what is going on.

Forth_on_Robots/Forth_Dictionary


Discussion Section

This section discusses the project goals and ideas in more depth.


Forth Model

  • How Forth Works
  • Forth Machine Model: memory and stacks
  • Action words versus equations and state
  • Differences with other languages


Forth Interpreter

  • Finds words separated by white space and interprets them
  • White space definition
  • Comments
  • Aborts


Extensions to Make Forth Easier To Use

Forth is simple in concept and use, but subtle. It has a reputation for being hard to learn, with some justification. Forth can be extended to provide some answers to this problem, as follows:

Documentation

Much has been written about Forth, but simple and clear documentation is scarce. One of the goals of this effort is to solve this problem. This includes:

  1. Showing the full Forth interpreter from the top to the primitives in a file-tree (folders =>files) like manner. Forth is very web-like and HTML compatible in that top level words are linked to lower level words with the last link being a primitive.
  2. Documenting each standard word in a Forth glossary/encyclopedia


Friendly Language Features

The data stack is the key to Forth and its power, but it is cumbersome to use for calculation. The programmer has to keep track of the condition of the stack at all times, and does a lot of stack manipulation ("stack gymnastics") to position stack variables for use. Some features that can help include:


Local Variables Page

This page discusses implementation of local variables in Forth. Local variables can be very convenient.

Forth_on_Robots/Local_Variables

Compound Variables Page

Standard Forth variables are atomic: byte, half-word (16-bit), word (32-bit), even double-word. It is relatively easy to pass one or two of these atomic words on the stack and return a result. However, we often want to define and/or pass groups of variables. This page discusses solutions to this problem.

Forth_on_Robots/Compound_Variables


Forth Potential Extensions and Ideas Page

This page discusses on-going, work in progress extensions to Forth such as aliases. As each extension becomes large enough, it will be moved to its own page.

Forth_on_Robots/Forth_Extensions


Applying Forth To Robots

A Forth Robot Controller

Robot control is a real-time machine control problem.

Two kinds of processing are required: Stream (continuous) processing and task (batch) processing.

  • Stream processing closes control loops by reading sensor data, processing it and using the results to drive motor servos. In concept, the stream processor runs continuously, without stopping. In the proposed architecture, a timer interrupt driven loop periodically updates the control loops, forming a sampled data control system. The update period is 1 to 10 milliseconds, selected to be at least 10 times the loop bandwidth of the servos.
  • Task processing performs tasks that run to completion and stop. These are typically human commanded tasks, such as requesting the robot to go to a particular location. In the simplest case, a single task is run, the background task.

Forth is proposed for both the stream and task processors.

The robot controller also needs a human text and graphics interface. A web server chip can provide this interface. Single ship web servers are available from WizNet (W5100) and Microchip (PIC18F97J60) for ~$5. All that is required is an RJ45 Ethernet connector. Such a chip can communicate directly with a web browser (e.g., Firefox) in a PC or laptop using a standard Ethernet cable at rates of 10 or 100 M Bits/sec. The controller can communicate with the web browser chip using a standard interface such as TTL UART or SPI, depending on the requirements of the web server chip.


A Web Page Based Integrated Development Environment (WIDE)

A common problem with development environments is that they are a block of software that must be installed and updated on a PC. The ongoing installation and update compatibility problems are well known. A good way to avoid this is to require no installation of software on the remote computer.

Forth can enable this. Forth is an interactive language that usually communicates with the user through a UART. You can develop programs in Forth using a standard terminal program on a PC such as Windows Hyperterm. The terminal program can communicate with the Forth chip and download Forth source code text files. These text files can be generated and edited using standard text programs such as Notebook, etc. The important point is that no new software need be installed on the PC.

A better way to accomplish this by having an Integrated Development Environment (IDE) software package on the robot itself, accessed using a standard web browser such as FireFox. The TCP/IP standard and the effective requirement that all web browsers must support all existing web pages provides a stable software standard for the PC end.

A web browser provides additional benefits. In addition to text I/O, it provides a standard graphical interface driven by ASCII text, HTML. A small amount of HTML text in the robot can generate useful web pages in the browser. Web browsers communicate can over Ethernet cables, and all PC's (including laptops) have Ethernet interfaces and RJ45 jacks for them. Wireless operation using WiFi is also available. Also, several users can remotely and simultaneously monitor (and control) robot activity over the web.

The Web IDE (WIDE) can be simple and run on a single chip Ethernet + TCP/IP chip such as available from WizNet and Microchip for $5. Static web pages with updated text will provide WIDE graphics. Software updates are made to the robot WIDE, while the desktop PC, laptop PC or phone accesses the WIDE using existing browsers.

The web browser can provide support features beyond text interaction and graphics. The PC/phone is a potentially good place to store files, copy and send them to others and to print the text and graphics displayed by the browser, for example. These functions can be done using the standard browser(s).

This is not intended to inhibit developing WIDE support on the connected desktop, laptop or phone. The idea is to provide basic WIDE service on the robot to insure that you can always talk to the robot. Extensions can be added on the laptop, etc. if it makes sense.


WIDE Components

Components are now available to implement the WIDE concept.


MicroChip and Ethernet

MicroChip has a single chip that has TCP/IP, an on-board 10/100/1000 BaseT Ethernet port and runs the web server for ~$5.

See http://www.microchip.com/wwwproducts/Devices.aspx?dDocName=en026442

WizNet and Ethernet/WiFi

WizNet has a single chip web server chip on a module for $22. It has a 100BaseT Ethernet port and plugs into a conventional PCB.

See: http://www.ewiznet.com/goods_detail.php?goodsIdx=132

WizNet also has a WiFi module for $50

See http://www.ewiznet.com/goods_detail.php?goodsIdx=135

Rabbit and WiFi

Rabbit has a server+wifi solution the server+wifi combo means the chip&robot running Forth has some wires going to this module.

The std dev kit is $99, w/ 1 yr tech support. The part used on robots is $70.

Links:

But wi-fi is a little energy intensive:

  • 625 mA @ 3.3 V while transmitting/receiving
  • 85 mA @ 3.3 V while not transmitting/receiving

Do you want to become the expert for this piece of the puzzle?


  • Hook device to a web page (John&Dave - TBD). Examples of prior art:
    • eye.fi
    • iobridge.com
  • Add Firefox browser extension so an Android phone provides access to cell phone hardware (ie accelerometer) (John has the phone)


WIDE Notes

The IDE can graphically animate parsing and stack operations; a picture is worth a thousand words, making it much easier for users to figure out how Forth works.

Since a web page running on a cell phone is an objective, the IDE should be designed to minimize typing.

Here is an example of how this might go:

http://mywebbasedcomputer.com/users/johngslater/robots/forth/tryForth.html

The IDE can use specific knowledge about certain words. For instance, you should only be presented with the words of the CONTEXT vocabulary.

Let circle1 be an instance of Circle. The word following circle1 should be a property. When the input focus is the word following circle1, only the vocabulary of Circle properties should be shown.


Personal tools