Skip to main content
ClaudeWave
Skill996 repo starsupdated 9d ago

matlab-review-fi-object-code

Reviews MATLAB fixed-point (fi) code for performance, code generation efficiency, and correctness. Identifies antipatterns and suggests idiomatic improvements. Use when reviewing fi, fimath, numerictype, or quantizenumeric code.

Install in Claude Code
Copy
git clone --depth 1 https://github.com/matlab/matlab-agentic-toolkit /tmp/matlab-review-fi-object-code && cp -r /tmp/matlab-review-fi-object-code/skills-catalog/code-generation/matlab-review-fi-object-code ~/.claude/skills/matlab-review-fi-object-code
Then start a new Claude Code session; the skill loads automatically.

SKILL.md

# fi Best Practices Review

Reviews MATLAB code for fixed-point (`fi`) best practices and suggests improvements for performance, code generation efficiency, and correctness.

## When to Use

- Reviewing MATLAB code that uses `fi`, `fimath`, `numerictype`, or `quantizenumeric`
- Optimizing fixed-point simulation speed
- Preparing fixed-point code for C or hardware code generation

## When Not to Use

- Code using only built-in integer types (`int8`, `uint16`, etc.) without `fi`
- Pure floating-point algorithms with no fixed-point intent
- Simulink-only workflows where fixed-point is configured through block dialogs (use Fixed-Point Tool instead)

## Checklist

When reviewing code, check for ALL of the following:

### 1. Vectorize fi() Calls

**Problem**: Scalar `fi()` in a loop is slow due to per-element object construction overhead.

**Fix**: Pass entire arrays to `fi()` at once.

```matlab
% BAD — slow: per-element fi object construction
for k = 1:N
    x_fi(k) = fi(x(k), 1, 18, 16, F);
end

% GOOD — fast: single vectorized call, bit-true identical result
x_fi = fi(x, 1, 18, 16, F);
```

### 2. Separate Data Types from Algorithm

**Problem**: Hardcoding fi types inside algorithm code makes it impossible to switch between float/fixed or compare configurations.

**Fix**: Use a types table with empty prototypes and `cast(...,'like',...)`.

```matlab
% Types table (separate function)
function T = mytypes(dt)
  switch dt
    case 'double'
      T.b = double([]);  T.x = double([]);  T.y = double([]);
    case 'single'
      T.b = single([]);  T.x = single([]);  T.y = single([]);
    case 'fixed16'
      F = fimath('RoundingMethod','Floor','OverflowAction','Wrap', ...
                 'ProductMode','KeepLSB','ProductWordLength',32, ...
                 'SumMode','KeepLSB','SumWordLength',32);
      T.b = fi([], 1, 16, 15, F);
      T.x = fi([], 1, 16, 15, F);
      T.y = fi([], 1, 16, 14, F);
  end
end

% Algorithm — no hardcoded types
function [y,z] = myfilter(b, x, z, T)
  y = zeros(size(x), 'like', T.y);
  for n = 1:length(x)
    z(:) = [x(n); z(1:end-1)];
    y(n) = b * z;
  end
end

% Entrypoint — wraps types + cast + algorithm
function [y,z] = entrypoint(dt, b, x)
  T = mytypes(dt);
  b = cast(b, 'like', T.b);
  x = cast(x, 'like', T.x);
  z = zeros(size(b'), 'like', T.x);
  [y,z] = myfilter(b, x, z, T);
end
```

**Validation**: Run with `'double'` first, then `'single'` (catches single-precision issues early — important for embedded targets where double is unavailable or slow), then `'fixed16'`.

### 3. Prevent Bit Growth with Subscripted Assignment

**Problem**: `acc = acc + x(n)` overwrites `acc` with a new fi object whose type may change due to FullPrecision word growth.

**Fix**: Use `acc(:) = acc + x(n)` to retain the original data type.

```matlab
% BAD — acc type may grow each iteration
acc = fi(0, 1, 32, 16);
for n = 1:numel(x)
    acc = acc + x(n);
end

% GOOD — preserves acc's declared type
acc = fi(0, 1, 32, 16);
for n = 1:numel(x)
    acc(:) = acc + x(n);
end
```

### 4. Configure fimath for Your Target

**Problem**: Default fimath (Nearest rounding, Saturate overflow, FullPrecision) generates bloated code. A simple `a + b` can produce many lines of C with sign-extension and overflow checks.

**Fix**: Choose fimath settings based on your code generation target.

```matlab
% For C targets (MATLAB Coder) — models integer truncation behavior
F_c = fimath('RoundingMethod','Floor', 'OverflowAction','Wrap', ...
             'ProductMode','KeepLSB', 'ProductWordLength',32, ...
             'SumMode','KeepLSB', 'SumWordLength',32);

% For DSP processor targets — models shift-right behavior
F_dsp = fimath('RoundingMethod','Floor', 'OverflowAction','Wrap', ...
               'ProductMode','KeepMSB', 'ProductWordLength',32, ...
               'SumMode','KeepMSB', 'SumWordLength',32);

% For FPGA/hardware targets — use the built-in helper
% hdlfimath = Floor/Wrap/FullPrecision (hardware coder manages bit widths internally)
F_hw = hdlfimath;
x_fi = fi(x, 1, 18, 16, F_hw);
```

**Product/Sum mode selection**:

| Mode | Behavior | Use when |
|------|----------|----------|
| `KeepLSB` | Keep least significant bits (C integer truncation) | Targeting C/C++ (MATLAB Coder) |
| `KeepMSB` | Keep most significant bits (shift-right) | Targeting DSP processors |
| `FullPrecision` | Retain all bits (word growth) | Hardware coder (manages widths internally), or debugging |
| `SpecifyPrecision` | Manual word/fraction lengths | Custom precision requirements |

**Note**: `hdlfimath` returns Floor/Wrap/FullPrecision. The hardware coder manages bit widths through its own pipeline — do not use `KeepLSB` or `KeepMSB` with it unless explicitly required by your design constraints.

**Rounding efficiency** (most to least efficient for codegen):
1. `Floor` — two's complement truncation, no extra logic
2. `Zero` — truncation toward zero
3. `Nearest` — ties to +inf (default)
4. `Convergent` — ties to nearest even
5. `Round` — ties away from zero (most expensive)

**Overflow**: `Wrap` (no logic) vs `Saturate` (requires comparison).

**Slope-bias scaling**: If your fi objects use slope-bias (non-power-of-two slope or non-zero bias):
- `ProductMode` and `SumMode` must be `'SpecifyPrecision'` with `CastBeforeSum` set to `true`
- Hardware code generation and DSP System Toolbox do not support slope-bias — use binary-point for hardware targets
- Slope-bias maximizes accuracy per bit when values are bunched away from zero (e.g., sensor ranges like 273–283 K)
- Match net scaling so operations resolve to shifts; non-zero bias makes multiplication costlier, but zero-bias with non-power-of-two slope can still produce shift-only code

### 5. Preallocate fi Arrays

**Problem**: Growing fi arrays inside loops causes quadratic memory and time growth.

**Fix**: Preallocate using `zeros(...,'like',...)` with a prototype.

```matlab
T = fi([], 1, 18, 16, F);       % empty prototype
Y = zeros(N, 1, 'like', T);     % preallocated out
matlab-train-networkSkill

>

matlab-driving-data-importerSkill

Import recorded driving sensor data (GPS, camera, lidar, actor tracks, lanes) into scenariobuilder.* objects (GPSData, CameraData, LidarData, ActorTrackData, Trajectory, laneData) and run preprocessing — synchronize, offset correction, crop, normalizeTimestamps, convertTimestamps. Also: compute actor tracks from lidar when no annotations exist, attach camera/lidar mounting + intrinsics, export to MAT/workspace/timetable/script. Use for raw driving dataset files (KITTI, nuScenes, Waymo, Pandaset, ROS/ROS2 bags, .mat, .csv, .mp4) or driving/vehicle/sensor logs that need wrapping. drivingLogAnalyzer (DLA) is OPT-IN ONLY — invoke only on explicit user request ('DLA', 'open in DLA', 'inspect/explore/analyze the recording') or reported sensor problem (sync drift, timestamp mismatch, overlay misalignment). NEVER auto-launch DLA after wrapping (Rule 0). For 'build scenario / export to RoadRunner / drivingScenario / OpenSCENARIO / Unreal / simulate', hand off to matlab-scenario-builder.

matlab-scenario-builderSkill

Generate driving scenes, scenarios, road surfaces, and 3D content from already-wrapped scenariobuilder.* sensor data (GPS, camera, lidar, actor tracks) using Scenario Builder for Automated Driving Toolbox. Use to BUILD, EXPORT, or AUGMENT a virtual scenario/scene/map: ego or actor trajectories, trajectory smoothing, OpenCRG road-surface extraction, 3D asset generation, static-object placement, point-cloud georeferencing + elevation, lane-based ego localization, sensor-fusion tracking, scenario-event extraction (cut-ins, hard brakes, near-misses, ADAS disengagements), or export to RoadRunner, drivingScenario, OpenDRIVE, OpenCRG, OpenSCENARIO, or Unreal Engine. Also: log-to-scenario, scenario harvesting, accident/near-miss reconstruction, SOTIF (ISO 21448) and ISO 26262 scenario coverage, USGS-aerial-lidar scene augmentation, traffic-sign placement from camera+lidar logs. NOT for raw-data import or multi-sensor sync/crop/offset/timestamp normalization — route those to matlab-driving-data-importer.

roadrunner-asset-mappingSkill

>

roadrunner-convert-lanelet2-to-rrhdSkill

>

roadrunner-import-sceneSkill

>

roadrunner-rrhd-authoringSkill

>

matlab-build-simbiology-modelSkill

Build, modify, and diagram SimBiology models — API reference, helper functions, and layout patterns. Use when constructing or editing models programmatically or visually.