# Documentation

## S-Function Concepts

### Direct Feedthrough

Direct feedthrough means that the output (or the variable sample time for variable sample time blocks) is controlled directly by the value of an input port signal. Typically, an S-function input port has direct feedthrough if

• The output function (`mdlOutputs`) is a function of the input `u`. That is, there is direct feedthrough if the input `u` is accessed by `mdlOutputs`. Outputs can also include graphical outputs, as in the case of an XY Graph scope.

• The "time of next hit" function (`mdlGetTimeOfNextVarHit`) of a variable sample time S-function accesses the input u.

An example of a system that requires its inputs (that is, has direct feedthrough) is the operation

`$y=k×u,$`

where u is the input, k is the gain, and y is the output.

An example of a system that does not require its inputs (that is, does not have direct feedthrough) is the simple integration algorithm

`$y=x,$`
`$\stackrel{˙}{x}=u,$`

where x is the state, $\stackrel{˙}{x}$ is the state derivative with respect to time, u is the input, and y is the output. Simulink® integrates the variable $\stackrel{˙}{x}.$

It is very important to set the direct feedthrough flag correctly because it affects the execution order of the blocks in your model and is used to detect algebraic loops (see Algebraic Loops in Using Simulink). If the simulation results for a model containing your S-function do not converge, or the simulation fails, you may have the direct feedthrough flag set incorrectly. Try turning on the direct feedthrough flag and setting the Algebraic loop solver diagnostic to `warning` (see the Algebraic loop option on the Model Configuration Parameters: Diagnostics reference page in Simulink Graphical User Interface). Subsequently running the simulation displays any algebraic loops in the model and shows if the engine has placed your S-function within an algebraic loop.

### Dynamically Sized Arrays

You can write your S-function to support arbitrary input dimensions. In this case, the Simulink engine determines the actual input dimensions when the simulation is started by evaluating the dimensions of the input vectors driving the S-function. Your S-function can also use the input dimensions to determine the number of continuous states, the number of discrete states, and the number of outputs.

 Note   A dynamically sized input can have a different size for each instance of the S-function in a particular model or during different simulations, however the input size of each instance of the S-function is static over the course of a particular simulation.

A C MEX S-function and Level-2 MATLAB® S-function can have multiple input and output ports and each port can have different dimensions. The number of dimensions and the size of each dimension can be determined dynamically.

For example, the following illustration shows two instances of the same S-Function block in a model.

The upper S-Function block is driven by a block with a three-element output vector. The lower S-Function block is driven by a block with a scalar output. By specifying that the S-Function block has dynamically sized inputs, the same S-function can accommodate both situations. The Simulink engine automatically calls the block with the appropriately sized input vector. Similarly, if other block characteristics, such as the number of outputs or the number of discrete or continuous states, are specified as dynamically sized, the engine defines these vectors to be the same length as the input vector.

See Input and Output Ports for more information on configuring S-function input and output ports.

### Setting Sample Times and Offsets

Both Level-2 MATLAB and C MEX S-functions provide the following sample time options, which allow for a high degree of flexibility in specifying when an S-function executes:

• Continuous sample time — For S-functions that have continuous states and/or nonsampled zero crossings (see Simulation Phases in Dynamic Systems for an explanation of zero crossings). For this type of S-function, the output changes in minor time steps.

• Continuous, but fixed in minor time step sample time — For S-functions that need to execute at every major simulation step, but do not change value during minor time steps.

• Discrete sample time — If the behavior of your S-function is a function of discrete time intervals, you can define a sample time to control when the Simulink engine calls the S-function. You can also define an offset that delays each sample time hit. The value of the offset cannot exceed the corresponding sample time.

A sample time hit occurs at time values determined by the formula

```TimeHit = (n * period) + offset ```

where the integer `n` is the current simulation step. The first value of `n` is always zero.

If you define a discrete sample time, the engine calls the S-function `mdlOutputs` and `mdlUpdate` routines at each sample time hit (as defined in the previous equation).

• Variable sample time — A discrete sample time where the intervals between sample hits can vary. At the start of each simulation step, S-functions with variable sample times are queried for the time of the next hit.

• Inherited sample time — Sometimes an S-function has no inherent sample time characteristics (that is, it is either continuous or discrete, depending on the sample time of some other block in the system). In this case, you can specify that the sample time is inherited. A simple example of this is a Gain block that inherits its sample time from the block driving it.

An S-function can inherit its sample time from

• The driving block

• The destination block

• The fastest sample time in the system

To specify an S-function sample time is inherited, use -1 in Level-2 MATLAB S-functions and `INHERITED_SAMPLE_TIME` in C MEX S-functions as the sample time. For more information on the propagation of sample times, see How Propagation Affects Inherited Sample Times in the Simulink User's Guide.

S-functions can be either single or multirate; a multirate S-function has multiple sample times.

Sample times are specified in pairs in this format: [`sample_time`, `offset_time`].

#### Valid C MEX S-Function Sample Times

The valid sample time pairs for a C MEX S-function are

```[CONTINUOUS_SAMPLE_TIME, 0.0] [CONTINUOUS_SAMPLE_TIME, FIXED_IN_MINOR_STEP_OFFSET] [discrete_sample_time_period, offset] [VARIABLE_SAMPLE_TIME, 0.0] ```

where

```CONTINUOUS_SAMPLE_TIME = 0.0 FIXED_IN_MINOR_STEP_OFFSET = 1.0 VARIABLE_SAMPLE_TIME = -2.0 ```

and variable names in italics indicate that a real value is required.

Alternatively, you can specify that the sample time is inherited from the driving block. In this case, the C MEX S-function has only one sample time pair, either

```[INHERITED_SAMPLE_TIME, 0.0] ```

or

```[INHERITED_SAMPLE_TIME, FIXED_IN_MINOR_STEP_OFFSET] ```

where

```INHERITED_SAMPLE_TIME = -1.0 ```

#### Valid Level-2 MATLAB S-Function Sample Times

The valid sample time pairs for a Level-2 MATLAB S-function are

```[0 offset] % Continuous sample time [discrete_sample_time_period, offset] % Discrete sample time [-1, 0] % Inherited sample time [-2, 0] % Variable sample time```

where variable names in italics indicate that a real value is required. When using a continuous sample time, an `offset` of `1` indicates the output is fixed in minor integration time steps. An `offset` of `0` indicates the output changes at every minor integration time step.

#### Guidelines for Choosing a Sample Time

Use the following guidelines for help with specifying sample times:

• A continuous S-function that changes during minor integration steps should register the [`CONTINUOUS_SAMPLE_TIME`, `0.0`] sample time.

• A continuous S-function that does not change during minor integration steps should register the ```[CONTINUOUS_SAMPLE_TIME, FIXED_IN_MINOR_STEP_OFFSET]``` sample time.

• A discrete S-function that changes at a specified rate should register the discrete sample time pair, [`discrete_sample_time_period`, `offset`], where

```discrete_sample_period > 0.0 ```

and

```0.0 ≤ offset < discrete_sample_period ```
• A discrete S-function that changes at a variable rate should register the variable-step discrete sample time.

```[VARIABLE_SAMPLE_TIME, 0.0] ```

In a C MEX S-function, the `mdlGetTimeOfNextVarHit` routine is called to get the time of the next sample hit for the variable-step discrete task. In a Level-2 MATLAB S-function, the `NextTimeHit` property is set in the `Outputs` method to set the next sample hit.

If your S-function has no intrinsic sample time, you must indicate that your sample time is inherited. There are two cases:

• An S-function that changes as its input changes, even during minor integration steps, should register the ```[INHERITED_SAMPLE_TIME, 0.0]``` sample time.

• An S-function that changes as its input changes, but does not change during minor integration steps (that is, remains fixed during minor time steps), should register the ```[INHERITED_SAMPLE_TIME, FIXED_IN_MINOR_STEP_OFFSET]``` sample time.

The Scope block is a good example of this type of block. This block runs at the rate of its driving block, either continuous or discrete, but never runs in minor steps. If it did, the scope display would show the intermediate computations of the solver rather than the final result at each time point.

See Sample Times for information on implementing different types of sample times in S-functions.