compile scripts for simd
This commit is contained in:
parent
d42872a91d
commit
0d34bb52cc
|
|
@ -0,0 +1,84 @@
|
|||
#!/bin/bash
|
||||
# ngspice build script for Linux, release or debug version, 64 bit
|
||||
# compile_linux.sh <d>
|
||||
|
||||
# Procedure:
|
||||
# Install gcc, bison, flex, libtool, autoconf, automake,
|
||||
# libx11 and libx11-dev (headers), libXaw and libXaw-dev, libreadline and dev
|
||||
# Declare 'compile_linux.sh' executable and start compiling with
|
||||
# './compile_linux.sh' or './compile_linux.sh d' from the ngspice directory.
|
||||
# Options:
|
||||
# --adms and --enable-adms will install extra HICUM, EKV and MEXTRAM models via the
|
||||
# adms interface. You need to download and install the *.va files via ng-adms-va.tgz
|
||||
# Please see the ngspice manual, chapt. 13, for more info on adms.
|
||||
# CIDER, XSPICE, and OpenMP may be selected at will.
|
||||
# --disable-debug will give O2 optimization (versus O0 for debug) and removes all debugging info.
|
||||
|
||||
# ngspice as shared library:
|
||||
# Replace --with-x by --with-ngshared in line ../configure ... .
|
||||
# Add (optionally) --enable-relpath to avoid absolute paths when searching for code models.
|
||||
# It might be necessary to uncomment and run ./autogen.sh .
|
||||
|
||||
SECONDS=0
|
||||
|
||||
if test "$1" = "d"; then
|
||||
if [ ! -d "debug" ]; then
|
||||
mkdir debug
|
||||
if [ $? -ne 0 ]; then echo "mkdir debug failed"; exit 1 ; fi
|
||||
fi
|
||||
else
|
||||
if [ ! -d "release" ]; then
|
||||
mkdir release
|
||||
if [ $? -ne 0 ]; then echo "mkdir release failed"; exit 1 ; fi
|
||||
fi
|
||||
fi
|
||||
|
||||
# If compiling sources from git, you may need to uncomment the following two lines:
|
||||
./autogen.sh
|
||||
if [ $? -ne 0 ]; then echo "./autogen.sh failed"; exit 1 ; fi
|
||||
|
||||
# Alternatively, if compiling sources from git, and want to add adms created devices,
|
||||
# you may need to uncomment the following two lines (and don't forget to add adms option
|
||||
# to the ../configure statement):
|
||||
#./autogen.sh --adms
|
||||
#if [ $? -ne 0 ]; then echo "./autogen.sh failed"; exit 1 ; fi
|
||||
|
||||
echo
|
||||
if test "$1" = "d"; then
|
||||
cd debug
|
||||
if [ $? -ne 0 ]; then echo "cd debug failed"; exit 1 ; fi
|
||||
echo "configuring for 64 bit debug"
|
||||
echo
|
||||
# You may add --enable-adms to the following command for adding adms generated devices
|
||||
../configure --with-x --enable-xspice --enable-cider --with-readline=yes --enable-openmp CFLAGS="-g -m64 -O0 -Wall -Wno-unused-but-set-variable -march=native" LDFLAGS="-m64 -g"
|
||||
else
|
||||
cd release
|
||||
if [ $? -ne 0 ]; then echo "cd release failed"; exit 1 ; fi
|
||||
echo "configuring for 64 bit release"
|
||||
echo
|
||||
# You may add --enable-adms to the following command for adding adms generated devices
|
||||
../configure --with-x --enable-xspice --enable-cider --with-readline=yes --enable-openmp --disable-debug CFLAGS="-m64 -O3 -march=native" LDFLAGS="-m64 -s"
|
||||
fi
|
||||
if [ $? -ne 0 ]; then echo "../configure failed"; exit 1 ; fi
|
||||
|
||||
echo
|
||||
# make clean is required for properly making the code models
|
||||
echo "cleaning (see make_clean.log)"
|
||||
make clean 2>&1 -j8 | tee make_clean.log
|
||||
exitcode=${PIPESTATUS[0]}
|
||||
if [ $exitcode -ne 0 ]; then echo "make clean failed"; exit 1 ; fi
|
||||
echo "compiling (see make.log)"
|
||||
make 2>&1 -j8 | tee make.log
|
||||
exitcode=${PIPESTATUS[0]}
|
||||
if [ $exitcode -ne 0 ]; then echo "make failed"; exit 1 ; fi
|
||||
# Install to /usr/local
|
||||
echo "installing (see make_install.log)"
|
||||
make install 2>&1 | tee make_install.log
|
||||
exitcode=${PIPESTATUS[0]}
|
||||
if [ $exitcode -ne 0 ]; then echo "make install failed"; exit 1 ; fi
|
||||
|
||||
ELAPSED="Elapsed compile time: $(($SECONDS / 3600))hrs $((($SECONDS / 60) % 60))min $(($SECONDS % 60))sec"
|
||||
echo
|
||||
echo $ELAPSED
|
||||
echo "success"
|
||||
exit 0
|
||||
|
|
@ -0,0 +1,92 @@
|
|||
#!/bin/bash
|
||||
# ngspice build script for MINGW-w64, release or debug version, 64 bit
|
||||
# compile_min.sh
|
||||
|
||||
#Procedure:
|
||||
# Install MSYS2, plus gcc 64 bit, libtool, autoconf, automake, bison, git, and make
|
||||
# See either https://github.com/orlp/dev-on-windows/wiki/Installing-GCC--&-MSYS2
|
||||
# (allows to generate either 32 or 64 bit executables by setting flag -m32 or -m64)
|
||||
# start compiling with
|
||||
# './compile_min.sh' for release or './compile_min.sh d' for debug version.
|
||||
|
||||
# Options:
|
||||
# --adms and --enable-adms will install extra HICUM, EKV and MEXTRAM models via the
|
||||
# adms interface.
|
||||
# Please see http://ngspice.sourceforge.net/admshowto.html for more info on adms.
|
||||
# CIDER, XSPICE, and OpenMP may be selected at will.
|
||||
# --disable-debug will give O2 optimization (versus O0 for debug) and removes all debugging info.
|
||||
# --enable-oldapps will make ngnutmeg ngsconvert ngproc2mod ngmultidec ngmakeidx in addition to ngspice
|
||||
|
||||
# ngspice as shared library:
|
||||
# Replace --with-wingui by --with-ngshared in line ../configure ... .
|
||||
# Add (optionally) --enable-relpath to avoid absolute paths when searching for code models.
|
||||
# It might be necessary to uncomment and run ./autogen.sh .
|
||||
|
||||
SECONDS=0
|
||||
|
||||
if test "$1" = "d"; then
|
||||
if [ ! -d "debug" ]; then
|
||||
mkdir debug
|
||||
if [ $? -ne 0 ]; then echo "mkdir debug failed"; exit 1 ; fi
|
||||
fi
|
||||
else
|
||||
if [ ! -d "release" ]; then
|
||||
mkdir release
|
||||
if [ $? -ne 0 ]; then echo "mkdir release failed"; exit 1 ; fi
|
||||
fi
|
||||
fi
|
||||
|
||||
# If compiling sources from git, you may need to uncomment the following two lines:
|
||||
./autogen.sh
|
||||
if [ $? -ne 0 ]; then echo "./autogen.sh failed"; exit 1 ; fi
|
||||
|
||||
# Alternatively, if compiling sources from git, and want to add adms created devices,
|
||||
# you may need to uncomment the following two lines (and don't forget to add adms option
|
||||
# to the ../configure statement):
|
||||
#./autogen.sh --adms
|
||||
#if [ $? -ne 0 ]; then echo "./autogen.sh failed"; exit 1 ; fi
|
||||
|
||||
echo
|
||||
if test "$1" = "d"; then
|
||||
cd debug
|
||||
if [ $? -ne 0 ]; then echo "cd debug failed"; exit 1 ; fi
|
||||
echo "configuring for 64 bit debug"
|
||||
echo
|
||||
# You may add --enable-adms to the following command for adding adms generated devices
|
||||
../configure --with-wingui --enable-xspice --enable-cider --enable-openmp prefix="C:/Spice64d" CFLAGS="-g -m64 -O0 -Wall -Wno-unused-but-set-variable -march=native" LDFLAGS="-g -m64"
|
||||
else
|
||||
cd release
|
||||
if [ $? -ne 0 ]; then echo "cd release failed"; exit 1 ; fi
|
||||
echo "configuring for 64 bit release"
|
||||
echo
|
||||
# You may add --enable-adms to the following command for adding adms generated devices
|
||||
../configure --with-wingui --enable-xspice --enable-cider --enable-openmp --disable-debug prefix="C:/Spice64" CFLAGS="-m64 -O3 -march=native " LDFLAGS="-m64 -s"
|
||||
fi
|
||||
if [ $? -ne 0 ]; then echo "../configure failed"; exit 1 ; fi
|
||||
|
||||
echo
|
||||
# make clean is required for properly making the code models
|
||||
echo "cleaning (see make_clean.log)"
|
||||
make clean 2>&1 -j8 | tee make_clean.log
|
||||
exitcode=${PIPESTATUS[0]}
|
||||
if [ $exitcode -ne 0 ]; then echo "make clean failed"; exit 1 ; fi
|
||||
echo "compiling the icon"
|
||||
windres ../src/ngicon.rc -O coff -o ./src/ngicon.o
|
||||
exitcode=${PIPESTATUS[0]}
|
||||
if [ $exitcode -ne 0 ]; then echo "compiling the icon failed"; exit 1 ; fi
|
||||
echo "compiling (see make.log)"
|
||||
make 2>&1 -j8 | tee make.log
|
||||
exitcode=${PIPESTATUS[0]}
|
||||
if [ $exitcode -ne 0 ]; then echo "make failed"; exit 1 ; fi
|
||||
# 64 bit debug: Install to C:\Spice64d
|
||||
# 64 bit: Install to C:\Spice64
|
||||
echo "installing (see make_install.log)"
|
||||
make install 2>&1 | tee make_install.log
|
||||
exitcode=${PIPESTATUS[0]}
|
||||
if [ $exitcode -ne 0 ]; then echo "make install failed"; exit 1 ; fi
|
||||
|
||||
ELAPSED="Elapsed compile time: $(($SECONDS / 3600))hrs $((($SECONDS / 60) % 60))min $(($SECONDS % 60))sec"
|
||||
echo
|
||||
echo $ELAPSED
|
||||
echo "success"
|
||||
exit 0
|
||||
|
|
@ -30,7 +30,7 @@ AC_CONFIG_HEADER([src/include/ngspice/config.h])
|
|||
|
||||
# Initialise automake stuff
|
||||
AM_INIT_AUTOMAKE([-Wall -Werror nostdinc serial-tests])
|
||||
m4_ifdef([AM_SILENT_RULES], [AM_SILENT_RULES([yes])])
|
||||
m4_ifdef([AM_SILENT_RULES], [AM_SILENT_RULES([no])])
|
||||
|
||||
ext_CFLAGS="${CFLAGS+yes}"
|
||||
|
||||
|
|
|
|||
|
|
@ -1402,9 +1402,14 @@ InterpFileAdd(runDesc *run, IFvalue *refValue, IFvalue *valuePtr)
|
|||
static double timeold = 0.0, timenew = 0.0, timestep = 0.0;
|
||||
bool nodata = FALSE;
|
||||
bool interpolatenow = FALSE;
|
||||
static bool pass2done = FALSE;
|
||||
|
||||
/* If tran with uic and interp, run fileInit_pass2 only once */
|
||||
if (run->pointCount == 1) {
|
||||
fileInit_pass2(run);
|
||||
if (!pass2done) {
|
||||
fileInit_pass2(run);
|
||||
pass2done = TRUE;
|
||||
}
|
||||
timestep = run->circuit->CKTinitTime + run->circuit->CKTstep;
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -24,12 +24,17 @@ libbsim3v32_la_SOURCES = \
|
|||
bsim3v32ext.h \
|
||||
bsim3v32init.c \
|
||||
bsim3v32init.h \
|
||||
bsim3v32itf.h
|
||||
bsim3v32itf.h \
|
||||
b3v32ldseq.c \
|
||||
b3v32ldsel.c \
|
||||
b3v32ldsimd.c \
|
||||
vec4_exp.c \
|
||||
vec4_log.c
|
||||
|
||||
|
||||
|
||||
AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include
|
||||
AM_CFLAGS = $(STATIC)
|
||||
AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include -DBSIM3v32SIMD
|
||||
AM_CFLAGS = $(STATIC) -Wall -fno-math-errno -ffast-math
|
||||
|
||||
MAINTAINERCLEANFILES = Makefile.in
|
||||
|
||||
|
|
|
|||
|
|
@ -10,7 +10,6 @@
|
|||
* Modified by Xuemei Xi, 10/05, 12/21, 2001.
|
||||
* Modified by Paolo Nenzi 2002 and Dietmar Warning 2003
|
||||
**********/
|
||||
|
||||
#include "ngspice/ngspice.h"
|
||||
#include "ngspice/cktdefs.h"
|
||||
#include "bsim3v32def.h"
|
||||
|
|
@ -70,17 +69,14 @@ double SourceSatCurrent, DrainSatCurrent;
|
|||
double ag0, qgd, qgs, qgb, von, cbhat, VgstNVt, ExpVgst;
|
||||
double cdrain, cdhat, cdreq, ceqbd, ceqbs, ceqqb, ceqqd, ceqqg, ceq, geq;
|
||||
double czbd, czbdsw, czbdswg, czbs, czbssw, czbsswg, evbd, evbs, arg, sarg;
|
||||
double delvbd, delvbs, delvds, delvgd, delvgs;
|
||||
/* double delvbd, delvbs, delvds, delvgd, delvgs; FB: moved decl into sub block */
|
||||
double Vfbeff, dVfbeff_dVg, dVfbeff_dVd = 0.0, dVfbeff_dVb, V3, V4;
|
||||
double gcbdb, gcbgb, gcbsb, gcddb, gcdgb, gcdsb, gcgdb, gcggb, gcgsb, gcsdb;
|
||||
#ifndef NEWCONV
|
||||
double tol;
|
||||
#endif
|
||||
/* FB: moved double to decl into NEWCONV block */
|
||||
|
||||
double gcsgb, gcssb, MJ, MJSW, MJSWG;
|
||||
double vbd, vbs, vds, vgb, vgd, vgs, vgdo;
|
||||
#ifndef PREDICTOR
|
||||
double xfact;
|
||||
#endif
|
||||
/* FB: xfact decl moved inside PREDICTOR block */
|
||||
double qgate = 0.0, qbulk = 0.0, qdrn = 0.0, qsrc;
|
||||
double qinoi, cqgate, cqbulk, cqdrn;
|
||||
double Vds, Vgs, Vbs, Gmbs, FwdSum, RevSum;
|
||||
|
|
@ -120,7 +116,7 @@ double Xdep, dXdep_dVb, lt1, dlt1_dVb, ltw, dltw_dVb, Delt_vth, dDelt_vth_dVb;
|
|||
double Theta0, dTheta0_dVb;
|
||||
double TempRatio, tmp1, tmp2, tmp3, tmp4;
|
||||
double DIBL_Sft, dDIBL_Sft_dVd, Lambda, dLambda_dVg;
|
||||
double Idtot, Ibtot;
|
||||
/* double Idtot, Ibtot; FB: moved Idtot and Ibtot decl into sub blocks */
|
||||
#ifndef NOBYPASS
|
||||
double tempv;
|
||||
#endif
|
||||
|
|
@ -211,9 +207,12 @@ for (; model != NULL; model = BSIM3v32nextModel(model))
|
|||
}
|
||||
else
|
||||
{
|
||||
double Idtot, Ibtot;
|
||||
double delvbd, delvbs, delvds, delvgd, delvgs;
|
||||
#ifndef PREDICTOR
|
||||
if ((ckt->CKTmode & MODEINITPRED))
|
||||
{ xfact = ckt->CKTdelta / ckt->CKTdeltaOld[1];
|
||||
{ double xfact;
|
||||
xfact = ckt->CKTdelta / ckt->CKTdeltaOld[1];
|
||||
*(ckt->CKTstate0 + here->BSIM3v32vbs) =
|
||||
*(ckt->CKTstate1 + here->BSIM3v32vbs);
|
||||
vbs = (1.0 + xfact)* (*(ckt->CKTstate1 + here->BSIM3v32vbs))
|
||||
|
|
@ -2747,13 +2746,24 @@ finished:
|
|||
/*
|
||||
* check convergence
|
||||
*/
|
||||
#ifdef USE_OMP
|
||||
here->BSIM3v32noncon=0;
|
||||
#endif
|
||||
if ((here->BSIM3v32off == 0) || (!(ckt->CKTmode & MODEINITFIX)))
|
||||
{ if (Check == 1)
|
||||
{ ckt->CKTnoncon++;
|
||||
{
|
||||
#ifdef USE_OMP
|
||||
here->BSIM3v32noncon++;
|
||||
#else
|
||||
ckt->CKTnoncon++;
|
||||
#endif
|
||||
#ifndef NEWCONV
|
||||
}
|
||||
else
|
||||
{ if (here->BSIM3v32mode >= 0)
|
||||
{
|
||||
double tol;
|
||||
double Idtot, Ibtot;
|
||||
if (here->BSIM3v32mode >= 0)
|
||||
{ Idtot = here->BSIM3v32cd + here->BSIM3v32csub - here->BSIM3v32cbd;
|
||||
}
|
||||
else
|
||||
|
|
@ -2769,7 +2779,12 @@ finished:
|
|||
tol = ckt->CKTreltol * MAX(fabs(cbhat), fabs(Ibtot))
|
||||
+ ckt->CKTabstol;
|
||||
if (fabs(cbhat - Ibtot) > tol)
|
||||
{ ckt->CKTnoncon++;
|
||||
{
|
||||
#ifdef USE_OMP
|
||||
here->BSIM3v32noncon++;
|
||||
#else
|
||||
ckt->CKTnoncon++;
|
||||
#endif
|
||||
}
|
||||
}
|
||||
#endif /* NEWCONV */
|
||||
|
|
@ -3172,7 +3187,9 @@ line850:
|
|||
|
||||
gqdef = gcqgb = gcqdb = gcqsb = gcqbb = 0.0;
|
||||
ggtg = ggtd = ggtb = ggts = 0.0;
|
||||
sxpart = (1.0 - (dxpart = (here->BSIM3v32mode > 0) ? 0.4 : 0.6));
|
||||
/* F.B: moved dxpart assignment outside the following expression */
|
||||
dxpart = (here->BSIM3v32mode > 0) ? 0.4 : 0.6;
|
||||
sxpart = (1.0 - dxpart);
|
||||
ddxpart_dVd = ddxpart_dVg = ddxpart_dVb = ddxpart_dVs = 0.0;
|
||||
dsxpart_dVd = dsxpart_dVg = dsxpart_dVb = dsxpart_dVs = 0.0;
|
||||
|
||||
|
|
@ -3310,8 +3327,13 @@ line900:
|
|||
here->BSIM3v32rhsD = m * (ceqbd - cdreq - ceqqd);
|
||||
here->BSIM3v32rhsS = m * (cdreq + ceqbs + ceqqg
|
||||
+ ceqqb + ceqqd);
|
||||
#ifndef OMP_EFFMEM
|
||||
if (here->BSIM3v32nqsMod)
|
||||
here->BSIM3v32rhsQ = m * (cqcheq - cqdef);
|
||||
#else
|
||||
if (here->BSIM3v32nqsMod)
|
||||
*(ckt->CKTrhs + here->BSIM3v32qNode) += m * (cqcheq - cqdef);
|
||||
#endif
|
||||
#else
|
||||
(*(ckt->CKTrhs + here->BSIM3v32gNode) -= m * ceqqg);
|
||||
(*(ckt->CKTrhs + here->BSIM3v32bNode) -= m * (ceqbs + ceqbd + ceqqb));
|
||||
|
|
@ -3329,27 +3351,17 @@ line900:
|
|||
T1 = qdef * here->BSIM3v32gtau;
|
||||
#ifdef USE_OMP
|
||||
here->BSIM3v32DdPt = m * here->BSIM3v32drainConductance;
|
||||
here->BSIM3v32SsPt = m * here->BSIM3v32sourceConductance;
|
||||
here->BSIM3v32GgPt = m * (gcggb - ggtg);
|
||||
here->BSIM3v32SsPt = m * here->BSIM3v32sourceConductance;
|
||||
here->BSIM3v32BbPt = m * (here->BSIM3v32gbd + here->BSIM3v32gbs
|
||||
here->BSIM3v32BbPt = m * (here->BSIM3v32gbd + here->BSIM3v32gbs
|
||||
- gcbgb - gcbdb - gcbsb - here->BSIM3v32gbbs);
|
||||
here->BSIM3v32DPdpPt = m * (here->BSIM3v32drainConductance
|
||||
+ here->BSIM3v32gds + here->BSIM3v32gbd
|
||||
+ RevSum + gcddb + dxpart * ggtd
|
||||
+ T1 * ddxpart_dVd + gbdpdp);
|
||||
here->BSIM3v32SPspPt = m * (here->BSIM3v32sourceConductance
|
||||
+ here->BSIM3v32gds + here->BSIM3v32gbs
|
||||
+ FwdSum + gcssb + sxpart * ggts
|
||||
+ T1 * dsxpart_dVs + gbspsp);
|
||||
here->BSIM3v32DdpPt = m * here->BSIM3v32drainConductance;
|
||||
|
||||
here->BSIM3v32GbPt = m * (gcggb + gcgdb + gcgsb + ggtb);
|
||||
here->BSIM3v32GdpPt = m * (gcgdb - ggtd);
|
||||
here->BSIM3v32GspPt = m * (gcgsb - ggts);
|
||||
here->BSIM3v32SspPt = m * here->BSIM3v32sourceConductance;
|
||||
here->BSIM3v32BgPt = m * (gcbgb - here->BSIM3v32gbgs);
|
||||
here->BSIM3v32BdpPt = m * (gcbdb - here->BSIM3v32gbd + gbbdp);
|
||||
here->BSIM3v32BspPt = m * (gcbsb - here->BSIM3v32gbs + gbbsp);
|
||||
here->BSIM3v32DPdPt = m * here->BSIM3v32drainConductance;
|
||||
here->BSIM3v32DPgPt = m * (Gm + gcdgb + dxpart * ggtg
|
||||
+ T1 * ddxpart_dVg + gbdpg);
|
||||
here->BSIM3v32DPbPt = m * (here->BSIM3v32gbd - Gmbs + gcdgb + gcddb
|
||||
|
|
@ -3359,14 +3371,25 @@ line900:
|
|||
- dxpart * ggts - T1 * ddxpart_dVs - gbdpsp);
|
||||
here->BSIM3v32SPgPt = m * (gcsgb - Gm + sxpart * ggtg
|
||||
+ T1 * dsxpart_dVg + gbspg);
|
||||
here->BSIM3v32SPsPt = m * here->BSIM3v32sourceConductance;
|
||||
here->BSIM3v32SPbPt = m * (here->BSIM3v32gbs + Gmbs + gcsgb + gcsdb
|
||||
+ gcssb - sxpart * ggtb
|
||||
- T1 * dsxpart_dVb - gbspb);
|
||||
here->BSIM3v32SPdpPt = m * (here->BSIM3v32gds + RevSum - gcsdb
|
||||
- sxpart * ggtd - T1 * dsxpart_dVd - gbspdp);
|
||||
|
||||
if (here->BSIM3v32nqsMod)
|
||||
here->BSIM3v32DPdpPt = m * (here->BSIM3v32drainConductance
|
||||
+ here->BSIM3v32gds + here->BSIM3v32gbd
|
||||
+ RevSum + gcddb + dxpart * ggtd
|
||||
+ T1 * ddxpart_dVd + gbdpdp);
|
||||
here->BSIM3v32SPspPt = m * (here->BSIM3v32sourceConductance
|
||||
+ here->BSIM3v32gds + here->BSIM3v32gbs
|
||||
+ FwdSum + gcssb + sxpart * ggts
|
||||
+ T1 * dsxpart_dVs + gbspsp);
|
||||
here->BSIM3v32DdpPt = m * here->BSIM3v32drainConductance;
|
||||
here->BSIM3v32SspPt = m * here->BSIM3v32sourceConductance;
|
||||
here->BSIM3v32DPdPt = m * here->BSIM3v32drainConductance;
|
||||
here->BSIM3v32SPsPt = m * here->BSIM3v32sourceConductance;
|
||||
#ifndef OMP_EFFMEM
|
||||
if (here->BSIM3v32nqsMod)
|
||||
{
|
||||
here->BSIM3v32QqPt = m * (gqdef + here->BSIM3v32gtau);
|
||||
|
||||
|
|
@ -3379,7 +3402,24 @@ line900:
|
|||
here->BSIM3v32QspPt = m * (ggts - gcqsb);
|
||||
here->BSIM3v32QbPt = m * (ggtb - gcqbb);
|
||||
}
|
||||
#else
|
||||
#else
|
||||
if (here->BSIM3v32nqsMod)
|
||||
{
|
||||
*(here->BSIM3v32QqPtr) += m * (gqdef + here->BSIM3v32gtau);
|
||||
|
||||
*(here->BSIM3v32DPqPtr) += m * (dxpart * here->BSIM3v32gtau);
|
||||
*(here->BSIM3v32SPqPtr) += m * (sxpart * here->BSIM3v32gtau);
|
||||
*(here->BSIM3v32GqPtr) -= m * here->BSIM3v32gtau;
|
||||
|
||||
*(here->BSIM3v32QgPtr) += m * (ggtg - gcqgb);
|
||||
*(here->BSIM3v32QdpPtr) += m * (ggtd - gcqdb);
|
||||
*(here->BSIM3v32QspPtr) += m * (ggts - gcqsb);
|
||||
*(here->BSIM3v32QbPtr) += m * (ggtb - gcqbb);
|
||||
}
|
||||
#endif
|
||||
#endif /* ifdef USE_OMP */
|
||||
|
||||
#ifndef USE_OMP
|
||||
(*(here->BSIM3v32DdPtr) += m * here->BSIM3v32drainConductance);
|
||||
(*(here->BSIM3v32GgPtr) += m * (gcggb - ggtg));
|
||||
(*(here->BSIM3v32SsPtr) += m * here->BSIM3v32sourceConductance);
|
||||
|
|
@ -3457,14 +3497,18 @@ void BSIM3v32LoadRhsMat(GENmodel *inModel, CKTcircuit *ckt)
|
|||
for (idx = 0; idx < InstCount; idx++) {
|
||||
here = InstArray[idx];
|
||||
model = BSIM3v32modPtr(here);
|
||||
/* F.B. Update non convergence count */
|
||||
ckt->CKTnoncon += here->BSIM3v32noncon;
|
||||
/* Update b for Ax = b */
|
||||
(*(ckt->CKTrhs + here->BSIM3v32gNode) -= here->BSIM3v32rhsG);
|
||||
(*(ckt->CKTrhs + here->BSIM3v32bNode) -= here->BSIM3v32rhsB);
|
||||
(*(ckt->CKTrhs + here->BSIM3v32dNodePrime) += here->BSIM3v32rhsD);
|
||||
(*(ckt->CKTrhs + here->BSIM3v32sNodePrime) += here->BSIM3v32rhsS);
|
||||
#ifndef OMP_EFFMEM
|
||||
if (here->BSIM3v32nqsMod)
|
||||
(*(ckt->CKTrhs + here->BSIM3v32qNode) += here->BSIM3v32rhsQ);
|
||||
|
||||
#endif
|
||||
|
||||
/* Update A for Ax = b */
|
||||
(*(here->BSIM3v32DdPtr) += here->BSIM3v32DdPt);
|
||||
(*(here->BSIM3v32GgPtr) += here->BSIM3v32GgPt);
|
||||
|
|
@ -3488,7 +3532,8 @@ void BSIM3v32LoadRhsMat(GENmodel *inModel, CKTcircuit *ckt)
|
|||
(*(here->BSIM3v32SPsPtr) -= here->BSIM3v32SPsPt);
|
||||
(*(here->BSIM3v32SPbPtr) -= here->BSIM3v32SPbPt);
|
||||
(*(here->BSIM3v32SPdpPtr) -= here->BSIM3v32SPdpPt);
|
||||
|
||||
|
||||
#ifndef OMP_EFFMEM
|
||||
if (here->BSIM3v32nqsMod)
|
||||
{
|
||||
*(here->BSIM3v32QqPtr) += here->BSIM3v32QqPt;
|
||||
|
|
@ -3502,6 +3547,7 @@ void BSIM3v32LoadRhsMat(GENmodel *inModel, CKTcircuit *ckt)
|
|||
*(here->BSIM3v32QspPtr) += here->BSIM3v32QspPt;
|
||||
*(here->BSIM3v32QbPtr) += here->BSIM3v32QbPt;
|
||||
}
|
||||
#endif
|
||||
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -6,6 +6,7 @@
|
|||
* Author: 1995 Min-Chie Jeng and Mansun Chan.
|
||||
* Author: 1997-1999 Weidong Liu.
|
||||
* Author: 2001 Xuemei Xi
|
||||
* Modified by Florian Ballenegger 2020 (for SIMD evaluation)
|
||||
**********/
|
||||
|
||||
#include "ngspice/ngspice.h"
|
||||
|
|
@ -39,7 +40,7 @@ CKTnode *tmp;
|
|||
CKTnode *tmpNode;
|
||||
IFuid tmpName;
|
||||
|
||||
#ifdef USE_OMP
|
||||
#if defined(USE_OMP) || defined(BSIM3v32SIMD)
|
||||
int idx, InstCount;
|
||||
BSIM3v32instance **InstArray;
|
||||
#endif
|
||||
|
|
@ -1034,7 +1035,7 @@ BSIM3v32instance **InstArray;
|
|||
/* process drain series resistance */
|
||||
if (DrainResistance != 0)
|
||||
{
|
||||
if(here->BSIM3v32dNodePrime == 0) {
|
||||
if(here->BSIM3v32dNodePrime == 0) {
|
||||
error = CKTmkVolt(ckt,&tmp,here->BSIM3v32name,"drain");
|
||||
if(error) return(error);
|
||||
here->BSIM3v32dNodePrime = tmp->number;
|
||||
|
|
@ -1135,7 +1136,7 @@ do { if((here->ptr = SMPmakeElt(matrix, here->first, here->second)) == NULL){\
|
|||
|
||||
}
|
||||
}
|
||||
#ifdef USE_OMP
|
||||
#if defined(USE_OMP) || defined(BSIM3v32SIMD)
|
||||
InstCount = 0;
|
||||
model = (BSIM3v32model*)inModel;
|
||||
/* loop through all the BSIM3 device models
|
||||
|
|
@ -1157,6 +1158,7 @@ do { if((here->ptr = SMPmakeElt(matrix, here->first, here->second)) == NULL){\
|
|||
/* store this in the first model only */
|
||||
model->BSIM3v32InstCount = InstCount;
|
||||
model->BSIM3v32InstanceArray = InstArray;
|
||||
#ifndef BSIM3v32SIMD
|
||||
idx = 0;
|
||||
for (; model != NULL; model = BSIM3v32nextModel(model))
|
||||
{
|
||||
|
|
@ -1168,7 +1170,45 @@ do { if((here->ptr = SMPmakeElt(matrix, here->first, here->second)) == NULL){\
|
|||
idx++;
|
||||
}
|
||||
}
|
||||
#else
|
||||
idx=0;
|
||||
int ngroups=0;
|
||||
for (; model != NULL; model = BSIM3v32nextModel(model))
|
||||
{
|
||||
BSIM3v32group *group;
|
||||
BSIM3v32instance *first;
|
||||
|
||||
model->groupHead=NULL;
|
||||
first = BSIM3v32instances(model);
|
||||
while((idx<InstCount) && (first!=NULL))
|
||||
{
|
||||
ngroups++;
|
||||
group = TMALLOC(BSIM3v32group, 1);
|
||||
group->InstArray=&InstArray[idx];
|
||||
group->InstArray[0] = first;
|
||||
group->InstCount=0;
|
||||
/* build linked list of groups */
|
||||
group->next = model->groupHead;
|
||||
model->groupHead=group;
|
||||
/* init the for loop below */
|
||||
here = first; first=NULL;
|
||||
for (; here != NULL; here = BSIM3v32nextInstance(here))
|
||||
{
|
||||
if((here->BSIM3v32nqsMod == group->InstArray[0]->BSIM3v32nqsMod)
|
||||
&& (here->pParam == group->InstArray[0]->pParam) /* compare if pParam point to the same */
|
||||
&& (here->BSIM3v32geo == group->InstArray[0]->BSIM3v32geo)
|
||||
&& (here->BSIM3v32off == group->InstArray[0]->BSIM3v32off) )
|
||||
{ /* instance can be grouped with the current group */
|
||||
InstArray[idx++] = here;
|
||||
group->InstCount++;
|
||||
}
|
||||
else if (first!=NULL)
|
||||
first=here; /* first different instance, start from here at next while iteration */
|
||||
}
|
||||
}
|
||||
}
|
||||
printf("BSIM3v32 has %d groups\n",ngroups);
|
||||
#endif
|
||||
#endif
|
||||
return(OK);
|
||||
}
|
||||
|
|
@ -1181,14 +1221,20 @@ BSIM3v32unsetup(
|
|||
BSIM3v32model *model;
|
||||
BSIM3v32instance *here;
|
||||
|
||||
#ifdef USE_OMP
|
||||
model = (BSIM3v32model*)inModel;
|
||||
tfree(model->BSIM3v32InstanceArray);
|
||||
#endif
|
||||
|
||||
|
||||
for (model = (BSIM3v32model *)inModel; model != NULL;
|
||||
model = BSIM3v32nextModel(model))
|
||||
{
|
||||
#ifdef BSIM3v32SIMD
|
||||
BSIM3v32group *group,*ngroup;
|
||||
group=model->groupHead;
|
||||
while(group) {
|
||||
ngroup=group->next;
|
||||
tfree(group);
|
||||
group=ngroup;
|
||||
}
|
||||
#endif
|
||||
for (here = BSIM3v32instances(model); here != NULL;
|
||||
here=BSIM3v32nextInstance(here))
|
||||
{
|
||||
|
|
@ -1207,6 +1253,12 @@ BSIM3v32unsetup(
|
|||
here->BSIM3v32dNodePrime = 0;
|
||||
}
|
||||
}
|
||||
|
||||
#if defined(USE_OMP) || defined(BSIM3v32SIMD)
|
||||
model = (BSIM3v32model*)inModel;
|
||||
tfree(model->BSIM3v32InstanceArray);
|
||||
#endif
|
||||
|
||||
return OK;
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -4,6 +4,7 @@ Author: 1995 Min-Chie Jeng and Mansun Chan.
|
|||
Author: 1997-1999 Weidong Liu.
|
||||
Author: 2001 Xuemei Xi
|
||||
Modified by Paolo Nenzi 2002 and Dietmar Warning 2003
|
||||
Modified by Florian Ballenegger 2020 (for SIMD evaluation)
|
||||
File: bsim3v32def.h
|
||||
**********/
|
||||
|
||||
|
|
@ -16,6 +17,10 @@ File: bsim3v32def.h
|
|||
#include "ngspice/complex.h"
|
||||
#include "ngspice/noisedef.h"
|
||||
|
||||
#ifdef BSIM3v32SIMD
|
||||
#define NSIMD 4
|
||||
#endif
|
||||
|
||||
typedef struct sBSIM3v32instance
|
||||
{
|
||||
|
||||
|
|
@ -36,7 +41,7 @@ typedef struct sBSIM3v32instance
|
|||
|
||||
/* MCJ */
|
||||
double BSIM3v32ueff;
|
||||
double BSIM3v32thetavth;
|
||||
double BSIM3v32thetavth; /* F.B. It is not useful to store this here, should be removed */
|
||||
double BSIM3v32von;
|
||||
double BSIM3v32vdsat;
|
||||
double BSIM3v32cgdo;
|
||||
|
|
@ -174,15 +179,29 @@ typedef struct sBSIM3v32instance
|
|||
double *BSIM3v32GqPtr;
|
||||
double *BSIM3v32SPqPtr;
|
||||
double *BSIM3v32BqPtr;
|
||||
|
||||
#ifdef USE_OMP
|
||||
#ifdef BSIM3v32SIMD
|
||||
/* store here values calculated before SIMD evaluation really start */
|
||||
double BSIM3v32SIMDvbs;
|
||||
double BSIM3v32SIMDvgs;
|
||||
double BSIM3v32SIMDvds;
|
||||
double BSIM3v32SIMDqdef;
|
||||
double BSIM3v32SIMDcdhat;
|
||||
double BSIM3v32SIMDcbhat;
|
||||
int BSIM3v32SIMDCheck;
|
||||
#endif
|
||||
#endif
|
||||
#ifdef USE_OMP
|
||||
/* per instance storage of results, to update matrix at a later stge */
|
||||
int BSIM3v32noncon; /* F.B. bug fix potential race when writing ckt->CKTnoncon */
|
||||
double BSIM3v32rhsG;
|
||||
double BSIM3v32rhsB;
|
||||
double BSIM3v32rhsD;
|
||||
double BSIM3v32rhsS;
|
||||
#ifndef OMP_EFFMEM
|
||||
double BSIM3v32rhsQ;
|
||||
|
||||
#endif
|
||||
|
||||
double BSIM3v32DdPt;
|
||||
double BSIM3v32GgPt;
|
||||
double BSIM3v32SsPt;
|
||||
|
|
@ -205,7 +224,7 @@ typedef struct sBSIM3v32instance
|
|||
double BSIM3v32DPbPt;
|
||||
double BSIM3v32SPbPt;
|
||||
double BSIM3v32SPdpPt;
|
||||
|
||||
#ifndef OMP_EFFMEM
|
||||
double BSIM3v32QqPt;
|
||||
double BSIM3v32QdpPt;
|
||||
double BSIM3v32QgPt;
|
||||
|
|
@ -215,6 +234,7 @@ typedef struct sBSIM3v32instance
|
|||
double BSIM3v32GqPt;
|
||||
double BSIM3v32SPqPt;
|
||||
double BSIM3v32BqPt;
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#define BSIM3v32vbd BSIM3v32states+ 0
|
||||
|
|
@ -397,6 +417,16 @@ struct bsim3v32SizeDependParam
|
|||
struct bsim3v32SizeDependParam *pNext;
|
||||
};
|
||||
|
||||
#ifdef BSIM3v32SIMD
|
||||
/* Group by same pParam, nqsMode, geo, off for more efficient SIMD processing */
|
||||
typedef struct sBSIM3v32group {
|
||||
int InstCount;
|
||||
int EvalCount;
|
||||
int SimdCount;
|
||||
BSIM3v32instance** InstArray; /* actually sub-array of one allocated array globally */
|
||||
struct sBSIM3v32group* next;
|
||||
} BSIM3v32group;
|
||||
#endif
|
||||
|
||||
typedef struct sBSIM3v32model
|
||||
{
|
||||
|
|
@ -887,8 +917,12 @@ typedef struct sBSIM3v32model
|
|||
double BSIM3v32vbdrMax;
|
||||
|
||||
struct bsim3v32SizeDependParam *pSizeDependParamKnot;
|
||||
|
||||
#ifdef BSIM3v32SIMD
|
||||
BSIM3v32group* groupHead;
|
||||
#endif
|
||||
|
||||
#ifdef USE_OMP
|
||||
#if defined(USE_OMP) || defined(BSIM3v32SIMD)
|
||||
int BSIM3v32InstCount;
|
||||
struct sBSIM3v32instance **BSIM3v32InstanceArray;
|
||||
#endif
|
||||
|
|
|
|||
|
|
@ -28,3 +28,9 @@ extern int BSIM3v32trunc(GENmodel*,CKTcircuit*,double*);
|
|||
extern int BSIM3v32noise(int,int,GENmodel*,CKTcircuit*,Ndata*,double*);
|
||||
extern int BSIM3v32unsetup(GENmodel*,CKTcircuit*);
|
||||
extern int BSIM3v32soaCheck(CKTcircuit *, GENmodel *);
|
||||
#ifndef BSIM3v32SIMD
|
||||
#define BSIM3v32SIMD
|
||||
#endif
|
||||
#ifdef BSIM3v32SIMD
|
||||
extern int BSIM3v32loadSel(GENmodel*,CKTcircuit*);
|
||||
#endif
|
||||
|
|
|
|||
|
|
@ -33,7 +33,11 @@ SPICEdev BSIM3v32info = {
|
|||
|
||||
.DEVparam = BSIM3v32param,
|
||||
.DEVmodParam = BSIM3v32mParam,
|
||||
#ifdef BSIM3v32SIMD
|
||||
.DEVload = BSIM3v32loadSel, /*F.B: point to load function wrapper */
|
||||
#else
|
||||
.DEVload = BSIM3v32load,
|
||||
#endif
|
||||
.DEVsetup = BSIM3v32setup,
|
||||
.DEVunsetup = BSIM3v32unsetup,
|
||||
.DEVpzSetup = BSIM3v32setup,
|
||||
|
|
|
|||
Loading…
Reference in New Issue