Models

Core data models for the topology synthesizer.

All structures are plain dataclasses — they carry no logic and can be freely inspected, serialized, or passed between pipeline stages.

class circuitgenome.synthesizer.models.Device(ref, type, terminals, params=<factory>)[source]

Bases: object

A single primitive device (MOSFET, resistor, or capacitor).

Parameters:
  • ref (str) – Reference designator within the module (e.g. m1, r2).

  • type (str) – Device type: nmos, pmos, resistor, or capacitor.

  • terminals (dict[str, str]) – Maps terminal names to local net names. MOSFETs use d/g/s/b; resistors use t1/t2; capacitors use p/m.

  • params (dict[str, str]) – Optional device parameters preserved verbatim from a sized SPICE line, keyed as written. MOSFETs carry W/L/nf/m (and any other key=value token, values kept as SI-suffixed SPICE strings like 0.5u); resistors/capacitors carry their positional value token under value (e.g. {"value": "1k"}). Empty for devices built by the synthesizer or parsed from an unsized netlist. See parse().

ref: str
type: str
terminals: dict[str, str]
params: dict[str, str]
class circuitgenome.synthesizer.models.PortDef(name, role, alias_of=None)[source]

Bases: object

A port on a module variant.

Parameters:
  • name (str) – Port name (must match the canonical interface for its category).

  • role (str) – One of input, output, supply, supply_in, or optional. Optional ports are skipped when not wired in a topology.

  • alias_of (str | None) – If set, this port is electrically the same node as the named port on the same variant (e.g. a non-cascode load’s out1 aliases its in1). Used to recover the global net for ports that no device terminal references directly.

name: str
role: str
alias_of: str | None = None
class circuitgenome.synthesizer.models.ModuleVariant(name, category, display_name, ports, devices, polarity=None, output_cardinality=None, unsupported=None, bias_infeasible=None)[source]

Bases: object

One concrete implementation of a module category.

Every variant in the same category exposes the same canonical port signature; only the internal devices differ.

Parameters:
  • name (str) – Unique snake_case identifier (e.g. differential_pair_pmos).

  • category (str) – Module category (e.g. input_pair, load).

  • display_name (str) – Human-readable name shown in listings.

  • ports (list[PortDef]) – Ordered list of port definitions.

  • devices (list[Device]) – Ordered list of primitive devices.

  • polarity (str | None) – Electrical compatibility tag, either "pmos_input", "nmos_input", or None. Variants that share a current-flow direction with a given input_pair polarity declare the matching tag; None means the variant is compatible with either polarity. Used by is_combination_valid() to filter out combinations with no DC current path.

  • output_cardinality (str | None) – load-only tag, either "single", "differential", or None. Declares which topology output_type the variant is structurally usable with: for the cascode loads, which output_type defines a net for the variant’s mandatory output port(s) (out for "single", out1/out2 for "differential"); for current_source_load_*, "differential" because their bias_cmfb-gated branch devices need the CMFB loop that only fully_differential topologies wire (issue #112). None means the variant imposes no constraint and is compatible with either output type. Used by is_output_type_compatible().

  • unsupported (str | None) – None for enumerable variants. A non-None reason string parks the variant: it stays loadable (recognizer patterns and hand-built variant maps keep working) but enumerate_circuits() skips it unless config={"include_unsupported": True}.

  • bias_infeasible (str | None) – None for variants whose bias/headroom is expected to close on typical (low-voltage) specs. A non-None reason string marks a variant whose wiring is functionally correct but whose DC bias is infeasible under normal supply/Vcm headroom (e.g. the stacked-diode cascode tails, which need |Vgs|+Vdsat of tail compliance — issue #111). Unlike unsupported the circuit is fully buildable and would size into a complete netlist; it is simply predicted to fail the DC bias gate (the "bias_infeasible" designer outcome) on the default spec class. enumerate_circuits() skips it unless config={"include_infeasible": True}, which design-space exploration sets to keep these correct-but-infeasible circuits as mutation seeds.

name: str
category: str
display_name: str
ports: list[PortDef]
devices: list[Device]
polarity: str | None = None
output_cardinality: str | None = None
unsupported: str | None = None
bias_infeasible: str | None = None
port_names()[source]

Return the set of all port names on this variant.

Return type:

set[str]

class circuitgenome.synthesizer.models.BiasLegLibrary(reference, pref_branch, legs)[source]

Bases: object

The typed leg templates that demand-driven bias construction assembles.

Loaded from config/bias_legs.yaml by load_bias_legs(); consumed by construct_bias_generation(). Device terminals use the template-local net names ibias, pref, out, vdd, gnd (see the YAML header for the contract).

Parameters:
  • reference (list[Device]) – The master reference devices (always emitted).

  • pref_branch (list[Device]) – Devices deriving the PMOS-side reference gate (emitted only when an instantiated leg references pref).

  • legs (dict[str, list[Device]]) – Maps each rail kind (gate_vdd, gate_gnd, current_source, current_sink, tunable) to its leg’s device templates.

reference: list[Device]
pref_branch: list[Device]
legs: dict[str, list[Device]]
class circuitgenome.synthesizer.models.Slot(name, category)[source]

Bases: object

A named placeholder for one module category in a topology template.

Parameters:
  • name (str) – Slot identifier used in connection rules (e.g. input_pair).

  • category (str) – Module category that fills this slot.

name: str
category: str
class circuitgenome.synthesizer.models.Connection(slot, port, net)[source]

Bases: object

Wires one port of a module slot to a global net in the assembled circuit.

Parameters:
  • slot (str) – Slot name this connection applies to.

  • port (str) – Port name on the module in that slot.

  • net (str) – Global net name in the assembled circuit.

slot: str
port: str
net: str
class circuitgenome.synthesizer.models.TopologyTemplate(name, config, external_ports, slots, connections)[source]

Bases: object

A wiring blueprint for a complete op-amp topology.

Defines which module slots are required and how their ports connect to global nets and to each other.

Parameters:
  • name (str) – Unique identifier (e.g. two_stage_opamp_single_ended).

  • config (dict) – Metadata dict — stages (int) and output_type (str).

  • external_ports (list[str]) – Ordered list of top-level subcircuit port names.

  • slots (list[Slot]) – All module slots in this topology.

  • connections (list[Connection]) – Complete set of port-to-net wiring rules.

name: str
config: dict
external_ports: list[str]
slots: list[Slot]
connections: list[Connection]
slot_connections(slot_name)[source]

Return {port: global_net} for slot_name.

Parameters:

slot_name (str)

Return type:

dict[str, str]

class circuitgenome.synthesizer.models.SynthesizedCircuit(name, topology, variant_map, external_ports, devices=<factory>)[source]

Bases: object

A fully instantiated circuit produced by the synthesizer.

Parameters:
  • name (str) – Auto-generated name encoding the topology and variant combo.

  • topology (str) – Name of the TopologyTemplate used.

  • variant_map (dict[str, ModuleVariant]) – Maps each slot name to the chosen ModuleVariant.

  • external_ports (list[str]) – Top-level subcircuit ports (inherited from the template).

  • devices (list[tuple[str, Device]]) – Flat list of (global_ref, Device) pairs after net substitution. Internal nets are prefixed with the slot name to avoid collisions.

name: str
topology: str
variant_map: dict[str, ModuleVariant]
external_ports: list[str]
devices: list[tuple[str, Device]]