Netlist extractor SPICE

Contents

Netlist extractor SPICE#

This notebook demonstrates how to extract the SPICE netlist of a Component or a GDS file using gdsfactory. It uses the :func:~get_netlist and :func:~get_l2n functions from the gplugins.klayout module to extract the netlist and connectivity mapping, respectively. It also uses the plot_nets function to visualize the connectivity.

import pathlib

from gdsfactory.samples.demo.lvs import pads_correct, pads_shorted

from gplugins.klayout.get_netlist import get_l2n, get_netlist
from gplugins.klayout.netlist_spice_reader import (
    GdsfactorySpiceReader,
)
from gplugins.klayout.plot_nets import plot_nets

Sample layouts#

We generate a sample layout using pads_correct and write a GDS file.

c = pads_correct()
gdspath = c.write_gds()
c.show()
c.plot()
../_images/63959de477b39349cac6ad2c495cb854e7fb4fde59171dff0f5f9560114863a8.png

We obtain the netlist using KLayout by simply calling the :func:~get_netlist function from the gplugins.klayout module. The function takes the path to the GDS file as an argument and returns the netlist as a kdb.Netlist object.

netlist = get_netlist(gdspath)
print(netlist)
Wrote '/home/runner/work/gplugins/gplugins/gplugins/klayout/layers.lyp'
/home/runner/work/gplugins/gplugins/gplugins/klayout/d25/generic.lyd25
Wrote '/home/runner/work/gplugins/gplugins/gplugins/klayout/tech.lyt'
circuit straight_gdsfactorypcomponentspwaveguidespstraight_L367_12efeeb9 ($1=$1);
end;
circuit straight_gdsfactorypcomponentspwaveguidespstraight_L190_c5fd8eec ($1=$1);
end;
circuit straight_gdsfactorypcomponentspwaveguidespstraight_L3_N_51c3cb9c ($1=$1);
end;
circuit wire_corner_gdsfactorypcomponentspwaveguidespwire_CSmet_507ea7e9 ($1=$1);
end;
circuit straight_gdsfactorypcomponentspwaveguidespstraight_L380_9b8fde9a ($1=$1);
end;
circuit taper_gdsfactorypcomponentsptapersptaper_L10_W100_W10_L_e6a63921 ($1=$1);
end;
circuit pad_gdsfactorypcomponentsppadsppad_S100_100_LMTOP_BLNon_457de54c ($1=$1,$2=$2);
end;
circuit pads_correct_Ppad_CSmetal3 ();
  subcircuit pad_gdsfactorypcomponentsppadsppad_S100_100_LMTOP_BLNon_457de54c $1 ($1='tl,tr',$2=tl);
  subcircuit pad_gdsfactorypcomponentsppadsppad_S100_100_LMTOP_BLNon_457de54c $2 ($1='tl,tr',$2=tr);
  subcircuit pad_gdsfactorypcomponentsppadsppad_S100_100_LMTOP_BLNon_457de54c $3 ($1='bl,br',$2=br);
  subcircuit pad_gdsfactorypcomponentsppadsppad_S100_100_LMTOP_BLNon_457de54c $4 ($1='bl,br',$2=bl);
  subcircuit taper_gdsfactorypcomponentsptapersptaper_L10_W100_W10_L_e6a63921 $5 ($1='tl,tr');
  subcircuit straight_gdsfactorypcomponentspwaveguidespstraight_L3_N_51c3cb9c $6 ($1='tl,tr');
  subcircuit wire_corner_gdsfactorypcomponentspwaveguidespwire_CSmet_507ea7e9 $7 ($1='tl,tr');
  subcircuit straight_gdsfactorypcomponentspwaveguidespstraight_L190_c5fd8eec $8 ($1='tl,tr');
  subcircuit wire_corner_gdsfactorypcomponentspwaveguidespwire_CSmet_507ea7e9 $9 ($1='tl,tr');
  subcircuit taper_gdsfactorypcomponentsptapersptaper_L10_W100_W10_L_e6a63921 $10 ($1='tl,tr');
  subcircuit straight_gdsfactorypcomponentspwaveguidespstraight_L367_12efeeb9 $11 ($1='tl,tr');
  subcircuit taper_gdsfactorypcomponentsptapersptaper_L10_W100_W10_L_e6a63921 $12 ($1='bl,br');
  subcircuit straight_gdsfactorypcomponentspwaveguidespstraight_L380_9b8fde9a $13 ($1='bl,br');
  subcircuit taper_gdsfactorypcomponentsptapersptaper_L10_W100_W10_L_e6a63921 $14 ($1='bl,br');
end;

The connectivity between the components in the GDS file can be visualized using the :func:~plot_nets function from the gplugins.klayout module. The function takes the path to the GDS file as an argument and plots the connectivity between the components in the GDS file.

l2n = get_l2n(gdspath)
cwd = pathlib.Path.cwd()
filepath = cwd / f"{c.name}.txt"
l2n.write_l2n(str(filepath))
plt = plot_nets(
    filepath, spice_reader=GdsfactorySpiceReader(components_as_subcircuits=[c.name])
)
plt.savefig(f"{c.name}.png")
plt.show()
Wrote '/home/runner/work/gplugins/gplugins/gplugins/klayout/layers.lyp'
/home/runner/work/gplugins/gplugins/gplugins/klayout/d25/generic.lyd25
Wrote '/home/runner/work/gplugins/gplugins/gplugins/klayout/tech.lyt'
../_images/07a5d30732e11276917a53469d5e776a29911eb8d455167f8a7adf1e72cf2541.png

The same steps as above are done for a shorted case.

c = pads_shorted()
gdspath = c.write_gds()
c.plot()
../_images/a7a880b361bd941f060bbfc8bdb2a00cf10c283bba46e5065490c411768b5a21.png
netlist = get_netlist(gdspath)
print(netlist)
Wrote '/home/runner/work/gplugins/gplugins/gplugins/klayout/layers.lyp'
/home/runner/work/gplugins/gplugins/gplugins/klayout/d25/generic.lyd25
Wrote '/home/runner/work/gplugins/gplugins/gplugins/klayout/tech.lyt'
circuit straight_gdsfactorypcomponentspwaveguidespstraight_L180_cafd862d ($1=$1);
end;
circuit straight_gdsfactorypcomponentspwaveguidespstraight_L367_12efeeb9 ($1=$1);
end;
circuit straight_gdsfactorypcomponentspwaveguidespstraight_L190_c5fd8eec ($1=$1);
end;
circuit straight_gdsfactorypcomponentspwaveguidespstraight_L3_N_51c3cb9c ($1=$1);
end;
circuit wire_corner_gdsfactorypcomponentspwaveguidespwire_CSmet_507ea7e9 ($1=$1);
end;
circuit straight_gdsfactorypcomponentspwaveguidespstraight_L380_9b8fde9a ($1=$1);
end;
circuit taper_gdsfactorypcomponentsptapersptaper_L10_W100_W10_L_e6a63921 ($1=$1);
end;
circuit pad_gdsfactorypcomponentsppadsppad_S100_100_LMTOP_BLNon_457de54c ($1=$1,$2=$2);
end;
circuit pads_shorted_Ppad_CSmetal3 ();
  subcircuit pad_gdsfactorypcomponentsppadsppad_S100_100_LMTOP_BLNon_457de54c $1 ($1='bl,br,tl,tr',$2=tl);
  subcircuit pad_gdsfactorypcomponentsppadsppad_S100_100_LMTOP_BLNon_457de54c $2 ($1='bl,br,tl,tr',$2=tr);
  subcircuit pad_gdsfactorypcomponentsppadsppad_S100_100_LMTOP_BLNon_457de54c $3 ($1='bl,br,tl,tr',$2=br);
  subcircuit pad_gdsfactorypcomponentsppadsppad_S100_100_LMTOP_BLNon_457de54c $4 ($1='bl,br,tl,tr',$2=bl);
  subcircuit taper_gdsfactorypcomponentsptapersptaper_L10_W100_W10_L_e6a63921 $5 ($1='bl,br,tl,tr');
  subcircuit taper_gdsfactorypcomponentsptapersptaper_L10_W100_W10_L_e6a63921 $6 ($1='bl,br,tl,tr');
  subcircuit straight_gdsfactorypcomponentspwaveguidespstraight_L380_9b8fde9a $7 ($1='bl,br,tl,tr');
  subcircuit taper_gdsfactorypcomponentsptapersptaper_L10_W100_W10_L_e6a63921 $8 ($1='bl,br,tl,tr');
  subcircuit straight_gdsfactorypcomponentspwaveguidespstraight_L180_cafd862d $9 ($1='bl,br,tl,tr');
  subcircuit taper_gdsfactorypcomponentsptapersptaper_L10_W100_W10_L_e6a63921 $10 ($1='bl,br,tl,tr');
  subcircuit taper_gdsfactorypcomponentsptapersptaper_L10_W100_W10_L_e6a63921 $11 ($1='bl,br,tl,tr');
  subcircuit straight_gdsfactorypcomponentspwaveguidespstraight_L3_N_51c3cb9c $12 ($1='bl,br,tl,tr');
  subcircuit wire_corner_gdsfactorypcomponentspwaveguidespwire_CSmet_507ea7e9 $13 ($1='bl,br,tl,tr');
  subcircuit straight_gdsfactorypcomponentspwaveguidespstraight_L190_c5fd8eec $14 ($1='bl,br,tl,tr');
  subcircuit wire_corner_gdsfactorypcomponentspwaveguidespwire_CSmet_507ea7e9 $15 ($1='bl,br,tl,tr');
  subcircuit taper_gdsfactorypcomponentsptapersptaper_L10_W100_W10_L_e6a63921 $16 ($1='bl,br,tl,tr');
  subcircuit straight_gdsfactorypcomponentspwaveguidespstraight_L367_12efeeb9 $17 ($1='bl,br,tl,tr');
end;
l2n = get_l2n(gdspath)
filepath = cwd / f"{c.name}.txt"
l2n.write_l2n(str(filepath))
plt = plot_nets(
    filepath, spice_reader=GdsfactorySpiceReader(components_as_subcircuits=[c.name])
)
plt.savefig(f"{c.name}.png")
plt.show()
Wrote '/home/runner/work/gplugins/gplugins/gplugins/klayout/layers.lyp'
/home/runner/work/gplugins/gplugins/gplugins/klayout/d25/generic.lyd25
Wrote '/home/runner/work/gplugins/gplugins/gplugins/klayout/tech.lyt'
../_images/e122644729cf5d7b28d82ef14047ab41f84a1b42177c97d4909898840fa2b219.png