MATLAB/Simulink model simulation and modeling with s-functions and variable-step solver

As a 10+ year old company working on HVAC system modeling on MATLAB/Simulink, we would like to transition to Julia for faster simulation and modeling of our Simulink model, where we also plan to accelerate the Simulation via surrogates.

However, our Simulink model contains s-functions and the variable-step solver as shown in the figure below:

MicrosoftTeams-image

Hence, we currently have two limitations:

  • Due to the presence of s-functions, the exported FMUs run slow in Python
    -The exported FMUs can only be run if the hardware contains matlab license.

Before transitioning to Julia, I therefore would like to ask:

  1. Does Julia support s-functions and variable-step solver when exporting and importing a model as FMU?
  2. Is a Matlab license needed to run the FMU if the FMU contains s-functions?

Thank you for your help.

1 Like

Well, if you continue to use Matlab solvers you need a Matlab license. But you will get the advantages of Julia only if you do NOT use the Matlab solvers but the DifferentialEquations.jl package. There are two different types of FMUs, FMU for co-simulation and FMU for model export (FMI Standard: Co-Simulation vs. Model Exchange FMUs). You will get the advantages of Julia only if you use an FMU for model export, because only then the Julia solvers will be used.

I cannot comment on your question regarding the s-functions.

I re-wrote a Simulink model (three A3 pages in printed form) in ModelingToolkit (Julia) and it had only
a length of half an A4 page and was 1000 times faster.

3 Likes

I looked around for an s-function API and couldn’t find one. I think that it is short for “Simulink Function” and I think that MathWorks intended it to be a MEX interface. This is pretty much most of what I found that was useful.

I imagine that if you wanted to keep your existing s-function source code, that you’d need to write a wrapper layer for it, however, porting it to Julia will likely make your life much easier in the long run.

Hello @ufechner7 I’ve been looking at moving my current Simulink model over to Julia’s ecosystem and I was wondering if you know of any resources/guides to help me get started, considering that you have gone through that experience.

What I’m most concerned about actually is how can I visualize the output of ModellingToolkit similar to how Simulink displays its model. I’m perfectly fine with using text to code up my models, but I’d really like the ability to graphical visualize the models I create.

I’ve been looking at moving my current Simulink model over to Julia’s ecosystem and I was wondering if you know of any resources/guides to help me get started, considering that you have gone through that experience.

Same here. I am especially interested in using FMI for model export of Simulink models for simulation in Julia.

1 Like

Did you look at GitHub - ThummeTo/FMI.jl: FMI.jl is a free-to-use software library for the Julia programming language which integrates FMI (fmi-standard.org): load or create, parameterize, differentiate and simulate FMUs seamlessly inside the Julia programming language! ?

2 Likes

Well, I just plot the output using one of the many plotting packages. Usually I write custom plot functions that plot for example four line plots in one diagram similar to the Simulink oscilloscope.

I had hardly any need yet to have a continues update of the output because Julia is so fast that the complete output is ready within a few seconds, but when I needed it for some real-time simulation with real-time input I used Makie.jl. But then you have to write your own, custom viewer like I did here:

A simple example for plotting the result of a ModelingToolkit model can be found here: Step response using ModelingToolkit

Thanks for the link to FMI.jl, will definitely need that to import the exported Simulink FMI’s into Julia.

Sorry I should have been more clear. I was asking more along the lines of visualizing the associated graphical model that is modelled in ModelingToolkit, akin to how we edit model files in Simulink.

I looked through the docs, but it was not immediately clear if fmiSimulate was only applicable for co-simulation or if it interfaces more generally to the SciML/DiffEq ecosystem. Looking at the src, I now see that it is.

I use Control Block Diagram with TikZ - Overleaf, Online LaTeX Editor , but that is time consuming. Good for scientific papers, not for daily engineering work.

I think Home · JuliaSimControl has a graphical model editor, but I never used it.

Thanks for the JuliaSim link.

Another thought considering that I’d like a graphical view of ModelingToolkit, was if I can graphically visualize an FMU that is exported from ModelingToolkit?

What do you want to visualize? The inner working of the FMU, or the inputs and outputs?

Really just the inputs and outputs so that I can understand the flow of data and requirements of each block.

I do not think that this exists in the Julia ecosystem. You could create a feature request in fmi.jl. But you can also use any other tool for this purpose, because the input/output definition of an FMI is just an xml file. Perhaps there exists a Python tool that can read this xml file and create a nice graph?

OMSimulator might be able to help visualize/simulate connected FMUs. 7. Graphical Modelling — OMSimulator v2.1.1.post191-gf9c815c documentation

Done: Ability to graphically visualize FMUs · Issue #195 · ThummeTo/FMI.jl · GitHub

Thanks for linking OMSimulator, @bilderbuchi !

1 Like

Also, there is a visualizer/editor for MTK models, but I think this is still in an early phase: GitHub - bradcarman/ModelingToolkitDesigner.jl: A helper tool for visualizing and editing a ModelingToolkit.jl system connections

1 Like

Thanks for your helpful answer. When re-writing the Simulink model, did you use JuliaSim, too, or plain Julia?

I just write the differential equations in ModelingToolkit without using components like this:

using ModelingToolkit

# Bessel filter with step signal as input
function model_bessel(step_time, step_size; w1=3.14, y0=0.0, yd0=0.0)
    @variables t u(t)=0 y(t)=y0 yd(t)=yd0
    @parameters w=w1
    
    D = Differential(t)
    eqs = [D(y)  ~ yd,
           D(yd) ~ 1/0.618 * (w*w * u - 1.3617w * yd - w*w*y),
           u     ~ if_else(t > step_time, step_size, 0.0)]
    
    @named sys = ODESystem(eqs, t)
    
    # sys = structural_simplify(sys)
    sys, u, y
end

But you will need to use components if you have more than (10…100?) equations…

1 Like