Build SI channel models by cascading measured S-parameter blocks (nport), lossy frequency-dependent transmission lines (txlineWRLGC, txlineWtable), and lumped parasitic elements (resistor, capacitor, inductor) in RF Toolbox circuit objects. Extract insertion loss, return loss, and crosstalk, then bridge to time-domain analysis via rational fitting.
When to Use
- Building channel models from cascaded nport S-parameter data (connectors, packages, PCB traces)
- Modeling frequency-dependent loss with txlineWRLGC or txlineWtable
- Analyzing differential and multi-port networks with port termination
- Combining lumped parasitics, transmission lines, and measured S-parameter blocks
- Extracting insertion/return loss from mixed lumped-distributed topologies
When NOT to Use
- Loading or plotting S-parameter data -- use
matlab-manage-sparameters - Cascading or de-embedding standalone S-parameter blocks -- use
matlab-deembed-rf-cascade - Composing general-purpose RF circuits (not SI-focused) -- use
matlab-compose-rf-circuit - Fitting rational models or computing TDR -- use
matlab-fit-rational-model - Designing impedance matching networks -- use
matlab-design-matching-network
Workflow
- Load blocks — Create nport elements from Touchstone files and transmission line models
- Build channel — Wire blocks, parasitics, and terminations in a
circuitobject - Extract S-parameters — Call
sparameters(ckt, freq)to get channel response - Analyze — Plot insertion/return loss, convert to mixed-mode, or fit for time-domain analysis
Lumped Parasitic Elements
Primitive R/L/C elements model vias, bond wires, pad capacitance, and termination resistors in SI channels. Each has terminals p (positive) and n (negative):
r = resistor(50, 'Rterm'); % 50 Ohm termination
c = capacitor(0.1e-12, 'Cvia'); % via pad capacitance
l = inductor(0.5e-9, 'Lvia'); % via barrel inductance
Gotcha: Primitive constructors are positional only: resistor(100, 'R1'). Name-value syntax like resistor('Resistance', 100) is not supported.
Handle semantics: Changing a property after adding to a circuit immediately affects the circuit -- no need to re-add.
Via Model (Lumped Subcircuit)
via = circuit('Via');
add(via, [1 2], inductor(0.5e-9, 'Lvia'));
add(via, [2 0], capacitor(0.1e-12, 'Cvia'));
setports(via, [1 0], [2 0]);
ESD/Decoupling Parasitic
esd = circuit('ESD');
add(esd, [1 0], capacitor(0.3e-12, 'Cesd'));
add(esd, [1 0], resistor(1e6, 'Resd')); % parallel RC to ground
setports(esd, [1 0]); % 1-port shunt element
nport Elements in Circuit
Embed measured or simulated S-parameter data (Touchstone files) as circuit elements. This is the primary building block for SI channel models -- connectors, packages, PCB segments, and fixtures are all characterized as S-parameter data.
2-Port nport
np = nport('connector.s2p');
np.Name = 'ConnIn';
ckt = circuit('Simple');
add(ckt, [1 2 0 0], np); % 4 nodes: p1+->1, p2+->2, p1-->0, p2-->0
add(ckt, [2 3], inductor(0.5e-9, 'L1'));
setports(ckt, [1 0], [3 0]);
A 2-port nport has 4 terminals (p1+, p2+, p1-, p2-), so add takes a 4-element node vector.
4-Port nport
A 4-port nport has 8 terminals. Two node-mapping forms:
np4 = nport('device.s4p');
np4.Name = 'Dev4P';
% Explicit 8-node form: [p1+ p2+ p3+ p4+ p1- p2- p3- p4-]
add(ckt, [1 2 3 4 0 0 0 0], np4); % all negatives grounded
% Shorthand N-node form: negatives implicitly grounded
add(ckt, [1 2 3 4], np4); % same result
Port Selection and Termination
Use setports on the circuit to select which nport ports become external ports. Unexposed ports are left open-circuited -- add explicit resistors for proper termination:
s4 = sparameters('device.s4p');
Z0 = s4.Impedance;
np4 = nport(s4);
np4.Name = 'Dev4P';
ckt = circuit('PortSelect');
add(ckt, [1 2 3 4 0 0 0 0], np4);
% Terminate unused ports 2 and 4 with matched loads
add(ckt, [2 0], resistor(Z0, 'Term2'));
add(ckt, [4 0], resistor(Z0, 'Term4'));
% Expose only ports 1 and 3 as a 2-port network
setports(ckt, [1 0], [3 0]);
freq = s4.Frequencies;
s = sparameters(ckt, freq); % S21 here equals S31 of original 4-port
Gotcha: Without explicit termination on unused ports, extracted S-parameters will differ from the original -- open-circuit reflections alter the network response.
Differential Port Mapping
For differential signaling, use the full 2N-node form with non-grounded negative terminals:
np4 = nport('diffpair.s4p');
np4.Name = 'DiffChan';
ckt = circuit('DiffAnalysis');
add(ckt, [1 2 3 4 5 6 7 8], np4); % non-grounded negatives
setports(ckt, [1 5], [3 7]); % differential: (p1+,p1-) -> (p3+,p3-)
Critical: every negative terminal must have a current path. Each nport port requires current to flow in through pi+ and return through pi-. If a negative terminal is mapped to a node that is not connected to anything (not grounded, not used as a port reference, not connected to another element), the current path is broken and the nport produces zero transmission (~-260 dB). There are three valid approaches:
- Ground all negatives (simplest):
add(ckt, [1 2 3 4 0 0 0 0], np)— all returns share node 0 - Use negatives as port references:
setports(ckt, [1 5], [3 7])— the port definition itself closes the loop throughpi- - Connect negatives to other elements: tie them to resistors, other nport terminals, etc.
Never leave negative terminals on isolated floating nodes.
Circuit Differential Ports vs s2sdd
The circuit approach (setports with differential node pairs) and the s2sdd function are not equivalent:
setports(ckt, [1 3], [2 4])with grounded negatives creates a physical voltage measurement between two single-ended nodes that each have their own ground return. This is effectively a series combination — it gives results like 2× the single-ended loss.s2sddperforms a mathematical modal decomposition of the full S-matrix. It algebraically separates differential and common modes without requiring a physical current path.
For extracting the true differential-mode response from a 4-port file, use s2sdd on the extracted S-parameters rather than trying to replicate it with differential setports. The circuit setports differential form is appropriate when ports physically correspond to differential terminals (e.g., a balanced amplifier with explicit + and - pins).
After extracting sparameters, convert to mixed-mode for differential/common-mode analysis:
s = sparameters(ckt, freq);
sdd = s2sdd(s.Parameters, 2); % 2x2xK differential array
% Wrap in sparameters with doubled impedance (differential Z0 = 2x single-ended)
sDiff = sparameters(sdd, s.Frequencies, 2*s.Impedance);
Multi-Port Channel Extraction
For a 4-port channel (e.g., near-end and far-end crosstalk):
np4 = nport('coupled_traces.s4p');
np4.Name = 'Traces';
ckt = circuit('CoupledChannel');
add(ckt, [1 2 3 4 0 0 0 0], np4);
setports(ckt, [1 0], [2 0], [3 0], [4 0]); % full 4-port extraction
s = sparameters(ckt, freq);
% S21 = through, S31 = NEXT, S41 = FEXT (depending on port assignment)
Frequency-Dependent Transmission Lines
txlineWRLGC and txlineWtable model lossy transmission lines with frequency-dependent parameters. Both are 2-port/4-terminal elements that work in circuit and rfbudget.
txlineWRLGC -- W-Element RLGC Model
Models frequency-dependent loss using an analytic formula (Djordjevic-Sarkar wideband model):
tw = txlineWRLGC;
tw.Lo = 350e-9; % inductance per unit length (H/m)
tw.Co = 130e-12; % capacitance per unit length (F/m)
tw.Ro = 2.0; % DC resistance (Ohm/m)
tw.Rs = 5e-4; % skin-effect resistance coefficient (Ohm/m/sqrt(Hz))
tw.Go = 0; % DC conductance (S/m)
tw.Gd = 1e-11; % dielectric loss conductance (S/m/Hz)
tw.LineLength = 0.05; tw.Name = 'PCBTrace'; % 50 mm
| Property | Default | Description |
|---|---|---|
Lo |
1e-9 | Inductance per unit length (H/m) |
Co |
4e-13 | Capacitance per unit length (F/m) |
Ro |
0 | DC series resistance (Ohm/m) |
Rs |
0 | Skin-effect resistance coefficient |
Go |
0 | DC shunt conductance (S/m) |
Gd |
0 | Dielectric loss conductance |
DielectricFrequency |
1e9 | Reference frequency for Gd (Hz) |
Nline |
1 | Number of signal conductors |
LineLength |
1 | Physical length (m) |
StubMode |
'NotAStub' |
'NotAStub', 'Series', or 'Shunt' |
Termination |
'NotApplicable' |
'NotApplicable', 'Short', or 'Open' |
Typical parameter ranges for common PCB technologies (50-Ohm single-ended):
| Technology | Lo (nH/m) | Co (pF/m) | Ro (Ohm/m) | Rs | Gd (S/m/Hz) |
|---|---|---|---|---|---|
| FR4 microstrip (outer layer) | 300-400 | 100-140 | 1-5 | 3e-4 to 8e-4 | 5e-12 to 2e-11 |
| FR4 stripline (inner layer) | 350-450 | 120-160 | 2-8 | 4e-4 to 1e-3 | 1e-11 to 5e-11 |
| Low-loss (Megtron6, Rogers) | 300-400 | 100-140 | 1-4 | 3e-4 to 6e-4 | 1e-12 to 5e-12 |
These are approximate starting points. For accurate models, extract RLGC parameters from a 2D field solver (e.g., Ansys Q2D, Cadence Sigrity) matched to your actual stackup geometry.
txlineWtable -- Table-Based Frequency-Dependent Model
Specifies R, L, G, C at discrete frequency points with interpolation. Use when you have extracted or measured per-unit-length parameters at specific frequencies:
wt = txlineWtable;
fpts = [1e8 1e9 10e9];
wt.R = [0.5 1.0 2.0]; wt.Rfreq = fpts; % Ohm/m
wt.L = [260 250 248]*1e-9; wt.Lfreq = fpts; % H/m
wt.C = [100 100 99]*1e-12; wt.Cfreq = fpts; % F/m
wt.G = [0 1e-4 1e-3]; wt.Gfreq = fpts; % S/m
wt.Lhf = 248e-9; wt.Chf = 99e-12; % HF asymptotes
wt.LineLength = 0.1; wt.Name = 'MeasuredTrace';
When to Use Each
| Model | Use Case |
|---|---|
txlineRLCGLine |
Constant RLCG -- quick estimates, frequency-independent loss |
txlineWRLGC |
Analytic frequency-dependent loss -- PCB traces, cables with skin effect |
txlineWtable |
Measured/extracted RLCG data at discrete frequencies |
Using in Circuit
All transmission lines have 4 terminals (p1+, p2+, p1-, p2-):
ckt = circuit('TraceLoss');
add(ckt, [1 2 0 0], tw); % 4-node mapping
setports(ckt, [1 0], [2 0]);
s = sparameters(ckt, linspace(1e8, 20e9, 500));
Mixed Topology Channel Models
Combine lumped elements, nport S-parameter blocks, and transmission lines in a single circuit -- the core pattern for SI channel modeling:
Connector-Trace-Via-Connector Channel
np_conn = nport('connector.s2p');
np_conn.Name = 'ConnIn';
trace = txlineWRLGC(Name='PCBTrace');
trace.Lo = 350e-9; trace.Co = 130e-12;
trace.Ro = 2.0; trace.Rs = 5e-4;
trace.Gd = 1e-11; trace.LineLength = 0.05;
via = circuit('Via');
add(via, [1 2], inductor(0.5e-9, 'Lvia'));
add(via, [2 0], capacitor(0.1e-12, 'Cvia'));
setports(via, [1 0], [2 0]);
ckt = circuit('Channel');
add(ckt, [1 2 0 0], np_conn); % input connector
add(ckt, [2 3 0 0], trace); % PCB trace
add(ckt, [3 4 0 0], via); % via transition
add(ckt, [4 5 0 0], clone(np_conn)); % output connector (cloned)
setports(ckt, [1 0], [5 0]);
freq = linspace(1e8, 10e9, 500);
s = sparameters(ckt, freq);
figure; tiledlayout(1, 2);
nexttile; rfplot(s, 2, 1); title('S21 -- Insertion Loss');
nexttile; rfplot(s, 1, 1); title('S11 -- Return Loss');
Differential Channel with Package
sPkg = sparameters('package.s4p');
Z0 = sPkg.Impedance;
pkg = nport(sPkg); pkg.Name = 'Package';
chan = nport('diffpair.s4p'); chan.Name = 'DiffTrace';
ckt = circuit('DiffChannel');
add(ckt, [1 2 3 4 0 0 0 0], pkg);
add(ckt, [2 4 5 6 0 0 0 0], chan); % ports 2,4 of pkg feed into channel
% Terminate unused package port 3 (near-end crosstalk victim)
add(ckt, [3 0], resistor(Z0, 'TermNEXT'));
% Expose: pkg port 1 -> channel port output
setports(ckt, [1 0], [5 0], [6 0]); % 3-port: input, thru, FEXT
s = sparameters(ckt, sPkg.Frequencies);
Multi-Path Analysis (Clone + Different Ports)
The clone() + different setports() pattern lets you analyze multiple signal paths through the same topology without rebuilding:
% Build an RC interconnect with crosstalk coupling
base = circuit('Interconnect');
add(base, [1 2], resistor(50, 'R1'));
add(base, [2 0], capacitor(1e-12, 'C1'));
add(base, [2 3], resistor(50, 'R2'));
add(base, [3 0], capacitor(1e-12, 'C2'));
add(base, [2 4], resistor(100, 'Rxtalk'));
add(base, [4 0], capacitor(2e-12, 'Cxtalk'));
% Main signal path
cktMain = clone(base);
setports(cktMain, [1 0], [3 0]);
% Crosstalk path
cktXtalk = clone(base);
setports(cktXtalk, [1 0], [4 0]);
freq = linspace(1e6, 10e9, 500);
sMain = sparameters(cktMain, freq);
sXtalk = sparameters(cktXtalk, freq);
Time-Domain Analysis
For time-domain channel characterization (TDR, impulse response, step response, eye diagrams), fit the extracted S-parameters with a rational model, then compute time responses. See the matlab-fit-rational-model skill for full details.
s = sparameters(ckt, freq);
fit = rational(s); % AAA algorithm (preferred over rationalfit)
[resp, t] = stepresp(fit, 1e-12, 10000, 50e-12); % (Ts, N, Trise)
% Multi-port fits return cell arrays for BOTH resp and t, indexed {output, input}
figure; plot(t{2,1}*1e9, resp{2,1}); % S21 step response
xlabel('Time (ns)'); ylabel('Voltage'); title('Channel Step Response');
Alternatively, convert to a voltage transfer function first, then fit the scalar result:
tf21 = s2tf(s); % S21 voltage transfer function (default)
fit21 = rational(tf21);
[h, t] = impulse(fit21, 1e-12, 10000);
Gotchas
- nport node count: min N, max 2N -- an N-port nport needs at least N nodes (negatives implicitly grounded) and at most 2N nodes. Fewer than N errors. For clarity, prefer the explicit 2N form with
0for grounded negatives. - Unexposed nport ports are open-circuited -- when using
setportsto expose only some ports of a multi-port nport, unused ports are left open. Add explicitresistor(Z0)terminations (where Z0 matches the S-parameter reference impedance, e.g.,s.Impedance) for correct S-parameter extraction. nport.Input/Outputare for rfbudget only -- these numeric port indices select the through-path forrfbudget. Incircuit, use node mapping andsetportsinstead.LineLengthnotLength-- all transmission line objects useLineLengthfor physical length. UsingLengtherrors.- txlineWtable needs multi-point RLCG data in circuit -- scalar R/L/G/C values (single frequency point) error with "number of data points should be equal to the number of frequency points" when extracting
sparametersfrom a circuit. Provide at least 2 frequency points in each RLCG table. - txlineWRLGC/txlineWtable constructors don't accept
StubMode/Termination-- set these as properties after construction. Only RLGC, length, and name parameters are accepted in the constructor. - txlineWRLGC
Nline>1with matrix Lo/Co -- multi-line coupled extraction has a sparameters bug in R2026a. Workaround: extract each line individually. - Elements cannot be shared across circuits -- always
clone()before reusing an element or subcircuit in a second circuit. setports/setterminalscan only be called once -- plan your topology before defining terminals.- Primitive constructors are positional --
resistor(100, 'R1'), notresistor('Resistance', 100). - Element Name must be a valid MATLAB identifier -- no spaces, no leading digits.
Conventions
- Use
tiledlayout/nexttilefor multi-panel channel analysis plots - Always label axes with units (dB, GHz, ns) and include figure titles
- Name elements descriptively for readable topology:
'ConnIn','PCBTrace','Lvia','Cpad' - Use
clone()liberally -- it deep-copies all nested elements and subcircuits - Plot both S21 (insertion loss) and S11 (return loss) for channel characterization
- For differential channels, convert to mixed-mode S-parameters with
s2sddafter extraction
Copyright 2026 The MathWorks, Inc.