LTSpiceのascファイルからHSPICE互換のネットリストを抽出する方法

同一回路のシミュレーションをして,LTSpiceでの解析精度はHSPICEの解析精度と全く同じである(※すくなくとも試した回路においては)ことは確認したのだが,シミュレーション結果を論文等に載せるのを考えるとやはりHSPICEでシミュレーションしておくと良い.そこで,研究室に残してきたノウハウ(2006-09-24)より転記.


まず,できる限りLTSpice上で,HSPICE互換のネットリストを作成しておく.

  • tran解析時は,0nsから始めるとうまくいかないことがあるので,.tran 10psのように少し遅らせる
  • バイスモデルを利用するときは,「.include "./TSMC-018.mod"」のように.includeを使う
  • 消費電力測定のために,電源電圧のノード名を「Vdd」としておく
  • 消費電力測定のために,以下の文を書いておく(LTSpice上ではエラーが出るが無視されるので特に問題ない)

.meas tran avepower P(Vdd) from=0ns to=??ns

View->Spice Netlistでネットリストが表示される.このとき,オプションで,終了時にネットリストは削除しないようにすると,????.netという名前で,ネットリストが保存される.(※この操作は,回路図更新後は必ず必要.この操作を行わないと,ネットリストが更新されない.)

この得られたネットリストは,以下のように若干修正する必要がある.

これらは,それぞれ以下のコマンドで対応可能

sed 's/{//g' moge.net
sed 's/}//g' moge.net
sed 's/\.model/\*\.model/' moge.net
sed 's/\.lib/\*\.lib/' moge.net

上記コマンドを一気にやろうとすると,

sed -e 's/{//g' -e 's/}//g' -e 's/\.model/\*\.model/' -e 's/\.lib/\*\.lib/' moge.net

実際は,下記のnet2sp.shを作って,

#!/bin/bash

# This script converts from LTSpice net file to sp file that can be used in HSPICE
# usage: net2sp.sh moge.net

name=`basename $1 .net`

sed -e 's/{//g' -e 's/}//g' -e 's/\.model/\*\.model/' -e 's/\.lib/\*\.lib/' $name.net > $name.sp

bash上で,以下のように実行した.

for f in *.sp; do sh net2sp.sh $f; done

MOSFETにAD, AS, PD, PSを付加する

研究室に残してきたノウハウ(2006-09-24)より転記.


シミュレーションする際,MOSFETにL, Wのみではなく,周辺長等のAD, AS, PD, PSのパラメータを追加しないと,正確なシミュレーションができない.しかし,実際はAD, AS, PD, PSのパラメータを計算し,手入力するのは大変である.

そこで,以前から使用していた,add-spice-adas-pdps.rbスクリプトを修正して,add-ltspice-adas-pdps.rbを作成した(本エントリ最後: add-ltspice-adas-pdps.rb).以下のコマンドで,MOSFETのL, WからAD, AS, PD, PSを追加することができる.

ruby add-ltspice-adas-pdps.rb hoge.asc > moge.asc

なお,スクリプト中には,lambdaを指定する必要がある.現在は,TSMC 0.18umプロセス用にlambda=0.1としてあるのに注意.

また,LTSpice上でサブサーキットを利用している場合は,サブサーキットの方にもAD, AS, PD, PSを付加しなくてはならないのに注意.


以下,add-ltspice-adas-pdps.rb

#!/usr/bin/env ruby
#!/opt/local/bin/ruby

#                作成 in 2003-11-29
#                修正 in 2003-07-16
#   LTSpice向けに修正 in 2006-09-23
# 使い方   : add-adas-pdps.rb hoge.sp > xxx.sp
# 結果     : W,L から AD,AS,PD,PS を計算して結果を挿入
# 対応書式 : M2 Y A VDD! VDD!  P  L=400E-9 W=1.9E-6 
#            M2 Y A VDD! VDD!  P  L=0.4u W=1.9u

# 0.1は,TSMC 0.18umの場合
lambda = 0.1

# W,L の値を入れる変数(小数)と計算パラメータ
p_w = 0.0; p_l = 0.0; p_adas = 0.0; p_pdps = 0.0;

lines = ARGF.readlines
lines.each do |x|
  flag_w = 0; flag_l = 0
  if /[Ww]\=([0-9]+(?:\.[0-9]+)?)(u|([eE]-[0-9]))/ =~ x then
    # W=0.4u または W=400E-9 にマッチ
    p_w = $1.to_f; flag_w = 1
    p_w = p_w * 0.001 if /[eE]-9/ =~ $2 # E-9 の場合は 0.001 をかける
  end
  if /[Ll]\=([0-9]+(?:\.[0-9]+)?)(u|([eE]-[0-9]))/ =~ x then
    # W=0.4u または W=400E-9 にマッチ
    p_l = $1.to_f; flag_l = 1
    p_l = p_l * 0.001 if /[eE]-9/ =~ $2 # E-9 の場合は 0.001 をかける
  end
  p_adas = p_w * 6*lambda         # AD=AS=W*6*lambda    
  p_pdps = 2 * (p_w + 6*lambda)   # PD=PS=2*(W+6*lambda)  see study note M1.5
  if flag_w==1 and flag_l==1 then
    x = x.chomp + " ad=#{p_adas}e-12 as=#{p_adas}e-12 pd=#{p_pdps}e-6 ps=#{p_pdps}e-6"
    puts x
  else
    print x
  end
end
>

HSPICEでシミュレーションした結果をgnuplotでプロットし直す方法

研究室に残してきたノウハウより転記.LTSpiceのことではなく,HSPICEに関するノウハウだけど.


.printステートメントで,出力したいノード名を書く.例えば,以下のような感じ.

.print i(vcarry) i(vintermidiate)

HSPICEでシミュレーションをすると.lisファイルができあがり,この中に

       time    current      current
                 vcarry    vintermidiat
   0.           27.3396p      1.6421n
  50.00000p     27.3396p      1.6421n
 100.00000p     27.3396p      1.6421n
 150.00000p     27.3396p      1.6421n
 200.00000p     27.3396p      1.6421n
 250.00000p     27.3396p      1.6421n
 300.00000p     27.3396p      1.6421n

という感じで,出力される.

あとは,この部分のみをgnuplotでプロットすればよいが,実際にはこのデータ以外にも色々と邪魔な情報が入っていて,このままではgnuplotに渡せない.そこで,以下のようなrubyスクリプトを利用することで,必要なデータ部分のみを取り出すことができる.

lines=ARGF.readlines
x_flag = 0
y_flag = 0
count  = 0
lines.each do |x|
  y_flag = 1 if x =~ /^y/
  if x_flag == 1 && y_flag == 0 then
    count += 1
    if count < 4
      print "#" + x
    else
      print x
    end
  end
  x_flag = 1 if x =~ /^x/
end

必要なデータは,xのみの行ではじまり,yのみの行で終わることを利用したスクリプト.また,数値データは3行目からはじまるので,それ以外は#でコメントアウトする.こ
スクリプトをfilter.rbとすると,以下のように利用する.

ruby filter.rb mogemoge.lis > hogehoge.dat

また,bashで以下のように実行しても良い.

for f in *.lis
do
  ruby filter.rb $f > `basename $f .lis`.dat
done