Skip to content

KVB

In order to build, for simulation, a railway safety device, the KVB (Automatic Speed Control, with a K instead of C), I had to develop both software: PC side (and simulator) and device side (Arduino).

For the creation part (design, 3D printing, electronics, assembly), I refer you to the dedicated article on my blog.

Photo of the finished 3D assembly Photo of the finished assembly, the case is entirely designed and 3D printed. I no longer use this exact case, I managed to find a real KVB case.

Photo of the real functional KVB Photo of the "real" functional KVB

The old model used an STM32F103C8T6, aka the cheapest STM32 on the market, which cost 1€60 (including shipping!) at the time. However, the COVID-19 pandemic and the shortages that followed particularly affected ST Microelectronics. Chips therefore increased in price. Where a devboard now costs about 3€ (including shipping), the price had exploded to almost 6€/unit, in July 2021.

I therefore chose to go back to a well-known base: the Arduino Mega 2560. This allowed me to reduce the production cost, and simplify development.

Arduino Part

For the "version 2" project, I chose to complicate my life, especially for the technical challenge: instead of simply sending a serialized JSON object via serial, I chose to make a binary protocol. This allowed me to reduce the size of messages, and therefore reduce transmission time. However, there are not only advantages: debugging is more complicated, the code is harder to write, and you really have to pay attention to synchronization.

It was a very enriching experience, but I don't know if the binary protocol is really necessary. That said, I'm very happy with the result, and I'm very proud of my code.

The code is available on my GitHub.

Libraries

I used several libraries for this project:

Custom Binary Protocol

Each frame consists of 4 bytes:

  • The first byte is a header, always 0x23. This allows "synchronizing" the communication.
  • The second byte is a byte that indicates what kind of data it is (lamp state, buttons pressed, etc).
  • The third byte is the information byte itself. This means we only transmit one "useful" byte
  • The fourth byte is a checksum, which allows verifying that the frame was not corrupted during transmission. This checksum is simply the sum of the first 3 bytes.

If a correct frame is received, we send an ACK (0x24) in return. If an incorrect frame is received, we don't respond. This has the disadvantage of not allowing to know if the frame was received correctly, but especially: we can only with difficulty know if the KVB is desynchronized with the PC (or vice versa!). In theory, this can never happen, but this is not at all the case in practice.

The protocol efficiency is therefore 25%, but this doesn't bother me: the KVB doesn't need a lot of data, and the transmission time is very short.

PC Part

Train Simulator only running on Windows, I therefore made the choice of development in C++ and a console application. The code is available on my GitHub.

I chose to split the code into several projects (solutions) for clarity:

  • RailDriverLib is a library that allows communication with Train Simulator. It exposes the Train Simulator API, and allows communication with the simulator.
    • RailDriverClient is a test application for the RailDriverLib library. It allows testing the library's functionalities, and seeing if it works correctly.
  • KVBProtocolLib is a library that allows communication with the KVB. It exposes an API to communicate with the KVB, and allows communication with the KVB.
  • KVBProtocolClient is a test application for the KVBProtocolLib library. It allows testing communication with the KVB.
  • KVBClient is the main application. It uses both libraries to communicate with the KVB and Train Simulator.

I chose to split the code into several projects for clarity, and to be able to reuse the libraries in other projects, even if I doubt that will ever happen. The code is under Unlicense license, so you can use it as you wish.

Configuration File Management

I chose to store the configuration in an INI file: they are natively supported by Windows, and are very simple to manipulate. However, these are "C-style" methods that require passing an array.

Qt Application

One of the substantial advantages of a simple text protocol is debugging: you can see what is sent and received with a simple serial terminal. However, this is not possible with a binary protocol. I therefore chose to make a Qt application to be able to see what is sent and received.

I used Qt with .ui files (with Qt Creator), because I don't need to make a very complex application.

Conclusion

This project was very enriching, and allowed me to discover new things. I learned to make a binary protocol and to split a project into several parts. I also learned to use third-party libraries (AceTMI/AceSegment), and to make console applications in C++ for Windows. Thanks to Qt, I also learned to make cross-platform graphical applications.