What is Tcc?

Tcc is a software package for assisting in the running of model railway layouts. It is software loaded onto a computer (Windows PC, Linux, Solaris, Mac) that drives interface hardware (such as RPC modules) that connect to model railway hardware such as signals, turnouts and control panels.

What hardware can Tcc drive?

Currently tcc can drive two types of hardware: Commercially available modules from an American company called CTI, and the RPC kits available to MERG members. Support for other types of hardware might be added later, if there is sufficient interest.

The CTI modules offer input lines (5V TTL/CMOS compatible with swappable pull-up resistors), current detect units, signal drive outputs, relay outputs and computer controlled throttles (called smart-cabs). All these modules each have a microcontroller on board and are connected into a loop using RS232 that connects directly to the computer. The drawback is primarily cost: inputs and outputs cost around US $10 per wire, and a throttle around $100. See http://www.cti-electronics.com for details.

The RPC modules offer input lines (5V TTL/CMOS compatible with fixed 100K pull-up), current detectors, open collector outputs and relay outputs. There is currently no kit for an RPC throttle, though the design in TB G16/51 is supported by Tcc. See http://www.mergrpc.freeserve.co.uk/rpc_page.htm for details of RPC kits.

RPC modules plug directly together in a 'stack', and connect to the controlling computer using a special stack header module. Tcc currently supports three types of stack header for RPC modules:

RPI-C
The RPIC (formerly RPI) is another RPC kit which connects to the computer at 9600baud half-duplex (a message arrives from the PC, the RPI does its magic and then replies to the computer).
RPI-Z
A two chip home-brew interface. This is called the RPI-Z in the software menu. This is a simple microcontroller (costing a couple of pounds) that connects to a MAX232 (RS232 interface chip) and directly drives the RPC stack. It runs at 9600 baud full-duplex (data both ways at the same time). I made this unit to save money.
QTU
The QTU module is currently in the prototype stage, and is primarily four throttles, but also has input and output cababilities and interfaces to the computer at 9600, 19200 or 38400 baud full-duplex.

What does Tcc do?

A difficult question to answer.

In simple terms it does very little, but it can be made to do anything you can define, with the inputs and outputs you have on the railway, and also it can display CTC (Computer Train Control), or MIMIC diagrams on the computer screen.

Tcc does NOT do interlocking, timetabling, route selection, or any of those tasks you associate with controlling or directing a railway. The reason it doesn't do any of these things is that however it chose to do something, there would be applications where the rules locked in for that task would get in the way. As a simple example lets suppose that Tcc automatically controlled signals. Which set of signalling rules should it use: which era, which operating company, which country? The Tcc answer is to build-in none of the options, but allow you to configure any of them, or another set of rules that you define yourself.

You tell it what to do by writing a configuration script file, that Tcc loads and runs. Some of the things it can do include:

  1. Control outputs according to the state of some inputs - for example drive signals dependant upon the positions of trains on the track, or set a collection of turnouts to select a route when a button on a panel is pressed.
  2. Remember what has happened before so that hardware errors do not cause problems - for example if a signal is set red when a train enters the next track, the signal will not go green just because the train derails.
  3. Display track and train information on CTC (MIMIC) windows on the computer screen. These can show which tracks are occupied, which way turnouts are set, which routes are booked, or even list a schedule of future arrivals at a station.
  4. Drive some of the trains so that you can have more activity on the layout than the operators alone could cope with.

You can put these basic operations together so that the computer can:

  1. Act like an intelligent PTP (Point-to-point) unit so that information is copied between a control panel and a layout.
  2. Just monitor whats happening and display track occupancy, signal state etc on the computer screen.
  3. Provide an interlocking function to prevent routes or signals being set if there is a conflict.
  4. Do collision avoidance by cutting power to a track section if the train gets too close to the one in front (has no effect on manual control as long as the operators follow the rules).
  5. Display the next operation to perform. Some clubs use a card index or ring binder holding a list of operations for each operator. When all operators have done their tasks they all tune over to the next page. You could get Tcc to recognise when the actions are complete, and display the next actions for each operator.
  6. Display the next entry in a timetable. Which train should arrive or depart from which station, and when.
  7. Remove the need to make control panels - use the computer screen instead (or as well). Useful as a quick prototype to test-run a panel design before making a 'real' panel.
  8. Drive some of the trains to make the layout more active - more visually appealing at an exhibition.

For a better analysis of what Tcc can be used for click here

So what does this 'script' look like?

A script consists of some declarations (which give names to inputs, outputs and memory variables), and then some statements defining what we want Tcc to do.

To take a really simple example, one that you might consider implementing with a few gates or a flip-flop: We want a train entering a hidden siding to stop automatically at the end of the siding. On this layout trains always run slowly when approaching the sidings and so we can safely stop them with a simple relay. We can detect their presence with some kind of detector, perhaps a light beam, an infra-red reflective unit like an IRDOT (from Heathcote electronics), a reed relay activated by a magnet on the train, an LDR (light dependant resistor) that changes resistance when light is obscured by a train, or whatever. We want the stationary train to depart again when a button on the control panel is pressed. (assume these are straight through sidings, and that the routes have been set somehow).

Suppose we have two inputs, called 'detector' (connected to whatever sensor we are using) and 'release' (connected to the button), and one output, called 'stop' (that is the relay that stops the train when energised).

We could define this behaviour with two instructions:

WHEN detector=1 DO relay=1      { stop train when detector is reached }

WHEN release=1 DO relay=0       { start train when called }

These two instructions are like edge-triggered set and reset lines on some kind of theoretical flip-flop.

Each instruction is executed once, when its condition becomes true, and then will not be executed again until the condition becomes false, and then true again.

The relay is only set to be energised when the front of the train is detected. After that the first statement is not executed again until the train has departed and another train arrives.

The relay is released when the button is first pressed. The two statements do not 'fight' to control the relay (unless the button is pressed at exactly the same moment that the rain arrives, in which case the button wins).

As another example suppose we were driving a three aspect signal, and we wanted it to be driven based upon track occupancy rather than the more complex route selection and interlocking rules.

We want the signal to show red when a train enters the section just after the signal, or when no train is approaching the signal.

We want yellow if the next section is clear, but the one after it is occupied.

And green if both following sections are clear.

OK, you might not like to drive signals that way, but it makes a simple example.

If the sections are called 'A' (before the signal), 'B' (just after the signal) and 'C' (the one after B, and we have inputs that come from an FTC module (Floating Track Circuit, or 8 track occupancy detectors) with the same names. Assume we also have outputs called red, yellow and green.

One possible script to do this (including the declarations this time) could be:

Constants:
Free=0, Occupied=1,     { define the polarity of our sensor inputs }
On=1, Off=0             { define polarity of our outputs }

Sensors:
A, B, C                 { current detectors attached to sections A, B & C }

Controls:
red, yellow, green      { outputs that drive our signal }

Actions:

WHEN A=Free                           { No train approaching }
OR   A=Occupied, B=Occupied           { Next section occupied }
DO red=On, yellow=Off, green=Off

WHEN A=Occupied, B=Free, C=Occupied
DO yellow=On, red=off, green=off      { Train may enter at caution }

WHEN A=Occupied, B=Free, C=Free
DO green=On, red=Off, yellow=Off      { Road ahead clear }

The text in brackets are just comments, so you can leave notes to remind you how your script works - Tcc ignores them completely.

The first few lines (headed 'Constants:') simply gives names to numbers, so that we can use On and Off to mean 1 and 0. This aids readability of the script.

The lines headed 'Sensors:' and 'Controls:' give names to the inputs and outputs that connect to the railway. these are the pins on the FTC and SRO4 modules (or whatever hardware you have chosen to interface to the layout).

After the heading 'Actions:' are the instructions telling Tcc exactly what to do. Each statement consists of the following items:


'WHEN' conditions 'DO' actions

The conditions are simple tests that are anded and or-ed together (the commas may be written 'AND', but a comma abbreviates things nicely).

The actions are things we want to happen when the conditions are true.

Note that a script is not really like a programming language - the statements are not executed in order. The script is more like a written version of logic gates and registers - all the 'WHEN' statements are in essence executing in parallel. The script would do exactly the same regardless of the ordering of the three WHEN statements shown here.

The script is largely compatible with the script used by the software that CTI supplies (free download from their web site http://www.cti-electronics.com) and that site has an excellent introduction to these scripts. Tcc adds some advanced capabilities such as structured data and arrays, but does not yet support the ability to play audio files.

How are the input and output lines associated with the names?

They are assigned in the order you list them. The first name is given to the signal on the first bit (bit 0) of the first byte after the stack header, the next seven names to bits 1 to 7. After that the next bit attaches to bit 0 of the next byte, and so on.

Regardless of the style of stack header used (the RPIC reverses the byte stream, the older RPI did not) the first 8 names attach to the first byte of the module closest to the stack header. So the first 8 Sensors (inputs) are the first byte of the input module closest to the stack header, and the first 8 Controls (outputs) are the first byte of the output module closest to the stack header.

You can leave signals unused either by inserting the special name "spare" into the list, or you can configure pins as spare in the network configuration window.

You tell Tcc about which modules are connected to which stacks, on which serial ports in the Network Configuration window. You can add interfaces (serial ports), change their baud rates (if the stack header permits it), add interface modules, resequence the interfaces and modules and define spare pins in this window.

What can the CTC (or MIMIC) window do?

Firstly Tcc currenly supports upto four CTC windows, just as the CTI software does. Each window is a grid of squares (as many or as few as you wish) and each square can contain a segment of track, some text, or both. A drawing pallette allows you to place segments of track (straight, curved, turnout or crossing) onto the grid. The track can be coloured if desired. Fixed text (in three sizes) can be placed (and coloured) also.

The script can change the colour of the track segments (or groups of segments), it can add text according to what is happening on the layout (such as showing a timetable), and change the colour of the text. It can also change the appearance of turnout and crossing track segments to show which way the turnouts are facing (or which direction the crossing is booked for).

Each square on the CTC panels can also be used as a button, and the script can take action when the mouse is clicked in any given square, perhaps by changing the state of a turnout there, perhaps by booking a route, or even stopping a train.

When you exit Tcc the CTC panel configuration (or at least the 'reset' state) is saved, along with the configuration of modules attached to your serial ports, and the list of windows you have open. It is saved in a file with a .tcp extension. When you launch Tcc it looks for a .tcp file with the same name as your script file.

You can also save (and relead) CTC panel configurations in a plain text format (File->Save As... ctc). This might be useful for doing certain edits, or even creating CTC panels automatically.

What exactly can you do in a script?

Lets break this down into inputs, outputs and special functions.

Inputs

Things that can be read from, and used in conditions and copied from in the actions:

  1. Sensor input lines. These are all (currently) single bit variables, taking the values 0 and 1.
  2. Data variables (just used in the script). These can take 16 bit values, colours or pointers to other inputs.
  3. Quick Keys. There is a window called QKeys which contains buttons, the labels of which can be defined in the script. When one of these is clicked (left or right button) a script statement can be triggered.
  4. Clicks in one (or a range of) squares of a CTC window can trigger script statements.
  5. The special functions $TIME and $SESSION can also be read (see below).

Outputs

Things that can be written to, in other words can be assigned a value in the actions part of a statement:

  1. Control output lines. Again these are all currently single bit variables, though I have plans for multi-bit outputs so that things like signals can appear as a single entity in the script.
  2. Data variables.

Special functions

The following may be used in a list of actions:

  1. $Draw message is used to put a text message onto a CTC panel. The text can include the values of data variables if desired. Like all functions that reference the CTC panels the square you wish to draw in is specified by its co-ordinates (column number, row number, CTC panel number).
  2. $Erase message and $Colour message do what you would expect them to do.
  3. $Switch is used to change the appearance of turnouts and crossings on the CTC panels. A turnout can display a default appearance, where all three track segments are shown (like the letter 'Y'), or just the 'normal' or 'reverse' appearance (straight or left or right facing).
  4. $Colour track can change the colour of a single segment of track in a CTC panel.
  5. $Colour block can change the colour of a group of track segments (probably those that represent a track section on the layout).
  6. $Realtime returns the time of day, as defined by the computer clock. This is the integer number of seconds since midnight, and wraps back to 0 at midnight. This value is read-only - you cannot change clock time.
  7. $Time is layout time, and can run fast if you wish, and can be changed in the script.
  8. $Session is the number of seconds since Tcc was launched, and can also be changed in the script. Realtime, Time and Session are all displayed in the status bar at the bottom of the Tcc window.
  9. Wait is a special action which causes a pause in the execution of the list of actions in a statement. The delay is local to that one statement and does not affect others. It takes a (floating point) number of seconds.
  10. Pulse sets an output on, waits for a delay and then sets the output off again. The actual polarity of the output is defined in the declarations section.
  11. $Random returns a random 16 bit value.

Sounds like the script and CTC panels can do anything, that cannot be true. What can't they do?

The main limitation to the scripting language is your imagination, or at least your programming ability. I believe that doing something to your layout in the scripting 'language' is easier to do than in any other programming language.

Another limitation is the bandwidth between the computer and the hardware. For most layout control scenarios this is not a problem, for example even if it took half a second for a signal to change state it would still be quick enough. But it would not be fast enough, if for example you were driving a stepper motor from 4 outputs on an SRO4 module. Using an RPIC you might get 10 messages per second and so you cannot advance the motor more than 10 times a second which might be too slow, depending upon the application.

The CTC panels cannot display animated GIF graphic images, nor can Tcc (as yet) play audio (though that is planned for the future). I quite like the idea of playing audio sounds, and routing the output through relays to the loudspeaker closest to where the train is currently...

If I were to find something that was particularly useful on a model railway, and you could not be done with Tcc (or was exceptionally difficult) then I'd probably extend the software to make it easy.

All the CTC panels have to be displayed on one screen (or more accurately, on the screen(s) attached to a single computer). I do plan on allowing remote CTC windows (hosted from another computer connected over ethernet) some time, but my layout hasn't progressed that far, and I don't know of anyone else wanting to do it yet.

How do I create a script?

Using any plain text editor, such as Windows 'WordPad', DOS 'edit', or unix's 'vi'. Tcc does not yet have a script editing window for the main script (though it has one to QTU scripts). The reason I haven't added one yet is that so much data has to be regenerated when the script changes that I havn't tried to do the uodate yet. Someday I will add a script editing window.

Once you have created (and saved) the script, launch Tcc with the command:


java -jar tcc.jar <script filename>
(or make a shortcut on the desktop to run it for you).

Tcc will compile the script and list any errors in the Log window, if there are any. If there are no compile errors Tcc will open any windows that you had open when you last closed down Tcc (using that same script file) and is ready for you to turn on the serial links and run the script.

So we have written a script, but it didn't work first time, what next?

Debugging is built into Tcc.

Firstly you can debug the hardware interfacing to the layout. From the 'View' menu you can launch windows that display Sensors and Controls. By activating each sensor in turn, you can see that the input is correctly wired, and reaching the computer. Also you can manually drive out outputs by clicking on buttons in the Controls window, and by doing so you can exercise all the hardware on the layout.

Next you can view the variables used by the script, as well as the inputs and outputs as the script runs. If a variable or output is in the wrong state then you can change it from these windows.

If the script runs too fast you can single step it, and see the variables and outputs change.

You can also log the execution of the script, and the amount of trace output can be controlled (from a simple indication of which statements have 'fired' to a complete log of which comparisons match and which actions are executed.

Unfortunately there isn't a magic 'fix the bugs in my script' button which makes the script do what you wanted it to do, rather than what you actually told it to do. If you know how to do one, I'd certainly like to know.

So how can you really drive trains automatically?

If you have some computer controlled throttles you can. Tcc supports the following:

  1. The smart-cab module from CTI. These have control of speed, inertia, brake and reverse.
  2. A simple throttle controlled by 7 bits of output defining speed, and the 8th bit (of the same byte) indicating reverse.
  3. A simple (home made) throttle controlled by 8 bits of speed, and a reversing relay (if required) elsewhere, perhaps on a DPR module. The design in TB G16/51 is one such design, though you can easily make your own.
  4. The throttles in QTU modules. These are more intelligent and flexible than the others, but are the subject of a TB, just a gleam in its authors eye.

For the simple throttles the inertia and brake are handled by Tcc internally, and so all throttle types appear the same to the script (except the QTU which provides more control and feedback to the script).

Another section of the declarations are the start of the script might look something like:


SmartCabs:
c1, c2, c3

Which defines three computer controlled throttles (of any of the kinds listed above). This gives the script access to the following variables;


c1.speed, c1.brake, c1.inertia, c1.direction, c2.speed etc...

Or it can also use the older CTI syntax:


c1=50 (BRAKE_OFF, MOMENTUM_1)

With this you can control the power output of each of the throttles, and with relays you can route the power to where it is required.

The automatic train parking script could be changed to drive the brake one such a throttle instead of dropping a relay. The train would then decelerate and accelerate smoothly instead of stopping suddenly (and perhaps derailing).

How fast does the script run?

On my machine I run an enormous script of some 1400 WHEN statements in a 3400 line script file and on an 800MHz AMD machine it would execute the whole script 700 times a second, except I have throttled the speed to that Tcc doesn't consume all available CPU.

Smaller scripts on more recent machine would run at many tens of thousands of times per second. Perhaps thats a tad faster than is actually required.

So that Tcc can share a computer with other programs (perhaps including programs that might exchange data with Tcc over ethernet or serial port simulators) I have set Tcc to run at under 100 loops per second if nothing is happening, faster when the script is actually executing.

Thats lots faster than I need - even with a QTU running at 38400 baud I only get 45 messages per second and anything over 100 loops of the script per second cannot do much as the inputs cannot have changed in that time (or at least such changes cannot have been read by the computer).

So what sort of computer do I need to run Tcc?

In terms of Windows PC hardware, you need a machine with one or more serial ports. This might mean getting a plug-in card or a USB to serial adaptor.

You need 128Mbytes of RAM if you are running Windows 98. Later versions may require more, I have not tried with such small amounts of memory. the key thing is that you have enough memory for windows to run in without needing to swap code in and out, and then perhaps 10-15Mbytes for Tcc. If windows swaps things in and out of memory it will cause problems with the serial interface, and the RPIC can crash (or at least older RPIC code would). I would guess that a Linux machine could run with less memory, but I have no personal experience with java on Linux.

Shorter scripts than mine (mentioned above) will run proportionally faster and so you really shouldn't need such a modern machine. Even a good '486 should be adequate for most purposes (as long as you have the memory).

If you want complex CTC panels then you will want a screen resolution rather better than 640 × 480, but you can grow into that in time.

Tcc is written in Java (which is why you can run it on Linux, Solaris, Mac and Windows). I do my development on a Mac, and then run the layout downstairs on a Windows 2000 PC. You will need a Java virtual machine installed (java 2 version 1.3 or later) which is available as a free download from http://java.sun.com You will also need the java comms package (which is another free download that adds access to serial and parallel ports), from the same sun site. You only need the JVM (runtime Java Virtual Machine), and not the full SDK (Software Development Kit) unless you want to write your own java programs. the SDK download is MUCH bigger.

I have tested Tcc on Java 2 version 1.5 (which fixes some bugs) and so it is probably a good idea to download that if you are downloading it, or better still get it on CD as the download can take a while if you do not have broadband.

Where can I get an updated copy of Tcc?

On the yahoo groups site, in the Merg files area:

http://groups.yahoo.com/group/merg/files/Layout%20Controls/tcc.jar

In addition there is a copy of (an older version of) my monster script, called ha1.tcl. Do not expect to understand how it works - it is enormous. I have uploaded it so you can check syntax, and look for examples in it, but read the CTI documentation first - they have done a good job of introducing the scripting language. One day I'll write a few extra chapters that define the extras that Tcc provides.