1. Setup
  2. Trainspotting
  3. A-mazed
  4. CCHAT

Lab 1: Trainspotting


Register for one time slot in one of these polls:

David, Liam, Ali, Ghaith

Use your group number in Fire as name. Please try to split evenly among the available rooms.

For the demo, please join the respective Zoom meeting: Liam, Ali, Ghaith password 585785, David at least 10 minutes before the beginning of your demo and have everything ready to run. Change you name in Zoom to your group number.

All demos are online over Zoom!

Lab description

In this assignment you will write a program to control two trains. The purpose is to write the program so that the trains move relatively independently of each other, but without colliding. Instead of a real railway, we have a simulator, where one can control the speeds of trains and change rail switches. The simulator gives a signal when a train passes sensors suitably placed on the tracks. It is part of the assignment to decide where sensors should be placed to give sufficient information for your program. The map without sensors looks as follows.

Programming language and environment

This lab assignment must be developed in Java.

See the computing resources page for setup instructions.


Your assignment is to write a program that controls the trains. The trains should run simultaneously between the two stations (note that each station has two tracks). It is important that the trains are able to move at the same time, and be as independent from each other as possible, without crashing. At the stations the trains should stop and then wait 1 to 2 seconds. The trains should run forever between the stations.

In the beginning there are no sensors on the tracks. You must decide where to place sensors so that the control program gets the necessary information.

The program that you deliver should work as follows. Each train should be controlled by an independent train program, which runs in its own Java thread. Independently running train programs are only allowed to communicate with each other by acquiring and releasing semaphores. In particular, no shared variables should be used for communication between running train programs. Also, both trains must use the same train program, and the behaviour of a train cannot depend on its train id. For example, the track that a train chooses cannot depend on its train id.


Distinction assignment

In order to be able to get the two distinction points on the first lab, you should modify your solution to work with monitors instead. A detailed description of the distinction assignment can be found here.

Train simulator

The simulator is called tsim; use it as follows:

Map editor

The train simulator tsim also works as a map editor.

You need to get your own copy of the map in order to be able to add the sensors. The map you will be working on is that shown above. The map file is included in the archive in the downloads section.

You modify the map with tsim The figure below shows how to use tsim. You should only select the sensor button in the tools window (the small T-like symbol) and then use the mouse to place sensors on the track.

Notice that editing the map file manually may lead to unexpected results. In particular, sensors added manually to switch locations do not work.


You may start tsim and interact with it using commands on standard input. Try for example the commands

SetSpeed 1 20
SetSwitch 17 7 RightSwitch

and see what happens. (The second command is necessary for the train to survive the first switch which initially is set in the wrong direction). We provide the Java library to handle the communication with tsim, which lets you change the speed of the trains and the state of the switches in a more convenient way (see next section).

Here are some things to note about the simulator:

Program/Simulator interaction

The simulator and your program run as separate OS processes. They use pipes to communicate. The Main class provided in the skeleton code takes care of joining together the pipes of your solution in Java with the tsim simulator.

All commands between the your program and the simulator are sent line-by-line as text strings, as you saw above. To aid you in your assignment we provide you with a Java library (TSim) that implements the protocol tsim is using. You must use this Java library. The package provides you with an interface to control the behaviour of the trains and switches. You can view the JavaDoc documentation of this library.


You cannot create instances of TSimInterface using its constructor, since it is private. Instead you use the static method getInstance() that creates an instance of the class if that has not already been done (singleton pattern).

TSimInterface tsi = TSimInterface.getInstance() ;

Useful classes

try {
catch (CommandException e) {

  /* If a command failed then something bad has
     happened and we probably don't want to
     continue executing */


Download material for the lab

To get started, you need the skeleton code package.

To download the skeleton in the remote server (e.g., remote11), execute the following command:


Then, extract it by writing:

‘tar -xzvf trainspotting-skeleton.tar.gz’

The extracted files should now be in a new ‘transpotting’ directory.

Getting started

You should implement your solution in the file (which can/should contain multiple classes). We provide a Main class which takes care of loading the simulator and connecting it to your solution. You shouldn’t need to change this file. This entry point expects at least 3 command line arguments:

  1. map file

  2. speed of train 1

  3. speed of train 2

  4. simulator speed [optional]

Using the command line

To build your solution, you can simply run the following command:

make all

from the root directory of the project. This will place the class files in the bin folder.

You can then run your solution with:

java -cp bin Main 5 15

Using Eclipse

You can also open the files as an Eclipse project:

  1. Extract the trainspotting folder into your workspace directory.
  2. In Eclipse, choose New → Java Project. Give it the exact name trainspotting to use the existing sources.

When running or debugging the Main class in Eclipse, you will need to specify the command-line arguments via the Run Configurations dialog.

Eclipse should be installed on all the StuDAT-linux workstations in the lab rooms but may not be available in the startup menu. To start it, open a terminal window and run

eclipse &

Tips and tricks


It was stated above but may be stated again: reasonable code quality is expected. You are programmers. Programming should be an art to you. The quality of your code will be vital for its reuse and maintenance.

Common reasons for rejection

Using polling/busy waiting for synchronization is a common mistake that leads to submissions being rejected.

Here are some examples of polling/busy waiting in pseudo code. Loops that behave similarly to the situations below (where the dots do not include any blocking wait) are considered as polling.

while (e) { // POLLING!

Using a blocking operation within a loop is not considered as polling

while (e) { // NO POLLING!

provided that it is not the case that that the waiting process is woken up from its wait at regular intervals. Thus, the following example is also an instance of polling:

obj o;

process a {
  while (true) {

process b {  // POLLING!
  while (e) {