- Notifications
You must be signed in to change notification settings - Fork5
A simple/minimal TCL interpreter, written in golang
License
skx/critical
Folders and files
Name | Name | Last commit message | Last commit date | |
---|---|---|---|---|
Repository files navigation
After re-readingTCL the Misunderstood, I decided to create a simple TCL evaluator of my own. This project is the result, and it has feature-parity with the two existing "small TCL" projects, written in C, which I examined:
There is a simple introduction to this project, and TCL syntax, on my blog here:
The name of this project was generated by looking for words containing the letters "T", "C", and "L", in order. I almost chose
arTiCLe
,TreaCLe
,myThiCaL
, ormysTiCaL
.Perhaps somebody else can write their own version of this project with one of those names!
This repository contains a TCL-like interpreter, along with a sample driver.
You can build both in the way you'd expect for golang applications:
$ go build.
Once built you can execute the application, supplying the path to a TCLscript which you wish to execute. For example:
$ ./critical examples/prime.tcl 0 1 2 is prime 3 is prime ..
The interpreter contains an embedded "standard-library", which you can view atstdlib/stdlib.tcl, which is loaded along with any file that you specify.
To disable the use of the standard library run:
$ ./critical -no-stdlib path/to/file.tcl
Generally the point of a scripting language is you can embed it insidea (host) application of your own - exporting project-specific variablesand functions.
You'll find an example of doing that beneath theembedded/ directory:
The following is a simple example program which shows what the code here looks like:
//// Fibonacci sequence, written in the naive/recursive fashion.//procfib {x} {if { <=$x 1 } {return 1 }else {return [expr [fib [expr$x - 1]] + [fib [expr$x - 2]]] }}//// Lets run this in a loop//set i 0set max 20while {<=$i$max } {puts"Fib$i is[fib$i]"incr i}
Another example is the test-code which @antirez posted with hispicol writeup which looks like this:
procsquare {x} { *$x$x}set a 1while {<=$a 10} {if {==$a 5} {puts {Missing five!}set a [+$a 1]continue }puts"I can compute that$a*$a =[square$a]"set a [+$a 1]}
This example is contained within this repository aspicol.tcl, so you can run it directly:
$ ./critical ./picol.tcl I can compute that 1*1 = 1 I can compute that 2*2 = 4 ..
Additional TCL-code can be found beneathexamples/.
The following commands are available, and work as you'd expect:
append
,break
,continue
,decr
,env
,eval
,exit
,expr
,for
,if
,incr
,proc
,puts
,regexp
,return
,set
,while
.
The complete list of standardTCL commands will almost certainly never be implemented, but pull-request to add omissions you need will be applied with thanks.
Read the fileinput.tcl to get a feel for the language, but in-brief you've got the following facilities available:
- Floating-point mathematical operations for
expr
+
-
/
*
%
.
- Comparison operations for
expr
<
>
<=
>=
,==
,!=
,eq
,ne
- Output to STDOUT via
puts
. - Inline command expansion, for example
puts [* 3 4]
- Inline variable expansion, for example
puts "$$name is $name"
. - The ability to define procedures, via
proc
.- See the later examples, or examine code such asexamples/prime.tcl.
The biggest missing feature is the complete absence of support for lists of any kind. This is common in the more minimal-TCL interpreters I examined.
The other obvious missing feature is support for theupvalue
command, which means we're always a little at risk of scope-related issues.
Addingupvalue
would be possible, but adding list-processing would be more work than I'd prefer to carry out at this time - see #19 for details of what would be required to implement this support.
Our code has 100% test-coverage, which you can exercise via the standard golang facilities:
$ gotest ./...
There are also fuzz-based testers supplied for thelexer andparser packages, to run these run one of the following two sets of commands:
cd parsergotest -fuzztime=300s -parallel=1 -fuzz=FuzzParser -v
cd lexergotest -fuzztime=300s -parallel=1 -fuzz=FuzzLexer -v
This repository was put together afterexperimenting with a scripting language, anevaluation engine, putting together aFORTH-like scripting language, writing aBASIC interpreter and creatingyet another lisp..
I've also played around with a couple of compilers which might be interesting to refer to:
- Brainfuck compiler:
- A math-compiler:
Please feel free to open a new issuewith your example included so I can see how to fix it.
Steve
About
A simple/minimal TCL interpreter, written in golang
Topics
Resources
License
Uh oh!
There was an error while loading.Please reload this page.
Stars
Watchers
Forks
Contributors2
Uh oh!
There was an error while loading.Please reload this page.