User:Soundandfury/ECLAIR

ECLAIR is an HDL for ternary ECL, if ECL were defined as "weighted summing amplifiers and diodes". eclair is a simulator for combinatoric ECLAIR circuits, and ecloop is a simulator for sequential ECLAIR circuits (also called "LOOPY ECLAIR").

General Format
An .ecl file consists of a series of lines, of the form value=FUNCTION operands... or one of the special lines or a block definition { 	ecl-lines... }
 * 1) NAME blockname
 * 2) IN inputs...
 * 3) OUT outputs...
 * 4) LOOPY

Operands
The universal datatype is the trit, represented with +,0,-.

Operands must not contain '.' as this is used to read members (this should really just be outputs) of instances.

eclair requires that all 'name' operands must have already been defined, thus precluding circular references. ecloop allows circular references (and thereby sequential logic). An ECLAIR circuit with circular references must contain the #LOOPY directive; eclair will reject any circuit with #LOOPY and advise you to use ecloop instead. Also, block definitions and instantiations are only supported in ecloop, not eclair (because the latter has a crummy old version of the parser. Though someday it might be re-done).

Block definitions may not be nested (though instantiations may appear within blocks). Instantiating a block within itself (even indirectly) is illegal and produces undefined behaviour (for example, the synthesis may get stuck in an unbounded recursion, or it may reject the input with a diagnostic, or just produce unexpected results. Just what "expected results" would be, I'm not quite sure). ecloop requires that a block must be defined before it is instantiated, which prevents recursive instantiation.

Functions
The FUNCTIONs are:

Blocks
A block definition is just an ordinary ECLAIR circuit, enclosed in curly braces. The block can then be instantiated (many times) by using its #NAME as a FUNCTION; the operands should be the inputs in the order they appear in the block's #IN. The instance's outputs can be read with instance.output

An example: { 	#NAME MEM ## 1-trit memory cell #IN S R 	#OUT D 	S=INPUT R=INPUT D=WSUM 2 S 1 Up 1 Dn 	DU=DIODE + D 	DD=DIODE - D 	Up=SUM R DU 	Dn=WSUM - R + DD } { 	#NAME NZ 	## Tests nonzero #IN X 	#OUT NZ 	X=INPUT U=DIODE + X 	D=DIODE - X 	NZ=WSUM + U - D } S=INPUT RR=NZ D R=WSUM 1 + -1 RR.NZ M=MEM D R D=SUM S M.D
 * 1) NAME Saturating counter
 * 2) Demonstrates the use of user-defined blocks and instantiations thereof
 * 3) When S is nonzero, add it to the value in M.  This can take up to four clocks.
 * 4) IN S
 * 5) OUT D
 * 6) LOOPY

Implementation
eclair and ecloop have both been implemented. The source is available at, together with some example programs.