External Code Integration of Libraries and C/C++ Code with Simulink Real-Time Models
Considerations for Integrating Third-Party Libraries and External Code into Simulink Real-Time
When integrating code into Simulink® Real-Time™ applications, start by following the guidance in Build Integrated Code Within the Simulink Environment. Developers who integrate C/C++ code with Simulink Real-Time applications notice some differences when they migrate the code that they integrated with Simulink Real-Time applications from previous releases to R2020b and later releases. These differences include:
In release R2020a and previous releases, the On-Time RTOS on the Speedgoat® target computer shared some libraries and system calls with Windows®. In release R2020b and later releases, the QNX® Neutrino® RTOS on the target computer does not share libraries or system calls specific to Windows.
In release R2020a and previous releases, developers could use Microsoft® Visual Studio® to compile libraries to integrate with Simulink Real-Time applications. In release R2020b and later releases, you cannot use the Microsoft Visual Studio compiler for this purpose. You can configure Microsoft Visual Studio to use the QNX Neutrino compiler from the Simulink Real-Time target support package.
In R2020b and later releases, developers use cross-compiling to produce libraries on their development computer for deployment to their target computer.
Value of Upgrading Your C/C++ Code for Integration into Simulink Real-Time
By updating your C/C++ code for integration into your Simulink Real-Time application, you gain these benefits:
Leverage the QNX Neutrino 64-bit and POSIX® compatible RTOS.
Code directly in C++ or wrap your legacy C code.
Use the code editor of your choice.
For instance, customizing Visual Studio Code with the source files and shipped QCC compiler from the Simulink Real-Time Target Support Package provides a similar experience to a full IDE.
Leverage the precompiled QNX Neutrino libraries and headers that are included in Simulink Real-Time to extend the functionality of your real-time application.
Integrate any C/C++ application based on modern build and package software such as CMake.
Approaches for C/C++ Code Integration into Simulink Real-Time
There are advantages and disadvantages to each of these external code integration approaches.
Approach 1: Directly Call C/C++ Code. In this approach, you use C Caller or C Function blocks in the model. For more information, see Integrate C/C++ Code Using C Function Blocks.
Advantages: There is no need to compile source code before building the model.
Disadvantages: This approach is hard to use for complex projects that have many files and dependencies.
Approach 2: Build, link, and use static libraries (.a
files)
Advantages: All required files are packed in the real-time application MLDATX file. In this approach, there is no need to install libraries on the target. And, this approach lets you protect your intellectual property.
Disadvantages: This approach is non-modular. A change in the library requires rebuilding the whole real-time application. Also, this approach tends to produce larger real-time application MLDATX files.
Approach 3: Build, deploy and use shared objects (.so
files)
Advantages: This approach is modular. You can build the real-time application and shared object independently. Also, this approach tends to produce smaller real-time application MLDATX files. And this approach lets you protect your intellectual property.
Disadvantages: In this approach, you need to access the target computer file system before running the real-time application and install (copy) the shared objects to any of the common
lib
paths on the target computers.
Build Libraries from Source Code for Simulink Real-Time
To integrate external code in a real-time application, the most flexible approaches are to build static libraries or shared objects from source code.
The library build workflow is similar to the workflow used by most developers for release R2020a and previous releases. In those releases, the library build workflow for the target computer On-Time RTOS produced static libraries built with Microsoft Visual Studio and produced
.lib
files.You achieve better usability when working with complex C++ projects that have many dependencies and source code files.
S-functions offer better granularity when handling third-party libraries in Simulink. S-functions enable the flexibility to use the same S-function source code with different platforms, including simulation on the desktop in different operating systems. The S-functions are deployed and function in real-time on a target computer.
Cross-compiling is compiling a library for a target operating system (for example, QNX Neutrino RTOS) on a development operating system (for example, Windows). Some cross-compiling considerations for Simulink Real-Time are:
Choice of development environment. Many modern C++ projects use the CMake build environment. For more information, see the CMake website.
Extensibility of development environment. For example, it is a common practice to extend most common CMake support for the QNX Neutrino RTOS by leveraging similarities with the UNIX® OS and its POSIX compatibility.
In your libraries, save cross-compiling libraries, including dependencies that might be already included in the Simulink Real-Time Target Support Package. These libraries can be linked to other C++ projects.
The suggested workflow for integration of complex C++ applications into Simulink Real-Time is:
Start from a C++ project with CMake as the build environment.
Set the dependencies, such as headers and libraries, in your Simulink model.
On the development computer, cross-compile libraries for the QNX Neutrino RTOS on the target computer.
Create an S-function, for instance using the S-function Builder block or a handwritten C-MEX S-function, as the main function that calls the C++ functions defined in the header files and implemented in the compiled libraries for the QNX Neutrino RTOS.
Build the real-time application.
By using SSH or FTP, copy your cross-compiled libraries to a location on the target computer where they can be found and loaded at run time. The recommended locations are
/lib
,/usr/lib
, or/usr/local/lib
.Load and run the real-time application.
External Code Integration for S-Functions and Simulink Real-Time
When you include static libraries or shared objects in S-functions for external code integration with a real-time application, there are some tips for your development.
When building from Simulink:
Use
rtwmakecfg.m
andmakeInfo
object to map libraries and header files. For more information, see Use makecfg to Customize Generated Makefiles for S-Functions.function makeInfo = rtwmakecfg proj = currentProject; rootPath = proj.RootFolder; makeInfo.linkLibsObjs = {}; sysTarget = get_param(bdroot, 'RTWSystemTargetFile'); switch sysTarget case 'speedgoat.tlc' makeInfo.includePath = '<includePath>'; makeInfo.linkLibsObjs{end+1} = '<libraryPath>'; otherwise error('No rtwmakecfg found for %s target file', sysTarget); end end
Enable linking for different target files.
Use macros, such as
SIMULINK_REAL_TIME
, in your source code to add lines at compile time for real-time simulation.SIMULINK_REAL_TIME
is useful to wrap the LOG function calls.
When cross-compiling, use macros such as __unix__
and
__QNXNTO__
in your source code to add lines at compile time.
Additional C/C++ Project for Simulink Real-Time
The eCAL Toolbox for Simulink project on github.com/mathworks/ecal-toolbox shows complete
external code integration with Simulink Real-Time, including S-function wrappers,
rtwmakecfg
customization, and shared object compilation. You also can
simulate this example on your development computer.
Related Topics
- Build Support for S-Functions
- Compile Source Code for Functional Mock-up Units
- Troubleshoot Model Links to Static Libraries or Shared Objects
- Troubleshoot Cannot Load Shared Object on Target Computer