> Topic: Rise and fall times swapped in an inve...
# analog-design
n
Topic: Rise and fall times swapped in an inverter while doing a sweep of widths.
PDK: Sky130
Hello everyone, hope you are well. I'm sweeping widths of transistors that make up an inverter, while I calculate the rise and fall times for each iteration. Ngspice runs and gives me a plot and values for each iteration but the behavior is not what I expect: If Wn increases: • The fall time must be decrease, because NMOS has now more area for the current while the rise time must be increase, because PMOS has now less area. If you check the plots, you could see some exponential behaviour at the beginning and at the end that I still can't explain (fig 1). But if you look at the center of both, there is a "normal" behaviour, where it seems like the rise and fall times swapped, Tr is decreasing while Tf is increasing (fig 2). I don't know if this is due to an error I'm getting in some iterations where apparently the simulation is not executed but despite that, I'm still getting values for the tr and tf (fig 3) @Stefan Schippers may be you have an idea? Thanks in advance. I attach the code.
Copy code
********************************
* Title
********************************
.title Calculation of tr, tf for the tt corner over a w sweep.

********************************
* Inclusion of library
********************************
.lib /home/nelson/cad/share/pdk/sky130A/libs.tech/ngspice/sky130.lib.spice tt

********************************
* Circuit netlist
********************************
xp    vdd in  out vdd sky130_fd_pr__pfet_01v8 l=0.15 w=2
xn    out in  gnd gnd sky130_fd_pr__nfet_01v8 l=0.15 w=1
vin   in  gnd PULSE(0 1.8 0 1n 1n 5n 14n)
vpwr  vdd gnd DC  1.8  


********************************
* Control section
********************************
.control

* Voltage values to calculate rise and fall times
let v_steady = 1.8
let per10 = v_steady * 0.1
let per90 = v_steady * 0.9
let per50 = v_steady * 0.5

* These limits are based on the design of a standard cell of 12 tracks.
let wp_max = 1.85
let wn_min = 0.41
let wp_min = 0.42
let wn_max = 1.84

* Initialization of variables and size of iteration.
let delta_w = 0.01
let wp = wp_max 
let wn = wn_min
let loop = 0

* These vectors will be used to save the data of each iteration.
let loops = (wp_max-wp_min)/0.01
let wpv = unitvec($&loops)
let wnv = unitvec($&loops)
let trv = unitvec($&loops)
let tfv = unitvec($&loops)

* Start loop
while wp ge wp_min

* Modify widths
  echo
  echo ********************************** Cycle $&loop **********************************
  echo
  alter @m.xn.msky130_fd_pr__nfet_01v8[w] = $&wn
  alter @m.xp.msky130_fd_pr__pfet_01v8[w] = $&wp

* Run transient analysis
  TRAN 1n 30n $ 3 periods

* Find rise and fall times
  echo
  meas  TRAN  t_rise  TRIG  v(out) VAL=per10 RISE=2  TARG v(out)  VAL=per90 RISE=2
  meas  TRAN  t_fall  TRIG  v(out) VAL=per90 FALL=2  TARG v(out)  VAL=per10 FALL=2
  echo Wn: $&wn
  echo Wp: $&wp
  echo

* Save widths, t_rise, t_fall in vectors
  let wnv[loop] = wn
  let wpv[loop] = wp
  let trv[loop] = t_rise
  let tfv[loop] = t_fall

* Modify widths
  let wn = wn + delta_w
  let wp = wp - delta_w

* Counter increment
  let loop = loop + 1

end

echo
echo ********************************** End of Simulation **********************************
echo

* Export vector data into raw file
write data_tt.raw wnv wpv trv tfv

* Plot both rise and fall times vs. NMOS widths
plot trv vs wnv, tfv vs wnv
.endc

********************************
* End of file
********************************
.end
c
Without diving into the details of your spice code, from the third pic you posted it seems that in your loop somewhere you messed up the scaling of the device parameters. You can see that your ngspice is complaining about L=1.5e-07, and in sky130nm by default, the unit used for the device parameters is in um, so you are running into some errors with L=1.5e-07um.
n
Hi Chris, those unit multiples are shown in the output by ngspice, sometimes appear e-10, e-09, etc. If you check my code, by default values are in um.
s
@Nelson Rodriguez try to avoid at all the
alter
instruction, set dimensions of p and n with .param: .param WP=... .param WN=... then use alterparam to change the value (followed by a reset instruction) The following is a dc simulation of a single nmos where the width is changed on every run.
Copy code
* ngspice commands
.param W=1
.options savecurrents
.dc v2 0 1.8 0.01
.control
  let start_w = 1
  let stop_w = 90
  let delta_w = 5
  let w_act = start_w
  while w_act le stop_w
    alterparam W = $&w_act
    reset
    save all
    run
    remzerovec
    write test_sweep_mos_w.raw
    let w_act = w_act + delta_w
    set appendwrite
  end
.endc
🍺 1
sweeping parameters with ngspice is an absolute pain, i always have to try all permutation of options and strategies until one approach works.
👍🏼 1
n
@Stefan Schippers Thanks Stefan! this time no error appeared in the console! but now I have a huge doubt about the step size for TRAN analysis. If you look at the fig (2) you'll see 4 different plots with their respective tstep. Omit the last one, because its step is huge in comparison with my voltage pulse source which has a RT = FT = 1n:
vin in gnd PULSE(0 1.8 0 1n 1n 5n 14n)
The first two doesn't have meaning (how is it possible that rise and fall times behave the same? I though the third is the only one that shows the behave expected: As Wn increases Tf decreases, while Tr increases. But why is happening that with the plot 1,2 and 4? What is the recommended size of the step with respect to the voltage source description? Two short questions more: 1. Is not possible to create parameters from the interactive mode isn't it? (fig 1) 2. Must the parameters be defined always before control section? (like I did in my code)
@Stefan Schippers Here is my code
s
@Nelson Rodriguez add a load capacitance to the output:
cload out gnd 100f
with zero loading making bigger transistor will increase drain capacitance, so there is no advantage. With above load capacitance you get this:
🍺 1
with 10fF load you get this:
n
Sorry for being late but yes sir! that was the solution! Thanks a lot @Stefan Schippers! This allows me to run all corners getting correct behavior, calculate the average of tr and tf for each wn, taking into account all corner data and (in theory) the best wn to choose for designing cells is Wn ~ 0.45 and Wp ~ 1.81.
s
Good! In these wn/wp sweeps you may see some discontinuities, this is because each mos transistor is described by a specific model 'bin' valid for a specific W and L range. The bin boundaries do not always match perfectly. But overall the result seems consistent.
🫡 1