I use Matlab/Simulink R2012b under Linux to model dynamic systems. In order to perform hardware-in-the-loop testing, I want to run my models in real-time on Linux with rt_preempt patch. Running a Simulink model in real-time can be achieved by converting the model to the C code, compiling it and running the resulting application. Simulink supports this by means of Simulink Coder. Producing a Linux application with Simulink Coder is not as straightforward as one might think, though.

About Simulink Coder

Simulink Coder (formerly called Real-Time Workshop) can generate the code in many styles and for several platforms and operating systems. Surprisingly, Linux is also among supported environments.

Simulink Coder can, by default, generate code for so called Generic Real-Time Target (GRT). Such code should be suitable for running on desktop platforms. If you want to run the code on a more constrained embedded system or you have additional requirements on the code (e.g. compliance with safety standards), there is Embedded Coder for you. Embedded Coder extends Simulink Coder with additional capabilities and targets. The default Embedded Coder target is called Embedded Real-Time Target (ERT).

As it turns out, neither GRT nor ERT target alone can be used to create Linux executable even if documentation says the opposite.

Available options for generating Linux applications

From the documentation it seems that there are several options available out of the box that allow to generate Linux applications from Simulink. They are:

  1. The use of Embedded Real-Time target (ert.tlc) and selecting NativeThreadExample as the target operating system in Model Configuration → Code Generation → Templates.

    When I tried to generate the code, I got this error:

    This model specifies the ‘Target operating system’ as ‘NativeThreadsExample’ from the ‘Template’ section of the ‘Code Generation’ pane of the Configuration parameters dialog. This example target is currently supported only when the model is configured for concurrent execution.

    After some searching, I figured out how to enable concurrent execution. It can be done at View → Model Explorer → right click on Configuration → Show Concurrent Execution options and then check Allow tasks to execute concurrently on target. Even though I enabled this and configure the tasks, I still got the same error.

  2. The second option might be using the IDE Link Target that allows to compile the generated code by Eclipse IDE. Even though I don’t like Eclipse, I tried to set it up according to the documentation. Again no success. I ended up with some strange errors suggesting that there is a problem with Eclipse (more precisely its JVM) being a 32 bit application and Matlab a 64 bit application. My guess is that this feature is tested only on Windows. Since Matlab R2012b is not distributed for 32 bit Linux, it is not possible to test this option with 32 bit Matlab. Furthermore, in release notes of R2013a it is announced that Eclipse support will be dropped in future releases.

Custom target for Linux applications

Simple target

Since I failed with both above options I decided to write a custom code generation target for Linux. One option would be to use a target previously developed at our department, but it has several drawbacks:

  1. The generated code cannot be compiled. It seems that the interface to the generated code changed between Simulink version from 2007 (when the target was developed) and R2012b used by me.
  2. I don’t like that the target is meant to be used on Windows (hardcoded backslashes etc.) and additionally,
  3. it contains features that I do not need (CANOpen block set).

Therefore I decided to write my own target that should be as simple as possible.

After creating the target by copying the ert.tlc file and modifying it slightly (basically replacing ert with ert_linux) and selecting NativeThreadsExample as in the step 1 above, the code was successfully generated. You can see this target here. Such a target has two problems:

  1. It does not support external mode, i.e. a mode in which Simulink can connect to the running application to provide on-line parameter tuning and real-time data plotting.
  2. The generated code uses POSIX timers that use signals to wake up the threads. Signals have quite big overhead and there are rumors that their delivery can suffer from priority inversion.

The only way to get Linux application with support for external mode seemed to develop a target with custom main.c file.

Advanced target

I developed the target that provides the main.c file (actually called ert_main.c) and supports external mode. Although the documentation is quite extensive (several thousands pages in total), if was really hard to figure out how to do it properly. Several times it was necessary to study awful TLC1 source code which is, IMHO, very badly structured. Fortunately, I could use Lukáš Hamáček’s target as an example, which helped me a lot.

The result of my work is can be downloaded from our repository. The target has the following features:

  • Support for external mode over TCP.
  • Support for both single-rate and multi-rate systems.
  • Simulation threads are scheduled as SCHED_FIFO (real-time priority).
  • External mode communication runs in non-real-time thread.

I tested the target on several systems and everything seemed to work as expected. My only concern now is about thread safety. Given that Simulink produces the error messages about concurrent execution of threads (see above), I’m not sure whether the generated code can be safely run in multiple threads. Also the code implementing external mode server contains several semaphores but only when it is compiled for the VxWorks OS. I’ll probably check this later if we encounter any problems that might be caused by the code not being thread safe.

Conclusion

It is surprising how few relevant results Google gives when one asks for “simulink real-time workshop linux”. It seems that the Embedded Coder target for Linux described in this post might be useful for people waning to run their Simulink models on Linux. Although that the target may not work perfectly and in all configurations, I think it is now good enough for interested people to try. If you experience any problems with the target, let me know.

Footnotes:

1

Target Language Compiler – the tool used to convert Simulink blocks to C code.

It seems we have the same pain (your last par.) but you’ve ‘created’ a solution. thanks for your work. I didn’t tried yet but I will try and share the results for improvements. our target is to bring simulink model on xenomai linux platform. which is done as said in articles but not documented anywhere. thanks again Mobin motallebizadeh IUST

Comment by Anonymous Tue Oct 14 18:58:43 2014

Hi,

First of all, thanks for this short tutorial on this issue. I did find some information in web: https://www.rtai.org/?About_RTAI-Lab Isn’t it related to the issue ? If I understand correctly, your article does not give a step-by-step solution, but the git source, might give some directions ?

Thank you, Ran

Comment by Anonymous Sat Jun 13 17:03:12 2015

Hi,

I have found the following http://www.clemson.edu/ces/crb/ece496/fall2000/rtlt.pdf

Are you familiar with that ? Do you think it might be a good step-by-step for this issue ?

Thank you, Ran

Comment by Anonymous Sat Jun 13 17:14:09 2015

Hi,

Is there any update for this page ? The conclusion leaves some concern about multiple threads…

Regards, Ran

Comment by Anonymous Mon Jun 22 17:48:47 2015

Hi Ran,

  1. The difference between ert_linux and RTAI-Lab is that for RTAI-Lab, you need to install RTAI in addition to “plain Linux”. ert_linux can be used with plain Linux. Of course, if you need real-time response, you should use rt-preempt kernel. This kernel is already shipped by many distributions and sooner or later it will be merged into mainline Linux.

    The difference between rt-preempt and RTAI is that RTAI is able to achieve slightly lower latencies, but it has more limited hardware support. rt-preempt runs almost everywhere, where normal Linux runs.

  2. I don’t know RTLT, but it seems pretty outdated and I doubt it will work today.

  3. We setup ert_linux homepage. You can find more information there. Currently, we do not work on improving ert_linux much, because we do not have any project where it is needed, but we plan to maintain it in a long term.

  4. Reagrding multi-threading support, we are adding it to our another target, which is not public. If there is time, we will add it to ert_linux as well.

– Michal

Comment by wsh Thu Jun 25 11:14:25 2015

Hi, I have not yet started working with Embedded coder nor Simulink coder. But I wander what is the exact prcoess of genrating linux application. Is it genrating c code with Embedded coder and then compile it into binary by myself? I will eventually need to work with Altera FPGA. It is described as if embedded coder knows how to generate code for this ARM FPGA. I wander if it will be straitforward or wether Ineed to use sone ert linux target.

Regards Ran

Comment by Anonymous Sat Jun 27 13:48:26 2015

Hi, I have not yet started working with Embedded coder nor Simulink coder. But I wander what is the exact prcoess of genrating linux application. Is it genrating c code with Embedded coder and then compile it into binary by myself? I will eventually need to work with Altera FPGA. It is described as if embedded coder knows how to generate code for this ARM FPGA. I wander if it will be straitforward or wether Ineed to use sone ert linux target.

Regards Ran

Comment by Anonymous Sat Jun 27 13:49:03 2015

Hi Ran,

Embedded coder generates both C code and Makefile. It also calls make to compile the code and optionally it can also download the binary to the target hardware. All of this is controlled by various templates and Matlab functions in the code generation target. The process of creating new code generation target is not conceptually difficult, but you need to read a lot of documentation. Some things are quite tricky to get right.

Comment by wsh Wed Jul 1 11:25:42 2015
I want to carry out the same task as you did because the inspiration of opal-rt realtime simulation tool-set. it can achieve realtime simulation with sample rate >100kHz. the target runs redhat linux. I am just starting work on it, my goal is to achieve 1khz sample rate hard realtime execuation of control algorithm. As there are limited research and support from mathworks and community, i think your work may provide a good base. thank you.
Comment by Anonymous Mon Dec 28 08:45:34 2015
I want to carry out the same task as you did because the inspiration of opal-rt realtime simulation tool-set. it can achieve realtime simulation with sample rate >100kHz. the target runs redhat linux. I am just starting work on it, my goal is to achieve 1khz sample rate hard realtime execuation of control algorithm. As there are limited research and support from mathworks and community, i think your work may provide a good base. thank you.
Comment by Anonymous Mon Dec 28 08:46:23 2015
I want to carry out the same task as you did because the inspiration of opal-rt realtime simulation tool-set. it can achieve realtime simulation with sample rate >100kHz. the target runs redhat linux. I am just starting work on it, my goal is to achieve 1khz sample rate hard realtime execuation of control algorithm. As there are limited research and support from mathworks and community, i think your work may provide a good base. thank you.
Comment by Anonymous Mon Dec 28 08:47:02 2015