diff --git a/src/spicelib/devices/asrc/asrcinit.c b/src/spicelib/devices/asrc/asrcinit.c index ab1a23c77..016ef9529 100644 --- a/src/spicelib/devices/asrc/asrcinit.c +++ b/src/spicelib/devices/asrc/asrcinit.c @@ -66,6 +66,11 @@ SPICEdev ASRCinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = NULL, + .DEVbindCSCComplex = NULL, + .DEVbindCSCComplexToReal = NULL, +#endif }; diff --git a/src/spicelib/devices/bjt/Makefile.am b/src/spicelib/devices/bjt/Makefile.am index 47aa59d69..e1ddb2a9d 100644 --- a/src/spicelib/devices/bjt/Makefile.am +++ b/src/spicelib/devices/bjt/Makefile.am @@ -36,6 +36,9 @@ libbjt_la_SOURCES = \ bjttrunc.c +if KLU_WANTED +libbjt_la_SOURCES += bjtbindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) diff --git a/src/spicelib/devices/bjt/bjtbindCSC.c b/src/spicelib/devices/bjt/bjtbindCSC.c new file mode 100644 index 000000000..296d78e64 --- /dev/null +++ b/src/spicelib/devices/bjt/bjtbindCSC.c @@ -0,0 +1,155 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "bjtdefs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +BJTbindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + BJTmodel *model = (BJTmodel *)inModel ; + BJTinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the BJT models */ + for ( ; model != NULL ; model = BJTnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = BJTinstances(model); here != NULL ; here = BJTnextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(BJTcolColPrimePtr, BJTcolColPrimeBinding, BJTcolNode, BJTcolPrimeNode); + CREATE_KLU_BINDING_TABLE(BJTbaseBasePrimePtr, BJTbaseBasePrimeBinding, BJTbaseNode, BJTbasePrimeNode); + CREATE_KLU_BINDING_TABLE(BJTemitEmitPrimePtr, BJTemitEmitPrimeBinding, BJTemitNode, BJTemitPrimeNode); + CREATE_KLU_BINDING_TABLE(BJTcolPrimeColPtr, BJTcolPrimeColBinding, BJTcolPrimeNode, BJTcolNode); + CREATE_KLU_BINDING_TABLE(BJTcolPrimeBasePrimePtr, BJTcolPrimeBasePrimeBinding, BJTcolPrimeNode, BJTbasePrimeNode); + CREATE_KLU_BINDING_TABLE(BJTcolPrimeEmitPrimePtr, BJTcolPrimeEmitPrimeBinding, BJTcolPrimeNode, BJTemitPrimeNode); + CREATE_KLU_BINDING_TABLE(BJTbasePrimeBasePtr, BJTbasePrimeBaseBinding, BJTbasePrimeNode, BJTbaseNode); + CREATE_KLU_BINDING_TABLE(BJTbasePrimeColPrimePtr, BJTbasePrimeColPrimeBinding, BJTbasePrimeNode, BJTcolPrimeNode); + CREATE_KLU_BINDING_TABLE(BJTbasePrimeEmitPrimePtr, BJTbasePrimeEmitPrimeBinding, BJTbasePrimeNode, BJTemitPrimeNode); + CREATE_KLU_BINDING_TABLE(BJTemitPrimeEmitPtr, BJTemitPrimeEmitBinding, BJTemitPrimeNode, BJTemitNode); + CREATE_KLU_BINDING_TABLE(BJTemitPrimeColPrimePtr, BJTemitPrimeColPrimeBinding, BJTemitPrimeNode, BJTcolPrimeNode); + CREATE_KLU_BINDING_TABLE(BJTemitPrimeBasePrimePtr, BJTemitPrimeBasePrimeBinding, BJTemitPrimeNode, BJTbasePrimeNode); + CREATE_KLU_BINDING_TABLE(BJTcolColPtr, BJTcolColBinding, BJTcolNode, BJTcolNode); + CREATE_KLU_BINDING_TABLE(BJTbaseBasePtr, BJTbaseBaseBinding, BJTbaseNode, BJTbaseNode); + CREATE_KLU_BINDING_TABLE(BJTemitEmitPtr, BJTemitEmitBinding, BJTemitNode, BJTemitNode); + CREATE_KLU_BINDING_TABLE(BJTcolPrimeColPrimePtr, BJTcolPrimeColPrimeBinding, BJTcolPrimeNode, BJTcolPrimeNode); + CREATE_KLU_BINDING_TABLE(BJTbasePrimeBasePrimePtr, BJTbasePrimeBasePrimeBinding, BJTbasePrimeNode, BJTbasePrimeNode); + CREATE_KLU_BINDING_TABLE(BJTemitPrimeEmitPrimePtr, BJTemitPrimeEmitPrimeBinding, BJTemitPrimeNode, BJTemitPrimeNode); + CREATE_KLU_BINDING_TABLE(BJTsubstSubstPtr, BJTsubstSubstBinding, BJTsubstNode, BJTsubstNode); + CREATE_KLU_BINDING_TABLE(BJTsubstConSubstPtr, BJTsubstConSubstBinding, BJTsubstConNode, BJTsubstNode); + CREATE_KLU_BINDING_TABLE(BJTsubstSubstConPtr, BJTsubstSubstConBinding, BJTsubstNode, BJTsubstConNode); + CREATE_KLU_BINDING_TABLE(BJTbaseColPrimePtr, BJTbaseColPrimeBinding, BJTbaseNode, BJTcolPrimeNode); + CREATE_KLU_BINDING_TABLE(BJTcolPrimeBasePtr, BJTcolPrimeBaseBinding, BJTcolPrimeNode, BJTbaseNode); + } + } + + return (OK) ; +} + +int +BJTbindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + BJTmodel *model = (BJTmodel *)inModel ; + BJTinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the BJT models */ + for ( ; model != NULL ; model = BJTnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = BJTinstances(model); here != NULL ; here = BJTnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BJTcolColPrimePtr, BJTcolColPrimeBinding, BJTcolNode, BJTcolPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BJTbaseBasePrimePtr, BJTbaseBasePrimeBinding, BJTbaseNode, BJTbasePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BJTemitEmitPrimePtr, BJTemitEmitPrimeBinding, BJTemitNode, BJTemitPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BJTcolPrimeColPtr, BJTcolPrimeColBinding, BJTcolPrimeNode, BJTcolNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BJTcolPrimeBasePrimePtr, BJTcolPrimeBasePrimeBinding, BJTcolPrimeNode, BJTbasePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BJTcolPrimeEmitPrimePtr, BJTcolPrimeEmitPrimeBinding, BJTcolPrimeNode, BJTemitPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BJTbasePrimeBasePtr, BJTbasePrimeBaseBinding, BJTbasePrimeNode, BJTbaseNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BJTbasePrimeColPrimePtr, BJTbasePrimeColPrimeBinding, BJTbasePrimeNode, BJTcolPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BJTbasePrimeEmitPrimePtr, BJTbasePrimeEmitPrimeBinding, BJTbasePrimeNode, BJTemitPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BJTemitPrimeEmitPtr, BJTemitPrimeEmitBinding, BJTemitPrimeNode, BJTemitNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BJTemitPrimeColPrimePtr, BJTemitPrimeColPrimeBinding, BJTemitPrimeNode, BJTcolPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BJTemitPrimeBasePrimePtr, BJTemitPrimeBasePrimeBinding, BJTemitPrimeNode, BJTbasePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BJTcolColPtr, BJTcolColBinding, BJTcolNode, BJTcolNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BJTbaseBasePtr, BJTbaseBaseBinding, BJTbaseNode, BJTbaseNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BJTemitEmitPtr, BJTemitEmitBinding, BJTemitNode, BJTemitNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BJTcolPrimeColPrimePtr, BJTcolPrimeColPrimeBinding, BJTcolPrimeNode, BJTcolPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BJTbasePrimeBasePrimePtr, BJTbasePrimeBasePrimeBinding, BJTbasePrimeNode, BJTbasePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BJTemitPrimeEmitPrimePtr, BJTemitPrimeEmitPrimeBinding, BJTemitPrimeNode, BJTemitPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BJTsubstSubstPtr, BJTsubstSubstBinding, BJTsubstNode, BJTsubstNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BJTsubstConSubstPtr, BJTsubstConSubstBinding, BJTsubstConNode, BJTsubstNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BJTsubstSubstConPtr, BJTsubstSubstConBinding, BJTsubstNode, BJTsubstConNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BJTbaseColPrimePtr, BJTbaseColPrimeBinding, BJTbaseNode, BJTcolPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BJTcolPrimeBasePtr, BJTcolPrimeBaseBinding, BJTcolPrimeNode, BJTbaseNode); + } + } + + return (OK) ; +} + +int +BJTbindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + BJTmodel *model = (BJTmodel *)inModel ; + BJTinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the BJT models */ + for ( ; model != NULL ; model = BJTnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = BJTinstances(model); here != NULL ; here = BJTnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(BJTcolColPrimePtr, BJTcolColPrimeBinding, BJTcolNode, BJTcolPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BJTbaseBasePrimePtr, BJTbaseBasePrimeBinding, BJTbaseNode, BJTbasePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BJTemitEmitPrimePtr, BJTemitEmitPrimeBinding, BJTemitNode, BJTemitPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BJTcolPrimeColPtr, BJTcolPrimeColBinding, BJTcolPrimeNode, BJTcolNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BJTcolPrimeBasePrimePtr, BJTcolPrimeBasePrimeBinding, BJTcolPrimeNode, BJTbasePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BJTcolPrimeEmitPrimePtr, BJTcolPrimeEmitPrimeBinding, BJTcolPrimeNode, BJTemitPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BJTbasePrimeBasePtr, BJTbasePrimeBaseBinding, BJTbasePrimeNode, BJTbaseNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BJTbasePrimeColPrimePtr, BJTbasePrimeColPrimeBinding, BJTbasePrimeNode, BJTcolPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BJTbasePrimeEmitPrimePtr, BJTbasePrimeEmitPrimeBinding, BJTbasePrimeNode, BJTemitPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BJTemitPrimeEmitPtr, BJTemitPrimeEmitBinding, BJTemitPrimeNode, BJTemitNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BJTemitPrimeColPrimePtr, BJTemitPrimeColPrimeBinding, BJTemitPrimeNode, BJTcolPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BJTemitPrimeBasePrimePtr, BJTemitPrimeBasePrimeBinding, BJTemitPrimeNode, BJTbasePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BJTcolColPtr, BJTcolColBinding, BJTcolNode, BJTcolNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BJTbaseBasePtr, BJTbaseBaseBinding, BJTbaseNode, BJTbaseNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BJTemitEmitPtr, BJTemitEmitBinding, BJTemitNode, BJTemitNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BJTcolPrimeColPrimePtr, BJTcolPrimeColPrimeBinding, BJTcolPrimeNode, BJTcolPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BJTbasePrimeBasePrimePtr, BJTbasePrimeBasePrimeBinding, BJTbasePrimeNode, BJTbasePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BJTemitPrimeEmitPrimePtr, BJTemitPrimeEmitPrimeBinding, BJTemitPrimeNode, BJTemitPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BJTsubstSubstPtr, BJTsubstSubstBinding, BJTsubstNode, BJTsubstNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BJTsubstConSubstPtr, BJTsubstConSubstBinding, BJTsubstConNode, BJTsubstNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BJTsubstSubstConPtr, BJTsubstSubstConBinding, BJTsubstNode, BJTsubstConNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BJTbaseColPrimePtr, BJTbaseColPrimeBinding, BJTbaseNode, BJTcolPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BJTcolPrimeBasePtr, BJTcolPrimeBaseBinding, BJTcolPrimeNode, BJTbaseNode); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/bjt/bjtdefs.h b/src/spicelib/devices/bjt/bjtdefs.h index dab3ef915..f3fdd675a 100644 --- a/src/spicelib/devices/bjt/bjtdefs.h +++ b/src/spicelib/devices/bjt/bjtdefs.h @@ -285,6 +285,33 @@ typedef struct sBJTinstance { #endif /*NONOISE*/ /* the above to avoid allocating memory when it is not needed */ +#ifdef KLU + BindElement *BJTcolColPrimeBinding ; + BindElement *BJTbaseBasePrimeBinding ; + BindElement *BJTemitEmitPrimeBinding ; + BindElement *BJTcolPrimeColBinding ; + BindElement *BJTcolPrimeBasePrimeBinding ; + BindElement *BJTcolPrimeEmitPrimeBinding ; + BindElement *BJTbasePrimeBaseBinding ; + BindElement *BJTbasePrimeColPrimeBinding ; + BindElement *BJTbasePrimeEmitPrimeBinding ; + BindElement *BJTemitPrimeEmitBinding ; + BindElement *BJTemitPrimeColPrimeBinding ; + BindElement *BJTemitPrimeBasePrimeBinding ; + BindElement *BJTcolColBinding ; + BindElement *BJTbaseBaseBinding ; + BindElement *BJTemitEmitBinding ; + BindElement *BJTcolPrimeColPrimeBinding ; + BindElement *BJTbasePrimeBasePrimeBinding ; + BindElement *BJTemitPrimeEmitPrimeBinding ; + BindElement *BJTsubstSubstBinding ; + BindElement *BJTsubstConSubstBinding ; + BindElement *BJTsubstSubstConBinding ; + BindElement *BJTsubstConSubstConBinding ; + BindElement *BJTbaseColPrimeBinding ; + BindElement *BJTcolPrimeBaseBinding ; +#endif + } BJTinstance ; /* entries in the state vector for bjt: */ diff --git a/src/spicelib/devices/bjt/bjtext.h b/src/spicelib/devices/bjt/bjtext.h index 39703b3b7..60f1c5689 100644 --- a/src/spicelib/devices/bjt/bjtext.h +++ b/src/spicelib/devices/bjt/bjtext.h @@ -34,3 +34,9 @@ extern int BJTdSetup(GENmodel*, register CKTcircuit*); extern int BJTsoaCheck(CKTcircuit *, GENmodel *); #endif + +#ifdef KLU +extern int BJTbindCSC (GENmodel*, CKTcircuit*) ; +extern int BJTbindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int BJTbindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/bjt/bjtinit.c b/src/spicelib/devices/bjt/bjtinit.c index aded3c9d2..1a568a9ea 100644 --- a/src/spicelib/devices/bjt/bjtinit.c +++ b/src/spicelib/devices/bjt/bjtinit.c @@ -66,6 +66,11 @@ SPICEdev BJTinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = BJTbindCSC, + .DEVbindCSCComplex = BJTbindCSCComplex, + .DEVbindCSCComplexToReal = BJTbindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/bsim1/Makefile.am b/src/spicelib/devices/bsim1/Makefile.am index da088cf5b..d08915b4c 100644 --- a/src/spicelib/devices/bsim1/Makefile.am +++ b/src/spicelib/devices/bsim1/Makefile.am @@ -31,7 +31,11 @@ libbsim1_la_SOURCES = \ bsim1itf.h +if KLU_WANTED +libbsim1_la_SOURCES += b1bindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) + MAINTAINERCLEANFILES = Makefile.in diff --git a/src/spicelib/devices/bsim1/b1bindCSC.c b/src/spicelib/devices/bsim1/b1bindCSC.c new file mode 100644 index 000000000..666cc032d --- /dev/null +++ b/src/spicelib/devices/bsim1/b1bindCSC.c @@ -0,0 +1,152 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "bsim1def.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +B1bindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + B1model *model = (B1model *)inModel ; + B1instance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the B1 models */ + for ( ; model != NULL ; model = B1nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = B1instances(model); here != NULL ; here = B1nextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(B1DdPtr, B1DdBinding, B1dNode, B1dNode); + CREATE_KLU_BINDING_TABLE(B1GgPtr, B1GgBinding, B1gNode, B1gNode); + CREATE_KLU_BINDING_TABLE(B1SsPtr, B1SsBinding, B1sNode, B1sNode); + CREATE_KLU_BINDING_TABLE(B1BbPtr, B1BbBinding, B1bNode, B1bNode); + CREATE_KLU_BINDING_TABLE(B1DPdpPtr, B1DPdpBinding, B1dNodePrime, B1dNodePrime); + CREATE_KLU_BINDING_TABLE(B1SPspPtr, B1SPspBinding, B1sNodePrime, B1sNodePrime); + CREATE_KLU_BINDING_TABLE(B1DdpPtr, B1DdpBinding, B1dNode, B1dNodePrime); + CREATE_KLU_BINDING_TABLE(B1GbPtr, B1GbBinding, B1gNode, B1bNode); + CREATE_KLU_BINDING_TABLE(B1GdpPtr, B1GdpBinding, B1gNode, B1dNodePrime); + CREATE_KLU_BINDING_TABLE(B1GspPtr, B1GspBinding, B1gNode, B1sNodePrime); + CREATE_KLU_BINDING_TABLE(B1SspPtr, B1SspBinding, B1sNode, B1sNodePrime); + CREATE_KLU_BINDING_TABLE(B1BdpPtr, B1BdpBinding, B1bNode, B1dNodePrime); + CREATE_KLU_BINDING_TABLE(B1BspPtr, B1BspBinding, B1bNode, B1sNodePrime); + CREATE_KLU_BINDING_TABLE(B1DPspPtr, B1DPspBinding, B1dNodePrime, B1sNodePrime); + CREATE_KLU_BINDING_TABLE(B1DPdPtr, B1DPdBinding, B1dNodePrime, B1dNode); + CREATE_KLU_BINDING_TABLE(B1BgPtr, B1BgBinding, B1bNode, B1gNode); + CREATE_KLU_BINDING_TABLE(B1DPgPtr, B1DPgBinding, B1dNodePrime, B1gNode); + CREATE_KLU_BINDING_TABLE(B1SPgPtr, B1SPgBinding, B1sNodePrime, B1gNode); + CREATE_KLU_BINDING_TABLE(B1SPsPtr, B1SPsBinding, B1sNodePrime, B1sNode); + CREATE_KLU_BINDING_TABLE(B1DPbPtr, B1DPbBinding, B1dNodePrime, B1bNode); + CREATE_KLU_BINDING_TABLE(B1SPbPtr, B1SPbBinding, B1sNodePrime, B1bNode); + CREATE_KLU_BINDING_TABLE(B1SPdpPtr, B1SPdpBinding, B1sNodePrime, B1dNodePrime); + } + } + + return (OK) ; +} + +int +B1bindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + B1model *model = (B1model *)inModel ; + B1instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the B1 models */ + for ( ; model != NULL ; model = B1nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = B1instances(model); here != NULL ; here = B1nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B1DdPtr, B1DdBinding, B1dNode, B1dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B1GgPtr, B1GgBinding, B1gNode, B1gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B1SsPtr, B1SsBinding, B1sNode, B1sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B1BbPtr, B1BbBinding, B1bNode, B1bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B1DPdpPtr, B1DPdpBinding, B1dNodePrime, B1dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B1SPspPtr, B1SPspBinding, B1sNodePrime, B1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B1DdpPtr, B1DdpBinding, B1dNode, B1dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B1GbPtr, B1GbBinding, B1gNode, B1bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B1GdpPtr, B1GdpBinding, B1gNode, B1dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B1GspPtr, B1GspBinding, B1gNode, B1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B1SspPtr, B1SspBinding, B1sNode, B1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B1BdpPtr, B1BdpBinding, B1bNode, B1dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B1BspPtr, B1BspBinding, B1bNode, B1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B1DPspPtr, B1DPspBinding, B1dNodePrime, B1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B1DPdPtr, B1DPdBinding, B1dNodePrime, B1dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B1BgPtr, B1BgBinding, B1bNode, B1gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B1DPgPtr, B1DPgBinding, B1dNodePrime, B1gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B1SPgPtr, B1SPgBinding, B1sNodePrime, B1gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B1SPsPtr, B1SPsBinding, B1sNodePrime, B1sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B1DPbPtr, B1DPbBinding, B1dNodePrime, B1bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B1SPbPtr, B1SPbBinding, B1sNodePrime, B1bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B1SPdpPtr, B1SPdpBinding, B1sNodePrime, B1dNodePrime); + } + } + + return (OK) ; +} + +int +B1bindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + B1model *model = (B1model *)inModel ; + B1instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the B1 models */ + for ( ; model != NULL ; model = B1nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = B1instances(model); here != NULL ; here = B1nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(B1DdPtr, B1DdBinding, B1dNode, B1dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B1GgPtr, B1GgBinding, B1gNode, B1gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B1SsPtr, B1SsBinding, B1sNode, B1sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B1BbPtr, B1BbBinding, B1bNode, B1bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B1DPdpPtr, B1DPdpBinding, B1dNodePrime, B1dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B1SPspPtr, B1SPspBinding, B1sNodePrime, B1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B1DdpPtr, B1DdpBinding, B1dNode, B1dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B1GbPtr, B1GbBinding, B1gNode, B1bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B1GdpPtr, B1GdpBinding, B1gNode, B1dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B1GspPtr, B1GspBinding, B1gNode, B1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B1SspPtr, B1SspBinding, B1sNode, B1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B1BdpPtr, B1BdpBinding, B1bNode, B1dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B1BspPtr, B1BspBinding, B1bNode, B1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B1DPspPtr, B1DPspBinding, B1dNodePrime, B1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B1DPdPtr, B1DPdBinding, B1dNodePrime, B1dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B1BgPtr, B1BgBinding, B1bNode, B1gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B1DPgPtr, B1DPgBinding, B1dNodePrime, B1gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B1SPgPtr, B1SPgBinding, B1sNodePrime, B1gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B1SPsPtr, B1SPsBinding, B1sNodePrime, B1sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B1DPbPtr, B1DPbBinding, B1dNodePrime, B1bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B1SPbPtr, B1SPbBinding, B1sNodePrime, B1bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B1SPdpPtr, B1SPdpBinding, B1sNodePrime, B1dNodePrime); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/bsim1/bsim1def.h b/src/spicelib/devices/bsim1/bsim1def.h index 34df9b3e6..bed659380 100644 --- a/src/spicelib/devices/bsim1/bsim1def.h +++ b/src/spicelib/devices/bsim1/bsim1def.h @@ -168,6 +168,30 @@ typedef struct sBSIM1instance { double **B1nVar; #endif /* NONOISE */ +#ifdef KLU + BindElement *B1DdBinding ; + BindElement *B1GgBinding ; + BindElement *B1SsBinding ; + BindElement *B1BbBinding ; + BindElement *B1DPdpBinding ; + BindElement *B1SPspBinding ; + BindElement *B1DdpBinding ; + BindElement *B1GbBinding ; + BindElement *B1GdpBinding ; + BindElement *B1GspBinding ; + BindElement *B1SspBinding ; + BindElement *B1BdpBinding ; + BindElement *B1BspBinding ; + BindElement *B1DPspBinding ; + BindElement *B1DPdBinding ; + BindElement *B1BgBinding ; + BindElement *B1DPgBinding ; + BindElement *B1SPgBinding ; + BindElement *B1SPsBinding ; + BindElement *B1DPbBinding ; + BindElement *B1SPbBinding ; + BindElement *B1SPdpBinding ; +#endif } B1instance ; diff --git a/src/spicelib/devices/bsim1/bsim1ext.h b/src/spicelib/devices/bsim1/bsim1ext.h index e1999c606..6cece2341 100644 --- a/src/spicelib/devices/bsim1/bsim1ext.h +++ b/src/spicelib/devices/bsim1/bsim1ext.h @@ -29,3 +29,9 @@ extern int B1temp(GENmodel*,CKTcircuit*); extern int B1trunc(GENmodel*,CKTcircuit*,double*); extern int B1disto(int,GENmodel*,CKTcircuit*); extern int B1dSetup(GENmodel*, register CKTcircuit*); + +#ifdef KLU +extern int B1bindCSC (GENmodel*, CKTcircuit*) ; +extern int B1bindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int B1bindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/bsim1/bsim1init.c b/src/spicelib/devices/bsim1/bsim1init.c index 416455477..35cbe3d3b 100644 --- a/src/spicelib/devices/bsim1/bsim1init.c +++ b/src/spicelib/devices/bsim1/bsim1init.c @@ -66,6 +66,11 @@ SPICEdev B1info = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = B1bindCSC, + .DEVbindCSCComplex = B1bindCSCComplex, + .DEVbindCSCComplexToReal = B1bindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/bsim2/Makefile.am b/src/spicelib/devices/bsim2/Makefile.am index ea8ae9855..97597da11 100644 --- a/src/spicelib/devices/bsim2/Makefile.am +++ b/src/spicelib/devices/bsim2/Makefile.am @@ -29,6 +29,9 @@ libbsim2_la_SOURCES = \ bsim2itf.h +if KLU_WANTED +libbsim2_la_SOURCES += b2bindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) diff --git a/src/spicelib/devices/bsim2/b2bindCSC.c b/src/spicelib/devices/bsim2/b2bindCSC.c new file mode 100644 index 000000000..7f2da6749 --- /dev/null +++ b/src/spicelib/devices/bsim2/b2bindCSC.c @@ -0,0 +1,152 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "bsim2def.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +B2bindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + B2model *model = (B2model *)inModel ; + B2instance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the B2 models */ + for ( ; model != NULL ; model = B2nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = B2instances(model); here != NULL ; here = B2nextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(B2DdPtr, B2DdBinding, B2dNode, B2dNode); + CREATE_KLU_BINDING_TABLE(B2GgPtr, B2GgBinding, B2gNode, B2gNode); + CREATE_KLU_BINDING_TABLE(B2SsPtr, B2SsBinding, B2sNode, B2sNode); + CREATE_KLU_BINDING_TABLE(B2BbPtr, B2BbBinding, B2bNode, B2bNode); + CREATE_KLU_BINDING_TABLE(B2DPdpPtr, B2DPdpBinding, B2dNodePrime, B2dNodePrime); + CREATE_KLU_BINDING_TABLE(B2SPspPtr, B2SPspBinding, B2sNodePrime, B2sNodePrime); + CREATE_KLU_BINDING_TABLE(B2DdpPtr, B2DdpBinding, B2dNode, B2dNodePrime); + CREATE_KLU_BINDING_TABLE(B2GbPtr, B2GbBinding, B2gNode, B2bNode); + CREATE_KLU_BINDING_TABLE(B2GdpPtr, B2GdpBinding, B2gNode, B2dNodePrime); + CREATE_KLU_BINDING_TABLE(B2GspPtr, B2GspBinding, B2gNode, B2sNodePrime); + CREATE_KLU_BINDING_TABLE(B2SspPtr, B2SspBinding, B2sNode, B2sNodePrime); + CREATE_KLU_BINDING_TABLE(B2BdpPtr, B2BdpBinding, B2bNode, B2dNodePrime); + CREATE_KLU_BINDING_TABLE(B2BspPtr, B2BspBinding, B2bNode, B2sNodePrime); + CREATE_KLU_BINDING_TABLE(B2DPspPtr, B2DPspBinding, B2dNodePrime, B2sNodePrime); + CREATE_KLU_BINDING_TABLE(B2DPdPtr, B2DPdBinding, B2dNodePrime, B2dNode); + CREATE_KLU_BINDING_TABLE(B2BgPtr, B2BgBinding, B2bNode, B2gNode); + CREATE_KLU_BINDING_TABLE(B2DPgPtr, B2DPgBinding, B2dNodePrime, B2gNode); + CREATE_KLU_BINDING_TABLE(B2SPgPtr, B2SPgBinding, B2sNodePrime, B2gNode); + CREATE_KLU_BINDING_TABLE(B2SPsPtr, B2SPsBinding, B2sNodePrime, B2sNode); + CREATE_KLU_BINDING_TABLE(B2DPbPtr, B2DPbBinding, B2dNodePrime, B2bNode); + CREATE_KLU_BINDING_TABLE(B2SPbPtr, B2SPbBinding, B2sNodePrime, B2bNode); + CREATE_KLU_BINDING_TABLE(B2SPdpPtr, B2SPdpBinding, B2sNodePrime, B2dNodePrime); + } + } + + return (OK) ; +} + +int +B2bindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + B2model *model = (B2model *)inModel ; + B2instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the B2 models */ + for ( ; model != NULL ; model = B2nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = B2instances(model); here != NULL ; here = B2nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B2DdPtr, B2DdBinding, B2dNode, B2dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B2GgPtr, B2GgBinding, B2gNode, B2gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B2SsPtr, B2SsBinding, B2sNode, B2sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B2BbPtr, B2BbBinding, B2bNode, B2bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B2DPdpPtr, B2DPdpBinding, B2dNodePrime, B2dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B2SPspPtr, B2SPspBinding, B2sNodePrime, B2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B2DdpPtr, B2DdpBinding, B2dNode, B2dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B2GbPtr, B2GbBinding, B2gNode, B2bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B2GdpPtr, B2GdpBinding, B2gNode, B2dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B2GspPtr, B2GspBinding, B2gNode, B2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B2SspPtr, B2SspBinding, B2sNode, B2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B2BdpPtr, B2BdpBinding, B2bNode, B2dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B2BspPtr, B2BspBinding, B2bNode, B2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B2DPspPtr, B2DPspBinding, B2dNodePrime, B2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B2DPdPtr, B2DPdBinding, B2dNodePrime, B2dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B2BgPtr, B2BgBinding, B2bNode, B2gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B2DPgPtr, B2DPgBinding, B2dNodePrime, B2gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B2SPgPtr, B2SPgBinding, B2sNodePrime, B2gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B2SPsPtr, B2SPsBinding, B2sNodePrime, B2sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B2DPbPtr, B2DPbBinding, B2dNodePrime, B2bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B2SPbPtr, B2SPbBinding, B2sNodePrime, B2bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B2SPdpPtr, B2SPdpBinding, B2sNodePrime, B2dNodePrime); + } + } + + return (OK) ; +} + +int +B2bindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + B2model *model = (B2model *)inModel ; + B2instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the B2 models */ + for ( ; model != NULL ; model = B2nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = B2instances(model); here != NULL ; here = B2nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(B2DdPtr, B2DdBinding, B2dNode, B2dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B2GgPtr, B2GgBinding, B2gNode, B2gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B2SsPtr, B2SsBinding, B2sNode, B2sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B2BbPtr, B2BbBinding, B2bNode, B2bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B2DPdpPtr, B2DPdpBinding, B2dNodePrime, B2dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B2SPspPtr, B2SPspBinding, B2sNodePrime, B2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B2DdpPtr, B2DdpBinding, B2dNode, B2dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B2GbPtr, B2GbBinding, B2gNode, B2bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B2GdpPtr, B2GdpBinding, B2gNode, B2dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B2GspPtr, B2GspBinding, B2gNode, B2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B2SspPtr, B2SspBinding, B2sNode, B2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B2BdpPtr, B2BdpBinding, B2bNode, B2dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B2BspPtr, B2BspBinding, B2bNode, B2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B2DPspPtr, B2DPspBinding, B2dNodePrime, B2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B2DPdPtr, B2DPdBinding, B2dNodePrime, B2dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B2BgPtr, B2BgBinding, B2bNode, B2gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B2DPgPtr, B2DPgBinding, B2dNodePrime, B2gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B2SPgPtr, B2SPgBinding, B2sNodePrime, B2gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B2SPsPtr, B2SPsBinding, B2sNodePrime, B2sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B2DPbPtr, B2DPbBinding, B2dNodePrime, B2bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B2SPbPtr, B2SPbBinding, B2sNodePrime, B2bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B2SPdpPtr, B2SPdpBinding, B2sNodePrime, B2dNodePrime); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/bsim2/bsim2def.h b/src/spicelib/devices/bsim2/bsim2def.h index 1dbda587a..078f8a62a 100644 --- a/src/spicelib/devices/bsim2/bsim2def.h +++ b/src/spicelib/devices/bsim2/bsim2def.h @@ -178,6 +178,31 @@ typedef struct sBSIM2instance { #define B2numStates 35 +#ifdef KLU + BindElement *B2DdBinding ; + BindElement *B2GgBinding ; + BindElement *B2SsBinding ; + BindElement *B2BbBinding ; + BindElement *B2DPdpBinding ; + BindElement *B2SPspBinding ; + BindElement *B2DdpBinding ; + BindElement *B2GbBinding ; + BindElement *B2GdpBinding ; + BindElement *B2GspBinding ; + BindElement *B2SspBinding ; + BindElement *B2BdpBinding ; + BindElement *B2BspBinding ; + BindElement *B2DPspBinding ; + BindElement *B2DPdBinding ; + BindElement *B2BgBinding ; + BindElement *B2DPgBinding ; + BindElement *B2SPgBinding ; + BindElement *B2SPsBinding ; + BindElement *B2DPbBinding ; + BindElement *B2SPbBinding ; + BindElement *B2SPdpBinding ; +#endif + } B2instance ; struct bsim2SizeDependParam diff --git a/src/spicelib/devices/bsim2/bsim2ext.h b/src/spicelib/devices/bsim2/bsim2ext.h index 337db65ae..0205d64a5 100644 --- a/src/spicelib/devices/bsim2/bsim2ext.h +++ b/src/spicelib/devices/bsim2/bsim2ext.h @@ -25,3 +25,9 @@ extern int B2setup(SMPmatrix*,GENmodel*,CKTcircuit*,int*); extern int B2unsetup(GENmodel*,CKTcircuit*); extern int B2temp(GENmodel*,CKTcircuit*); extern int B2trunc(GENmodel*,CKTcircuit*,double*); + +#ifdef KLU +extern int B2bindCSC (GENmodel*, CKTcircuit*) ; +extern int B2bindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int B2bindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/bsim2/bsim2init.c b/src/spicelib/devices/bsim2/bsim2init.c index 168a80e4b..cde441ba9 100644 --- a/src/spicelib/devices/bsim2/bsim2init.c +++ b/src/spicelib/devices/bsim2/bsim2init.c @@ -66,6 +66,11 @@ SPICEdev B2info = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = B2bindCSC, + .DEVbindCSCComplex = B2bindCSCComplex, + .DEVbindCSCComplexToReal = B2bindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/bsim3/Makefile.am b/src/spicelib/devices/bsim3/Makefile.am index 2489d1e5a..397e19595 100644 --- a/src/spicelib/devices/bsim3/Makefile.am +++ b/src/spicelib/devices/bsim3/Makefile.am @@ -29,6 +29,9 @@ libbsim3_la_SOURCES = \ bsim3itf.h +if KLU_WANTED +libbsim3_la_SOURCES += b3bindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) diff --git a/src/spicelib/devices/bsim3/b3bindCSC.c b/src/spicelib/devices/bsim3/b3bindCSC.c new file mode 100644 index 000000000..8807b6328 --- /dev/null +++ b/src/spicelib/devices/bsim3/b3bindCSC.c @@ -0,0 +1,179 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "bsim3def.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +BSIM3bindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + BSIM3model *model = (BSIM3model *)inModel ; + BSIM3instance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the BSIM3 models */ + for ( ; model != NULL ; model = BSIM3nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = BSIM3instances(model); here != NULL ; here = BSIM3nextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(BSIM3DdPtr, BSIM3DdBinding, BSIM3dNode, BSIM3dNode); + CREATE_KLU_BINDING_TABLE(BSIM3GgPtr, BSIM3GgBinding, BSIM3gNode, BSIM3gNode); + CREATE_KLU_BINDING_TABLE(BSIM3SsPtr, BSIM3SsBinding, BSIM3sNode, BSIM3sNode); + CREATE_KLU_BINDING_TABLE(BSIM3BbPtr, BSIM3BbBinding, BSIM3bNode, BSIM3bNode); + CREATE_KLU_BINDING_TABLE(BSIM3DPdpPtr, BSIM3DPdpBinding, BSIM3dNodePrime, BSIM3dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3SPspPtr, BSIM3SPspBinding, BSIM3sNodePrime, BSIM3sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3DdpPtr, BSIM3DdpBinding, BSIM3dNode, BSIM3dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3GbPtr, BSIM3GbBinding, BSIM3gNode, BSIM3bNode); + CREATE_KLU_BINDING_TABLE(BSIM3GdpPtr, BSIM3GdpBinding, BSIM3gNode, BSIM3dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3GspPtr, BSIM3GspBinding, BSIM3gNode, BSIM3sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3SspPtr, BSIM3SspBinding, BSIM3sNode, BSIM3sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3BdpPtr, BSIM3BdpBinding, BSIM3bNode, BSIM3dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3BspPtr, BSIM3BspBinding, BSIM3bNode, BSIM3sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3DPspPtr, BSIM3DPspBinding, BSIM3dNodePrime, BSIM3sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3DPdPtr, BSIM3DPdBinding, BSIM3dNodePrime, BSIM3dNode); + CREATE_KLU_BINDING_TABLE(BSIM3BgPtr, BSIM3BgBinding, BSIM3bNode, BSIM3gNode); + CREATE_KLU_BINDING_TABLE(BSIM3DPgPtr, BSIM3DPgBinding, BSIM3dNodePrime, BSIM3gNode); + CREATE_KLU_BINDING_TABLE(BSIM3SPgPtr, BSIM3SPgBinding, BSIM3sNodePrime, BSIM3gNode); + CREATE_KLU_BINDING_TABLE(BSIM3SPsPtr, BSIM3SPsBinding, BSIM3sNodePrime, BSIM3sNode); + CREATE_KLU_BINDING_TABLE(BSIM3DPbPtr, BSIM3DPbBinding, BSIM3dNodePrime, BSIM3bNode); + CREATE_KLU_BINDING_TABLE(BSIM3SPbPtr, BSIM3SPbBinding, BSIM3sNodePrime, BSIM3bNode); + CREATE_KLU_BINDING_TABLE(BSIM3SPdpPtr, BSIM3SPdpBinding, BSIM3sNodePrime, BSIM3dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3QqPtr, BSIM3QqBinding, BSIM3qNode, BSIM3qNode); + CREATE_KLU_BINDING_TABLE(BSIM3QdpPtr, BSIM3QdpBinding, BSIM3qNode, BSIM3dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3QgPtr, BSIM3QgBinding, BSIM3qNode, BSIM3gNode); + CREATE_KLU_BINDING_TABLE(BSIM3QspPtr, BSIM3QspBinding, BSIM3qNode, BSIM3sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3QbPtr, BSIM3QbBinding, BSIM3qNode, BSIM3bNode); + CREATE_KLU_BINDING_TABLE(BSIM3DPqPtr, BSIM3DPqBinding, BSIM3dNodePrime, BSIM3qNode); + CREATE_KLU_BINDING_TABLE(BSIM3GqPtr, BSIM3GqBinding, BSIM3gNode, BSIM3qNode); + CREATE_KLU_BINDING_TABLE(BSIM3SPqPtr, BSIM3SPqBinding, BSIM3sNodePrime, BSIM3qNode); + CREATE_KLU_BINDING_TABLE(BSIM3BqPtr, BSIM3BqBinding, BSIM3bNode, BSIM3qNode); + } + } + + return (OK) ; +} + +int +BSIM3bindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + BSIM3model *model = (BSIM3model *)inModel ; + BSIM3instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the BSIM3 models */ + for ( ; model != NULL ; model = BSIM3nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = BSIM3instances(model); here != NULL ; here = BSIM3nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3DdPtr, BSIM3DdBinding, BSIM3dNode, BSIM3dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3GgPtr, BSIM3GgBinding, BSIM3gNode, BSIM3gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3SsPtr, BSIM3SsBinding, BSIM3sNode, BSIM3sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3BbPtr, BSIM3BbBinding, BSIM3bNode, BSIM3bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3DPdpPtr, BSIM3DPdpBinding, BSIM3dNodePrime, BSIM3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3SPspPtr, BSIM3SPspBinding, BSIM3sNodePrime, BSIM3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3DdpPtr, BSIM3DdpBinding, BSIM3dNode, BSIM3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3GbPtr, BSIM3GbBinding, BSIM3gNode, BSIM3bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3GdpPtr, BSIM3GdpBinding, BSIM3gNode, BSIM3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3GspPtr, BSIM3GspBinding, BSIM3gNode, BSIM3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3SspPtr, BSIM3SspBinding, BSIM3sNode, BSIM3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3BdpPtr, BSIM3BdpBinding, BSIM3bNode, BSIM3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3BspPtr, BSIM3BspBinding, BSIM3bNode, BSIM3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3DPspPtr, BSIM3DPspBinding, BSIM3dNodePrime, BSIM3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3DPdPtr, BSIM3DPdBinding, BSIM3dNodePrime, BSIM3dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3BgPtr, BSIM3BgBinding, BSIM3bNode, BSIM3gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3DPgPtr, BSIM3DPgBinding, BSIM3dNodePrime, BSIM3gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3SPgPtr, BSIM3SPgBinding, BSIM3sNodePrime, BSIM3gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3SPsPtr, BSIM3SPsBinding, BSIM3sNodePrime, BSIM3sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3DPbPtr, BSIM3DPbBinding, BSIM3dNodePrime, BSIM3bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3SPbPtr, BSIM3SPbBinding, BSIM3sNodePrime, BSIM3bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3SPdpPtr, BSIM3SPdpBinding, BSIM3sNodePrime, BSIM3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3QqPtr, BSIM3QqBinding, BSIM3qNode, BSIM3qNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3QdpPtr, BSIM3QdpBinding, BSIM3qNode, BSIM3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3QgPtr, BSIM3QgBinding, BSIM3qNode, BSIM3gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3QspPtr, BSIM3QspBinding, BSIM3qNode, BSIM3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3QbPtr, BSIM3QbBinding, BSIM3qNode, BSIM3bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3DPqPtr, BSIM3DPqBinding, BSIM3dNodePrime, BSIM3qNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3GqPtr, BSIM3GqBinding, BSIM3gNode, BSIM3qNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3SPqPtr, BSIM3SPqBinding, BSIM3sNodePrime, BSIM3qNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3BqPtr, BSIM3BqBinding, BSIM3bNode, BSIM3qNode); + } + } + + return (OK) ; +} + +int +BSIM3bindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + BSIM3model *model = (BSIM3model *)inModel ; + BSIM3instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the BSIM3 models */ + for ( ; model != NULL ; model = BSIM3nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = BSIM3instances(model); here != NULL ; here = BSIM3nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3DdPtr, BSIM3DdBinding, BSIM3dNode, BSIM3dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3GgPtr, BSIM3GgBinding, BSIM3gNode, BSIM3gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3SsPtr, BSIM3SsBinding, BSIM3sNode, BSIM3sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3BbPtr, BSIM3BbBinding, BSIM3bNode, BSIM3bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3DPdpPtr, BSIM3DPdpBinding, BSIM3dNodePrime, BSIM3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3SPspPtr, BSIM3SPspBinding, BSIM3sNodePrime, BSIM3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3DdpPtr, BSIM3DdpBinding, BSIM3dNode, BSIM3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3GbPtr, BSIM3GbBinding, BSIM3gNode, BSIM3bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3GdpPtr, BSIM3GdpBinding, BSIM3gNode, BSIM3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3GspPtr, BSIM3GspBinding, BSIM3gNode, BSIM3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3SspPtr, BSIM3SspBinding, BSIM3sNode, BSIM3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3BdpPtr, BSIM3BdpBinding, BSIM3bNode, BSIM3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3BspPtr, BSIM3BspBinding, BSIM3bNode, BSIM3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3DPspPtr, BSIM3DPspBinding, BSIM3dNodePrime, BSIM3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3DPdPtr, BSIM3DPdBinding, BSIM3dNodePrime, BSIM3dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3BgPtr, BSIM3BgBinding, BSIM3bNode, BSIM3gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3DPgPtr, BSIM3DPgBinding, BSIM3dNodePrime, BSIM3gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3SPgPtr, BSIM3SPgBinding, BSIM3sNodePrime, BSIM3gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3SPsPtr, BSIM3SPsBinding, BSIM3sNodePrime, BSIM3sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3DPbPtr, BSIM3DPbBinding, BSIM3dNodePrime, BSIM3bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3SPbPtr, BSIM3SPbBinding, BSIM3sNodePrime, BSIM3bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3SPdpPtr, BSIM3SPdpBinding, BSIM3sNodePrime, BSIM3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3QqPtr, BSIM3QqBinding, BSIM3qNode, BSIM3qNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3QdpPtr, BSIM3QdpBinding, BSIM3qNode, BSIM3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3QgPtr, BSIM3QgBinding, BSIM3qNode, BSIM3gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3QspPtr, BSIM3QspBinding, BSIM3qNode, BSIM3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3QbPtr, BSIM3QbBinding, BSIM3qNode, BSIM3bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3DPqPtr, BSIM3DPqBinding, BSIM3dNodePrime, BSIM3qNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3GqPtr, BSIM3GqBinding, BSIM3gNode, BSIM3qNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3SPqPtr, BSIM3SPqBinding, BSIM3sNodePrime, BSIM3qNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3BqPtr, BSIM3BqBinding, BSIM3bNode, BSIM3qNode); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/bsim3/bsim3def.h b/src/spicelib/devices/bsim3/bsim3def.h index 13c5afc26..dbb195994 100644 --- a/src/spicelib/devices/bsim3/bsim3def.h +++ b/src/spicelib/devices/bsim3/bsim3def.h @@ -261,6 +261,40 @@ typedef struct sBSIM3instance double **BSIM3nVar; #endif /* NONOISE */ +#ifdef KLU + BindElement *BSIM3DdBinding ; + BindElement *BSIM3GgBinding ; + BindElement *BSIM3SsBinding ; + BindElement *BSIM3BbBinding ; + BindElement *BSIM3DPdpBinding ; + BindElement *BSIM3SPspBinding ; + BindElement *BSIM3DdpBinding ; + BindElement *BSIM3GbBinding ; + BindElement *BSIM3GdpBinding ; + BindElement *BSIM3GspBinding ; + BindElement *BSIM3SspBinding ; + BindElement *BSIM3BdpBinding ; + BindElement *BSIM3BspBinding ; + BindElement *BSIM3DPspBinding ; + BindElement *BSIM3DPdBinding ; + BindElement *BSIM3BgBinding ; + BindElement *BSIM3DPgBinding ; + BindElement *BSIM3SPgBinding ; + BindElement *BSIM3SPsBinding ; + BindElement *BSIM3DPbBinding ; + BindElement *BSIM3SPbBinding ; + BindElement *BSIM3SPdpBinding ; + BindElement *BSIM3QqBinding ; + BindElement *BSIM3QdpBinding ; + BindElement *BSIM3QgBinding ; + BindElement *BSIM3QspBinding ; + BindElement *BSIM3QbBinding ; + BindElement *BSIM3DPqBinding ; + BindElement *BSIM3GqBinding ; + BindElement *BSIM3SPqBinding ; + BindElement *BSIM3BqBinding ; +#endif + } BSIM3instance ; struct bsim3SizeDependParam diff --git a/src/spicelib/devices/bsim3/bsim3ext.h b/src/spicelib/devices/bsim3/bsim3ext.h index 0c03e8be5..a33cf2c3f 100644 --- a/src/spicelib/devices/bsim3/bsim3ext.h +++ b/src/spicelib/devices/bsim3/bsim3ext.h @@ -29,3 +29,9 @@ extern int BSIM3trunc(GENmodel*,CKTcircuit*,double*); extern int BSIM3noise(int,int,GENmodel*,CKTcircuit*,Ndata*,double*); extern int BSIM3unsetup(GENmodel*,CKTcircuit*); extern int BSIM3soaCheck(CKTcircuit *, GENmodel *); + +#ifdef KLU +extern int BSIM3bindCSC (GENmodel*, CKTcircuit*) ; +extern int BSIM3bindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int BSIM3bindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/bsim3/bsim3init.c b/src/spicelib/devices/bsim3/bsim3init.c index 420ec6f20..cb461e47c 100644 --- a/src/spicelib/devices/bsim3/bsim3init.c +++ b/src/spicelib/devices/bsim3/bsim3init.c @@ -66,6 +66,11 @@ SPICEdev BSIM3info = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = BSIM3bindCSC, + .DEVbindCSCComplex = BSIM3bindCSCComplex, + .DEVbindCSCComplexToReal = BSIM3bindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/bsim3soi_dd/Makefile.am b/src/spicelib/devices/bsim3soi_dd/Makefile.am index 5187d67e3..df3b14beb 100644 --- a/src/spicelib/devices/bsim3soi_dd/Makefile.am +++ b/src/spicelib/devices/bsim3soi_dd/Makefile.am @@ -28,6 +28,9 @@ libbsim3soidd_la_SOURCES = \ b3soidditf.h +if KLU_WANTED +libbsim3soidd_la_SOURCES += b3soiddbindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) diff --git a/src/spicelib/devices/bsim3soi_dd/b3soiddbindCSC.c b/src/spicelib/devices/bsim3soi_dd/b3soiddbindCSC.c new file mode 100644 index 000000000..a8adf8d67 --- /dev/null +++ b/src/spicelib/devices/bsim3soi_dd/b3soiddbindCSC.c @@ -0,0 +1,410 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "b3soidddef.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +B3SOIDDbindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + B3SOIDDmodel *model = (B3SOIDDmodel *)inModel ; + B3SOIDDinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the B3SOIDD models */ + for ( ; model != NULL ; model = B3SOIDDnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = B3SOIDDinstances(model); here != NULL ; here = B3SOIDDnextInstance(here)) + { + if ((model->B3SOIDDshMod == 1) && (here->B3SOIDDrth0 != 0.0)) + { + CREATE_KLU_BINDING_TABLE(B3SOIDDTemptempPtr, B3SOIDDTemptempBinding, B3SOIDDtempNode, B3SOIDDtempNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDTempdpPtr, B3SOIDDTempdpBinding, B3SOIDDtempNode, B3SOIDDdNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIDDTempspPtr, B3SOIDDTempspBinding, B3SOIDDtempNode, B3SOIDDsNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIDDTempgPtr, B3SOIDDTempgBinding, B3SOIDDtempNode, B3SOIDDgNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDTempbPtr, B3SOIDDTempbBinding, B3SOIDDtempNode, B3SOIDDbNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDTempePtr, B3SOIDDTempeBinding, B3SOIDDtempNode, B3SOIDDeNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDGtempPtr, B3SOIDDGtempBinding, B3SOIDDgNode, B3SOIDDtempNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDDPtempPtr, B3SOIDDDPtempBinding, B3SOIDDdNodePrime, B3SOIDDtempNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDSPtempPtr, B3SOIDDSPtempBinding, B3SOIDDsNodePrime, B3SOIDDtempNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDEtempPtr, B3SOIDDEtempBinding, B3SOIDDeNode, B3SOIDDtempNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDBtempPtr, B3SOIDDBtempBinding, B3SOIDDbNode, B3SOIDDtempNode); + if (here->B3SOIDDbodyMod == 1) + { + CREATE_KLU_BINDING_TABLE(B3SOIDDPtempPtr, B3SOIDDPtempBinding, B3SOIDDpNode, B3SOIDDtempNode); + } + } + if (here->B3SOIDDbodyMod == 2) + { + } + else if (here->B3SOIDDbodyMod == 1) + { + CREATE_KLU_BINDING_TABLE(B3SOIDDBpPtr, B3SOIDDBpBinding, B3SOIDDbNode, B3SOIDDpNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDPbPtr, B3SOIDDPbBinding, B3SOIDDpNode, B3SOIDDbNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDPpPtr, B3SOIDDPpBinding, B3SOIDDpNode, B3SOIDDpNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDPgPtr, B3SOIDDPgBinding, B3SOIDDpNode, B3SOIDDgNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDPdpPtr, B3SOIDDPdpBinding, B3SOIDDpNode, B3SOIDDdNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIDDPspPtr, B3SOIDDPspBinding, B3SOIDDpNode, B3SOIDDsNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIDDPePtr, B3SOIDDPeBinding, B3SOIDDpNode, B3SOIDDeNode); + } + CREATE_KLU_BINDING_TABLE(B3SOIDDEgPtr, B3SOIDDEgBinding, B3SOIDDeNode, B3SOIDDgNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDEdpPtr, B3SOIDDEdpBinding, B3SOIDDeNode, B3SOIDDdNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIDDEspPtr, B3SOIDDEspBinding, B3SOIDDeNode, B3SOIDDsNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIDDGePtr, B3SOIDDGeBinding, B3SOIDDgNode, B3SOIDDeNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDDPePtr, B3SOIDDDPeBinding, B3SOIDDdNodePrime, B3SOIDDeNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDSPePtr, B3SOIDDSPeBinding, B3SOIDDsNodePrime, B3SOIDDeNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDEbPtr, B3SOIDDEbBinding, B3SOIDDeNode, B3SOIDDbNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDGbPtr, B3SOIDDGbBinding, B3SOIDDgNode, B3SOIDDbNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDDPbPtr, B3SOIDDDPbBinding, B3SOIDDdNodePrime, B3SOIDDbNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDSPbPtr, B3SOIDDSPbBinding, B3SOIDDsNodePrime, B3SOIDDbNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDBePtr, B3SOIDDBeBinding, B3SOIDDbNode, B3SOIDDeNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDBgPtr, B3SOIDDBgBinding, B3SOIDDbNode, B3SOIDDgNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDBdpPtr, B3SOIDDBdpBinding, B3SOIDDbNode, B3SOIDDdNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIDDBspPtr, B3SOIDDBspBinding, B3SOIDDbNode, B3SOIDDsNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIDDBbPtr, B3SOIDDBbBinding, B3SOIDDbNode, B3SOIDDbNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDEePtr, B3SOIDDEeBinding, B3SOIDDeNode, B3SOIDDeNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDGgPtr, B3SOIDDGgBinding, B3SOIDDgNode, B3SOIDDgNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDGdpPtr, B3SOIDDGdpBinding, B3SOIDDgNode, B3SOIDDdNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIDDGspPtr, B3SOIDDGspBinding, B3SOIDDgNode, B3SOIDDsNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIDDDPgPtr, B3SOIDDDPgBinding, B3SOIDDdNodePrime, B3SOIDDgNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDDPdpPtr, B3SOIDDDPdpBinding, B3SOIDDdNodePrime, B3SOIDDdNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIDDDPspPtr, B3SOIDDDPspBinding, B3SOIDDdNodePrime, B3SOIDDsNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIDDDPdPtr, B3SOIDDDPdBinding, B3SOIDDdNodePrime, B3SOIDDdNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDSPgPtr, B3SOIDDSPgBinding, B3SOIDDsNodePrime, B3SOIDDgNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDSPdpPtr, B3SOIDDSPdpBinding, B3SOIDDsNodePrime, B3SOIDDdNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIDDSPspPtr, B3SOIDDSPspBinding, B3SOIDDsNodePrime, B3SOIDDsNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIDDSPsPtr, B3SOIDDSPsBinding, B3SOIDDsNodePrime, B3SOIDDsNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDDdPtr, B3SOIDDDdBinding, B3SOIDDdNode, B3SOIDDdNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDDdpPtr, B3SOIDDDdpBinding, B3SOIDDdNode, B3SOIDDdNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIDDSsPtr, B3SOIDDSsBinding, B3SOIDDsNode, B3SOIDDsNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDSspPtr, B3SOIDDSspBinding, B3SOIDDsNode, B3SOIDDsNodePrime); + if ((here->B3SOIDDdebugMod > 1) || (here->B3SOIDDdebugMod == -1)) + { + CREATE_KLU_BINDING_TABLE(B3SOIDDVbsPtr, B3SOIDDVbsBinding, B3SOIDDvbsNode, B3SOIDDvbsNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDIdsPtr, B3SOIDDIdsBinding, B3SOIDDidsNode, B3SOIDDidsNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDIcPtr, B3SOIDDIcBinding, B3SOIDDicNode, B3SOIDDicNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDIbsPtr, B3SOIDDIbsBinding, B3SOIDDibsNode, B3SOIDDibsNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDIbdPtr, B3SOIDDIbdBinding, B3SOIDDibdNode, B3SOIDDibdNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDIiiPtr, B3SOIDDIiiBinding, B3SOIDDiiiNode, B3SOIDDiiiNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDIgidlPtr, B3SOIDDIgidlBinding, B3SOIDDigidlNode, B3SOIDDigidlNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDItunPtr, B3SOIDDItunBinding, B3SOIDDitunNode, B3SOIDDitunNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDIbpPtr, B3SOIDDIbpBinding, B3SOIDDibpNode, B3SOIDDibpNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDAbeffPtr, B3SOIDDAbeffBinding, B3SOIDDabeffNode, B3SOIDDabeffNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDVbs0effPtr, B3SOIDDVbs0effBinding, B3SOIDDvbs0effNode, B3SOIDDvbs0effNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDVbseffPtr, B3SOIDDVbseffBinding, B3SOIDDvbseffNode, B3SOIDDvbseffNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDXcPtr, B3SOIDDXcBinding, B3SOIDDxcNode, B3SOIDDxcNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDCbbPtr, B3SOIDDCbbBinding, B3SOIDDcbbNode, B3SOIDDcbbNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDCbdPtr, B3SOIDDCbdBinding, B3SOIDDcbdNode, B3SOIDDcbdNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDCbgPtr, B3SOIDDCbgBinding, B3SOIDDcbgNode, B3SOIDDcbgNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDqbPtr, B3SOIDDqbBinding, B3SOIDDqbNode, B3SOIDDqbNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDQbfPtr, B3SOIDDQbfBinding, B3SOIDDqbfNode, B3SOIDDqbfNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDQjsPtr, B3SOIDDQjsBinding, B3SOIDDqjsNode, B3SOIDDqjsNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDQjdPtr, B3SOIDDQjdBinding, B3SOIDDqjdNode, B3SOIDDqjdNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDGmPtr, B3SOIDDGmBinding, B3SOIDDgmNode, B3SOIDDgmNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDGmbsPtr, B3SOIDDGmbsBinding, B3SOIDDgmbsNode, B3SOIDDgmbsNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDGdsPtr, B3SOIDDGdsBinding, B3SOIDDgdsNode, B3SOIDDgdsNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDGmePtr, B3SOIDDGmeBinding, B3SOIDDgmeNode, B3SOIDDgmeNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDVbs0teffPtr, B3SOIDDVbs0teffBinding, B3SOIDDvbs0teffNode, B3SOIDDvbs0teffNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDVthPtr, B3SOIDDVthBinding, B3SOIDDvthNode, B3SOIDDvthNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDVgsteffPtr, B3SOIDDVgsteffBinding, B3SOIDDvgsteffNode, B3SOIDDvgsteffNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDXcsatPtr, B3SOIDDXcsatBinding, B3SOIDDxcsatNode, B3SOIDDxcsatNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDVcscvPtr, B3SOIDDVcscvBinding, B3SOIDDvcscvNode, B3SOIDDvcscvNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDVdscvPtr, B3SOIDDVdscvBinding, B3SOIDDvdscvNode, B3SOIDDvdscvNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDCbePtr, B3SOIDDCbeBinding, B3SOIDDcbeNode, B3SOIDDcbeNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDDum1Ptr, B3SOIDDDum1Binding, B3SOIDDdum1Node, B3SOIDDdum1Node); + CREATE_KLU_BINDING_TABLE(B3SOIDDDum2Ptr, B3SOIDDDum2Binding, B3SOIDDdum2Node, B3SOIDDdum2Node); + CREATE_KLU_BINDING_TABLE(B3SOIDDDum3Ptr, B3SOIDDDum3Binding, B3SOIDDdum3Node, B3SOIDDdum3Node); + CREATE_KLU_BINDING_TABLE(B3SOIDDDum4Ptr, B3SOIDDDum4Binding, B3SOIDDdum4Node, B3SOIDDdum4Node); + CREATE_KLU_BINDING_TABLE(B3SOIDDDum5Ptr, B3SOIDDDum5Binding, B3SOIDDdum5Node, B3SOIDDdum5Node); + CREATE_KLU_BINDING_TABLE(B3SOIDDQaccPtr, B3SOIDDQaccBinding, B3SOIDDqaccNode, B3SOIDDqaccNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDQsub0Ptr, B3SOIDDQsub0Binding, B3SOIDDqsub0Node, B3SOIDDqsub0Node); + CREATE_KLU_BINDING_TABLE(B3SOIDDQsubs1Ptr, B3SOIDDQsubs1Binding, B3SOIDDqsubs1Node, B3SOIDDqsubs1Node); + CREATE_KLU_BINDING_TABLE(B3SOIDDQsubs2Ptr, B3SOIDDQsubs2Binding, B3SOIDDqsubs2Node, B3SOIDDqsubs2Node); + CREATE_KLU_BINDING_TABLE(B3SOIDDqePtr, B3SOIDDqeBinding, B3SOIDDqeNode, B3SOIDDqeNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDqdPtr, B3SOIDDqdBinding, B3SOIDDqdNode, B3SOIDDqdNode); + CREATE_KLU_BINDING_TABLE(B3SOIDDqgPtr, B3SOIDDqgBinding, B3SOIDDqgNode, B3SOIDDqgNode); + } + } + } + + return (OK) ; +} + +int +B3SOIDDbindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + B3SOIDDmodel *model = (B3SOIDDmodel *)inModel ; + B3SOIDDinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the B3SOIDD models */ + for ( ; model != NULL ; model = B3SOIDDnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = B3SOIDDinstances(model); here != NULL ; here = B3SOIDDnextInstance(here)) + { + if ((model->B3SOIDDshMod == 1) && (here->B3SOIDDrth0 != 0.0)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDTemptempPtr, B3SOIDDTemptempBinding, B3SOIDDtempNode, B3SOIDDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDTempdpPtr, B3SOIDDTempdpBinding, B3SOIDDtempNode, B3SOIDDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDTempspPtr, B3SOIDDTempspBinding, B3SOIDDtempNode, B3SOIDDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDTempgPtr, B3SOIDDTempgBinding, B3SOIDDtempNode, B3SOIDDgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDTempbPtr, B3SOIDDTempbBinding, B3SOIDDtempNode, B3SOIDDbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDTempePtr, B3SOIDDTempeBinding, B3SOIDDtempNode, B3SOIDDeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDGtempPtr, B3SOIDDGtempBinding, B3SOIDDgNode, B3SOIDDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDDPtempPtr, B3SOIDDDPtempBinding, B3SOIDDdNodePrime, B3SOIDDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDSPtempPtr, B3SOIDDSPtempBinding, B3SOIDDsNodePrime, B3SOIDDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDEtempPtr, B3SOIDDEtempBinding, B3SOIDDeNode, B3SOIDDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDBtempPtr, B3SOIDDBtempBinding, B3SOIDDbNode, B3SOIDDtempNode); + if (here->B3SOIDDbodyMod == 1) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDPtempPtr, B3SOIDDPtempBinding, B3SOIDDpNode, B3SOIDDtempNode); + } + } + if (here->B3SOIDDbodyMod == 2) + { + } + else if (here->B3SOIDDbodyMod == 1) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDBpPtr, B3SOIDDBpBinding, B3SOIDDbNode, B3SOIDDpNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDPbPtr, B3SOIDDPbBinding, B3SOIDDpNode, B3SOIDDbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDPpPtr, B3SOIDDPpBinding, B3SOIDDpNode, B3SOIDDpNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDPgPtr, B3SOIDDPgBinding, B3SOIDDpNode, B3SOIDDgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDPdpPtr, B3SOIDDPdpBinding, B3SOIDDpNode, B3SOIDDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDPspPtr, B3SOIDDPspBinding, B3SOIDDpNode, B3SOIDDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDPePtr, B3SOIDDPeBinding, B3SOIDDpNode, B3SOIDDeNode); + } + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDEgPtr, B3SOIDDEgBinding, B3SOIDDeNode, B3SOIDDgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDEdpPtr, B3SOIDDEdpBinding, B3SOIDDeNode, B3SOIDDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDEspPtr, B3SOIDDEspBinding, B3SOIDDeNode, B3SOIDDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDGePtr, B3SOIDDGeBinding, B3SOIDDgNode, B3SOIDDeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDDPePtr, B3SOIDDDPeBinding, B3SOIDDdNodePrime, B3SOIDDeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDSPePtr, B3SOIDDSPeBinding, B3SOIDDsNodePrime, B3SOIDDeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDEbPtr, B3SOIDDEbBinding, B3SOIDDeNode, B3SOIDDbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDGbPtr, B3SOIDDGbBinding, B3SOIDDgNode, B3SOIDDbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDDPbPtr, B3SOIDDDPbBinding, B3SOIDDdNodePrime, B3SOIDDbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDSPbPtr, B3SOIDDSPbBinding, B3SOIDDsNodePrime, B3SOIDDbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDBePtr, B3SOIDDBeBinding, B3SOIDDbNode, B3SOIDDeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDBgPtr, B3SOIDDBgBinding, B3SOIDDbNode, B3SOIDDgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDBdpPtr, B3SOIDDBdpBinding, B3SOIDDbNode, B3SOIDDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDBspPtr, B3SOIDDBspBinding, B3SOIDDbNode, B3SOIDDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDBbPtr, B3SOIDDBbBinding, B3SOIDDbNode, B3SOIDDbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDEePtr, B3SOIDDEeBinding, B3SOIDDeNode, B3SOIDDeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDGgPtr, B3SOIDDGgBinding, B3SOIDDgNode, B3SOIDDgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDGdpPtr, B3SOIDDGdpBinding, B3SOIDDgNode, B3SOIDDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDGspPtr, B3SOIDDGspBinding, B3SOIDDgNode, B3SOIDDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDDPgPtr, B3SOIDDDPgBinding, B3SOIDDdNodePrime, B3SOIDDgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDDPdpPtr, B3SOIDDDPdpBinding, B3SOIDDdNodePrime, B3SOIDDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDDPspPtr, B3SOIDDDPspBinding, B3SOIDDdNodePrime, B3SOIDDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDDPdPtr, B3SOIDDDPdBinding, B3SOIDDdNodePrime, B3SOIDDdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDSPgPtr, B3SOIDDSPgBinding, B3SOIDDsNodePrime, B3SOIDDgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDSPdpPtr, B3SOIDDSPdpBinding, B3SOIDDsNodePrime, B3SOIDDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDSPspPtr, B3SOIDDSPspBinding, B3SOIDDsNodePrime, B3SOIDDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDSPsPtr, B3SOIDDSPsBinding, B3SOIDDsNodePrime, B3SOIDDsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDDdPtr, B3SOIDDDdBinding, B3SOIDDdNode, B3SOIDDdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDDdpPtr, B3SOIDDDdpBinding, B3SOIDDdNode, B3SOIDDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDSsPtr, B3SOIDDSsBinding, B3SOIDDsNode, B3SOIDDsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDSspPtr, B3SOIDDSspBinding, B3SOIDDsNode, B3SOIDDsNodePrime); + if ((here->B3SOIDDdebugMod > 1) || (here->B3SOIDDdebugMod == -1)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDVbsPtr, B3SOIDDVbsBinding, B3SOIDDvbsNode, B3SOIDDvbsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDIdsPtr, B3SOIDDIdsBinding, B3SOIDDidsNode, B3SOIDDidsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDIcPtr, B3SOIDDIcBinding, B3SOIDDicNode, B3SOIDDicNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDIbsPtr, B3SOIDDIbsBinding, B3SOIDDibsNode, B3SOIDDibsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDIbdPtr, B3SOIDDIbdBinding, B3SOIDDibdNode, B3SOIDDibdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDIiiPtr, B3SOIDDIiiBinding, B3SOIDDiiiNode, B3SOIDDiiiNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDIgidlPtr, B3SOIDDIgidlBinding, B3SOIDDigidlNode, B3SOIDDigidlNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDItunPtr, B3SOIDDItunBinding, B3SOIDDitunNode, B3SOIDDitunNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDIbpPtr, B3SOIDDIbpBinding, B3SOIDDibpNode, B3SOIDDibpNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDAbeffPtr, B3SOIDDAbeffBinding, B3SOIDDabeffNode, B3SOIDDabeffNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDVbs0effPtr, B3SOIDDVbs0effBinding, B3SOIDDvbs0effNode, B3SOIDDvbs0effNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDVbseffPtr, B3SOIDDVbseffBinding, B3SOIDDvbseffNode, B3SOIDDvbseffNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDXcPtr, B3SOIDDXcBinding, B3SOIDDxcNode, B3SOIDDxcNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDCbbPtr, B3SOIDDCbbBinding, B3SOIDDcbbNode, B3SOIDDcbbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDCbdPtr, B3SOIDDCbdBinding, B3SOIDDcbdNode, B3SOIDDcbdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDCbgPtr, B3SOIDDCbgBinding, B3SOIDDcbgNode, B3SOIDDcbgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDqbPtr, B3SOIDDqbBinding, B3SOIDDqbNode, B3SOIDDqbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDQbfPtr, B3SOIDDQbfBinding, B3SOIDDqbfNode, B3SOIDDqbfNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDQjsPtr, B3SOIDDQjsBinding, B3SOIDDqjsNode, B3SOIDDqjsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDQjdPtr, B3SOIDDQjdBinding, B3SOIDDqjdNode, B3SOIDDqjdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDGmPtr, B3SOIDDGmBinding, B3SOIDDgmNode, B3SOIDDgmNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDGmbsPtr, B3SOIDDGmbsBinding, B3SOIDDgmbsNode, B3SOIDDgmbsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDGdsPtr, B3SOIDDGdsBinding, B3SOIDDgdsNode, B3SOIDDgdsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDGmePtr, B3SOIDDGmeBinding, B3SOIDDgmeNode, B3SOIDDgmeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDVbs0teffPtr, B3SOIDDVbs0teffBinding, B3SOIDDvbs0teffNode, B3SOIDDvbs0teffNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDVthPtr, B3SOIDDVthBinding, B3SOIDDvthNode, B3SOIDDvthNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDVgsteffPtr, B3SOIDDVgsteffBinding, B3SOIDDvgsteffNode, B3SOIDDvgsteffNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDXcsatPtr, B3SOIDDXcsatBinding, B3SOIDDxcsatNode, B3SOIDDxcsatNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDVcscvPtr, B3SOIDDVcscvBinding, B3SOIDDvcscvNode, B3SOIDDvcscvNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDVdscvPtr, B3SOIDDVdscvBinding, B3SOIDDvdscvNode, B3SOIDDvdscvNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDCbePtr, B3SOIDDCbeBinding, B3SOIDDcbeNode, B3SOIDDcbeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDDum1Ptr, B3SOIDDDum1Binding, B3SOIDDdum1Node, B3SOIDDdum1Node); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDDum2Ptr, B3SOIDDDum2Binding, B3SOIDDdum2Node, B3SOIDDdum2Node); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDDum3Ptr, B3SOIDDDum3Binding, B3SOIDDdum3Node, B3SOIDDdum3Node); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDDum4Ptr, B3SOIDDDum4Binding, B3SOIDDdum4Node, B3SOIDDdum4Node); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDDum5Ptr, B3SOIDDDum5Binding, B3SOIDDdum5Node, B3SOIDDdum5Node); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDQaccPtr, B3SOIDDQaccBinding, B3SOIDDqaccNode, B3SOIDDqaccNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDQsub0Ptr, B3SOIDDQsub0Binding, B3SOIDDqsub0Node, B3SOIDDqsub0Node); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDQsubs1Ptr, B3SOIDDQsubs1Binding, B3SOIDDqsubs1Node, B3SOIDDqsubs1Node); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDQsubs2Ptr, B3SOIDDQsubs2Binding, B3SOIDDqsubs2Node, B3SOIDDqsubs2Node); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDqePtr, B3SOIDDqeBinding, B3SOIDDqeNode, B3SOIDDqeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDqdPtr, B3SOIDDqdBinding, B3SOIDDqdNode, B3SOIDDqdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIDDqgPtr, B3SOIDDqgBinding, B3SOIDDqgNode, B3SOIDDqgNode); + } + } + } + + return (OK) ; +} + +int +B3SOIDDbindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + B3SOIDDmodel *model = (B3SOIDDmodel *)inModel ; + B3SOIDDinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the B3SOIDD models */ + for ( ; model != NULL ; model = B3SOIDDnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = B3SOIDDinstances(model); here != NULL ; here = B3SOIDDnextInstance(here)) + { + if ((model->B3SOIDDshMod == 1) && (here->B3SOIDDrth0 != 0.0)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDTemptempPtr, B3SOIDDTemptempBinding, B3SOIDDtempNode, B3SOIDDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDTempdpPtr, B3SOIDDTempdpBinding, B3SOIDDtempNode, B3SOIDDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDTempspPtr, B3SOIDDTempspBinding, B3SOIDDtempNode, B3SOIDDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDTempgPtr, B3SOIDDTempgBinding, B3SOIDDtempNode, B3SOIDDgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDTempbPtr, B3SOIDDTempbBinding, B3SOIDDtempNode, B3SOIDDbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDTempePtr, B3SOIDDTempeBinding, B3SOIDDtempNode, B3SOIDDeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDGtempPtr, B3SOIDDGtempBinding, B3SOIDDgNode, B3SOIDDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDDPtempPtr, B3SOIDDDPtempBinding, B3SOIDDdNodePrime, B3SOIDDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDSPtempPtr, B3SOIDDSPtempBinding, B3SOIDDsNodePrime, B3SOIDDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDEtempPtr, B3SOIDDEtempBinding, B3SOIDDeNode, B3SOIDDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDBtempPtr, B3SOIDDBtempBinding, B3SOIDDbNode, B3SOIDDtempNode); + if (here->B3SOIDDbodyMod == 1) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDPtempPtr, B3SOIDDPtempBinding, B3SOIDDpNode, B3SOIDDtempNode); + } + } + if (here->B3SOIDDbodyMod == 2) + { + } + else if (here->B3SOIDDbodyMod == 1) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDBpPtr, B3SOIDDBpBinding, B3SOIDDbNode, B3SOIDDpNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDPbPtr, B3SOIDDPbBinding, B3SOIDDpNode, B3SOIDDbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDPpPtr, B3SOIDDPpBinding, B3SOIDDpNode, B3SOIDDpNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDPgPtr, B3SOIDDPgBinding, B3SOIDDpNode, B3SOIDDgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDPdpPtr, B3SOIDDPdpBinding, B3SOIDDpNode, B3SOIDDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDPspPtr, B3SOIDDPspBinding, B3SOIDDpNode, B3SOIDDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDPePtr, B3SOIDDPeBinding, B3SOIDDpNode, B3SOIDDeNode); + } + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDEgPtr, B3SOIDDEgBinding, B3SOIDDeNode, B3SOIDDgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDEdpPtr, B3SOIDDEdpBinding, B3SOIDDeNode, B3SOIDDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDEspPtr, B3SOIDDEspBinding, B3SOIDDeNode, B3SOIDDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDGePtr, B3SOIDDGeBinding, B3SOIDDgNode, B3SOIDDeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDDPePtr, B3SOIDDDPeBinding, B3SOIDDdNodePrime, B3SOIDDeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDSPePtr, B3SOIDDSPeBinding, B3SOIDDsNodePrime, B3SOIDDeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDEbPtr, B3SOIDDEbBinding, B3SOIDDeNode, B3SOIDDbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDGbPtr, B3SOIDDGbBinding, B3SOIDDgNode, B3SOIDDbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDDPbPtr, B3SOIDDDPbBinding, B3SOIDDdNodePrime, B3SOIDDbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDSPbPtr, B3SOIDDSPbBinding, B3SOIDDsNodePrime, B3SOIDDbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDBePtr, B3SOIDDBeBinding, B3SOIDDbNode, B3SOIDDeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDBgPtr, B3SOIDDBgBinding, B3SOIDDbNode, B3SOIDDgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDBdpPtr, B3SOIDDBdpBinding, B3SOIDDbNode, B3SOIDDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDBspPtr, B3SOIDDBspBinding, B3SOIDDbNode, B3SOIDDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDBbPtr, B3SOIDDBbBinding, B3SOIDDbNode, B3SOIDDbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDEePtr, B3SOIDDEeBinding, B3SOIDDeNode, B3SOIDDeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDGgPtr, B3SOIDDGgBinding, B3SOIDDgNode, B3SOIDDgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDGdpPtr, B3SOIDDGdpBinding, B3SOIDDgNode, B3SOIDDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDGspPtr, B3SOIDDGspBinding, B3SOIDDgNode, B3SOIDDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDDPgPtr, B3SOIDDDPgBinding, B3SOIDDdNodePrime, B3SOIDDgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDDPdpPtr, B3SOIDDDPdpBinding, B3SOIDDdNodePrime, B3SOIDDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDDPspPtr, B3SOIDDDPspBinding, B3SOIDDdNodePrime, B3SOIDDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDDPdPtr, B3SOIDDDPdBinding, B3SOIDDdNodePrime, B3SOIDDdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDSPgPtr, B3SOIDDSPgBinding, B3SOIDDsNodePrime, B3SOIDDgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDSPdpPtr, B3SOIDDSPdpBinding, B3SOIDDsNodePrime, B3SOIDDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDSPspPtr, B3SOIDDSPspBinding, B3SOIDDsNodePrime, B3SOIDDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDSPsPtr, B3SOIDDSPsBinding, B3SOIDDsNodePrime, B3SOIDDsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDDdPtr, B3SOIDDDdBinding, B3SOIDDdNode, B3SOIDDdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDDdpPtr, B3SOIDDDdpBinding, B3SOIDDdNode, B3SOIDDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDSsPtr, B3SOIDDSsBinding, B3SOIDDsNode, B3SOIDDsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDSspPtr, B3SOIDDSspBinding, B3SOIDDsNode, B3SOIDDsNodePrime); + if ((here->B3SOIDDdebugMod > 1) || (here->B3SOIDDdebugMod == -1)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDVbsPtr, B3SOIDDVbsBinding, B3SOIDDvbsNode, B3SOIDDvbsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDIdsPtr, B3SOIDDIdsBinding, B3SOIDDidsNode, B3SOIDDidsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDIcPtr, B3SOIDDIcBinding, B3SOIDDicNode, B3SOIDDicNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDIbsPtr, B3SOIDDIbsBinding, B3SOIDDibsNode, B3SOIDDibsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDIbdPtr, B3SOIDDIbdBinding, B3SOIDDibdNode, B3SOIDDibdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDIiiPtr, B3SOIDDIiiBinding, B3SOIDDiiiNode, B3SOIDDiiiNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDIgidlPtr, B3SOIDDIgidlBinding, B3SOIDDigidlNode, B3SOIDDigidlNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDItunPtr, B3SOIDDItunBinding, B3SOIDDitunNode, B3SOIDDitunNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDIbpPtr, B3SOIDDIbpBinding, B3SOIDDibpNode, B3SOIDDibpNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDAbeffPtr, B3SOIDDAbeffBinding, B3SOIDDabeffNode, B3SOIDDabeffNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDVbs0effPtr, B3SOIDDVbs0effBinding, B3SOIDDvbs0effNode, B3SOIDDvbs0effNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDVbseffPtr, B3SOIDDVbseffBinding, B3SOIDDvbseffNode, B3SOIDDvbseffNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDXcPtr, B3SOIDDXcBinding, B3SOIDDxcNode, B3SOIDDxcNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDCbbPtr, B3SOIDDCbbBinding, B3SOIDDcbbNode, B3SOIDDcbbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDCbdPtr, B3SOIDDCbdBinding, B3SOIDDcbdNode, B3SOIDDcbdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDCbgPtr, B3SOIDDCbgBinding, B3SOIDDcbgNode, B3SOIDDcbgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDqbPtr, B3SOIDDqbBinding, B3SOIDDqbNode, B3SOIDDqbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDQbfPtr, B3SOIDDQbfBinding, B3SOIDDqbfNode, B3SOIDDqbfNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDQjsPtr, B3SOIDDQjsBinding, B3SOIDDqjsNode, B3SOIDDqjsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDQjdPtr, B3SOIDDQjdBinding, B3SOIDDqjdNode, B3SOIDDqjdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDGmPtr, B3SOIDDGmBinding, B3SOIDDgmNode, B3SOIDDgmNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDGmbsPtr, B3SOIDDGmbsBinding, B3SOIDDgmbsNode, B3SOIDDgmbsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDGdsPtr, B3SOIDDGdsBinding, B3SOIDDgdsNode, B3SOIDDgdsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDGmePtr, B3SOIDDGmeBinding, B3SOIDDgmeNode, B3SOIDDgmeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDVbs0teffPtr, B3SOIDDVbs0teffBinding, B3SOIDDvbs0teffNode, B3SOIDDvbs0teffNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDVthPtr, B3SOIDDVthBinding, B3SOIDDvthNode, B3SOIDDvthNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDVgsteffPtr, B3SOIDDVgsteffBinding, B3SOIDDvgsteffNode, B3SOIDDvgsteffNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDXcsatPtr, B3SOIDDXcsatBinding, B3SOIDDxcsatNode, B3SOIDDxcsatNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDVcscvPtr, B3SOIDDVcscvBinding, B3SOIDDvcscvNode, B3SOIDDvcscvNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDVdscvPtr, B3SOIDDVdscvBinding, B3SOIDDvdscvNode, B3SOIDDvdscvNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDCbePtr, B3SOIDDCbeBinding, B3SOIDDcbeNode, B3SOIDDcbeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDDum1Ptr, B3SOIDDDum1Binding, B3SOIDDdum1Node, B3SOIDDdum1Node); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDDum2Ptr, B3SOIDDDum2Binding, B3SOIDDdum2Node, B3SOIDDdum2Node); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDDum3Ptr, B3SOIDDDum3Binding, B3SOIDDdum3Node, B3SOIDDdum3Node); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDDum4Ptr, B3SOIDDDum4Binding, B3SOIDDdum4Node, B3SOIDDdum4Node); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDDum5Ptr, B3SOIDDDum5Binding, B3SOIDDdum5Node, B3SOIDDdum5Node); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDQaccPtr, B3SOIDDQaccBinding, B3SOIDDqaccNode, B3SOIDDqaccNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDQsub0Ptr, B3SOIDDQsub0Binding, B3SOIDDqsub0Node, B3SOIDDqsub0Node); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDQsubs1Ptr, B3SOIDDQsubs1Binding, B3SOIDDqsubs1Node, B3SOIDDqsubs1Node); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDQsubs2Ptr, B3SOIDDQsubs2Binding, B3SOIDDqsubs2Node, B3SOIDDqsubs2Node); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDqePtr, B3SOIDDqeBinding, B3SOIDDqeNode, B3SOIDDqeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDqdPtr, B3SOIDDqdBinding, B3SOIDDqdNode, B3SOIDDqdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIDDqgPtr, B3SOIDDqgBinding, B3SOIDDqgNode, B3SOIDDqgNode); + } + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/bsim3soi_dd/b3soidddef.h b/src/spicelib/devices/bsim3soi_dd/b3soidddef.h index 93402cda7..67cef35e2 100644 --- a/src/spicelib/devices/bsim3soi_dd/b3soidddef.h +++ b/src/spicelib/devices/bsim3soi_dd/b3soidddef.h @@ -420,6 +420,102 @@ typedef struct sB3SOIDDinstance double **B3SOIDDnVar; #endif /* NONOISE */ +#ifdef KLU + BindElement *B3SOIDDTemptempBinding ; + BindElement *B3SOIDDTempdpBinding ; + BindElement *B3SOIDDTempspBinding ; + BindElement *B3SOIDDTempgBinding ; + BindElement *B3SOIDDTempbBinding ; + BindElement *B3SOIDDTempeBinding ; + BindElement *B3SOIDDGtempBinding ; + BindElement *B3SOIDDDPtempBinding ; + BindElement *B3SOIDDSPtempBinding ; + BindElement *B3SOIDDEtempBinding ; + BindElement *B3SOIDDBtempBinding ; + BindElement *B3SOIDDPtempBinding ; + BindElement *B3SOIDDBpBinding ; + BindElement *B3SOIDDPbBinding ; + BindElement *B3SOIDDPpBinding ; + BindElement *B3SOIDDPgBinding ; + BindElement *B3SOIDDPdpBinding ; + BindElement *B3SOIDDPspBinding ; + BindElement *B3SOIDDPeBinding ; + BindElement *B3SOIDDEgBinding ; + BindElement *B3SOIDDEdpBinding ; + BindElement *B3SOIDDEspBinding ; + BindElement *B3SOIDDGeBinding ; + BindElement *B3SOIDDDPeBinding ; + BindElement *B3SOIDDSPeBinding ; + BindElement *B3SOIDDEbBinding ; + BindElement *B3SOIDDGbBinding ; + BindElement *B3SOIDDDPbBinding ; + BindElement *B3SOIDDSPbBinding ; + BindElement *B3SOIDDBeBinding ; + BindElement *B3SOIDDBgBinding ; + BindElement *B3SOIDDBdpBinding ; + BindElement *B3SOIDDBspBinding ; + BindElement *B3SOIDDBbBinding ; + BindElement *B3SOIDDEeBinding ; + BindElement *B3SOIDDGgBinding ; + BindElement *B3SOIDDGdpBinding ; + BindElement *B3SOIDDGspBinding ; + BindElement *B3SOIDDDPgBinding ; + BindElement *B3SOIDDDPdpBinding ; + BindElement *B3SOIDDDPspBinding ; + BindElement *B3SOIDDDPdBinding ; + BindElement *B3SOIDDSPgBinding ; + BindElement *B3SOIDDSPdpBinding ; + BindElement *B3SOIDDSPspBinding ; + BindElement *B3SOIDDSPsBinding ; + BindElement *B3SOIDDDdBinding ; + BindElement *B3SOIDDDdpBinding ; + BindElement *B3SOIDDSsBinding ; + BindElement *B3SOIDDSspBinding ; + BindElement *B3SOIDDVbsBinding ; + BindElement *B3SOIDDIdsBinding ; + BindElement *B3SOIDDIcBinding ; + BindElement *B3SOIDDIbsBinding ; + BindElement *B3SOIDDIbdBinding ; + BindElement *B3SOIDDIiiBinding ; + BindElement *B3SOIDDIgidlBinding ; + BindElement *B3SOIDDItunBinding ; + BindElement *B3SOIDDIbpBinding ; + BindElement *B3SOIDDAbeffBinding ; + BindElement *B3SOIDDVbs0effBinding ; + BindElement *B3SOIDDVbseffBinding ; + BindElement *B3SOIDDXcBinding ; + BindElement *B3SOIDDCbbBinding ; + BindElement *B3SOIDDCbdBinding ; + BindElement *B3SOIDDCbgBinding ; + BindElement *B3SOIDDqbBinding ; + BindElement *B3SOIDDQbfBinding ; + BindElement *B3SOIDDQjsBinding ; + BindElement *B3SOIDDQjdBinding ; + BindElement *B3SOIDDGmBinding ; + BindElement *B3SOIDDGmbsBinding ; + BindElement *B3SOIDDGdsBinding ; + BindElement *B3SOIDDGmeBinding ; + BindElement *B3SOIDDVbs0teffBinding ; + BindElement *B3SOIDDVthBinding ; + BindElement *B3SOIDDVgsteffBinding ; + BindElement *B3SOIDDXcsatBinding ; + BindElement *B3SOIDDVcscvBinding ; + BindElement *B3SOIDDVdscvBinding ; + BindElement *B3SOIDDCbeBinding ; + BindElement *B3SOIDDDum1Binding ; + BindElement *B3SOIDDDum2Binding ; + BindElement *B3SOIDDDum3Binding ; + BindElement *B3SOIDDDum4Binding ; + BindElement *B3SOIDDDum5Binding ; + BindElement *B3SOIDDQaccBinding ; + BindElement *B3SOIDDQsub0Binding ; + BindElement *B3SOIDDQsubs1Binding ; + BindElement *B3SOIDDQsubs2Binding ; + BindElement *B3SOIDDqeBinding ; + BindElement *B3SOIDDqdBinding ; + BindElement *B3SOIDDqgBinding ; +#endif + } B3SOIDDinstance ; struct b3soiddSizeDependParam diff --git a/src/spicelib/devices/bsim3soi_dd/b3soiddext.h b/src/spicelib/devices/bsim3soi_dd/b3soiddext.h index 107b4d7ab..edb74c31c 100644 --- a/src/spicelib/devices/bsim3soi_dd/b3soiddext.h +++ b/src/spicelib/devices/bsim3soi_dd/b3soiddext.h @@ -28,3 +28,9 @@ extern int B3SOIDDtemp(GENmodel*,CKTcircuit*); extern int B3SOIDDtrunc(GENmodel*,CKTcircuit*,double*); extern int B3SOIDDnoise(int,int,GENmodel*,CKTcircuit*,Ndata*,double*); extern int B3SOIDDunsetup(GENmodel*,CKTcircuit*); + +#ifdef KLU +extern int B3SOIDDbindCSC (GENmodel*, CKTcircuit*) ; +extern int B3SOIDDbindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int B3SOIDDbindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/bsim3soi_dd/b3soiddinit.c b/src/spicelib/devices/bsim3soi_dd/b3soiddinit.c index fbc36aa13..fa5a41dee 100644 --- a/src/spicelib/devices/bsim3soi_dd/b3soiddinit.c +++ b/src/spicelib/devices/bsim3soi_dd/b3soiddinit.c @@ -64,6 +64,11 @@ SPICEdev B3SOIDDinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = B3SOIDDbindCSC, + .DEVbindCSCComplex = B3SOIDDbindCSCComplex, + .DEVbindCSCComplexToReal = B3SOIDDbindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/bsim3soi_fd/Makefile.am b/src/spicelib/devices/bsim3soi_fd/Makefile.am index aac0e863a..dad13649e 100644 --- a/src/spicelib/devices/bsim3soi_fd/Makefile.am +++ b/src/spicelib/devices/bsim3soi_fd/Makefile.am @@ -28,6 +28,9 @@ libbsim3soifd_la_SOURCES = \ b3soifditf.h +if KLU_WANTED +libbsim3soifd_la_SOURCES += b3soifdbindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) diff --git a/src/spicelib/devices/bsim3soi_fd/b3soifdbindCSC.c b/src/spicelib/devices/bsim3soi_fd/b3soifdbindCSC.c new file mode 100644 index 000000000..28924c8cb --- /dev/null +++ b/src/spicelib/devices/bsim3soi_fd/b3soifdbindCSC.c @@ -0,0 +1,386 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "b3soifddef.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +B3SOIFDbindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + B3SOIFDmodel *model = (B3SOIFDmodel *)inModel ; + B3SOIFDinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the B3SOIFD models */ + for ( ; model != NULL ; model = B3SOIFDnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = B3SOIFDinstances(model); here != NULL ; here = B3SOIFDnextInstance(here)) + { + if ((model->B3SOIFDshMod == 1) && (here->B3SOIFDrth0 != 0.0)) + { + CREATE_KLU_BINDING_TABLE(B3SOIFDTemptempPtr, B3SOIFDTemptempBinding, B3SOIFDtempNode, B3SOIFDtempNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDTempdpPtr, B3SOIFDTempdpBinding, B3SOIFDtempNode, B3SOIFDdNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIFDTempspPtr, B3SOIFDTempspBinding, B3SOIFDtempNode, B3SOIFDsNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIFDTempgPtr, B3SOIFDTempgBinding, B3SOIFDtempNode, B3SOIFDgNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDTempbPtr, B3SOIFDTempbBinding, B3SOIFDtempNode, B3SOIFDbNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDTempePtr, B3SOIFDTempeBinding, B3SOIFDtempNode, B3SOIFDeNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDGtempPtr, B3SOIFDGtempBinding, B3SOIFDgNode, B3SOIFDtempNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDDPtempPtr, B3SOIFDDPtempBinding, B3SOIFDdNodePrime, B3SOIFDtempNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDSPtempPtr, B3SOIFDSPtempBinding, B3SOIFDsNodePrime, B3SOIFDtempNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDEtempPtr, B3SOIFDEtempBinding, B3SOIFDeNode, B3SOIFDtempNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDBtempPtr, B3SOIFDBtempBinding, B3SOIFDbNode, B3SOIFDtempNode); + if (here->B3SOIFDbodyMod == 1) + { + CREATE_KLU_BINDING_TABLE(B3SOIFDPtempPtr, B3SOIFDPtempBinding, B3SOIFDpNode, B3SOIFDtempNode); + } + } + if (here->B3SOIFDbodyMod == 2) + { + } + else if (here->B3SOIFDbodyMod == 1) + { + CREATE_KLU_BINDING_TABLE(B3SOIFDBpPtr, B3SOIFDBpBinding, B3SOIFDbNode, B3SOIFDpNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDPbPtr, B3SOIFDPbBinding, B3SOIFDpNode, B3SOIFDbNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDPpPtr, B3SOIFDPpBinding, B3SOIFDpNode, B3SOIFDpNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDPgPtr, B3SOIFDPgBinding, B3SOIFDpNode, B3SOIFDgNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDPdpPtr, B3SOIFDPdpBinding, B3SOIFDpNode, B3SOIFDdNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIFDPspPtr, B3SOIFDPspBinding, B3SOIFDpNode, B3SOIFDsNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIFDPePtr, B3SOIFDPeBinding, B3SOIFDpNode, B3SOIFDeNode); + } + CREATE_KLU_BINDING_TABLE(B3SOIFDEgPtr, B3SOIFDEgBinding, B3SOIFDeNode, B3SOIFDgNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDEdpPtr, B3SOIFDEdpBinding, B3SOIFDeNode, B3SOIFDdNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIFDEspPtr, B3SOIFDEspBinding, B3SOIFDeNode, B3SOIFDsNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIFDGePtr, B3SOIFDGeBinding, B3SOIFDgNode, B3SOIFDeNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDDPePtr, B3SOIFDDPeBinding, B3SOIFDdNodePrime, B3SOIFDeNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDSPePtr, B3SOIFDSPeBinding, B3SOIFDsNodePrime, B3SOIFDeNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDEbPtr, B3SOIFDEbBinding, B3SOIFDeNode, B3SOIFDbNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDEePtr, B3SOIFDEeBinding, B3SOIFDeNode, B3SOIFDeNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDGgPtr, B3SOIFDGgBinding, B3SOIFDgNode, B3SOIFDgNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDGdpPtr, B3SOIFDGdpBinding, B3SOIFDgNode, B3SOIFDdNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIFDGspPtr, B3SOIFDGspBinding, B3SOIFDgNode, B3SOIFDsNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIFDDPgPtr, B3SOIFDDPgBinding, B3SOIFDdNodePrime, B3SOIFDgNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDDPdpPtr, B3SOIFDDPdpBinding, B3SOIFDdNodePrime, B3SOIFDdNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIFDDPspPtr, B3SOIFDDPspBinding, B3SOIFDdNodePrime, B3SOIFDsNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIFDDPdPtr, B3SOIFDDPdBinding, B3SOIFDdNodePrime, B3SOIFDdNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDSPgPtr, B3SOIFDSPgBinding, B3SOIFDsNodePrime, B3SOIFDgNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDSPdpPtr, B3SOIFDSPdpBinding, B3SOIFDsNodePrime, B3SOIFDdNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIFDSPspPtr, B3SOIFDSPspBinding, B3SOIFDsNodePrime, B3SOIFDsNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIFDSPsPtr, B3SOIFDSPsBinding, B3SOIFDsNodePrime, B3SOIFDsNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDDdPtr, B3SOIFDDdBinding, B3SOIFDdNode, B3SOIFDdNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDDdpPtr, B3SOIFDDdpBinding, B3SOIFDdNode, B3SOIFDdNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIFDSsPtr, B3SOIFDSsBinding, B3SOIFDsNode, B3SOIFDsNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDSspPtr, B3SOIFDSspBinding, B3SOIFDsNode, B3SOIFDsNodePrime); + if ((here->B3SOIFDdebugMod > 1) || (here->B3SOIFDdebugMod == -1)) + { + CREATE_KLU_BINDING_TABLE(B3SOIFDVbsPtr, B3SOIFDVbsBinding, B3SOIFDvbsNode, B3SOIFDvbsNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDIdsPtr, B3SOIFDIdsBinding, B3SOIFDidsNode, B3SOIFDidsNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDIcPtr, B3SOIFDIcBinding, B3SOIFDicNode, B3SOIFDicNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDIbsPtr, B3SOIFDIbsBinding, B3SOIFDibsNode, B3SOIFDibsNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDIbdPtr, B3SOIFDIbdBinding, B3SOIFDibdNode, B3SOIFDibdNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDIiiPtr, B3SOIFDIiiBinding, B3SOIFDiiiNode, B3SOIFDiiiNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDIgidlPtr, B3SOIFDIgidlBinding, B3SOIFDigidlNode, B3SOIFDigidlNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDItunPtr, B3SOIFDItunBinding, B3SOIFDitunNode, B3SOIFDitunNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDIbpPtr, B3SOIFDIbpBinding, B3SOIFDibpNode, B3SOIFDibpNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDAbeffPtr, B3SOIFDAbeffBinding, B3SOIFDabeffNode, B3SOIFDabeffNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDVbs0effPtr, B3SOIFDVbs0effBinding, B3SOIFDvbs0effNode, B3SOIFDvbs0effNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDVbseffPtr, B3SOIFDVbseffBinding, B3SOIFDvbseffNode, B3SOIFDvbseffNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDXcPtr, B3SOIFDXcBinding, B3SOIFDxcNode, B3SOIFDxcNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDCbbPtr, B3SOIFDCbbBinding, B3SOIFDcbbNode, B3SOIFDcbbNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDCbdPtr, B3SOIFDCbdBinding, B3SOIFDcbdNode, B3SOIFDcbdNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDCbgPtr, B3SOIFDCbgBinding, B3SOIFDcbgNode, B3SOIFDcbgNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDqbPtr, B3SOIFDqbBinding, B3SOIFDqbNode, B3SOIFDqbNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDQbfPtr, B3SOIFDQbfBinding, B3SOIFDqbfNode, B3SOIFDqbfNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDQjsPtr, B3SOIFDQjsBinding, B3SOIFDqjsNode, B3SOIFDqjsNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDQjdPtr, B3SOIFDQjdBinding, B3SOIFDqjdNode, B3SOIFDqjdNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDGmPtr, B3SOIFDGmBinding, B3SOIFDgmNode, B3SOIFDgmNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDGmbsPtr, B3SOIFDGmbsBinding, B3SOIFDgmbsNode, B3SOIFDgmbsNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDGdsPtr, B3SOIFDGdsBinding, B3SOIFDgdsNode, B3SOIFDgdsNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDGmePtr, B3SOIFDGmeBinding, B3SOIFDgmeNode, B3SOIFDgmeNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDVbs0teffPtr, B3SOIFDVbs0teffBinding, B3SOIFDvbs0teffNode, B3SOIFDvbs0teffNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDVthPtr, B3SOIFDVthBinding, B3SOIFDvthNode, B3SOIFDvthNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDVgsteffPtr, B3SOIFDVgsteffBinding, B3SOIFDvgsteffNode, B3SOIFDvgsteffNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDXcsatPtr, B3SOIFDXcsatBinding, B3SOIFDxcsatNode, B3SOIFDxcsatNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDVcscvPtr, B3SOIFDVcscvBinding, B3SOIFDvcscvNode, B3SOIFDvcscvNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDVdscvPtr, B3SOIFDVdscvBinding, B3SOIFDvdscvNode, B3SOIFDvdscvNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDCbePtr, B3SOIFDCbeBinding, B3SOIFDcbeNode, B3SOIFDcbeNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDDum1Ptr, B3SOIFDDum1Binding, B3SOIFDdum1Node, B3SOIFDdum1Node); + CREATE_KLU_BINDING_TABLE(B3SOIFDDum2Ptr, B3SOIFDDum2Binding, B3SOIFDdum2Node, B3SOIFDdum2Node); + CREATE_KLU_BINDING_TABLE(B3SOIFDDum3Ptr, B3SOIFDDum3Binding, B3SOIFDdum3Node, B3SOIFDdum3Node); + CREATE_KLU_BINDING_TABLE(B3SOIFDDum4Ptr, B3SOIFDDum4Binding, B3SOIFDdum4Node, B3SOIFDdum4Node); + CREATE_KLU_BINDING_TABLE(B3SOIFDDum5Ptr, B3SOIFDDum5Binding, B3SOIFDdum5Node, B3SOIFDdum5Node); + CREATE_KLU_BINDING_TABLE(B3SOIFDQaccPtr, B3SOIFDQaccBinding, B3SOIFDqaccNode, B3SOIFDqaccNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDQsub0Ptr, B3SOIFDQsub0Binding, B3SOIFDqsub0Node, B3SOIFDqsub0Node); + CREATE_KLU_BINDING_TABLE(B3SOIFDQsubs1Ptr, B3SOIFDQsubs1Binding, B3SOIFDqsubs1Node, B3SOIFDqsubs1Node); + CREATE_KLU_BINDING_TABLE(B3SOIFDQsubs2Ptr, B3SOIFDQsubs2Binding, B3SOIFDqsubs2Node, B3SOIFDqsubs2Node); + CREATE_KLU_BINDING_TABLE(B3SOIFDqePtr, B3SOIFDqeBinding, B3SOIFDqeNode, B3SOIFDqeNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDqdPtr, B3SOIFDqdBinding, B3SOIFDqdNode, B3SOIFDqdNode); + CREATE_KLU_BINDING_TABLE(B3SOIFDqgPtr, B3SOIFDqgBinding, B3SOIFDqgNode, B3SOIFDqgNode); + } + } + } + + return (OK) ; +} + +int +B3SOIFDbindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + B3SOIFDmodel *model = (B3SOIFDmodel *)inModel ; + B3SOIFDinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the B3SOIFD models */ + for ( ; model != NULL ; model = B3SOIFDnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = B3SOIFDinstances(model); here != NULL ; here = B3SOIFDnextInstance(here)) + { + if ((model->B3SOIFDshMod == 1) && (here->B3SOIFDrth0 != 0.0)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDTemptempPtr, B3SOIFDTemptempBinding, B3SOIFDtempNode, B3SOIFDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDTempdpPtr, B3SOIFDTempdpBinding, B3SOIFDtempNode, B3SOIFDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDTempspPtr, B3SOIFDTempspBinding, B3SOIFDtempNode, B3SOIFDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDTempgPtr, B3SOIFDTempgBinding, B3SOIFDtempNode, B3SOIFDgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDTempbPtr, B3SOIFDTempbBinding, B3SOIFDtempNode, B3SOIFDbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDTempePtr, B3SOIFDTempeBinding, B3SOIFDtempNode, B3SOIFDeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDGtempPtr, B3SOIFDGtempBinding, B3SOIFDgNode, B3SOIFDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDDPtempPtr, B3SOIFDDPtempBinding, B3SOIFDdNodePrime, B3SOIFDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDSPtempPtr, B3SOIFDSPtempBinding, B3SOIFDsNodePrime, B3SOIFDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDEtempPtr, B3SOIFDEtempBinding, B3SOIFDeNode, B3SOIFDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDBtempPtr, B3SOIFDBtempBinding, B3SOIFDbNode, B3SOIFDtempNode); + if (here->B3SOIFDbodyMod == 1) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDPtempPtr, B3SOIFDPtempBinding, B3SOIFDpNode, B3SOIFDtempNode); + } + } + if (here->B3SOIFDbodyMod == 2) + { + } + else if (here->B3SOIFDbodyMod == 1) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDBpPtr, B3SOIFDBpBinding, B3SOIFDbNode, B3SOIFDpNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDPbPtr, B3SOIFDPbBinding, B3SOIFDpNode, B3SOIFDbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDPpPtr, B3SOIFDPpBinding, B3SOIFDpNode, B3SOIFDpNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDPgPtr, B3SOIFDPgBinding, B3SOIFDpNode, B3SOIFDgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDPdpPtr, B3SOIFDPdpBinding, B3SOIFDpNode, B3SOIFDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDPspPtr, B3SOIFDPspBinding, B3SOIFDpNode, B3SOIFDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDPePtr, B3SOIFDPeBinding, B3SOIFDpNode, B3SOIFDeNode); + } + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDEgPtr, B3SOIFDEgBinding, B3SOIFDeNode, B3SOIFDgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDEdpPtr, B3SOIFDEdpBinding, B3SOIFDeNode, B3SOIFDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDEspPtr, B3SOIFDEspBinding, B3SOIFDeNode, B3SOIFDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDGePtr, B3SOIFDGeBinding, B3SOIFDgNode, B3SOIFDeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDDPePtr, B3SOIFDDPeBinding, B3SOIFDdNodePrime, B3SOIFDeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDSPePtr, B3SOIFDSPeBinding, B3SOIFDsNodePrime, B3SOIFDeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDEbPtr, B3SOIFDEbBinding, B3SOIFDeNode, B3SOIFDbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDEePtr, B3SOIFDEeBinding, B3SOIFDeNode, B3SOIFDeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDGgPtr, B3SOIFDGgBinding, B3SOIFDgNode, B3SOIFDgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDGdpPtr, B3SOIFDGdpBinding, B3SOIFDgNode, B3SOIFDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDGspPtr, B3SOIFDGspBinding, B3SOIFDgNode, B3SOIFDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDDPgPtr, B3SOIFDDPgBinding, B3SOIFDdNodePrime, B3SOIFDgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDDPdpPtr, B3SOIFDDPdpBinding, B3SOIFDdNodePrime, B3SOIFDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDDPspPtr, B3SOIFDDPspBinding, B3SOIFDdNodePrime, B3SOIFDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDDPdPtr, B3SOIFDDPdBinding, B3SOIFDdNodePrime, B3SOIFDdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDSPgPtr, B3SOIFDSPgBinding, B3SOIFDsNodePrime, B3SOIFDgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDSPdpPtr, B3SOIFDSPdpBinding, B3SOIFDsNodePrime, B3SOIFDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDSPspPtr, B3SOIFDSPspBinding, B3SOIFDsNodePrime, B3SOIFDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDSPsPtr, B3SOIFDSPsBinding, B3SOIFDsNodePrime, B3SOIFDsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDDdPtr, B3SOIFDDdBinding, B3SOIFDdNode, B3SOIFDdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDDdpPtr, B3SOIFDDdpBinding, B3SOIFDdNode, B3SOIFDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDSsPtr, B3SOIFDSsBinding, B3SOIFDsNode, B3SOIFDsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDSspPtr, B3SOIFDSspBinding, B3SOIFDsNode, B3SOIFDsNodePrime); + if ((here->B3SOIFDdebugMod > 1) || (here->B3SOIFDdebugMod == -1)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDVbsPtr, B3SOIFDVbsBinding, B3SOIFDvbsNode, B3SOIFDvbsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDIdsPtr, B3SOIFDIdsBinding, B3SOIFDidsNode, B3SOIFDidsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDIcPtr, B3SOIFDIcBinding, B3SOIFDicNode, B3SOIFDicNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDIbsPtr, B3SOIFDIbsBinding, B3SOIFDibsNode, B3SOIFDibsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDIbdPtr, B3SOIFDIbdBinding, B3SOIFDibdNode, B3SOIFDibdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDIiiPtr, B3SOIFDIiiBinding, B3SOIFDiiiNode, B3SOIFDiiiNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDIgidlPtr, B3SOIFDIgidlBinding, B3SOIFDigidlNode, B3SOIFDigidlNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDItunPtr, B3SOIFDItunBinding, B3SOIFDitunNode, B3SOIFDitunNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDIbpPtr, B3SOIFDIbpBinding, B3SOIFDibpNode, B3SOIFDibpNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDAbeffPtr, B3SOIFDAbeffBinding, B3SOIFDabeffNode, B3SOIFDabeffNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDVbs0effPtr, B3SOIFDVbs0effBinding, B3SOIFDvbs0effNode, B3SOIFDvbs0effNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDVbseffPtr, B3SOIFDVbseffBinding, B3SOIFDvbseffNode, B3SOIFDvbseffNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDXcPtr, B3SOIFDXcBinding, B3SOIFDxcNode, B3SOIFDxcNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDCbbPtr, B3SOIFDCbbBinding, B3SOIFDcbbNode, B3SOIFDcbbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDCbdPtr, B3SOIFDCbdBinding, B3SOIFDcbdNode, B3SOIFDcbdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDCbgPtr, B3SOIFDCbgBinding, B3SOIFDcbgNode, B3SOIFDcbgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDqbPtr, B3SOIFDqbBinding, B3SOIFDqbNode, B3SOIFDqbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDQbfPtr, B3SOIFDQbfBinding, B3SOIFDqbfNode, B3SOIFDqbfNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDQjsPtr, B3SOIFDQjsBinding, B3SOIFDqjsNode, B3SOIFDqjsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDQjdPtr, B3SOIFDQjdBinding, B3SOIFDqjdNode, B3SOIFDqjdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDGmPtr, B3SOIFDGmBinding, B3SOIFDgmNode, B3SOIFDgmNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDGmbsPtr, B3SOIFDGmbsBinding, B3SOIFDgmbsNode, B3SOIFDgmbsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDGdsPtr, B3SOIFDGdsBinding, B3SOIFDgdsNode, B3SOIFDgdsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDGmePtr, B3SOIFDGmeBinding, B3SOIFDgmeNode, B3SOIFDgmeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDVbs0teffPtr, B3SOIFDVbs0teffBinding, B3SOIFDvbs0teffNode, B3SOIFDvbs0teffNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDVthPtr, B3SOIFDVthBinding, B3SOIFDvthNode, B3SOIFDvthNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDVgsteffPtr, B3SOIFDVgsteffBinding, B3SOIFDvgsteffNode, B3SOIFDvgsteffNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDXcsatPtr, B3SOIFDXcsatBinding, B3SOIFDxcsatNode, B3SOIFDxcsatNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDVcscvPtr, B3SOIFDVcscvBinding, B3SOIFDvcscvNode, B3SOIFDvcscvNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDVdscvPtr, B3SOIFDVdscvBinding, B3SOIFDvdscvNode, B3SOIFDvdscvNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDCbePtr, B3SOIFDCbeBinding, B3SOIFDcbeNode, B3SOIFDcbeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDDum1Ptr, B3SOIFDDum1Binding, B3SOIFDdum1Node, B3SOIFDdum1Node); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDDum2Ptr, B3SOIFDDum2Binding, B3SOIFDdum2Node, B3SOIFDdum2Node); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDDum3Ptr, B3SOIFDDum3Binding, B3SOIFDdum3Node, B3SOIFDdum3Node); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDDum4Ptr, B3SOIFDDum4Binding, B3SOIFDdum4Node, B3SOIFDdum4Node); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDDum5Ptr, B3SOIFDDum5Binding, B3SOIFDdum5Node, B3SOIFDdum5Node); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDQaccPtr, B3SOIFDQaccBinding, B3SOIFDqaccNode, B3SOIFDqaccNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDQsub0Ptr, B3SOIFDQsub0Binding, B3SOIFDqsub0Node, B3SOIFDqsub0Node); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDQsubs1Ptr, B3SOIFDQsubs1Binding, B3SOIFDqsubs1Node, B3SOIFDqsubs1Node); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDQsubs2Ptr, B3SOIFDQsubs2Binding, B3SOIFDqsubs2Node, B3SOIFDqsubs2Node); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDqePtr, B3SOIFDqeBinding, B3SOIFDqeNode, B3SOIFDqeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDqdPtr, B3SOIFDqdBinding, B3SOIFDqdNode, B3SOIFDqdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIFDqgPtr, B3SOIFDqgBinding, B3SOIFDqgNode, B3SOIFDqgNode); + } + } + } + + return (OK) ; +} + +int +B3SOIFDbindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + B3SOIFDmodel *model = (B3SOIFDmodel *)inModel ; + B3SOIFDinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the B3SOIFD models */ + for ( ; model != NULL ; model = B3SOIFDnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = B3SOIFDinstances(model); here != NULL ; here = B3SOIFDnextInstance(here)) + { + if ((model->B3SOIFDshMod == 1) && (here->B3SOIFDrth0 != 0.0)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDTemptempPtr, B3SOIFDTemptempBinding, B3SOIFDtempNode, B3SOIFDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDTempdpPtr, B3SOIFDTempdpBinding, B3SOIFDtempNode, B3SOIFDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDTempspPtr, B3SOIFDTempspBinding, B3SOIFDtempNode, B3SOIFDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDTempgPtr, B3SOIFDTempgBinding, B3SOIFDtempNode, B3SOIFDgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDTempbPtr, B3SOIFDTempbBinding, B3SOIFDtempNode, B3SOIFDbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDTempePtr, B3SOIFDTempeBinding, B3SOIFDtempNode, B3SOIFDeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDGtempPtr, B3SOIFDGtempBinding, B3SOIFDgNode, B3SOIFDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDDPtempPtr, B3SOIFDDPtempBinding, B3SOIFDdNodePrime, B3SOIFDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDSPtempPtr, B3SOIFDSPtempBinding, B3SOIFDsNodePrime, B3SOIFDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDEtempPtr, B3SOIFDEtempBinding, B3SOIFDeNode, B3SOIFDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDBtempPtr, B3SOIFDBtempBinding, B3SOIFDbNode, B3SOIFDtempNode); + if (here->B3SOIFDbodyMod == 1) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDPtempPtr, B3SOIFDPtempBinding, B3SOIFDpNode, B3SOIFDtempNode); + } + } + if (here->B3SOIFDbodyMod == 2) + { + } + else if (here->B3SOIFDbodyMod == 1) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDBpPtr, B3SOIFDBpBinding, B3SOIFDbNode, B3SOIFDpNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDPbPtr, B3SOIFDPbBinding, B3SOIFDpNode, B3SOIFDbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDPpPtr, B3SOIFDPpBinding, B3SOIFDpNode, B3SOIFDpNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDPgPtr, B3SOIFDPgBinding, B3SOIFDpNode, B3SOIFDgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDPdpPtr, B3SOIFDPdpBinding, B3SOIFDpNode, B3SOIFDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDPspPtr, B3SOIFDPspBinding, B3SOIFDpNode, B3SOIFDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDPePtr, B3SOIFDPeBinding, B3SOIFDpNode, B3SOIFDeNode); + } + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDEgPtr, B3SOIFDEgBinding, B3SOIFDeNode, B3SOIFDgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDEdpPtr, B3SOIFDEdpBinding, B3SOIFDeNode, B3SOIFDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDEspPtr, B3SOIFDEspBinding, B3SOIFDeNode, B3SOIFDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDGePtr, B3SOIFDGeBinding, B3SOIFDgNode, B3SOIFDeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDDPePtr, B3SOIFDDPeBinding, B3SOIFDdNodePrime, B3SOIFDeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDSPePtr, B3SOIFDSPeBinding, B3SOIFDsNodePrime, B3SOIFDeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDEbPtr, B3SOIFDEbBinding, B3SOIFDeNode, B3SOIFDbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDEePtr, B3SOIFDEeBinding, B3SOIFDeNode, B3SOIFDeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDGgPtr, B3SOIFDGgBinding, B3SOIFDgNode, B3SOIFDgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDGdpPtr, B3SOIFDGdpBinding, B3SOIFDgNode, B3SOIFDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDGspPtr, B3SOIFDGspBinding, B3SOIFDgNode, B3SOIFDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDDPgPtr, B3SOIFDDPgBinding, B3SOIFDdNodePrime, B3SOIFDgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDDPdpPtr, B3SOIFDDPdpBinding, B3SOIFDdNodePrime, B3SOIFDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDDPspPtr, B3SOIFDDPspBinding, B3SOIFDdNodePrime, B3SOIFDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDDPdPtr, B3SOIFDDPdBinding, B3SOIFDdNodePrime, B3SOIFDdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDSPgPtr, B3SOIFDSPgBinding, B3SOIFDsNodePrime, B3SOIFDgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDSPdpPtr, B3SOIFDSPdpBinding, B3SOIFDsNodePrime, B3SOIFDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDSPspPtr, B3SOIFDSPspBinding, B3SOIFDsNodePrime, B3SOIFDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDSPsPtr, B3SOIFDSPsBinding, B3SOIFDsNodePrime, B3SOIFDsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDDdPtr, B3SOIFDDdBinding, B3SOIFDdNode, B3SOIFDdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDDdpPtr, B3SOIFDDdpBinding, B3SOIFDdNode, B3SOIFDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDSsPtr, B3SOIFDSsBinding, B3SOIFDsNode, B3SOIFDsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDSspPtr, B3SOIFDSspBinding, B3SOIFDsNode, B3SOIFDsNodePrime); + if ((here->B3SOIFDdebugMod > 1) || (here->B3SOIFDdebugMod == -1)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDVbsPtr, B3SOIFDVbsBinding, B3SOIFDvbsNode, B3SOIFDvbsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDIdsPtr, B3SOIFDIdsBinding, B3SOIFDidsNode, B3SOIFDidsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDIcPtr, B3SOIFDIcBinding, B3SOIFDicNode, B3SOIFDicNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDIbsPtr, B3SOIFDIbsBinding, B3SOIFDibsNode, B3SOIFDibsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDIbdPtr, B3SOIFDIbdBinding, B3SOIFDibdNode, B3SOIFDibdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDIiiPtr, B3SOIFDIiiBinding, B3SOIFDiiiNode, B3SOIFDiiiNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDIgidlPtr, B3SOIFDIgidlBinding, B3SOIFDigidlNode, B3SOIFDigidlNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDItunPtr, B3SOIFDItunBinding, B3SOIFDitunNode, B3SOIFDitunNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDIbpPtr, B3SOIFDIbpBinding, B3SOIFDibpNode, B3SOIFDibpNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDAbeffPtr, B3SOIFDAbeffBinding, B3SOIFDabeffNode, B3SOIFDabeffNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDVbs0effPtr, B3SOIFDVbs0effBinding, B3SOIFDvbs0effNode, B3SOIFDvbs0effNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDVbseffPtr, B3SOIFDVbseffBinding, B3SOIFDvbseffNode, B3SOIFDvbseffNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDXcPtr, B3SOIFDXcBinding, B3SOIFDxcNode, B3SOIFDxcNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDCbbPtr, B3SOIFDCbbBinding, B3SOIFDcbbNode, B3SOIFDcbbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDCbdPtr, B3SOIFDCbdBinding, B3SOIFDcbdNode, B3SOIFDcbdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDCbgPtr, B3SOIFDCbgBinding, B3SOIFDcbgNode, B3SOIFDcbgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDqbPtr, B3SOIFDqbBinding, B3SOIFDqbNode, B3SOIFDqbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDQbfPtr, B3SOIFDQbfBinding, B3SOIFDqbfNode, B3SOIFDqbfNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDQjsPtr, B3SOIFDQjsBinding, B3SOIFDqjsNode, B3SOIFDqjsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDQjdPtr, B3SOIFDQjdBinding, B3SOIFDqjdNode, B3SOIFDqjdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDGmPtr, B3SOIFDGmBinding, B3SOIFDgmNode, B3SOIFDgmNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDGmbsPtr, B3SOIFDGmbsBinding, B3SOIFDgmbsNode, B3SOIFDgmbsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDGdsPtr, B3SOIFDGdsBinding, B3SOIFDgdsNode, B3SOIFDgdsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDGmePtr, B3SOIFDGmeBinding, B3SOIFDgmeNode, B3SOIFDgmeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDVbs0teffPtr, B3SOIFDVbs0teffBinding, B3SOIFDvbs0teffNode, B3SOIFDvbs0teffNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDVthPtr, B3SOIFDVthBinding, B3SOIFDvthNode, B3SOIFDvthNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDVgsteffPtr, B3SOIFDVgsteffBinding, B3SOIFDvgsteffNode, B3SOIFDvgsteffNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDXcsatPtr, B3SOIFDXcsatBinding, B3SOIFDxcsatNode, B3SOIFDxcsatNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDVcscvPtr, B3SOIFDVcscvBinding, B3SOIFDvcscvNode, B3SOIFDvcscvNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDVdscvPtr, B3SOIFDVdscvBinding, B3SOIFDvdscvNode, B3SOIFDvdscvNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDCbePtr, B3SOIFDCbeBinding, B3SOIFDcbeNode, B3SOIFDcbeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDDum1Ptr, B3SOIFDDum1Binding, B3SOIFDdum1Node, B3SOIFDdum1Node); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDDum2Ptr, B3SOIFDDum2Binding, B3SOIFDdum2Node, B3SOIFDdum2Node); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDDum3Ptr, B3SOIFDDum3Binding, B3SOIFDdum3Node, B3SOIFDdum3Node); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDDum4Ptr, B3SOIFDDum4Binding, B3SOIFDdum4Node, B3SOIFDdum4Node); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDDum5Ptr, B3SOIFDDum5Binding, B3SOIFDdum5Node, B3SOIFDdum5Node); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDQaccPtr, B3SOIFDQaccBinding, B3SOIFDqaccNode, B3SOIFDqaccNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDQsub0Ptr, B3SOIFDQsub0Binding, B3SOIFDqsub0Node, B3SOIFDqsub0Node); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDQsubs1Ptr, B3SOIFDQsubs1Binding, B3SOIFDqsubs1Node, B3SOIFDqsubs1Node); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDQsubs2Ptr, B3SOIFDQsubs2Binding, B3SOIFDqsubs2Node, B3SOIFDqsubs2Node); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDqePtr, B3SOIFDqeBinding, B3SOIFDqeNode, B3SOIFDqeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDqdPtr, B3SOIFDqdBinding, B3SOIFDqdNode, B3SOIFDqdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIFDqgPtr, B3SOIFDqgBinding, B3SOIFDqgNode, B3SOIFDqgNode); + } + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/bsim3soi_fd/b3soifddef.h b/src/spicelib/devices/bsim3soi_fd/b3soifddef.h index 7bbe71fc9..6fe56a250 100644 --- a/src/spicelib/devices/bsim3soi_fd/b3soifddef.h +++ b/src/spicelib/devices/bsim3soi_fd/b3soifddef.h @@ -420,6 +420,94 @@ typedef struct sB3SOIFDinstance double **B3SOIFDnVar; #endif /* NONOISE */ +#ifdef KLU + BindElement *B3SOIFDTemptempBinding ; + BindElement *B3SOIFDTempdpBinding ; + BindElement *B3SOIFDTempspBinding ; + BindElement *B3SOIFDTempgBinding ; + BindElement *B3SOIFDTempbBinding ; + BindElement *B3SOIFDTempeBinding ; + BindElement *B3SOIFDGtempBinding ; + BindElement *B3SOIFDDPtempBinding ; + BindElement *B3SOIFDSPtempBinding ; + BindElement *B3SOIFDEtempBinding ; + BindElement *B3SOIFDBtempBinding ; + BindElement *B3SOIFDPtempBinding ; + BindElement *B3SOIFDBpBinding ; + BindElement *B3SOIFDPbBinding ; + BindElement *B3SOIFDPpBinding ; + BindElement *B3SOIFDPgBinding ; + BindElement *B3SOIFDPdpBinding ; + BindElement *B3SOIFDPspBinding ; + BindElement *B3SOIFDPeBinding ; + BindElement *B3SOIFDEgBinding ; + BindElement *B3SOIFDEdpBinding ; + BindElement *B3SOIFDEspBinding ; + BindElement *B3SOIFDGeBinding ; + BindElement *B3SOIFDDPeBinding ; + BindElement *B3SOIFDSPeBinding ; + BindElement *B3SOIFDEbBinding ; + BindElement *B3SOIFDEeBinding ; + BindElement *B3SOIFDGgBinding ; + BindElement *B3SOIFDGdpBinding ; + BindElement *B3SOIFDGspBinding ; + BindElement *B3SOIFDDPgBinding ; + BindElement *B3SOIFDDPdpBinding ; + BindElement *B3SOIFDDPspBinding ; + BindElement *B3SOIFDDPdBinding ; + BindElement *B3SOIFDSPgBinding ; + BindElement *B3SOIFDSPdpBinding ; + BindElement *B3SOIFDSPspBinding ; + BindElement *B3SOIFDSPsBinding ; + BindElement *B3SOIFDDdBinding ; + BindElement *B3SOIFDDdpBinding ; + BindElement *B3SOIFDSsBinding ; + BindElement *B3SOIFDSspBinding ; + BindElement *B3SOIFDVbsBinding ; + BindElement *B3SOIFDIdsBinding ; + BindElement *B3SOIFDIcBinding ; + BindElement *B3SOIFDIbsBinding ; + BindElement *B3SOIFDIbdBinding ; + BindElement *B3SOIFDIiiBinding ; + BindElement *B3SOIFDIgidlBinding ; + BindElement *B3SOIFDItunBinding ; + BindElement *B3SOIFDIbpBinding ; + BindElement *B3SOIFDAbeffBinding ; + BindElement *B3SOIFDVbs0effBinding ; + BindElement *B3SOIFDVbseffBinding ; + BindElement *B3SOIFDXcBinding ; + BindElement *B3SOIFDCbbBinding ; + BindElement *B3SOIFDCbdBinding ; + BindElement *B3SOIFDCbgBinding ; + BindElement *B3SOIFDqbBinding ; + BindElement *B3SOIFDQbfBinding ; + BindElement *B3SOIFDQjsBinding ; + BindElement *B3SOIFDQjdBinding ; + BindElement *B3SOIFDGmBinding ; + BindElement *B3SOIFDGmbsBinding ; + BindElement *B3SOIFDGdsBinding ; + BindElement *B3SOIFDGmeBinding ; + BindElement *B3SOIFDVbs0teffBinding ; + BindElement *B3SOIFDVthBinding ; + BindElement *B3SOIFDVgsteffBinding ; + BindElement *B3SOIFDXcsatBinding ; + BindElement *B3SOIFDVcscvBinding ; + BindElement *B3SOIFDVdscvBinding ; + BindElement *B3SOIFDCbeBinding ; + BindElement *B3SOIFDDum1Binding ; + BindElement *B3SOIFDDum2Binding ; + BindElement *B3SOIFDDum3Binding ; + BindElement *B3SOIFDDum4Binding ; + BindElement *B3SOIFDDum5Binding ; + BindElement *B3SOIFDQaccBinding ; + BindElement *B3SOIFDQsub0Binding ; + BindElement *B3SOIFDQsubs1Binding ; + BindElement *B3SOIFDQsubs2Binding ; + BindElement *B3SOIFDqeBinding ; + BindElement *B3SOIFDqdBinding ; + BindElement *B3SOIFDqgBinding ; +#endif + } B3SOIFDinstance ; struct b3soifdSizeDependParam diff --git a/src/spicelib/devices/bsim3soi_fd/b3soifdext.h b/src/spicelib/devices/bsim3soi_fd/b3soifdext.h index a1a30408f..51974ca5e 100644 --- a/src/spicelib/devices/bsim3soi_fd/b3soifdext.h +++ b/src/spicelib/devices/bsim3soi_fd/b3soifdext.h @@ -29,3 +29,8 @@ extern int B3SOIFDtrunc(GENmodel*,CKTcircuit*,double*); extern int B3SOIFDnoise(int,int,GENmodel*,CKTcircuit*,Ndata*,double*); extern int B3SOIFDunsetup(GENmodel*,CKTcircuit*); +#ifdef KLU +extern int B3SOIFDbindCSC (GENmodel*, CKTcircuit*) ; +extern int B3SOIFDbindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int B3SOIFDbindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/bsim3soi_fd/b3soifdinit.c b/src/spicelib/devices/bsim3soi_fd/b3soifdinit.c index c41973691..be2f77e38 100644 --- a/src/spicelib/devices/bsim3soi_fd/b3soifdinit.c +++ b/src/spicelib/devices/bsim3soi_fd/b3soifdinit.c @@ -64,6 +64,11 @@ SPICEdev B3SOIFDinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = B3SOIFDbindCSC, + .DEVbindCSCComplex = B3SOIFDbindCSCComplex, + .DEVbindCSCComplexToReal = B3SOIFDbindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/bsim3soi_pd/Makefile.am b/src/spicelib/devices/bsim3soi_pd/Makefile.am index f363b1d0e..5c426c521 100644 --- a/src/spicelib/devices/bsim3soi_pd/Makefile.am +++ b/src/spicelib/devices/bsim3soi_pd/Makefile.am @@ -28,6 +28,9 @@ libbsim3soipd_la_SOURCES = \ b3soipditf.h +if KLU_WANTED +libbsim3soipd_la_SOURCES += b3soipdbindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) diff --git a/src/spicelib/devices/bsim3soi_pd/b3soipdbindCSC.c b/src/spicelib/devices/bsim3soi_pd/b3soipdbindCSC.c new file mode 100644 index 000000000..d70337918 --- /dev/null +++ b/src/spicelib/devices/bsim3soi_pd/b3soipdbindCSC.c @@ -0,0 +1,323 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "b3soipddef.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +B3SOIPDbindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + B3SOIPDmodel *model = (B3SOIPDmodel *)inModel ; + B3SOIPDinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the B3SOIPD models */ + for ( ; model != NULL ; model = B3SOIPDnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = B3SOIPDinstances(model); here != NULL ; here = B3SOIPDnextInstance(here)) + { + if ((model->B3SOIPDshMod == 1) && (here->B3SOIPDrth0 != 0.0)) + { + CREATE_KLU_BINDING_TABLE(B3SOIPDTemptempPtr, B3SOIPDTemptempBinding, B3SOIPDtempNode, B3SOIPDtempNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDTempdpPtr, B3SOIPDTempdpBinding, B3SOIPDtempNode, B3SOIPDdNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIPDTempspPtr, B3SOIPDTempspBinding, B3SOIPDtempNode, B3SOIPDsNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIPDTempgPtr, B3SOIPDTempgBinding, B3SOIPDtempNode, B3SOIPDgNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDTempbPtr, B3SOIPDTempbBinding, B3SOIPDtempNode, B3SOIPDbNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDGtempPtr, B3SOIPDGtempBinding, B3SOIPDgNode, B3SOIPDtempNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDDPtempPtr, B3SOIPDDPtempBinding, B3SOIPDdNodePrime, B3SOIPDtempNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDSPtempPtr, B3SOIPDSPtempBinding, B3SOIPDsNodePrime, B3SOIPDtempNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDEtempPtr, B3SOIPDEtempBinding, B3SOIPDeNode, B3SOIPDtempNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDBtempPtr, B3SOIPDBtempBinding, B3SOIPDbNode, B3SOIPDtempNode); + if (here->B3SOIPDbodyMod == 1) + { + CREATE_KLU_BINDING_TABLE(B3SOIPDPtempPtr, B3SOIPDPtempBinding, B3SOIPDpNode, B3SOIPDtempNode); + } + } + if (here->B3SOIPDbodyMod == 2) + { + } + else if (here->B3SOIPDbodyMod == 1) + { + CREATE_KLU_BINDING_TABLE(B3SOIPDBpPtr, B3SOIPDBpBinding, B3SOIPDbNode, B3SOIPDpNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDPbPtr, B3SOIPDPbBinding, B3SOIPDpNode, B3SOIPDbNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDPpPtr, B3SOIPDPpBinding, B3SOIPDpNode, B3SOIPDpNode); + } + CREATE_KLU_BINDING_TABLE(B3SOIPDEbPtr, B3SOIPDEbBinding, B3SOIPDeNode, B3SOIPDbNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDGbPtr, B3SOIPDGbBinding, B3SOIPDgNode, B3SOIPDbNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDDPbPtr, B3SOIPDDPbBinding, B3SOIPDdNodePrime, B3SOIPDbNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDSPbPtr, B3SOIPDSPbBinding, B3SOIPDsNodePrime, B3SOIPDbNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDBePtr, B3SOIPDBeBinding, B3SOIPDbNode, B3SOIPDeNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDBgPtr, B3SOIPDBgBinding, B3SOIPDbNode, B3SOIPDgNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDBdpPtr, B3SOIPDBdpBinding, B3SOIPDbNode, B3SOIPDdNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIPDBspPtr, B3SOIPDBspBinding, B3SOIPDbNode, B3SOIPDsNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIPDBbPtr, B3SOIPDBbBinding, B3SOIPDbNode, B3SOIPDbNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDEgPtr, B3SOIPDEgBinding, B3SOIPDeNode, B3SOIPDgNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDEdpPtr, B3SOIPDEdpBinding, B3SOIPDeNode, B3SOIPDdNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIPDEspPtr, B3SOIPDEspBinding, B3SOIPDeNode, B3SOIPDsNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIPDGePtr, B3SOIPDGeBinding, B3SOIPDgNode, B3SOIPDeNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDDPePtr, B3SOIPDDPeBinding, B3SOIPDdNodePrime, B3SOIPDeNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDSPePtr, B3SOIPDSPeBinding, B3SOIPDsNodePrime, B3SOIPDeNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDEePtr, B3SOIPDEeBinding, B3SOIPDeNode, B3SOIPDeNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDGgPtr, B3SOIPDGgBinding, B3SOIPDgNode, B3SOIPDgNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDGdpPtr, B3SOIPDGdpBinding, B3SOIPDgNode, B3SOIPDdNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIPDGspPtr, B3SOIPDGspBinding, B3SOIPDgNode, B3SOIPDsNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIPDDPgPtr, B3SOIPDDPgBinding, B3SOIPDdNodePrime, B3SOIPDgNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDDPdpPtr, B3SOIPDDPdpBinding, B3SOIPDdNodePrime, B3SOIPDdNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIPDDPspPtr, B3SOIPDDPspBinding, B3SOIPDdNodePrime, B3SOIPDsNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIPDDPdPtr, B3SOIPDDPdBinding, B3SOIPDdNodePrime, B3SOIPDdNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDSPgPtr, B3SOIPDSPgBinding, B3SOIPDsNodePrime, B3SOIPDgNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDSPdpPtr, B3SOIPDSPdpBinding, B3SOIPDsNodePrime, B3SOIPDdNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIPDSPspPtr, B3SOIPDSPspBinding, B3SOIPDsNodePrime, B3SOIPDsNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIPDSPsPtr, B3SOIPDSPsBinding, B3SOIPDsNodePrime, B3SOIPDsNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDDdPtr, B3SOIPDDdBinding, B3SOIPDdNode, B3SOIPDdNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDDdpPtr, B3SOIPDDdpBinding, B3SOIPDdNode, B3SOIPDdNodePrime); + CREATE_KLU_BINDING_TABLE(B3SOIPDSsPtr, B3SOIPDSsBinding, B3SOIPDsNode, B3SOIPDsNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDSspPtr, B3SOIPDSspBinding, B3SOIPDsNode, B3SOIPDsNodePrime); + if (here->B3SOIPDdebugMod != 0) + { + CREATE_KLU_BINDING_TABLE(B3SOIPDVbsPtr, B3SOIPDVbsBinding, B3SOIPDvbsNode, B3SOIPDvbsNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDIdsPtr, B3SOIPDIdsBinding, B3SOIPDidsNode, B3SOIPDidsNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDIcPtr, B3SOIPDIcBinding, B3SOIPDicNode, B3SOIPDicNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDIbsPtr, B3SOIPDIbsBinding, B3SOIPDibsNode, B3SOIPDibsNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDIbdPtr, B3SOIPDIbdBinding, B3SOIPDibdNode, B3SOIPDibdNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDIiiPtr, B3SOIPDIiiBinding, B3SOIPDiiiNode, B3SOIPDiiiNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDIgPtr, B3SOIPDIgBinding, B3SOIPDigNode, B3SOIPDigNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDGiggPtr, B3SOIPDGiggBinding, B3SOIPDgiggNode, B3SOIPDgiggNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDGigdPtr, B3SOIPDGigdBinding, B3SOIPDgigdNode, B3SOIPDgigdNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDGigbPtr, B3SOIPDGigbBinding, B3SOIPDgigbNode, B3SOIPDgigbNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDIgidlPtr, B3SOIPDIgidlBinding, B3SOIPDigidlNode, B3SOIPDigidlNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDItunPtr, B3SOIPDItunBinding, B3SOIPDitunNode, B3SOIPDitunNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDIbpPtr, B3SOIPDIbpBinding, B3SOIPDibpNode, B3SOIPDibpNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDCbbPtr, B3SOIPDCbbBinding, B3SOIPDcbbNode, B3SOIPDcbbNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDCbdPtr, B3SOIPDCbdBinding, B3SOIPDcbdNode, B3SOIPDcbdNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDCbgPtr, B3SOIPDCbgBinding, B3SOIPDcbgNode, B3SOIPDcbgNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDQbfPtr, B3SOIPDQbfBinding, B3SOIPDqbfNode, B3SOIPDqbfNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDQjsPtr, B3SOIPDQjsBinding, B3SOIPDqjsNode, B3SOIPDqjsNode); + CREATE_KLU_BINDING_TABLE(B3SOIPDQjdPtr, B3SOIPDQjdBinding, B3SOIPDqjdNode, B3SOIPDqjdNode); + } + } + } + + return (OK) ; +} + +int +B3SOIPDbindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + B3SOIPDmodel *model = (B3SOIPDmodel *)inModel ; + B3SOIPDinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the B3SOIPD models */ + for ( ; model != NULL ; model = B3SOIPDnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = B3SOIPDinstances(model); here != NULL ; here = B3SOIPDnextInstance(here)) + { + if ((model->B3SOIPDshMod == 1) && (here->B3SOIPDrth0 != 0.0)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDTemptempPtr, B3SOIPDTemptempBinding, B3SOIPDtempNode, B3SOIPDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDTempdpPtr, B3SOIPDTempdpBinding, B3SOIPDtempNode, B3SOIPDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDTempspPtr, B3SOIPDTempspBinding, B3SOIPDtempNode, B3SOIPDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDTempgPtr, B3SOIPDTempgBinding, B3SOIPDtempNode, B3SOIPDgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDTempbPtr, B3SOIPDTempbBinding, B3SOIPDtempNode, B3SOIPDbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDGtempPtr, B3SOIPDGtempBinding, B3SOIPDgNode, B3SOIPDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDDPtempPtr, B3SOIPDDPtempBinding, B3SOIPDdNodePrime, B3SOIPDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDSPtempPtr, B3SOIPDSPtempBinding, B3SOIPDsNodePrime, B3SOIPDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDEtempPtr, B3SOIPDEtempBinding, B3SOIPDeNode, B3SOIPDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDBtempPtr, B3SOIPDBtempBinding, B3SOIPDbNode, B3SOIPDtempNode); + if (here->B3SOIPDbodyMod == 1) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDPtempPtr, B3SOIPDPtempBinding, B3SOIPDpNode, B3SOIPDtempNode); + } + } + if (here->B3SOIPDbodyMod == 2) + { + } + else if (here->B3SOIPDbodyMod == 1) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDBpPtr, B3SOIPDBpBinding, B3SOIPDbNode, B3SOIPDpNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDPbPtr, B3SOIPDPbBinding, B3SOIPDpNode, B3SOIPDbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDPpPtr, B3SOIPDPpBinding, B3SOIPDpNode, B3SOIPDpNode); + } + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDEbPtr, B3SOIPDEbBinding, B3SOIPDeNode, B3SOIPDbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDGbPtr, B3SOIPDGbBinding, B3SOIPDgNode, B3SOIPDbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDDPbPtr, B3SOIPDDPbBinding, B3SOIPDdNodePrime, B3SOIPDbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDSPbPtr, B3SOIPDSPbBinding, B3SOIPDsNodePrime, B3SOIPDbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDBePtr, B3SOIPDBeBinding, B3SOIPDbNode, B3SOIPDeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDBgPtr, B3SOIPDBgBinding, B3SOIPDbNode, B3SOIPDgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDBdpPtr, B3SOIPDBdpBinding, B3SOIPDbNode, B3SOIPDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDBspPtr, B3SOIPDBspBinding, B3SOIPDbNode, B3SOIPDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDBbPtr, B3SOIPDBbBinding, B3SOIPDbNode, B3SOIPDbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDEgPtr, B3SOIPDEgBinding, B3SOIPDeNode, B3SOIPDgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDEdpPtr, B3SOIPDEdpBinding, B3SOIPDeNode, B3SOIPDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDEspPtr, B3SOIPDEspBinding, B3SOIPDeNode, B3SOIPDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDGePtr, B3SOIPDGeBinding, B3SOIPDgNode, B3SOIPDeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDDPePtr, B3SOIPDDPeBinding, B3SOIPDdNodePrime, B3SOIPDeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDSPePtr, B3SOIPDSPeBinding, B3SOIPDsNodePrime, B3SOIPDeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDEePtr, B3SOIPDEeBinding, B3SOIPDeNode, B3SOIPDeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDGgPtr, B3SOIPDGgBinding, B3SOIPDgNode, B3SOIPDgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDGdpPtr, B3SOIPDGdpBinding, B3SOIPDgNode, B3SOIPDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDGspPtr, B3SOIPDGspBinding, B3SOIPDgNode, B3SOIPDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDDPgPtr, B3SOIPDDPgBinding, B3SOIPDdNodePrime, B3SOIPDgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDDPdpPtr, B3SOIPDDPdpBinding, B3SOIPDdNodePrime, B3SOIPDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDDPspPtr, B3SOIPDDPspBinding, B3SOIPDdNodePrime, B3SOIPDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDDPdPtr, B3SOIPDDPdBinding, B3SOIPDdNodePrime, B3SOIPDdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDSPgPtr, B3SOIPDSPgBinding, B3SOIPDsNodePrime, B3SOIPDgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDSPdpPtr, B3SOIPDSPdpBinding, B3SOIPDsNodePrime, B3SOIPDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDSPspPtr, B3SOIPDSPspBinding, B3SOIPDsNodePrime, B3SOIPDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDSPsPtr, B3SOIPDSPsBinding, B3SOIPDsNodePrime, B3SOIPDsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDDdPtr, B3SOIPDDdBinding, B3SOIPDdNode, B3SOIPDdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDDdpPtr, B3SOIPDDdpBinding, B3SOIPDdNode, B3SOIPDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDSsPtr, B3SOIPDSsBinding, B3SOIPDsNode, B3SOIPDsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDSspPtr, B3SOIPDSspBinding, B3SOIPDsNode, B3SOIPDsNodePrime); + if (here->B3SOIPDdebugMod != 0) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDVbsPtr, B3SOIPDVbsBinding, B3SOIPDvbsNode, B3SOIPDvbsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDIdsPtr, B3SOIPDIdsBinding, B3SOIPDidsNode, B3SOIPDidsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDIcPtr, B3SOIPDIcBinding, B3SOIPDicNode, B3SOIPDicNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDIbsPtr, B3SOIPDIbsBinding, B3SOIPDibsNode, B3SOIPDibsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDIbdPtr, B3SOIPDIbdBinding, B3SOIPDibdNode, B3SOIPDibdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDIiiPtr, B3SOIPDIiiBinding, B3SOIPDiiiNode, B3SOIPDiiiNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDIgPtr, B3SOIPDIgBinding, B3SOIPDigNode, B3SOIPDigNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDGiggPtr, B3SOIPDGiggBinding, B3SOIPDgiggNode, B3SOIPDgiggNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDGigdPtr, B3SOIPDGigdBinding, B3SOIPDgigdNode, B3SOIPDgigdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDGigbPtr, B3SOIPDGigbBinding, B3SOIPDgigbNode, B3SOIPDgigbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDIgidlPtr, B3SOIPDIgidlBinding, B3SOIPDigidlNode, B3SOIPDigidlNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDItunPtr, B3SOIPDItunBinding, B3SOIPDitunNode, B3SOIPDitunNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDIbpPtr, B3SOIPDIbpBinding, B3SOIPDibpNode, B3SOIPDibpNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDCbbPtr, B3SOIPDCbbBinding, B3SOIPDcbbNode, B3SOIPDcbbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDCbdPtr, B3SOIPDCbdBinding, B3SOIPDcbdNode, B3SOIPDcbdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDCbgPtr, B3SOIPDCbgBinding, B3SOIPDcbgNode, B3SOIPDcbgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDQbfPtr, B3SOIPDQbfBinding, B3SOIPDqbfNode, B3SOIPDqbfNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDQjsPtr, B3SOIPDQjsBinding, B3SOIPDqjsNode, B3SOIPDqjsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B3SOIPDQjdPtr, B3SOIPDQjdBinding, B3SOIPDqjdNode, B3SOIPDqjdNode); + } + } + } + + return (OK) ; +} + +int +B3SOIPDbindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + B3SOIPDmodel *model = (B3SOIPDmodel *)inModel ; + B3SOIPDinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the B3SOIPD models */ + for ( ; model != NULL ; model = B3SOIPDnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = B3SOIPDinstances(model); here != NULL ; here = B3SOIPDnextInstance(here)) + { + if ((model->B3SOIPDshMod == 1) && (here->B3SOIPDrth0 != 0.0)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDTemptempPtr, B3SOIPDTemptempBinding, B3SOIPDtempNode, B3SOIPDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDTempdpPtr, B3SOIPDTempdpBinding, B3SOIPDtempNode, B3SOIPDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDTempspPtr, B3SOIPDTempspBinding, B3SOIPDtempNode, B3SOIPDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDTempgPtr, B3SOIPDTempgBinding, B3SOIPDtempNode, B3SOIPDgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDTempbPtr, B3SOIPDTempbBinding, B3SOIPDtempNode, B3SOIPDbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDGtempPtr, B3SOIPDGtempBinding, B3SOIPDgNode, B3SOIPDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDDPtempPtr, B3SOIPDDPtempBinding, B3SOIPDdNodePrime, B3SOIPDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDSPtempPtr, B3SOIPDSPtempBinding, B3SOIPDsNodePrime, B3SOIPDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDEtempPtr, B3SOIPDEtempBinding, B3SOIPDeNode, B3SOIPDtempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDBtempPtr, B3SOIPDBtempBinding, B3SOIPDbNode, B3SOIPDtempNode); + if (here->B3SOIPDbodyMod == 1) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDPtempPtr, B3SOIPDPtempBinding, B3SOIPDpNode, B3SOIPDtempNode); + } + } + if (here->B3SOIPDbodyMod == 2) + { + } + else if (here->B3SOIPDbodyMod == 1) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDBpPtr, B3SOIPDBpBinding, B3SOIPDbNode, B3SOIPDpNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDPbPtr, B3SOIPDPbBinding, B3SOIPDpNode, B3SOIPDbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDPpPtr, B3SOIPDPpBinding, B3SOIPDpNode, B3SOIPDpNode); + } + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDEbPtr, B3SOIPDEbBinding, B3SOIPDeNode, B3SOIPDbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDGbPtr, B3SOIPDGbBinding, B3SOIPDgNode, B3SOIPDbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDDPbPtr, B3SOIPDDPbBinding, B3SOIPDdNodePrime, B3SOIPDbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDSPbPtr, B3SOIPDSPbBinding, B3SOIPDsNodePrime, B3SOIPDbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDBePtr, B3SOIPDBeBinding, B3SOIPDbNode, B3SOIPDeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDBgPtr, B3SOIPDBgBinding, B3SOIPDbNode, B3SOIPDgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDBdpPtr, B3SOIPDBdpBinding, B3SOIPDbNode, B3SOIPDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDBspPtr, B3SOIPDBspBinding, B3SOIPDbNode, B3SOIPDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDBbPtr, B3SOIPDBbBinding, B3SOIPDbNode, B3SOIPDbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDEgPtr, B3SOIPDEgBinding, B3SOIPDeNode, B3SOIPDgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDEdpPtr, B3SOIPDEdpBinding, B3SOIPDeNode, B3SOIPDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDEspPtr, B3SOIPDEspBinding, B3SOIPDeNode, B3SOIPDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDGePtr, B3SOIPDGeBinding, B3SOIPDgNode, B3SOIPDeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDDPePtr, B3SOIPDDPeBinding, B3SOIPDdNodePrime, B3SOIPDeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDSPePtr, B3SOIPDSPeBinding, B3SOIPDsNodePrime, B3SOIPDeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDEePtr, B3SOIPDEeBinding, B3SOIPDeNode, B3SOIPDeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDGgPtr, B3SOIPDGgBinding, B3SOIPDgNode, B3SOIPDgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDGdpPtr, B3SOIPDGdpBinding, B3SOIPDgNode, B3SOIPDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDGspPtr, B3SOIPDGspBinding, B3SOIPDgNode, B3SOIPDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDDPgPtr, B3SOIPDDPgBinding, B3SOIPDdNodePrime, B3SOIPDgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDDPdpPtr, B3SOIPDDPdpBinding, B3SOIPDdNodePrime, B3SOIPDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDDPspPtr, B3SOIPDDPspBinding, B3SOIPDdNodePrime, B3SOIPDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDDPdPtr, B3SOIPDDPdBinding, B3SOIPDdNodePrime, B3SOIPDdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDSPgPtr, B3SOIPDSPgBinding, B3SOIPDsNodePrime, B3SOIPDgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDSPdpPtr, B3SOIPDSPdpBinding, B3SOIPDsNodePrime, B3SOIPDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDSPspPtr, B3SOIPDSPspBinding, B3SOIPDsNodePrime, B3SOIPDsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDSPsPtr, B3SOIPDSPsBinding, B3SOIPDsNodePrime, B3SOIPDsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDDdPtr, B3SOIPDDdBinding, B3SOIPDdNode, B3SOIPDdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDDdpPtr, B3SOIPDDdpBinding, B3SOIPDdNode, B3SOIPDdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDSsPtr, B3SOIPDSsBinding, B3SOIPDsNode, B3SOIPDsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDSspPtr, B3SOIPDSspBinding, B3SOIPDsNode, B3SOIPDsNodePrime); + if (here->B3SOIPDdebugMod != 0) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDVbsPtr, B3SOIPDVbsBinding, B3SOIPDvbsNode, B3SOIPDvbsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDIdsPtr, B3SOIPDIdsBinding, B3SOIPDidsNode, B3SOIPDidsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDIcPtr, B3SOIPDIcBinding, B3SOIPDicNode, B3SOIPDicNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDIbsPtr, B3SOIPDIbsBinding, B3SOIPDibsNode, B3SOIPDibsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDIbdPtr, B3SOIPDIbdBinding, B3SOIPDibdNode, B3SOIPDibdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDIiiPtr, B3SOIPDIiiBinding, B3SOIPDiiiNode, B3SOIPDiiiNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDIgPtr, B3SOIPDIgBinding, B3SOIPDigNode, B3SOIPDigNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDGiggPtr, B3SOIPDGiggBinding, B3SOIPDgiggNode, B3SOIPDgiggNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDGigdPtr, B3SOIPDGigdBinding, B3SOIPDgigdNode, B3SOIPDgigdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDGigbPtr, B3SOIPDGigbBinding, B3SOIPDgigbNode, B3SOIPDgigbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDIgidlPtr, B3SOIPDIgidlBinding, B3SOIPDigidlNode, B3SOIPDigidlNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDItunPtr, B3SOIPDItunBinding, B3SOIPDitunNode, B3SOIPDitunNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDIbpPtr, B3SOIPDIbpBinding, B3SOIPDibpNode, B3SOIPDibpNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDCbbPtr, B3SOIPDCbbBinding, B3SOIPDcbbNode, B3SOIPDcbbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDCbdPtr, B3SOIPDCbdBinding, B3SOIPDcbdNode, B3SOIPDcbdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDCbgPtr, B3SOIPDCbgBinding, B3SOIPDcbgNode, B3SOIPDcbgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDQbfPtr, B3SOIPDQbfBinding, B3SOIPDqbfNode, B3SOIPDqbfNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDQjsPtr, B3SOIPDQjsBinding, B3SOIPDqjsNode, B3SOIPDqjsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B3SOIPDQjdPtr, B3SOIPDQjdBinding, B3SOIPDqjdNode, B3SOIPDqjdNode); + } + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/bsim3soi_pd/b3soipddef.h b/src/spicelib/devices/bsim3soi_pd/b3soipddef.h index 769eca872..779a92c6e 100644 --- a/src/spicelib/devices/bsim3soi_pd/b3soipddef.h +++ b/src/spicelib/devices/bsim3soi_pd/b3soipddef.h @@ -385,6 +385,73 @@ typedef struct sB3SOIPDinstance double **B3SOIPDnVar; #endif /* NONOISE */ +#ifdef KLU + BindElement *B3SOIPDTemptempBinding ; + BindElement *B3SOIPDTempdpBinding ; + BindElement *B3SOIPDTempspBinding ; + BindElement *B3SOIPDTempgBinding ; + BindElement *B3SOIPDTempbBinding ; + BindElement *B3SOIPDGtempBinding ; + BindElement *B3SOIPDDPtempBinding ; + BindElement *B3SOIPDSPtempBinding ; + BindElement *B3SOIPDEtempBinding ; + BindElement *B3SOIPDBtempBinding ; + BindElement *B3SOIPDPtempBinding ; + BindElement *B3SOIPDBpBinding ; + BindElement *B3SOIPDPbBinding ; + BindElement *B3SOIPDPpBinding ; + BindElement *B3SOIPDEbBinding ; + BindElement *B3SOIPDGbBinding ; + BindElement *B3SOIPDDPbBinding ; + BindElement *B3SOIPDSPbBinding ; + BindElement *B3SOIPDBeBinding ; + BindElement *B3SOIPDBgBinding ; + BindElement *B3SOIPDBdpBinding ; + BindElement *B3SOIPDBspBinding ; + BindElement *B3SOIPDBbBinding ; + BindElement *B3SOIPDEgBinding ; + BindElement *B3SOIPDEdpBinding ; + BindElement *B3SOIPDEspBinding ; + BindElement *B3SOIPDGeBinding ; + BindElement *B3SOIPDDPeBinding ; + BindElement *B3SOIPDSPeBinding ; + BindElement *B3SOIPDEeBinding ; + BindElement *B3SOIPDGgBinding ; + BindElement *B3SOIPDGdpBinding ; + BindElement *B3SOIPDGspBinding ; + BindElement *B3SOIPDDPgBinding ; + BindElement *B3SOIPDDPdpBinding ; + BindElement *B3SOIPDDPspBinding ; + BindElement *B3SOIPDDPdBinding ; + BindElement *B3SOIPDSPgBinding ; + BindElement *B3SOIPDSPdpBinding ; + BindElement *B3SOIPDSPspBinding ; + BindElement *B3SOIPDSPsBinding ; + BindElement *B3SOIPDDdBinding ; + BindElement *B3SOIPDDdpBinding ; + BindElement *B3SOIPDSsBinding ; + BindElement *B3SOIPDSspBinding ; + BindElement *B3SOIPDVbsBinding ; + BindElement *B3SOIPDIdsBinding ; + BindElement *B3SOIPDIcBinding ; + BindElement *B3SOIPDIbsBinding ; + BindElement *B3SOIPDIbdBinding ; + BindElement *B3SOIPDIiiBinding ; + BindElement *B3SOIPDIgBinding ; + BindElement *B3SOIPDGiggBinding ; + BindElement *B3SOIPDGigdBinding ; + BindElement *B3SOIPDGigbBinding ; + BindElement *B3SOIPDIgidlBinding ; + BindElement *B3SOIPDItunBinding ; + BindElement *B3SOIPDIbpBinding ; + BindElement *B3SOIPDCbbBinding ; + BindElement *B3SOIPDCbdBinding ; + BindElement *B3SOIPDCbgBinding ; + BindElement *B3SOIPDQbfBinding ; + BindElement *B3SOIPDQjsBinding ; + BindElement *B3SOIPDQjdBinding ; +#endif + } B3SOIPDinstance ; struct b3soipdSizeDependParam diff --git a/src/spicelib/devices/bsim3soi_pd/b3soipdext.h b/src/spicelib/devices/bsim3soi_pd/b3soipdext.h index 78fb436b0..2ca5f109f 100644 --- a/src/spicelib/devices/bsim3soi_pd/b3soipdext.h +++ b/src/spicelib/devices/bsim3soi_pd/b3soipdext.h @@ -28,3 +28,9 @@ extern int B3SOIPDtemp(GENmodel*,CKTcircuit*); extern int B3SOIPDtrunc(GENmodel*,CKTcircuit*,double*); extern int B3SOIPDnoise(int,int,GENmodel*,CKTcircuit*,Ndata*,double*); extern int B3SOIPDunsetup(GENmodel*,CKTcircuit*); + +#ifdef KLU +extern int B3SOIPDbindCSC (GENmodel*, CKTcircuit*) ; +extern int B3SOIPDbindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int B3SOIPDbindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/bsim3soi_pd/b3soipdinit.c b/src/spicelib/devices/bsim3soi_pd/b3soipdinit.c index 381ea938e..bbd74b700 100644 --- a/src/spicelib/devices/bsim3soi_pd/b3soipdinit.c +++ b/src/spicelib/devices/bsim3soi_pd/b3soipdinit.c @@ -65,6 +65,11 @@ SPICEdev B3SOIPDinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = B3SOIPDbindCSC, + .DEVbindCSCComplex = B3SOIPDbindCSCComplex, + .DEVbindCSCComplexToReal = B3SOIPDbindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/bsim3v0/Makefile.am b/src/spicelib/devices/bsim3v0/Makefile.am index 4db27a86d..8273566bf 100644 --- a/src/spicelib/devices/bsim3v0/Makefile.am +++ b/src/spicelib/devices/bsim3v0/Makefile.am @@ -27,6 +27,9 @@ libbsim3v0_la_SOURCES = \ bsim3v0itf.h +if KLU_WANTED +libbsim3v0_la_SOURCES += b3v0bindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) diff --git a/src/spicelib/devices/bsim3v0/b3v0bindCSC.c b/src/spicelib/devices/bsim3v0/b3v0bindCSC.c new file mode 100644 index 000000000..179aa4025 --- /dev/null +++ b/src/spicelib/devices/bsim3v0/b3v0bindCSC.c @@ -0,0 +1,179 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "bsim3v0def.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +BSIM3v0bindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + BSIM3v0model *model = (BSIM3v0model *)inModel ; + BSIM3v0instance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the BSIM3v0 models */ + for ( ; model != NULL ; model = BSIM3v0nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = BSIM3v0instances(model); here != NULL ; here = BSIM3v0nextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(BSIM3v0DdPtr, BSIM3v0DdBinding, BSIM3v0dNode, BSIM3v0dNode); + CREATE_KLU_BINDING_TABLE(BSIM3v0GgPtr, BSIM3v0GgBinding, BSIM3v0gNode, BSIM3v0gNode); + CREATE_KLU_BINDING_TABLE(BSIM3v0SsPtr, BSIM3v0SsBinding, BSIM3v0sNode, BSIM3v0sNode); + CREATE_KLU_BINDING_TABLE(BSIM3v0BbPtr, BSIM3v0BbBinding, BSIM3v0bNode, BSIM3v0bNode); + CREATE_KLU_BINDING_TABLE(BSIM3v0DPdpPtr, BSIM3v0DPdpBinding, BSIM3v0dNodePrime, BSIM3v0dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v0SPspPtr, BSIM3v0SPspBinding, BSIM3v0sNodePrime, BSIM3v0sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v0DdpPtr, BSIM3v0DdpBinding, BSIM3v0dNode, BSIM3v0dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v0GbPtr, BSIM3v0GbBinding, BSIM3v0gNode, BSIM3v0bNode); + CREATE_KLU_BINDING_TABLE(BSIM3v0GdpPtr, BSIM3v0GdpBinding, BSIM3v0gNode, BSIM3v0dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v0GspPtr, BSIM3v0GspBinding, BSIM3v0gNode, BSIM3v0sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v0SspPtr, BSIM3v0SspBinding, BSIM3v0sNode, BSIM3v0sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v0BdpPtr, BSIM3v0BdpBinding, BSIM3v0bNode, BSIM3v0dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v0BspPtr, BSIM3v0BspBinding, BSIM3v0bNode, BSIM3v0sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v0DPspPtr, BSIM3v0DPspBinding, BSIM3v0dNodePrime, BSIM3v0sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v0DPdPtr, BSIM3v0DPdBinding, BSIM3v0dNodePrime, BSIM3v0dNode); + CREATE_KLU_BINDING_TABLE(BSIM3v0BgPtr, BSIM3v0BgBinding, BSIM3v0bNode, BSIM3v0gNode); + CREATE_KLU_BINDING_TABLE(BSIM3v0DPgPtr, BSIM3v0DPgBinding, BSIM3v0dNodePrime, BSIM3v0gNode); + CREATE_KLU_BINDING_TABLE(BSIM3v0SPgPtr, BSIM3v0SPgBinding, BSIM3v0sNodePrime, BSIM3v0gNode); + CREATE_KLU_BINDING_TABLE(BSIM3v0SPsPtr, BSIM3v0SPsBinding, BSIM3v0sNodePrime, BSIM3v0sNode); + CREATE_KLU_BINDING_TABLE(BSIM3v0DPbPtr, BSIM3v0DPbBinding, BSIM3v0dNodePrime, BSIM3v0bNode); + CREATE_KLU_BINDING_TABLE(BSIM3v0SPbPtr, BSIM3v0SPbBinding, BSIM3v0sNodePrime, BSIM3v0bNode); + CREATE_KLU_BINDING_TABLE(BSIM3v0SPdpPtr, BSIM3v0SPdpBinding, BSIM3v0sNodePrime, BSIM3v0dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v0QqPtr, BSIM3v0QqBinding, BSIM3v0qNode, BSIM3v0qNode); + CREATE_KLU_BINDING_TABLE(BSIM3v0QdpPtr, BSIM3v0QdpBinding, BSIM3v0qNode, BSIM3v0dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v0QspPtr, BSIM3v0QspBinding, BSIM3v0qNode, BSIM3v0sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v0QgPtr, BSIM3v0QgBinding, BSIM3v0qNode, BSIM3v0gNode); + CREATE_KLU_BINDING_TABLE(BSIM3v0QbPtr, BSIM3v0QbBinding, BSIM3v0qNode, BSIM3v0bNode); + CREATE_KLU_BINDING_TABLE(BSIM3v0DPqPtr, BSIM3v0DPqBinding, BSIM3v0dNodePrime, BSIM3v0qNode); + CREATE_KLU_BINDING_TABLE(BSIM3v0SPqPtr, BSIM3v0SPqBinding, BSIM3v0sNodePrime, BSIM3v0qNode); + CREATE_KLU_BINDING_TABLE(BSIM3v0GqPtr, BSIM3v0GqBinding, BSIM3v0gNode, BSIM3v0qNode); + CREATE_KLU_BINDING_TABLE(BSIM3v0BqPtr, BSIM3v0BqBinding, BSIM3v0bNode, BSIM3v0qNode); + } + } + + return (OK) ; +} + +int +BSIM3v0bindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + BSIM3v0model *model = (BSIM3v0model *)inModel ; + BSIM3v0instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the BSIM3v0 models */ + for ( ; model != NULL ; model = BSIM3v0nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = BSIM3v0instances(model); here != NULL ; here = BSIM3v0nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0DdPtr, BSIM3v0DdBinding, BSIM3v0dNode, BSIM3v0dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0GgPtr, BSIM3v0GgBinding, BSIM3v0gNode, BSIM3v0gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0SsPtr, BSIM3v0SsBinding, BSIM3v0sNode, BSIM3v0sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0BbPtr, BSIM3v0BbBinding, BSIM3v0bNode, BSIM3v0bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0DPdpPtr, BSIM3v0DPdpBinding, BSIM3v0dNodePrime, BSIM3v0dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0SPspPtr, BSIM3v0SPspBinding, BSIM3v0sNodePrime, BSIM3v0sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0DdpPtr, BSIM3v0DdpBinding, BSIM3v0dNode, BSIM3v0dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0GbPtr, BSIM3v0GbBinding, BSIM3v0gNode, BSIM3v0bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0GdpPtr, BSIM3v0GdpBinding, BSIM3v0gNode, BSIM3v0dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0GspPtr, BSIM3v0GspBinding, BSIM3v0gNode, BSIM3v0sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0SspPtr, BSIM3v0SspBinding, BSIM3v0sNode, BSIM3v0sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0BdpPtr, BSIM3v0BdpBinding, BSIM3v0bNode, BSIM3v0dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0BspPtr, BSIM3v0BspBinding, BSIM3v0bNode, BSIM3v0sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0DPspPtr, BSIM3v0DPspBinding, BSIM3v0dNodePrime, BSIM3v0sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0DPdPtr, BSIM3v0DPdBinding, BSIM3v0dNodePrime, BSIM3v0dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0BgPtr, BSIM3v0BgBinding, BSIM3v0bNode, BSIM3v0gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0DPgPtr, BSIM3v0DPgBinding, BSIM3v0dNodePrime, BSIM3v0gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0SPgPtr, BSIM3v0SPgBinding, BSIM3v0sNodePrime, BSIM3v0gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0SPsPtr, BSIM3v0SPsBinding, BSIM3v0sNodePrime, BSIM3v0sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0DPbPtr, BSIM3v0DPbBinding, BSIM3v0dNodePrime, BSIM3v0bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0SPbPtr, BSIM3v0SPbBinding, BSIM3v0sNodePrime, BSIM3v0bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0SPdpPtr, BSIM3v0SPdpBinding, BSIM3v0sNodePrime, BSIM3v0dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0QqPtr, BSIM3v0QqBinding, BSIM3v0qNode, BSIM3v0qNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0QdpPtr, BSIM3v0QdpBinding, BSIM3v0qNode, BSIM3v0dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0QspPtr, BSIM3v0QspBinding, BSIM3v0qNode, BSIM3v0sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0QgPtr, BSIM3v0QgBinding, BSIM3v0qNode, BSIM3v0gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0QbPtr, BSIM3v0QbBinding, BSIM3v0qNode, BSIM3v0bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0DPqPtr, BSIM3v0DPqBinding, BSIM3v0dNodePrime, BSIM3v0qNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0SPqPtr, BSIM3v0SPqBinding, BSIM3v0sNodePrime, BSIM3v0qNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0GqPtr, BSIM3v0GqBinding, BSIM3v0gNode, BSIM3v0qNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v0BqPtr, BSIM3v0BqBinding, BSIM3v0bNode, BSIM3v0qNode); + } + } + + return (OK) ; +} + +int +BSIM3v0bindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + BSIM3v0model *model = (BSIM3v0model *)inModel ; + BSIM3v0instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the BSIM3v0 models */ + for ( ; model != NULL ; model = BSIM3v0nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = BSIM3v0instances(model); here != NULL ; here = BSIM3v0nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0DdPtr, BSIM3v0DdBinding, BSIM3v0dNode, BSIM3v0dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0GgPtr, BSIM3v0GgBinding, BSIM3v0gNode, BSIM3v0gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0SsPtr, BSIM3v0SsBinding, BSIM3v0sNode, BSIM3v0sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0BbPtr, BSIM3v0BbBinding, BSIM3v0bNode, BSIM3v0bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0DPdpPtr, BSIM3v0DPdpBinding, BSIM3v0dNodePrime, BSIM3v0dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0SPspPtr, BSIM3v0SPspBinding, BSIM3v0sNodePrime, BSIM3v0sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0DdpPtr, BSIM3v0DdpBinding, BSIM3v0dNode, BSIM3v0dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0GbPtr, BSIM3v0GbBinding, BSIM3v0gNode, BSIM3v0bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0GdpPtr, BSIM3v0GdpBinding, BSIM3v0gNode, BSIM3v0dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0GspPtr, BSIM3v0GspBinding, BSIM3v0gNode, BSIM3v0sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0SspPtr, BSIM3v0SspBinding, BSIM3v0sNode, BSIM3v0sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0BdpPtr, BSIM3v0BdpBinding, BSIM3v0bNode, BSIM3v0dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0BspPtr, BSIM3v0BspBinding, BSIM3v0bNode, BSIM3v0sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0DPspPtr, BSIM3v0DPspBinding, BSIM3v0dNodePrime, BSIM3v0sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0DPdPtr, BSIM3v0DPdBinding, BSIM3v0dNodePrime, BSIM3v0dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0BgPtr, BSIM3v0BgBinding, BSIM3v0bNode, BSIM3v0gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0DPgPtr, BSIM3v0DPgBinding, BSIM3v0dNodePrime, BSIM3v0gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0SPgPtr, BSIM3v0SPgBinding, BSIM3v0sNodePrime, BSIM3v0gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0SPsPtr, BSIM3v0SPsBinding, BSIM3v0sNodePrime, BSIM3v0sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0DPbPtr, BSIM3v0DPbBinding, BSIM3v0dNodePrime, BSIM3v0bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0SPbPtr, BSIM3v0SPbBinding, BSIM3v0sNodePrime, BSIM3v0bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0SPdpPtr, BSIM3v0SPdpBinding, BSIM3v0sNodePrime, BSIM3v0dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0QqPtr, BSIM3v0QqBinding, BSIM3v0qNode, BSIM3v0qNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0QdpPtr, BSIM3v0QdpBinding, BSIM3v0qNode, BSIM3v0dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0QspPtr, BSIM3v0QspBinding, BSIM3v0qNode, BSIM3v0sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0QgPtr, BSIM3v0QgBinding, BSIM3v0qNode, BSIM3v0gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0QbPtr, BSIM3v0QbBinding, BSIM3v0qNode, BSIM3v0bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0DPqPtr, BSIM3v0DPqBinding, BSIM3v0dNodePrime, BSIM3v0qNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0SPqPtr, BSIM3v0SPqBinding, BSIM3v0sNodePrime, BSIM3v0qNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0GqPtr, BSIM3v0GqBinding, BSIM3v0gNode, BSIM3v0qNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v0BqPtr, BSIM3v0BqBinding, BSIM3v0bNode, BSIM3v0qNode); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/bsim3v0/bsim3v0def.h b/src/spicelib/devices/bsim3v0/bsim3v0def.h index 062d010df..de1b8a4c2 100644 --- a/src/spicelib/devices/bsim3v0/bsim3v0def.h +++ b/src/spicelib/devices/bsim3v0/bsim3v0def.h @@ -191,6 +191,40 @@ typedef struct sBSIM3v0instance double **BSIM3v0nVar; #endif /* NONOISE */ +#ifdef KLU + BindElement *BSIM3v0DdBinding ; + BindElement *BSIM3v0GgBinding ; + BindElement *BSIM3v0SsBinding ; + BindElement *BSIM3v0BbBinding ; + BindElement *BSIM3v0DPdpBinding ; + BindElement *BSIM3v0SPspBinding ; + BindElement *BSIM3v0DdpBinding ; + BindElement *BSIM3v0GbBinding ; + BindElement *BSIM3v0GdpBinding ; + BindElement *BSIM3v0GspBinding ; + BindElement *BSIM3v0SspBinding ; + BindElement *BSIM3v0BdpBinding ; + BindElement *BSIM3v0BspBinding ; + BindElement *BSIM3v0DPspBinding ; + BindElement *BSIM3v0DPdBinding ; + BindElement *BSIM3v0BgBinding ; + BindElement *BSIM3v0DPgBinding ; + BindElement *BSIM3v0SPgBinding ; + BindElement *BSIM3v0SPsBinding ; + BindElement *BSIM3v0DPbBinding ; + BindElement *BSIM3v0SPbBinding ; + BindElement *BSIM3v0SPdpBinding ; + BindElement *BSIM3v0QqBinding ; + BindElement *BSIM3v0QdpBinding ; + BindElement *BSIM3v0QspBinding ; + BindElement *BSIM3v0QgBinding ; + BindElement *BSIM3v0QbBinding ; + BindElement *BSIM3v0DPqBinding ; + BindElement *BSIM3v0SPqBinding ; + BindElement *BSIM3v0GqBinding ; + BindElement *BSIM3v0BqBinding ; +#endif + } BSIM3v0instance ; struct bsim3v0SizeDependParam diff --git a/src/spicelib/devices/bsim3v0/bsim3v0ext.h b/src/spicelib/devices/bsim3v0/bsim3v0ext.h index 2c5fdfcf6..6d56a3b73 100644 --- a/src/spicelib/devices/bsim3v0/bsim3v0ext.h +++ b/src/spicelib/devices/bsim3v0/bsim3v0ext.h @@ -28,3 +28,8 @@ extern int BSIM3v0trunc(GENmodel*,CKTcircuit*,double*); extern int BSIM3v0noise(int,int,GENmodel*,CKTcircuit*,Ndata*,double*); extern int BSIM3v0unsetup(GENmodel *, CKTcircuit *); +#ifdef KLU +extern int BSIM3v0bindCSC (GENmodel*, CKTcircuit*) ; +extern int BSIM3v0bindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int BSIM3v0bindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/bsim3v0/bsim3v0init.c b/src/spicelib/devices/bsim3v0/bsim3v0init.c index 0b673bca9..6cf4353da 100644 --- a/src/spicelib/devices/bsim3v0/bsim3v0init.c +++ b/src/spicelib/devices/bsim3v0/bsim3v0init.c @@ -65,6 +65,11 @@ SPICEdev B3v0info = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = BSIM3v0bindCSC, + .DEVbindCSCComplex = BSIM3v0bindCSCComplex, + .DEVbindCSCComplexToReal = BSIM3v0bindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/bsim3v1/Makefile.am b/src/spicelib/devices/bsim3v1/Makefile.am index 9ede60cb9..3b22e68ce 100644 --- a/src/spicelib/devices/bsim3v1/Makefile.am +++ b/src/spicelib/devices/bsim3v1/Makefile.am @@ -28,6 +28,9 @@ libbsim3v1_la_SOURCES = \ bsim3v1itf.h +if KLU_WANTED +libbsim3v1_la_SOURCES += b3v1bindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) diff --git a/src/spicelib/devices/bsim3v1/b3v1bindCSC.c b/src/spicelib/devices/bsim3v1/b3v1bindCSC.c new file mode 100644 index 000000000..5e72f2bfa --- /dev/null +++ b/src/spicelib/devices/bsim3v1/b3v1bindCSC.c @@ -0,0 +1,179 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "bsim3v1def.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +BSIM3v1bindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + BSIM3v1model *model = (BSIM3v1model *)inModel ; + BSIM3v1instance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the BSIM3v1 models */ + for ( ; model != NULL ; model = BSIM3v1nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = BSIM3v1instances(model); here != NULL ; here = BSIM3v1nextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(BSIM3v1DdPtr, BSIM3v1DdBinding, BSIM3v1dNode, BSIM3v1dNode); + CREATE_KLU_BINDING_TABLE(BSIM3v1GgPtr, BSIM3v1GgBinding, BSIM3v1gNode, BSIM3v1gNode); + CREATE_KLU_BINDING_TABLE(BSIM3v1SsPtr, BSIM3v1SsBinding, BSIM3v1sNode, BSIM3v1sNode); + CREATE_KLU_BINDING_TABLE(BSIM3v1BbPtr, BSIM3v1BbBinding, BSIM3v1bNode, BSIM3v1bNode); + CREATE_KLU_BINDING_TABLE(BSIM3v1DPdpPtr, BSIM3v1DPdpBinding, BSIM3v1dNodePrime, BSIM3v1dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v1SPspPtr, BSIM3v1SPspBinding, BSIM3v1sNodePrime, BSIM3v1sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v1DdpPtr, BSIM3v1DdpBinding, BSIM3v1dNode, BSIM3v1dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v1GbPtr, BSIM3v1GbBinding, BSIM3v1gNode, BSIM3v1bNode); + CREATE_KLU_BINDING_TABLE(BSIM3v1GdpPtr, BSIM3v1GdpBinding, BSIM3v1gNode, BSIM3v1dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v1GspPtr, BSIM3v1GspBinding, BSIM3v1gNode, BSIM3v1sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v1SspPtr, BSIM3v1SspBinding, BSIM3v1sNode, BSIM3v1sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v1BdpPtr, BSIM3v1BdpBinding, BSIM3v1bNode, BSIM3v1dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v1BspPtr, BSIM3v1BspBinding, BSIM3v1bNode, BSIM3v1sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v1DPspPtr, BSIM3v1DPspBinding, BSIM3v1dNodePrime, BSIM3v1sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v1DPdPtr, BSIM3v1DPdBinding, BSIM3v1dNodePrime, BSIM3v1dNode); + CREATE_KLU_BINDING_TABLE(BSIM3v1BgPtr, BSIM3v1BgBinding, BSIM3v1bNode, BSIM3v1gNode); + CREATE_KLU_BINDING_TABLE(BSIM3v1DPgPtr, BSIM3v1DPgBinding, BSIM3v1dNodePrime, BSIM3v1gNode); + CREATE_KLU_BINDING_TABLE(BSIM3v1SPgPtr, BSIM3v1SPgBinding, BSIM3v1sNodePrime, BSIM3v1gNode); + CREATE_KLU_BINDING_TABLE(BSIM3v1SPsPtr, BSIM3v1SPsBinding, BSIM3v1sNodePrime, BSIM3v1sNode); + CREATE_KLU_BINDING_TABLE(BSIM3v1DPbPtr, BSIM3v1DPbBinding, BSIM3v1dNodePrime, BSIM3v1bNode); + CREATE_KLU_BINDING_TABLE(BSIM3v1SPbPtr, BSIM3v1SPbBinding, BSIM3v1sNodePrime, BSIM3v1bNode); + CREATE_KLU_BINDING_TABLE(BSIM3v1SPdpPtr, BSIM3v1SPdpBinding, BSIM3v1sNodePrime, BSIM3v1dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v1QqPtr, BSIM3v1QqBinding, BSIM3v1qNode, BSIM3v1qNode); + CREATE_KLU_BINDING_TABLE(BSIM3v1QdpPtr, BSIM3v1QdpBinding, BSIM3v1qNode, BSIM3v1dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v1QspPtr, BSIM3v1QspBinding, BSIM3v1qNode, BSIM3v1sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v1QgPtr, BSIM3v1QgBinding, BSIM3v1qNode, BSIM3v1gNode); + CREATE_KLU_BINDING_TABLE(BSIM3v1QbPtr, BSIM3v1QbBinding, BSIM3v1qNode, BSIM3v1bNode); + CREATE_KLU_BINDING_TABLE(BSIM3v1DPqPtr, BSIM3v1DPqBinding, BSIM3v1dNodePrime, BSIM3v1qNode); + CREATE_KLU_BINDING_TABLE(BSIM3v1SPqPtr, BSIM3v1SPqBinding, BSIM3v1sNodePrime, BSIM3v1qNode); + CREATE_KLU_BINDING_TABLE(BSIM3v1GqPtr, BSIM3v1GqBinding, BSIM3v1gNode, BSIM3v1qNode); + CREATE_KLU_BINDING_TABLE(BSIM3v1BqPtr, BSIM3v1BqBinding, BSIM3v1bNode, BSIM3v1qNode); + } + } + + return (OK) ; +} + +int +BSIM3v1bindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + BSIM3v1model *model = (BSIM3v1model *)inModel ; + BSIM3v1instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the BSIM3v1 models */ + for ( ; model != NULL ; model = BSIM3v1nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = BSIM3v1instances(model); here != NULL ; here = BSIM3v1nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1DdPtr, BSIM3v1DdBinding, BSIM3v1dNode, BSIM3v1dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1GgPtr, BSIM3v1GgBinding, BSIM3v1gNode, BSIM3v1gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1SsPtr, BSIM3v1SsBinding, BSIM3v1sNode, BSIM3v1sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1BbPtr, BSIM3v1BbBinding, BSIM3v1bNode, BSIM3v1bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1DPdpPtr, BSIM3v1DPdpBinding, BSIM3v1dNodePrime, BSIM3v1dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1SPspPtr, BSIM3v1SPspBinding, BSIM3v1sNodePrime, BSIM3v1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1DdpPtr, BSIM3v1DdpBinding, BSIM3v1dNode, BSIM3v1dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1GbPtr, BSIM3v1GbBinding, BSIM3v1gNode, BSIM3v1bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1GdpPtr, BSIM3v1GdpBinding, BSIM3v1gNode, BSIM3v1dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1GspPtr, BSIM3v1GspBinding, BSIM3v1gNode, BSIM3v1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1SspPtr, BSIM3v1SspBinding, BSIM3v1sNode, BSIM3v1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1BdpPtr, BSIM3v1BdpBinding, BSIM3v1bNode, BSIM3v1dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1BspPtr, BSIM3v1BspBinding, BSIM3v1bNode, BSIM3v1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1DPspPtr, BSIM3v1DPspBinding, BSIM3v1dNodePrime, BSIM3v1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1DPdPtr, BSIM3v1DPdBinding, BSIM3v1dNodePrime, BSIM3v1dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1BgPtr, BSIM3v1BgBinding, BSIM3v1bNode, BSIM3v1gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1DPgPtr, BSIM3v1DPgBinding, BSIM3v1dNodePrime, BSIM3v1gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1SPgPtr, BSIM3v1SPgBinding, BSIM3v1sNodePrime, BSIM3v1gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1SPsPtr, BSIM3v1SPsBinding, BSIM3v1sNodePrime, BSIM3v1sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1DPbPtr, BSIM3v1DPbBinding, BSIM3v1dNodePrime, BSIM3v1bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1SPbPtr, BSIM3v1SPbBinding, BSIM3v1sNodePrime, BSIM3v1bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1SPdpPtr, BSIM3v1SPdpBinding, BSIM3v1sNodePrime, BSIM3v1dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1QqPtr, BSIM3v1QqBinding, BSIM3v1qNode, BSIM3v1qNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1QdpPtr, BSIM3v1QdpBinding, BSIM3v1qNode, BSIM3v1dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1QspPtr, BSIM3v1QspBinding, BSIM3v1qNode, BSIM3v1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1QgPtr, BSIM3v1QgBinding, BSIM3v1qNode, BSIM3v1gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1QbPtr, BSIM3v1QbBinding, BSIM3v1qNode, BSIM3v1bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1DPqPtr, BSIM3v1DPqBinding, BSIM3v1dNodePrime, BSIM3v1qNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1SPqPtr, BSIM3v1SPqBinding, BSIM3v1sNodePrime, BSIM3v1qNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1GqPtr, BSIM3v1GqBinding, BSIM3v1gNode, BSIM3v1qNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v1BqPtr, BSIM3v1BqBinding, BSIM3v1bNode, BSIM3v1qNode); + } + } + + return (OK) ; +} + +int +BSIM3v1bindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + BSIM3v1model *model = (BSIM3v1model *)inModel ; + BSIM3v1instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the BSIM3v1 models */ + for ( ; model != NULL ; model = BSIM3v1nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = BSIM3v1instances(model); here != NULL ; here = BSIM3v1nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1DdPtr, BSIM3v1DdBinding, BSIM3v1dNode, BSIM3v1dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1GgPtr, BSIM3v1GgBinding, BSIM3v1gNode, BSIM3v1gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1SsPtr, BSIM3v1SsBinding, BSIM3v1sNode, BSIM3v1sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1BbPtr, BSIM3v1BbBinding, BSIM3v1bNode, BSIM3v1bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1DPdpPtr, BSIM3v1DPdpBinding, BSIM3v1dNodePrime, BSIM3v1dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1SPspPtr, BSIM3v1SPspBinding, BSIM3v1sNodePrime, BSIM3v1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1DdpPtr, BSIM3v1DdpBinding, BSIM3v1dNode, BSIM3v1dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1GbPtr, BSIM3v1GbBinding, BSIM3v1gNode, BSIM3v1bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1GdpPtr, BSIM3v1GdpBinding, BSIM3v1gNode, BSIM3v1dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1GspPtr, BSIM3v1GspBinding, BSIM3v1gNode, BSIM3v1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1SspPtr, BSIM3v1SspBinding, BSIM3v1sNode, BSIM3v1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1BdpPtr, BSIM3v1BdpBinding, BSIM3v1bNode, BSIM3v1dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1BspPtr, BSIM3v1BspBinding, BSIM3v1bNode, BSIM3v1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1DPspPtr, BSIM3v1DPspBinding, BSIM3v1dNodePrime, BSIM3v1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1DPdPtr, BSIM3v1DPdBinding, BSIM3v1dNodePrime, BSIM3v1dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1BgPtr, BSIM3v1BgBinding, BSIM3v1bNode, BSIM3v1gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1DPgPtr, BSIM3v1DPgBinding, BSIM3v1dNodePrime, BSIM3v1gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1SPgPtr, BSIM3v1SPgBinding, BSIM3v1sNodePrime, BSIM3v1gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1SPsPtr, BSIM3v1SPsBinding, BSIM3v1sNodePrime, BSIM3v1sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1DPbPtr, BSIM3v1DPbBinding, BSIM3v1dNodePrime, BSIM3v1bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1SPbPtr, BSIM3v1SPbBinding, BSIM3v1sNodePrime, BSIM3v1bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1SPdpPtr, BSIM3v1SPdpBinding, BSIM3v1sNodePrime, BSIM3v1dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1QqPtr, BSIM3v1QqBinding, BSIM3v1qNode, BSIM3v1qNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1QdpPtr, BSIM3v1QdpBinding, BSIM3v1qNode, BSIM3v1dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1QspPtr, BSIM3v1QspBinding, BSIM3v1qNode, BSIM3v1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1QgPtr, BSIM3v1QgBinding, BSIM3v1qNode, BSIM3v1gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1QbPtr, BSIM3v1QbBinding, BSIM3v1qNode, BSIM3v1bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1DPqPtr, BSIM3v1DPqBinding, BSIM3v1dNodePrime, BSIM3v1qNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1SPqPtr, BSIM3v1SPqBinding, BSIM3v1sNodePrime, BSIM3v1qNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1GqPtr, BSIM3v1GqBinding, BSIM3v1gNode, BSIM3v1qNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v1BqPtr, BSIM3v1BqBinding, BSIM3v1bNode, BSIM3v1qNode); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/bsim3v1/bsim3v1def.h b/src/spicelib/devices/bsim3v1/bsim3v1def.h index be9f83846..c37679eed 100644 --- a/src/spicelib/devices/bsim3v1/bsim3v1def.h +++ b/src/spicelib/devices/bsim3v1/bsim3v1def.h @@ -192,6 +192,40 @@ typedef struct sBSIM3v1instance double **BSIM3v1nVar; #endif /* NONOISE */ +#ifdef KLU + BindElement *BSIM3v1DdBinding ; + BindElement *BSIM3v1GgBinding ; + BindElement *BSIM3v1SsBinding ; + BindElement *BSIM3v1BbBinding ; + BindElement *BSIM3v1DPdpBinding ; + BindElement *BSIM3v1SPspBinding ; + BindElement *BSIM3v1DdpBinding ; + BindElement *BSIM3v1GbBinding ; + BindElement *BSIM3v1GdpBinding ; + BindElement *BSIM3v1GspBinding ; + BindElement *BSIM3v1SspBinding ; + BindElement *BSIM3v1BdpBinding ; + BindElement *BSIM3v1BspBinding ; + BindElement *BSIM3v1DPspBinding ; + BindElement *BSIM3v1DPdBinding ; + BindElement *BSIM3v1BgBinding ; + BindElement *BSIM3v1DPgBinding ; + BindElement *BSIM3v1SPgBinding ; + BindElement *BSIM3v1SPsBinding ; + BindElement *BSIM3v1DPbBinding ; + BindElement *BSIM3v1SPbBinding ; + BindElement *BSIM3v1SPdpBinding ; + BindElement *BSIM3v1QqBinding ; + BindElement *BSIM3v1QdpBinding ; + BindElement *BSIM3v1QspBinding ; + BindElement *BSIM3v1QgBinding ; + BindElement *BSIM3v1QbBinding ; + BindElement *BSIM3v1DPqBinding ; + BindElement *BSIM3v1SPqBinding ; + BindElement *BSIM3v1GqBinding ; + BindElement *BSIM3v1BqBinding ; +#endif + } BSIM3v1instance ; struct bsim3v1SizeDependParam diff --git a/src/spicelib/devices/bsim3v1/bsim3v1ext.h b/src/spicelib/devices/bsim3v1/bsim3v1ext.h index 972b089ad..e001f8eb3 100644 --- a/src/spicelib/devices/bsim3v1/bsim3v1ext.h +++ b/src/spicelib/devices/bsim3v1/bsim3v1ext.h @@ -29,3 +29,8 @@ extern int BSIM3v1trunc(GENmodel *, CKTcircuit *, double *); extern int BSIM3v1noise(int, int, GENmodel *, CKTcircuit *, Ndata *, double *); extern int BSIM3v1unsetup(GENmodel *, CKTcircuit *); +#ifdef KLU +extern int BSIM3v1bindCSC (GENmodel*, CKTcircuit*) ; +extern int BSIM3v1bindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int BSIM3v1bindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/bsim3v1/bsim3v1init.c b/src/spicelib/devices/bsim3v1/bsim3v1init.c index b290af7e2..6268854d0 100644 --- a/src/spicelib/devices/bsim3v1/bsim3v1init.c +++ b/src/spicelib/devices/bsim3v1/bsim3v1init.c @@ -65,6 +65,11 @@ SPICEdev BSIM3v1info = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = BSIM3v1bindCSC, + .DEVbindCSCComplex = BSIM3v1bindCSCComplex, + .DEVbindCSCComplexToReal = BSIM3v1bindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/bsim3v32/Makefile.am b/src/spicelib/devices/bsim3v32/Makefile.am index 8c5bb529a..dccdb398f 100644 --- a/src/spicelib/devices/bsim3v32/Makefile.am +++ b/src/spicelib/devices/bsim3v32/Makefile.am @@ -29,6 +29,9 @@ libbsim3v32_la_SOURCES = \ bsim3v32itf.h +if KLU_WANTED +libbsim3v32_la_SOURCES += b3v32bindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) diff --git a/src/spicelib/devices/bsim3v32/b3v32bindCSC.c b/src/spicelib/devices/bsim3v32/b3v32bindCSC.c new file mode 100644 index 000000000..b958d0e68 --- /dev/null +++ b/src/spicelib/devices/bsim3v32/b3v32bindCSC.c @@ -0,0 +1,179 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "bsim3v32def.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +BSIM3v32bindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + BSIM3v32model *model = (BSIM3v32model *)inModel ; + BSIM3v32instance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the BSIM3v32 models */ + for ( ; model != NULL ; model = BSIM3v32nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = BSIM3v32instances(model); here != NULL ; here = BSIM3v32nextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(BSIM3v32DdPtr, BSIM3v32DdBinding, BSIM3v32dNode, BSIM3v32dNode); + CREATE_KLU_BINDING_TABLE(BSIM3v32GgPtr, BSIM3v32GgBinding, BSIM3v32gNode, BSIM3v32gNode); + CREATE_KLU_BINDING_TABLE(BSIM3v32SsPtr, BSIM3v32SsBinding, BSIM3v32sNode, BSIM3v32sNode); + CREATE_KLU_BINDING_TABLE(BSIM3v32BbPtr, BSIM3v32BbBinding, BSIM3v32bNode, BSIM3v32bNode); + CREATE_KLU_BINDING_TABLE(BSIM3v32DPdpPtr, BSIM3v32DPdpBinding, BSIM3v32dNodePrime, BSIM3v32dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v32SPspPtr, BSIM3v32SPspBinding, BSIM3v32sNodePrime, BSIM3v32sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v32DdpPtr, BSIM3v32DdpBinding, BSIM3v32dNode, BSIM3v32dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v32GbPtr, BSIM3v32GbBinding, BSIM3v32gNode, BSIM3v32bNode); + CREATE_KLU_BINDING_TABLE(BSIM3v32GdpPtr, BSIM3v32GdpBinding, BSIM3v32gNode, BSIM3v32dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v32GspPtr, BSIM3v32GspBinding, BSIM3v32gNode, BSIM3v32sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v32SspPtr, BSIM3v32SspBinding, BSIM3v32sNode, BSIM3v32sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v32BdpPtr, BSIM3v32BdpBinding, BSIM3v32bNode, BSIM3v32dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v32BspPtr, BSIM3v32BspBinding, BSIM3v32bNode, BSIM3v32sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v32DPspPtr, BSIM3v32DPspBinding, BSIM3v32dNodePrime, BSIM3v32sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v32DPdPtr, BSIM3v32DPdBinding, BSIM3v32dNodePrime, BSIM3v32dNode); + CREATE_KLU_BINDING_TABLE(BSIM3v32BgPtr, BSIM3v32BgBinding, BSIM3v32bNode, BSIM3v32gNode); + CREATE_KLU_BINDING_TABLE(BSIM3v32DPgPtr, BSIM3v32DPgBinding, BSIM3v32dNodePrime, BSIM3v32gNode); + CREATE_KLU_BINDING_TABLE(BSIM3v32SPgPtr, BSIM3v32SPgBinding, BSIM3v32sNodePrime, BSIM3v32gNode); + CREATE_KLU_BINDING_TABLE(BSIM3v32SPsPtr, BSIM3v32SPsBinding, BSIM3v32sNodePrime, BSIM3v32sNode); + CREATE_KLU_BINDING_TABLE(BSIM3v32DPbPtr, BSIM3v32DPbBinding, BSIM3v32dNodePrime, BSIM3v32bNode); + CREATE_KLU_BINDING_TABLE(BSIM3v32SPbPtr, BSIM3v32SPbBinding, BSIM3v32sNodePrime, BSIM3v32bNode); + CREATE_KLU_BINDING_TABLE(BSIM3v32SPdpPtr, BSIM3v32SPdpBinding, BSIM3v32sNodePrime, BSIM3v32dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v32QqPtr, BSIM3v32QqBinding, BSIM3v32qNode, BSIM3v32qNode); + CREATE_KLU_BINDING_TABLE(BSIM3v32QdpPtr, BSIM3v32QdpBinding, BSIM3v32qNode, BSIM3v32dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v32QspPtr, BSIM3v32QspBinding, BSIM3v32qNode, BSIM3v32sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM3v32QgPtr, BSIM3v32QgBinding, BSIM3v32qNode, BSIM3v32gNode); + CREATE_KLU_BINDING_TABLE(BSIM3v32QbPtr, BSIM3v32QbBinding, BSIM3v32qNode, BSIM3v32bNode); + CREATE_KLU_BINDING_TABLE(BSIM3v32DPqPtr, BSIM3v32DPqBinding, BSIM3v32dNodePrime, BSIM3v32qNode); + CREATE_KLU_BINDING_TABLE(BSIM3v32SPqPtr, BSIM3v32SPqBinding, BSIM3v32sNodePrime, BSIM3v32qNode); + CREATE_KLU_BINDING_TABLE(BSIM3v32GqPtr, BSIM3v32GqBinding, BSIM3v32gNode, BSIM3v32qNode); + CREATE_KLU_BINDING_TABLE(BSIM3v32BqPtr, BSIM3v32BqBinding, BSIM3v32bNode, BSIM3v32qNode); + } + } + + return (OK) ; +} + +int +BSIM3v32bindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + BSIM3v32model *model = (BSIM3v32model *)inModel ; + BSIM3v32instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the BSIM3v32 models */ + for ( ; model != NULL ; model = BSIM3v32nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = BSIM3v32instances(model); here != NULL ; here = BSIM3v32nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32DdPtr, BSIM3v32DdBinding, BSIM3v32dNode, BSIM3v32dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32GgPtr, BSIM3v32GgBinding, BSIM3v32gNode, BSIM3v32gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32SsPtr, BSIM3v32SsBinding, BSIM3v32sNode, BSIM3v32sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32BbPtr, BSIM3v32BbBinding, BSIM3v32bNode, BSIM3v32bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32DPdpPtr, BSIM3v32DPdpBinding, BSIM3v32dNodePrime, BSIM3v32dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32SPspPtr, BSIM3v32SPspBinding, BSIM3v32sNodePrime, BSIM3v32sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32DdpPtr, BSIM3v32DdpBinding, BSIM3v32dNode, BSIM3v32dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32GbPtr, BSIM3v32GbBinding, BSIM3v32gNode, BSIM3v32bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32GdpPtr, BSIM3v32GdpBinding, BSIM3v32gNode, BSIM3v32dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32GspPtr, BSIM3v32GspBinding, BSIM3v32gNode, BSIM3v32sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32SspPtr, BSIM3v32SspBinding, BSIM3v32sNode, BSIM3v32sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32BdpPtr, BSIM3v32BdpBinding, BSIM3v32bNode, BSIM3v32dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32BspPtr, BSIM3v32BspBinding, BSIM3v32bNode, BSIM3v32sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32DPspPtr, BSIM3v32DPspBinding, BSIM3v32dNodePrime, BSIM3v32sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32DPdPtr, BSIM3v32DPdBinding, BSIM3v32dNodePrime, BSIM3v32dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32BgPtr, BSIM3v32BgBinding, BSIM3v32bNode, BSIM3v32gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32DPgPtr, BSIM3v32DPgBinding, BSIM3v32dNodePrime, BSIM3v32gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32SPgPtr, BSIM3v32SPgBinding, BSIM3v32sNodePrime, BSIM3v32gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32SPsPtr, BSIM3v32SPsBinding, BSIM3v32sNodePrime, BSIM3v32sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32DPbPtr, BSIM3v32DPbBinding, BSIM3v32dNodePrime, BSIM3v32bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32SPbPtr, BSIM3v32SPbBinding, BSIM3v32sNodePrime, BSIM3v32bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32SPdpPtr, BSIM3v32SPdpBinding, BSIM3v32sNodePrime, BSIM3v32dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32QqPtr, BSIM3v32QqBinding, BSIM3v32qNode, BSIM3v32qNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32QdpPtr, BSIM3v32QdpBinding, BSIM3v32qNode, BSIM3v32dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32QspPtr, BSIM3v32QspBinding, BSIM3v32qNode, BSIM3v32sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32QgPtr, BSIM3v32QgBinding, BSIM3v32qNode, BSIM3v32gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32QbPtr, BSIM3v32QbBinding, BSIM3v32qNode, BSIM3v32bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32DPqPtr, BSIM3v32DPqBinding, BSIM3v32dNodePrime, BSIM3v32qNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32SPqPtr, BSIM3v32SPqBinding, BSIM3v32sNodePrime, BSIM3v32qNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32GqPtr, BSIM3v32GqBinding, BSIM3v32gNode, BSIM3v32qNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM3v32BqPtr, BSIM3v32BqBinding, BSIM3v32bNode, BSIM3v32qNode); + } + } + + return (OK) ; +} + +int +BSIM3v32bindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + BSIM3v32model *model = (BSIM3v32model *)inModel ; + BSIM3v32instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the BSIM3v32 models */ + for ( ; model != NULL ; model = BSIM3v32nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = BSIM3v32instances(model); here != NULL ; here = BSIM3v32nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32DdPtr, BSIM3v32DdBinding, BSIM3v32dNode, BSIM3v32dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32GgPtr, BSIM3v32GgBinding, BSIM3v32gNode, BSIM3v32gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32SsPtr, BSIM3v32SsBinding, BSIM3v32sNode, BSIM3v32sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32BbPtr, BSIM3v32BbBinding, BSIM3v32bNode, BSIM3v32bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32DPdpPtr, BSIM3v32DPdpBinding, BSIM3v32dNodePrime, BSIM3v32dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32SPspPtr, BSIM3v32SPspBinding, BSIM3v32sNodePrime, BSIM3v32sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32DdpPtr, BSIM3v32DdpBinding, BSIM3v32dNode, BSIM3v32dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32GbPtr, BSIM3v32GbBinding, BSIM3v32gNode, BSIM3v32bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32GdpPtr, BSIM3v32GdpBinding, BSIM3v32gNode, BSIM3v32dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32GspPtr, BSIM3v32GspBinding, BSIM3v32gNode, BSIM3v32sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32SspPtr, BSIM3v32SspBinding, BSIM3v32sNode, BSIM3v32sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32BdpPtr, BSIM3v32BdpBinding, BSIM3v32bNode, BSIM3v32dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32BspPtr, BSIM3v32BspBinding, BSIM3v32bNode, BSIM3v32sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32DPspPtr, BSIM3v32DPspBinding, BSIM3v32dNodePrime, BSIM3v32sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32DPdPtr, BSIM3v32DPdBinding, BSIM3v32dNodePrime, BSIM3v32dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32BgPtr, BSIM3v32BgBinding, BSIM3v32bNode, BSIM3v32gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32DPgPtr, BSIM3v32DPgBinding, BSIM3v32dNodePrime, BSIM3v32gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32SPgPtr, BSIM3v32SPgBinding, BSIM3v32sNodePrime, BSIM3v32gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32SPsPtr, BSIM3v32SPsBinding, BSIM3v32sNodePrime, BSIM3v32sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32DPbPtr, BSIM3v32DPbBinding, BSIM3v32dNodePrime, BSIM3v32bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32SPbPtr, BSIM3v32SPbBinding, BSIM3v32sNodePrime, BSIM3v32bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32SPdpPtr, BSIM3v32SPdpBinding, BSIM3v32sNodePrime, BSIM3v32dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32QqPtr, BSIM3v32QqBinding, BSIM3v32qNode, BSIM3v32qNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32QdpPtr, BSIM3v32QdpBinding, BSIM3v32qNode, BSIM3v32dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32QspPtr, BSIM3v32QspBinding, BSIM3v32qNode, BSIM3v32sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32QgPtr, BSIM3v32QgBinding, BSIM3v32qNode, BSIM3v32gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32QbPtr, BSIM3v32QbBinding, BSIM3v32qNode, BSIM3v32bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32DPqPtr, BSIM3v32DPqBinding, BSIM3v32dNodePrime, BSIM3v32qNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32SPqPtr, BSIM3v32SPqBinding, BSIM3v32sNodePrime, BSIM3v32qNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32GqPtr, BSIM3v32GqBinding, BSIM3v32gNode, BSIM3v32qNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM3v32BqPtr, BSIM3v32BqBinding, BSIM3v32bNode, BSIM3v32qNode); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/bsim3v32/bsim3v32def.h b/src/spicelib/devices/bsim3v32/bsim3v32def.h index 85192c57f..ae9aa7176 100644 --- a/src/spicelib/devices/bsim3v32/bsim3v32def.h +++ b/src/spicelib/devices/bsim3v32/bsim3v32def.h @@ -258,6 +258,40 @@ typedef struct sBSIM3v32instance double **BSIM3v32nVar; #endif /* NONOISE */ +#ifdef KLU + BindElement *BSIM3v32DdBinding ; + BindElement *BSIM3v32GgBinding ; + BindElement *BSIM3v32SsBinding ; + BindElement *BSIM3v32BbBinding ; + BindElement *BSIM3v32DPdpBinding ; + BindElement *BSIM3v32SPspBinding ; + BindElement *BSIM3v32DdpBinding ; + BindElement *BSIM3v32GbBinding ; + BindElement *BSIM3v32GdpBinding ; + BindElement *BSIM3v32GspBinding ; + BindElement *BSIM3v32SspBinding ; + BindElement *BSIM3v32BdpBinding ; + BindElement *BSIM3v32BspBinding ; + BindElement *BSIM3v32DPspBinding ; + BindElement *BSIM3v32DPdBinding ; + BindElement *BSIM3v32BgBinding ; + BindElement *BSIM3v32DPgBinding ; + BindElement *BSIM3v32SPgBinding ; + BindElement *BSIM3v32SPsBinding ; + BindElement *BSIM3v32DPbBinding ; + BindElement *BSIM3v32SPbBinding ; + BindElement *BSIM3v32SPdpBinding ; + BindElement *BSIM3v32QqBinding ; + BindElement *BSIM3v32QdpBinding ; + BindElement *BSIM3v32QspBinding ; + BindElement *BSIM3v32QgBinding ; + BindElement *BSIM3v32QbBinding ; + BindElement *BSIM3v32DPqBinding ; + BindElement *BSIM3v32SPqBinding ; + BindElement *BSIM3v32GqBinding ; + BindElement *BSIM3v32BqBinding ; +#endif + } BSIM3v32instance ; struct bsim3v32SizeDependParam diff --git a/src/spicelib/devices/bsim3v32/bsim3v32ext.h b/src/spicelib/devices/bsim3v32/bsim3v32ext.h index 9d02c7e3b..f4c115aea 100644 --- a/src/spicelib/devices/bsim3v32/bsim3v32ext.h +++ b/src/spicelib/devices/bsim3v32/bsim3v32ext.h @@ -30,3 +30,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 *); + +#ifdef KLU +extern int BSIM3v32bindCSC (GENmodel*, CKTcircuit*) ; +extern int BSIM3v32bindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int BSIM3v32bindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/bsim3v32/bsim3v32init.c b/src/spicelib/devices/bsim3v32/bsim3v32init.c index 960d7fd81..3d7f0aa9c 100644 --- a/src/spicelib/devices/bsim3v32/bsim3v32init.c +++ b/src/spicelib/devices/bsim3v32/bsim3v32init.c @@ -66,6 +66,11 @@ SPICEdev BSIM3v32info = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = BSIM3v32bindCSC, + .DEVbindCSCComplex = BSIM3v32bindCSCComplex, + .DEVbindCSCComplexToReal = BSIM3v32bindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/bsim4v5/Makefile.am b/src/spicelib/devices/bsim4v5/Makefile.am index 4438ce323..7941bbdd5 100644 --- a/src/spicelib/devices/bsim4v5/Makefile.am +++ b/src/spicelib/devices/bsim4v5/Makefile.am @@ -30,6 +30,9 @@ libbsim4v5_la_SOURCES = \ bsim4v5itf.h +if KLU_WANTED +libbsim4v5_la_SOURCES += b4v5bindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) diff --git a/src/spicelib/devices/bsim4v5/b4v5bindCSC.c b/src/spicelib/devices/bsim4v5/b4v5bindCSC.c new file mode 100644 index 000000000..806e9bf7a --- /dev/null +++ b/src/spicelib/devices/bsim4v5/b4v5bindCSC.c @@ -0,0 +1,323 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "bsim4v5def.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +BSIM4v5bindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + BSIM4v5model *model = (BSIM4v5model *)inModel ; + BSIM4v5instance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the BSIM4v5 models */ + for ( ; model != NULL ; model = BSIM4v5nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = BSIM4v5instances(model); here != NULL ; here = BSIM4v5nextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(BSIM4v5DPbpPtr, BSIM4v5DPbpBinding, BSIM4v5dNodePrime, BSIM4v5bNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5GPbpPtr, BSIM4v5GPbpBinding, BSIM4v5gNodePrime, BSIM4v5bNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5SPbpPtr, BSIM4v5SPbpBinding, BSIM4v5sNodePrime, BSIM4v5bNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5BPdpPtr, BSIM4v5BPdpBinding, BSIM4v5bNodePrime, BSIM4v5dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5BPgpPtr, BSIM4v5BPgpBinding, BSIM4v5bNodePrime, BSIM4v5gNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5BPspPtr, BSIM4v5BPspBinding, BSIM4v5bNodePrime, BSIM4v5sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5BPbpPtr, BSIM4v5BPbpBinding, BSIM4v5bNodePrime, BSIM4v5bNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5DdPtr, BSIM4v5DdBinding, BSIM4v5dNode, BSIM4v5dNode); + CREATE_KLU_BINDING_TABLE(BSIM4v5GPgpPtr, BSIM4v5GPgpBinding, BSIM4v5gNodePrime, BSIM4v5gNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5SsPtr, BSIM4v5SsBinding, BSIM4v5sNode, BSIM4v5sNode); + CREATE_KLU_BINDING_TABLE(BSIM4v5DPdpPtr, BSIM4v5DPdpBinding, BSIM4v5dNodePrime, BSIM4v5dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5SPspPtr, BSIM4v5SPspBinding, BSIM4v5sNodePrime, BSIM4v5sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5DdpPtr, BSIM4v5DdpBinding, BSIM4v5dNode, BSIM4v5dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5GPdpPtr, BSIM4v5GPdpBinding, BSIM4v5gNodePrime, BSIM4v5dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5GPspPtr, BSIM4v5GPspBinding, BSIM4v5gNodePrime, BSIM4v5sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5SspPtr, BSIM4v5SspBinding, BSIM4v5sNode, BSIM4v5sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5DPspPtr, BSIM4v5DPspBinding, BSIM4v5dNodePrime, BSIM4v5sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5DPdPtr, BSIM4v5DPdBinding, BSIM4v5dNodePrime, BSIM4v5dNode); + CREATE_KLU_BINDING_TABLE(BSIM4v5DPgpPtr, BSIM4v5DPgpBinding, BSIM4v5dNodePrime, BSIM4v5gNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5SPgpPtr, BSIM4v5SPgpBinding, BSIM4v5sNodePrime, BSIM4v5gNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5SPsPtr, BSIM4v5SPsBinding, BSIM4v5sNodePrime, BSIM4v5sNode); + CREATE_KLU_BINDING_TABLE(BSIM4v5SPdpPtr, BSIM4v5SPdpBinding, BSIM4v5sNodePrime, BSIM4v5dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5QqPtr, BSIM4v5QqBinding, BSIM4v5qNode, BSIM4v5qNode); + CREATE_KLU_BINDING_TABLE(BSIM4v5QbpPtr, BSIM4v5QbpBinding, BSIM4v5qNode, BSIM4v5bNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5QdpPtr, BSIM4v5QdpBinding, BSIM4v5qNode, BSIM4v5dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5QspPtr, BSIM4v5QspBinding, BSIM4v5qNode, BSIM4v5sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5QgpPtr, BSIM4v5QgpBinding, BSIM4v5qNode, BSIM4v5gNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5DPqPtr, BSIM4v5DPqBinding, BSIM4v5dNodePrime, BSIM4v5qNode); + CREATE_KLU_BINDING_TABLE(BSIM4v5SPqPtr, BSIM4v5SPqBinding, BSIM4v5sNodePrime, BSIM4v5qNode); + CREATE_KLU_BINDING_TABLE(BSIM4v5GPqPtr, BSIM4v5GPqBinding, BSIM4v5gNodePrime, BSIM4v5qNode); + if (here->BSIM4v5rgateMod != 0) + { + CREATE_KLU_BINDING_TABLE(BSIM4v5GEgePtr, BSIM4v5GEgeBinding, BSIM4v5gNodeExt, BSIM4v5gNodeExt); + CREATE_KLU_BINDING_TABLE(BSIM4v5GEgpPtr, BSIM4v5GEgpBinding, BSIM4v5gNodeExt, BSIM4v5gNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5GPgePtr, BSIM4v5GPgeBinding, BSIM4v5gNodePrime, BSIM4v5gNodeExt); + CREATE_KLU_BINDING_TABLE(BSIM4v5GEdpPtr, BSIM4v5GEdpBinding, BSIM4v5gNodeExt, BSIM4v5dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5GEspPtr, BSIM4v5GEspBinding, BSIM4v5gNodeExt, BSIM4v5sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5GEbpPtr, BSIM4v5GEbpBinding, BSIM4v5gNodeExt, BSIM4v5bNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5GMdpPtr, BSIM4v5GMdpBinding, BSIM4v5gNodeMid, BSIM4v5dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5GMgpPtr, BSIM4v5GMgpBinding, BSIM4v5gNodeMid, BSIM4v5gNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5GMgmPtr, BSIM4v5GMgmBinding, BSIM4v5gNodeMid, BSIM4v5gNodeMid); + CREATE_KLU_BINDING_TABLE(BSIM4v5GMgePtr, BSIM4v5GMgeBinding, BSIM4v5gNodeMid, BSIM4v5gNodeExt); + CREATE_KLU_BINDING_TABLE(BSIM4v5GMspPtr, BSIM4v5GMspBinding, BSIM4v5gNodeMid, BSIM4v5sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5GMbpPtr, BSIM4v5GMbpBinding, BSIM4v5gNodeMid, BSIM4v5bNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5DPgmPtr, BSIM4v5DPgmBinding, BSIM4v5dNodePrime, BSIM4v5gNodeMid); + CREATE_KLU_BINDING_TABLE(BSIM4v5GPgmPtr, BSIM4v5GPgmBinding, BSIM4v5gNodePrime, BSIM4v5gNodeMid); + CREATE_KLU_BINDING_TABLE(BSIM4v5GEgmPtr, BSIM4v5GEgmBinding, BSIM4v5gNodeExt, BSIM4v5gNodeMid); + CREATE_KLU_BINDING_TABLE(BSIM4v5SPgmPtr, BSIM4v5SPgmBinding, BSIM4v5sNodePrime, BSIM4v5gNodeMid); + CREATE_KLU_BINDING_TABLE(BSIM4v5BPgmPtr, BSIM4v5BPgmBinding, BSIM4v5bNodePrime, BSIM4v5gNodeMid); + } + if ((here->BSIM4v5rbodyMod == 1) || (here->BSIM4v5rbodyMod == 2)) + { + CREATE_KLU_BINDING_TABLE(BSIM4v5DPdbPtr, BSIM4v5DPdbBinding, BSIM4v5dNodePrime, BSIM4v5dbNode); + CREATE_KLU_BINDING_TABLE(BSIM4v5SPsbPtr, BSIM4v5SPsbBinding, BSIM4v5sNodePrime, BSIM4v5sbNode); + CREATE_KLU_BINDING_TABLE(BSIM4v5DBdpPtr, BSIM4v5DBdpBinding, BSIM4v5dbNode, BSIM4v5dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5DBdbPtr, BSIM4v5DBdbBinding, BSIM4v5dbNode, BSIM4v5dbNode); + CREATE_KLU_BINDING_TABLE(BSIM4v5DBbpPtr, BSIM4v5DBbpBinding, BSIM4v5dbNode, BSIM4v5bNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5DBbPtr, BSIM4v5DBbBinding, BSIM4v5dbNode, BSIM4v5bNode); + CREATE_KLU_BINDING_TABLE(BSIM4v5BPdbPtr, BSIM4v5BPdbBinding, BSIM4v5bNodePrime, BSIM4v5dbNode); + CREATE_KLU_BINDING_TABLE(BSIM4v5BPbPtr, BSIM4v5BPbBinding, BSIM4v5bNodePrime, BSIM4v5bNode); + CREATE_KLU_BINDING_TABLE(BSIM4v5BPsbPtr, BSIM4v5BPsbBinding, BSIM4v5bNodePrime, BSIM4v5sbNode); + CREATE_KLU_BINDING_TABLE(BSIM4v5SBspPtr, BSIM4v5SBspBinding, BSIM4v5sbNode, BSIM4v5sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5SBbpPtr, BSIM4v5SBbpBinding, BSIM4v5sbNode, BSIM4v5bNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5SBbPtr, BSIM4v5SBbBinding, BSIM4v5sbNode, BSIM4v5bNode); + CREATE_KLU_BINDING_TABLE(BSIM4v5SBsbPtr, BSIM4v5SBsbBinding, BSIM4v5sbNode, BSIM4v5sbNode); + CREATE_KLU_BINDING_TABLE(BSIM4v5BdbPtr, BSIM4v5BdbBinding, BSIM4v5bNode, BSIM4v5dbNode); + CREATE_KLU_BINDING_TABLE(BSIM4v5BbpPtr, BSIM4v5BbpBinding, BSIM4v5bNode, BSIM4v5bNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5BsbPtr, BSIM4v5BsbBinding, BSIM4v5bNode, BSIM4v5sbNode); + CREATE_KLU_BINDING_TABLE(BSIM4v5BbPtr, BSIM4v5BbBinding, BSIM4v5bNode, BSIM4v5bNode); + } + if (model->BSIM4v5rdsMod) + { + CREATE_KLU_BINDING_TABLE(BSIM4v5DgpPtr, BSIM4v5DgpBinding, BSIM4v5dNode, BSIM4v5gNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5DspPtr, BSIM4v5DspBinding, BSIM4v5dNode, BSIM4v5sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5DbpPtr, BSIM4v5DbpBinding, BSIM4v5dNode, BSIM4v5bNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5SdpPtr, BSIM4v5SdpBinding, BSIM4v5sNode, BSIM4v5dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5SgpPtr, BSIM4v5SgpBinding, BSIM4v5sNode, BSIM4v5gNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v5SbpPtr, BSIM4v5SbpBinding, BSIM4v5sNode, BSIM4v5bNodePrime); + } + } + } + + return (OK) ; +} + +int +BSIM4v5bindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + BSIM4v5model *model = (BSIM4v5model *)inModel ; + BSIM4v5instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the BSIM4v5 models */ + for ( ; model != NULL ; model = BSIM4v5nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = BSIM4v5instances(model); here != NULL ; here = BSIM4v5nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5DPbpPtr, BSIM4v5DPbpBinding, BSIM4v5dNodePrime, BSIM4v5bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5GPbpPtr, BSIM4v5GPbpBinding, BSIM4v5gNodePrime, BSIM4v5bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5SPbpPtr, BSIM4v5SPbpBinding, BSIM4v5sNodePrime, BSIM4v5bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5BPdpPtr, BSIM4v5BPdpBinding, BSIM4v5bNodePrime, BSIM4v5dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5BPgpPtr, BSIM4v5BPgpBinding, BSIM4v5bNodePrime, BSIM4v5gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5BPspPtr, BSIM4v5BPspBinding, BSIM4v5bNodePrime, BSIM4v5sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5BPbpPtr, BSIM4v5BPbpBinding, BSIM4v5bNodePrime, BSIM4v5bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5DdPtr, BSIM4v5DdBinding, BSIM4v5dNode, BSIM4v5dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5GPgpPtr, BSIM4v5GPgpBinding, BSIM4v5gNodePrime, BSIM4v5gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5SsPtr, BSIM4v5SsBinding, BSIM4v5sNode, BSIM4v5sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5DPdpPtr, BSIM4v5DPdpBinding, BSIM4v5dNodePrime, BSIM4v5dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5SPspPtr, BSIM4v5SPspBinding, BSIM4v5sNodePrime, BSIM4v5sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5DdpPtr, BSIM4v5DdpBinding, BSIM4v5dNode, BSIM4v5dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5GPdpPtr, BSIM4v5GPdpBinding, BSIM4v5gNodePrime, BSIM4v5dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5GPspPtr, BSIM4v5GPspBinding, BSIM4v5gNodePrime, BSIM4v5sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5SspPtr, BSIM4v5SspBinding, BSIM4v5sNode, BSIM4v5sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5DPspPtr, BSIM4v5DPspBinding, BSIM4v5dNodePrime, BSIM4v5sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5DPdPtr, BSIM4v5DPdBinding, BSIM4v5dNodePrime, BSIM4v5dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5DPgpPtr, BSIM4v5DPgpBinding, BSIM4v5dNodePrime, BSIM4v5gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5SPgpPtr, BSIM4v5SPgpBinding, BSIM4v5sNodePrime, BSIM4v5gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5SPsPtr, BSIM4v5SPsBinding, BSIM4v5sNodePrime, BSIM4v5sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5SPdpPtr, BSIM4v5SPdpBinding, BSIM4v5sNodePrime, BSIM4v5dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5QqPtr, BSIM4v5QqBinding, BSIM4v5qNode, BSIM4v5qNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5QbpPtr, BSIM4v5QbpBinding, BSIM4v5qNode, BSIM4v5bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5QdpPtr, BSIM4v5QdpBinding, BSIM4v5qNode, BSIM4v5dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5QspPtr, BSIM4v5QspBinding, BSIM4v5qNode, BSIM4v5sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5QgpPtr, BSIM4v5QgpBinding, BSIM4v5qNode, BSIM4v5gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5DPqPtr, BSIM4v5DPqBinding, BSIM4v5dNodePrime, BSIM4v5qNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5SPqPtr, BSIM4v5SPqBinding, BSIM4v5sNodePrime, BSIM4v5qNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5GPqPtr, BSIM4v5GPqBinding, BSIM4v5gNodePrime, BSIM4v5qNode); + if (here->BSIM4v5rgateMod != 0) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5GEgePtr, BSIM4v5GEgeBinding, BSIM4v5gNodeExt, BSIM4v5gNodeExt); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5GEgpPtr, BSIM4v5GEgpBinding, BSIM4v5gNodeExt, BSIM4v5gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5GPgePtr, BSIM4v5GPgeBinding, BSIM4v5gNodePrime, BSIM4v5gNodeExt); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5GEdpPtr, BSIM4v5GEdpBinding, BSIM4v5gNodeExt, BSIM4v5dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5GEspPtr, BSIM4v5GEspBinding, BSIM4v5gNodeExt, BSIM4v5sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5GEbpPtr, BSIM4v5GEbpBinding, BSIM4v5gNodeExt, BSIM4v5bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5GMdpPtr, BSIM4v5GMdpBinding, BSIM4v5gNodeMid, BSIM4v5dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5GMgpPtr, BSIM4v5GMgpBinding, BSIM4v5gNodeMid, BSIM4v5gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5GMgmPtr, BSIM4v5GMgmBinding, BSIM4v5gNodeMid, BSIM4v5gNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5GMgePtr, BSIM4v5GMgeBinding, BSIM4v5gNodeMid, BSIM4v5gNodeExt); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5GMspPtr, BSIM4v5GMspBinding, BSIM4v5gNodeMid, BSIM4v5sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5GMbpPtr, BSIM4v5GMbpBinding, BSIM4v5gNodeMid, BSIM4v5bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5DPgmPtr, BSIM4v5DPgmBinding, BSIM4v5dNodePrime, BSIM4v5gNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5GPgmPtr, BSIM4v5GPgmBinding, BSIM4v5gNodePrime, BSIM4v5gNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5GEgmPtr, BSIM4v5GEgmBinding, BSIM4v5gNodeExt, BSIM4v5gNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5SPgmPtr, BSIM4v5SPgmBinding, BSIM4v5sNodePrime, BSIM4v5gNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5BPgmPtr, BSIM4v5BPgmBinding, BSIM4v5bNodePrime, BSIM4v5gNodeMid); + } + if ((here->BSIM4v5rbodyMod == 1) || (here->BSIM4v5rbodyMod == 2)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5DPdbPtr, BSIM4v5DPdbBinding, BSIM4v5dNodePrime, BSIM4v5dbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5SPsbPtr, BSIM4v5SPsbBinding, BSIM4v5sNodePrime, BSIM4v5sbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5DBdpPtr, BSIM4v5DBdpBinding, BSIM4v5dbNode, BSIM4v5dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5DBdbPtr, BSIM4v5DBdbBinding, BSIM4v5dbNode, BSIM4v5dbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5DBbpPtr, BSIM4v5DBbpBinding, BSIM4v5dbNode, BSIM4v5bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5DBbPtr, BSIM4v5DBbBinding, BSIM4v5dbNode, BSIM4v5bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5BPdbPtr, BSIM4v5BPdbBinding, BSIM4v5bNodePrime, BSIM4v5dbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5BPbPtr, BSIM4v5BPbBinding, BSIM4v5bNodePrime, BSIM4v5bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5BPsbPtr, BSIM4v5BPsbBinding, BSIM4v5bNodePrime, BSIM4v5sbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5SBspPtr, BSIM4v5SBspBinding, BSIM4v5sbNode, BSIM4v5sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5SBbpPtr, BSIM4v5SBbpBinding, BSIM4v5sbNode, BSIM4v5bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5SBbPtr, BSIM4v5SBbBinding, BSIM4v5sbNode, BSIM4v5bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5SBsbPtr, BSIM4v5SBsbBinding, BSIM4v5sbNode, BSIM4v5sbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5BdbPtr, BSIM4v5BdbBinding, BSIM4v5bNode, BSIM4v5dbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5BbpPtr, BSIM4v5BbpBinding, BSIM4v5bNode, BSIM4v5bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5BsbPtr, BSIM4v5BsbBinding, BSIM4v5bNode, BSIM4v5sbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5BbPtr, BSIM4v5BbBinding, BSIM4v5bNode, BSIM4v5bNode); + } + if (model->BSIM4v5rdsMod) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5DgpPtr, BSIM4v5DgpBinding, BSIM4v5dNode, BSIM4v5gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5DspPtr, BSIM4v5DspBinding, BSIM4v5dNode, BSIM4v5sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5DbpPtr, BSIM4v5DbpBinding, BSIM4v5dNode, BSIM4v5bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5SdpPtr, BSIM4v5SdpBinding, BSIM4v5sNode, BSIM4v5dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5SgpPtr, BSIM4v5SgpBinding, BSIM4v5sNode, BSIM4v5gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v5SbpPtr, BSIM4v5SbpBinding, BSIM4v5sNode, BSIM4v5bNodePrime); + } + } + } + + return (OK) ; +} + +int +BSIM4v5bindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + BSIM4v5model *model = (BSIM4v5model *)inModel ; + BSIM4v5instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the BSIM4v5 models */ + for ( ; model != NULL ; model = BSIM4v5nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = BSIM4v5instances(model); here != NULL ; here = BSIM4v5nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5DPbpPtr, BSIM4v5DPbpBinding, BSIM4v5dNodePrime, BSIM4v5bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5GPbpPtr, BSIM4v5GPbpBinding, BSIM4v5gNodePrime, BSIM4v5bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5SPbpPtr, BSIM4v5SPbpBinding, BSIM4v5sNodePrime, BSIM4v5bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5BPdpPtr, BSIM4v5BPdpBinding, BSIM4v5bNodePrime, BSIM4v5dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5BPgpPtr, BSIM4v5BPgpBinding, BSIM4v5bNodePrime, BSIM4v5gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5BPspPtr, BSIM4v5BPspBinding, BSIM4v5bNodePrime, BSIM4v5sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5BPbpPtr, BSIM4v5BPbpBinding, BSIM4v5bNodePrime, BSIM4v5bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5DdPtr, BSIM4v5DdBinding, BSIM4v5dNode, BSIM4v5dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5GPgpPtr, BSIM4v5GPgpBinding, BSIM4v5gNodePrime, BSIM4v5gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5SsPtr, BSIM4v5SsBinding, BSIM4v5sNode, BSIM4v5sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5DPdpPtr, BSIM4v5DPdpBinding, BSIM4v5dNodePrime, BSIM4v5dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5SPspPtr, BSIM4v5SPspBinding, BSIM4v5sNodePrime, BSIM4v5sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5DdpPtr, BSIM4v5DdpBinding, BSIM4v5dNode, BSIM4v5dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5GPdpPtr, BSIM4v5GPdpBinding, BSIM4v5gNodePrime, BSIM4v5dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5GPspPtr, BSIM4v5GPspBinding, BSIM4v5gNodePrime, BSIM4v5sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5SspPtr, BSIM4v5SspBinding, BSIM4v5sNode, BSIM4v5sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5DPspPtr, BSIM4v5DPspBinding, BSIM4v5dNodePrime, BSIM4v5sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5DPdPtr, BSIM4v5DPdBinding, BSIM4v5dNodePrime, BSIM4v5dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5DPgpPtr, BSIM4v5DPgpBinding, BSIM4v5dNodePrime, BSIM4v5gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5SPgpPtr, BSIM4v5SPgpBinding, BSIM4v5sNodePrime, BSIM4v5gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5SPsPtr, BSIM4v5SPsBinding, BSIM4v5sNodePrime, BSIM4v5sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5SPdpPtr, BSIM4v5SPdpBinding, BSIM4v5sNodePrime, BSIM4v5dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5QqPtr, BSIM4v5QqBinding, BSIM4v5qNode, BSIM4v5qNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5QbpPtr, BSIM4v5QbpBinding, BSIM4v5qNode, BSIM4v5bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5QdpPtr, BSIM4v5QdpBinding, BSIM4v5qNode, BSIM4v5dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5QspPtr, BSIM4v5QspBinding, BSIM4v5qNode, BSIM4v5sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5QgpPtr, BSIM4v5QgpBinding, BSIM4v5qNode, BSIM4v5gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5DPqPtr, BSIM4v5DPqBinding, BSIM4v5dNodePrime, BSIM4v5qNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5SPqPtr, BSIM4v5SPqBinding, BSIM4v5sNodePrime, BSIM4v5qNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5GPqPtr, BSIM4v5GPqBinding, BSIM4v5gNodePrime, BSIM4v5qNode); + if (here->BSIM4v5rgateMod != 0) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5GEgePtr, BSIM4v5GEgeBinding, BSIM4v5gNodeExt, BSIM4v5gNodeExt); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5GEgpPtr, BSIM4v5GEgpBinding, BSIM4v5gNodeExt, BSIM4v5gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5GPgePtr, BSIM4v5GPgeBinding, BSIM4v5gNodePrime, BSIM4v5gNodeExt); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5GEdpPtr, BSIM4v5GEdpBinding, BSIM4v5gNodeExt, BSIM4v5dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5GEspPtr, BSIM4v5GEspBinding, BSIM4v5gNodeExt, BSIM4v5sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5GEbpPtr, BSIM4v5GEbpBinding, BSIM4v5gNodeExt, BSIM4v5bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5GMdpPtr, BSIM4v5GMdpBinding, BSIM4v5gNodeMid, BSIM4v5dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5GMgpPtr, BSIM4v5GMgpBinding, BSIM4v5gNodeMid, BSIM4v5gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5GMgmPtr, BSIM4v5GMgmBinding, BSIM4v5gNodeMid, BSIM4v5gNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5GMgePtr, BSIM4v5GMgeBinding, BSIM4v5gNodeMid, BSIM4v5gNodeExt); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5GMspPtr, BSIM4v5GMspBinding, BSIM4v5gNodeMid, BSIM4v5sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5GMbpPtr, BSIM4v5GMbpBinding, BSIM4v5gNodeMid, BSIM4v5bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5DPgmPtr, BSIM4v5DPgmBinding, BSIM4v5dNodePrime, BSIM4v5gNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5GPgmPtr, BSIM4v5GPgmBinding, BSIM4v5gNodePrime, BSIM4v5gNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5GEgmPtr, BSIM4v5GEgmBinding, BSIM4v5gNodeExt, BSIM4v5gNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5SPgmPtr, BSIM4v5SPgmBinding, BSIM4v5sNodePrime, BSIM4v5gNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5BPgmPtr, BSIM4v5BPgmBinding, BSIM4v5bNodePrime, BSIM4v5gNodeMid); + } + if ((here->BSIM4v5rbodyMod == 1) || (here->BSIM4v5rbodyMod == 2)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5DPdbPtr, BSIM4v5DPdbBinding, BSIM4v5dNodePrime, BSIM4v5dbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5SPsbPtr, BSIM4v5SPsbBinding, BSIM4v5sNodePrime, BSIM4v5sbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5DBdpPtr, BSIM4v5DBdpBinding, BSIM4v5dbNode, BSIM4v5dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5DBdbPtr, BSIM4v5DBdbBinding, BSIM4v5dbNode, BSIM4v5dbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5DBbpPtr, BSIM4v5DBbpBinding, BSIM4v5dbNode, BSIM4v5bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5DBbPtr, BSIM4v5DBbBinding, BSIM4v5dbNode, BSIM4v5bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5BPdbPtr, BSIM4v5BPdbBinding, BSIM4v5bNodePrime, BSIM4v5dbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5BPbPtr, BSIM4v5BPbBinding, BSIM4v5bNodePrime, BSIM4v5bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5BPsbPtr, BSIM4v5BPsbBinding, BSIM4v5bNodePrime, BSIM4v5sbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5SBspPtr, BSIM4v5SBspBinding, BSIM4v5sbNode, BSIM4v5sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5SBbpPtr, BSIM4v5SBbpBinding, BSIM4v5sbNode, BSIM4v5bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5SBbPtr, BSIM4v5SBbBinding, BSIM4v5sbNode, BSIM4v5bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5SBsbPtr, BSIM4v5SBsbBinding, BSIM4v5sbNode, BSIM4v5sbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5BdbPtr, BSIM4v5BdbBinding, BSIM4v5bNode, BSIM4v5dbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5BbpPtr, BSIM4v5BbpBinding, BSIM4v5bNode, BSIM4v5bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5BsbPtr, BSIM4v5BsbBinding, BSIM4v5bNode, BSIM4v5sbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5BbPtr, BSIM4v5BbBinding, BSIM4v5bNode, BSIM4v5bNode); + } + if (model->BSIM4v5rdsMod) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5DgpPtr, BSIM4v5DgpBinding, BSIM4v5dNode, BSIM4v5gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5DspPtr, BSIM4v5DspBinding, BSIM4v5dNode, BSIM4v5sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5DbpPtr, BSIM4v5DbpBinding, BSIM4v5dNode, BSIM4v5bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5SdpPtr, BSIM4v5SdpBinding, BSIM4v5sNode, BSIM4v5dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5SgpPtr, BSIM4v5SgpBinding, BSIM4v5sNode, BSIM4v5gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v5SbpPtr, BSIM4v5SbpBinding, BSIM4v5sNode, BSIM4v5bNodePrime); + } + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/bsim4v5/bsim4v5def.h b/src/spicelib/devices/bsim4v5/bsim4v5def.h index 443be7b02..b7d76e037 100644 --- a/src/spicelib/devices/bsim4v5/bsim4v5def.h +++ b/src/spicelib/devices/bsim4v5/bsim4v5def.h @@ -561,6 +561,79 @@ typedef struct sBSIM4v5instance double **BSIM4v5nVar; #endif /* NONOISE */ +#ifdef KLU + BindElement *BSIM4v5DPbpBinding ; + BindElement *BSIM4v5GPbpBinding ; + BindElement *BSIM4v5SPbpBinding ; + BindElement *BSIM4v5BPdpBinding ; + BindElement *BSIM4v5BPgpBinding ; + BindElement *BSIM4v5BPspBinding ; + BindElement *BSIM4v5BPbpBinding ; + BindElement *BSIM4v5DdBinding ; + BindElement *BSIM4v5GPgpBinding ; + BindElement *BSIM4v5SsBinding ; + BindElement *BSIM4v5DPdpBinding ; + BindElement *BSIM4v5SPspBinding ; + BindElement *BSIM4v5DdpBinding ; + BindElement *BSIM4v5GPdpBinding ; + BindElement *BSIM4v5GPspBinding ; + BindElement *BSIM4v5SspBinding ; + BindElement *BSIM4v5DPspBinding ; + BindElement *BSIM4v5DPdBinding ; + BindElement *BSIM4v5DPgpBinding ; + BindElement *BSIM4v5SPgpBinding ; + BindElement *BSIM4v5SPsBinding ; + BindElement *BSIM4v5SPdpBinding ; + BindElement *BSIM4v5QqBinding ; + BindElement *BSIM4v5QbpBinding ; + BindElement *BSIM4v5QdpBinding ; + BindElement *BSIM4v5QspBinding ; + BindElement *BSIM4v5QgpBinding ; + BindElement *BSIM4v5DPqBinding ; + BindElement *BSIM4v5SPqBinding ; + BindElement *BSIM4v5GPqBinding ; + BindElement *BSIM4v5GEgeBinding ; + BindElement *BSIM4v5GEgpBinding ; + BindElement *BSIM4v5GPgeBinding ; + BindElement *BSIM4v5GEdpBinding ; + BindElement *BSIM4v5GEspBinding ; + BindElement *BSIM4v5GEbpBinding ; + BindElement *BSIM4v5GMdpBinding ; + BindElement *BSIM4v5GMgpBinding ; + BindElement *BSIM4v5GMgmBinding ; + BindElement *BSIM4v5GMgeBinding ; + BindElement *BSIM4v5GMspBinding ; + BindElement *BSIM4v5GMbpBinding ; + BindElement *BSIM4v5DPgmBinding ; + BindElement *BSIM4v5GPgmBinding ; + BindElement *BSIM4v5GEgmBinding ; + BindElement *BSIM4v5SPgmBinding ; + BindElement *BSIM4v5BPgmBinding ; + BindElement *BSIM4v5DPdbBinding ; + BindElement *BSIM4v5SPsbBinding ; + BindElement *BSIM4v5DBdpBinding ; + BindElement *BSIM4v5DBdbBinding ; + BindElement *BSIM4v5DBbpBinding ; + BindElement *BSIM4v5DBbBinding ; + BindElement *BSIM4v5BPdbBinding ; + BindElement *BSIM4v5BPbBinding ; + BindElement *BSIM4v5BPsbBinding ; + BindElement *BSIM4v5SBspBinding ; + BindElement *BSIM4v5SBbpBinding ; + BindElement *BSIM4v5SBbBinding ; + BindElement *BSIM4v5SBsbBinding ; + BindElement *BSIM4v5BdbBinding ; + BindElement *BSIM4v5BbpBinding ; + BindElement *BSIM4v5BsbBinding ; + BindElement *BSIM4v5BbBinding ; + BindElement *BSIM4v5DgpBinding ; + BindElement *BSIM4v5DspBinding ; + BindElement *BSIM4v5DbpBinding ; + BindElement *BSIM4v5SdpBinding ; + BindElement *BSIM4v5SgpBinding ; + BindElement *BSIM4v5SbpBinding ; +#endif + } BSIM4v5instance ; struct bsim4v5SizeDependParam diff --git a/src/spicelib/devices/bsim4v5/bsim4v5ext.h b/src/spicelib/devices/bsim4v5/bsim4v5ext.h index 3e043b9bc..2ef1f38df 100644 --- a/src/spicelib/devices/bsim4v5/bsim4v5ext.h +++ b/src/spicelib/devices/bsim4v5/bsim4v5ext.h @@ -29,3 +29,9 @@ extern int BSIM4v5trunc(GENmodel*,CKTcircuit*,double*); extern int BSIM4v5noise(int,int,GENmodel*,CKTcircuit*,Ndata*,double*); extern int BSIM4v5unsetup(GENmodel*,CKTcircuit*); extern int BSIM4v5soaCheck(CKTcircuit *, GENmodel *); + +#ifdef KLU +extern int BSIM4v5bindCSC (GENmodel*, CKTcircuit*) ; +extern int BSIM4v5bindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int BSIM4v5bindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/bsim4v5/bsim4v5init.c b/src/spicelib/devices/bsim4v5/bsim4v5init.c index 8ac071444..36f9b2cce 100644 --- a/src/spicelib/devices/bsim4v5/bsim4v5init.c +++ b/src/spicelib/devices/bsim4v5/bsim4v5init.c @@ -66,6 +66,11 @@ SPICEdev BSIM4v5info = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = BSIM4v5bindCSC, + .DEVbindCSCComplex = BSIM4v5bindCSCComplex, + .DEVbindCSCComplexToReal = BSIM4v5bindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/bsim4v6/Makefile.am b/src/spicelib/devices/bsim4v6/Makefile.am index ad03052c0..a8277ad2c 100644 --- a/src/spicelib/devices/bsim4v6/Makefile.am +++ b/src/spicelib/devices/bsim4v6/Makefile.am @@ -30,6 +30,9 @@ libbsim4v6_la_SOURCES = \ bsim4v6itf.h +if KLU_WANTED +libbsim4v6_la_SOURCES += b4v6bindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) diff --git a/src/spicelib/devices/bsim4v6/b4v6bindCSC.c b/src/spicelib/devices/bsim4v6/b4v6bindCSC.c new file mode 100644 index 000000000..b4ab1535e --- /dev/null +++ b/src/spicelib/devices/bsim4v6/b4v6bindCSC.c @@ -0,0 +1,323 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "bsim4v6def.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +BSIM4v6bindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + BSIM4v6model *model = (BSIM4v6model *)inModel ; + BSIM4v6instance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the BSIM4v6 models */ + for ( ; model != NULL ; model = BSIM4v6nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = BSIM4v6instances(model); here != NULL ; here = BSIM4v6nextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(BSIM4v6DPbpPtr, BSIM4v6DPbpBinding, BSIM4v6dNodePrime, BSIM4v6bNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6GPbpPtr, BSIM4v6GPbpBinding, BSIM4v6gNodePrime, BSIM4v6bNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6SPbpPtr, BSIM4v6SPbpBinding, BSIM4v6sNodePrime, BSIM4v6bNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6BPdpPtr, BSIM4v6BPdpBinding, BSIM4v6bNodePrime, BSIM4v6dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6BPgpPtr, BSIM4v6BPgpBinding, BSIM4v6bNodePrime, BSIM4v6gNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6BPspPtr, BSIM4v6BPspBinding, BSIM4v6bNodePrime, BSIM4v6sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6BPbpPtr, BSIM4v6BPbpBinding, BSIM4v6bNodePrime, BSIM4v6bNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6DdPtr, BSIM4v6DdBinding, BSIM4v6dNode, BSIM4v6dNode); + CREATE_KLU_BINDING_TABLE(BSIM4v6GPgpPtr, BSIM4v6GPgpBinding, BSIM4v6gNodePrime, BSIM4v6gNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6SsPtr, BSIM4v6SsBinding, BSIM4v6sNode, BSIM4v6sNode); + CREATE_KLU_BINDING_TABLE(BSIM4v6DPdpPtr, BSIM4v6DPdpBinding, BSIM4v6dNodePrime, BSIM4v6dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6SPspPtr, BSIM4v6SPspBinding, BSIM4v6sNodePrime, BSIM4v6sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6DdpPtr, BSIM4v6DdpBinding, BSIM4v6dNode, BSIM4v6dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6GPdpPtr, BSIM4v6GPdpBinding, BSIM4v6gNodePrime, BSIM4v6dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6GPspPtr, BSIM4v6GPspBinding, BSIM4v6gNodePrime, BSIM4v6sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6SspPtr, BSIM4v6SspBinding, BSIM4v6sNode, BSIM4v6sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6DPspPtr, BSIM4v6DPspBinding, BSIM4v6dNodePrime, BSIM4v6sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6DPdPtr, BSIM4v6DPdBinding, BSIM4v6dNodePrime, BSIM4v6dNode); + CREATE_KLU_BINDING_TABLE(BSIM4v6DPgpPtr, BSIM4v6DPgpBinding, BSIM4v6dNodePrime, BSIM4v6gNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6SPgpPtr, BSIM4v6SPgpBinding, BSIM4v6sNodePrime, BSIM4v6gNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6SPsPtr, BSIM4v6SPsBinding, BSIM4v6sNodePrime, BSIM4v6sNode); + CREATE_KLU_BINDING_TABLE(BSIM4v6SPdpPtr, BSIM4v6SPdpBinding, BSIM4v6sNodePrime, BSIM4v6dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6QqPtr, BSIM4v6QqBinding, BSIM4v6qNode, BSIM4v6qNode); + CREATE_KLU_BINDING_TABLE(BSIM4v6QbpPtr, BSIM4v6QbpBinding, BSIM4v6qNode, BSIM4v6bNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6QdpPtr, BSIM4v6QdpBinding, BSIM4v6qNode, BSIM4v6dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6QspPtr, BSIM4v6QspBinding, BSIM4v6qNode, BSIM4v6sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6QgpPtr, BSIM4v6QgpBinding, BSIM4v6qNode, BSIM4v6gNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6DPqPtr, BSIM4v6DPqBinding, BSIM4v6dNodePrime, BSIM4v6qNode); + CREATE_KLU_BINDING_TABLE(BSIM4v6SPqPtr, BSIM4v6SPqBinding, BSIM4v6sNodePrime, BSIM4v6qNode); + CREATE_KLU_BINDING_TABLE(BSIM4v6GPqPtr, BSIM4v6GPqBinding, BSIM4v6gNodePrime, BSIM4v6qNode); + if (here->BSIM4v6rgateMod != 0) + { + CREATE_KLU_BINDING_TABLE(BSIM4v6GEgePtr, BSIM4v6GEgeBinding, BSIM4v6gNodeExt, BSIM4v6gNodeExt); + CREATE_KLU_BINDING_TABLE(BSIM4v6GEgpPtr, BSIM4v6GEgpBinding, BSIM4v6gNodeExt, BSIM4v6gNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6GPgePtr, BSIM4v6GPgeBinding, BSIM4v6gNodePrime, BSIM4v6gNodeExt); + CREATE_KLU_BINDING_TABLE(BSIM4v6GEdpPtr, BSIM4v6GEdpBinding, BSIM4v6gNodeExt, BSIM4v6dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6GEspPtr, BSIM4v6GEspBinding, BSIM4v6gNodeExt, BSIM4v6sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6GEbpPtr, BSIM4v6GEbpBinding, BSIM4v6gNodeExt, BSIM4v6bNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6GMdpPtr, BSIM4v6GMdpBinding, BSIM4v6gNodeMid, BSIM4v6dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6GMgpPtr, BSIM4v6GMgpBinding, BSIM4v6gNodeMid, BSIM4v6gNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6GMgmPtr, BSIM4v6GMgmBinding, BSIM4v6gNodeMid, BSIM4v6gNodeMid); + CREATE_KLU_BINDING_TABLE(BSIM4v6GMgePtr, BSIM4v6GMgeBinding, BSIM4v6gNodeMid, BSIM4v6gNodeExt); + CREATE_KLU_BINDING_TABLE(BSIM4v6GMspPtr, BSIM4v6GMspBinding, BSIM4v6gNodeMid, BSIM4v6sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6GMbpPtr, BSIM4v6GMbpBinding, BSIM4v6gNodeMid, BSIM4v6bNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6DPgmPtr, BSIM4v6DPgmBinding, BSIM4v6dNodePrime, BSIM4v6gNodeMid); + CREATE_KLU_BINDING_TABLE(BSIM4v6GPgmPtr, BSIM4v6GPgmBinding, BSIM4v6gNodePrime, BSIM4v6gNodeMid); + CREATE_KLU_BINDING_TABLE(BSIM4v6GEgmPtr, BSIM4v6GEgmBinding, BSIM4v6gNodeExt, BSIM4v6gNodeMid); + CREATE_KLU_BINDING_TABLE(BSIM4v6SPgmPtr, BSIM4v6SPgmBinding, BSIM4v6sNodePrime, BSIM4v6gNodeMid); + CREATE_KLU_BINDING_TABLE(BSIM4v6BPgmPtr, BSIM4v6BPgmBinding, BSIM4v6bNodePrime, BSIM4v6gNodeMid); + } + if ((here->BSIM4v6rbodyMod == 1) || (here->BSIM4v6rbodyMod == 2)) + { + CREATE_KLU_BINDING_TABLE(BSIM4v6DPdbPtr, BSIM4v6DPdbBinding, BSIM4v6dNodePrime, BSIM4v6dbNode); + CREATE_KLU_BINDING_TABLE(BSIM4v6SPsbPtr, BSIM4v6SPsbBinding, BSIM4v6sNodePrime, BSIM4v6sbNode); + CREATE_KLU_BINDING_TABLE(BSIM4v6DBdpPtr, BSIM4v6DBdpBinding, BSIM4v6dbNode, BSIM4v6dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6DBdbPtr, BSIM4v6DBdbBinding, BSIM4v6dbNode, BSIM4v6dbNode); + CREATE_KLU_BINDING_TABLE(BSIM4v6DBbpPtr, BSIM4v6DBbpBinding, BSIM4v6dbNode, BSIM4v6bNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6DBbPtr, BSIM4v6DBbBinding, BSIM4v6dbNode, BSIM4v6bNode); + CREATE_KLU_BINDING_TABLE(BSIM4v6BPdbPtr, BSIM4v6BPdbBinding, BSIM4v6bNodePrime, BSIM4v6dbNode); + CREATE_KLU_BINDING_TABLE(BSIM4v6BPbPtr, BSIM4v6BPbBinding, BSIM4v6bNodePrime, BSIM4v6bNode); + CREATE_KLU_BINDING_TABLE(BSIM4v6BPsbPtr, BSIM4v6BPsbBinding, BSIM4v6bNodePrime, BSIM4v6sbNode); + CREATE_KLU_BINDING_TABLE(BSIM4v6SBspPtr, BSIM4v6SBspBinding, BSIM4v6sbNode, BSIM4v6sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6SBbpPtr, BSIM4v6SBbpBinding, BSIM4v6sbNode, BSIM4v6bNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6SBbPtr, BSIM4v6SBbBinding, BSIM4v6sbNode, BSIM4v6bNode); + CREATE_KLU_BINDING_TABLE(BSIM4v6SBsbPtr, BSIM4v6SBsbBinding, BSIM4v6sbNode, BSIM4v6sbNode); + CREATE_KLU_BINDING_TABLE(BSIM4v6BdbPtr, BSIM4v6BdbBinding, BSIM4v6bNode, BSIM4v6dbNode); + CREATE_KLU_BINDING_TABLE(BSIM4v6BbpPtr, BSIM4v6BbpBinding, BSIM4v6bNode, BSIM4v6bNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6BsbPtr, BSIM4v6BsbBinding, BSIM4v6bNode, BSIM4v6sbNode); + CREATE_KLU_BINDING_TABLE(BSIM4v6BbPtr, BSIM4v6BbBinding, BSIM4v6bNode, BSIM4v6bNode); + } + if (model->BSIM4v6rdsMod) + { + CREATE_KLU_BINDING_TABLE(BSIM4v6DgpPtr, BSIM4v6DgpBinding, BSIM4v6dNode, BSIM4v6gNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6DspPtr, BSIM4v6DspBinding, BSIM4v6dNode, BSIM4v6sNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6DbpPtr, BSIM4v6DbpBinding, BSIM4v6dNode, BSIM4v6bNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6SdpPtr, BSIM4v6SdpBinding, BSIM4v6sNode, BSIM4v6dNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6SgpPtr, BSIM4v6SgpBinding, BSIM4v6sNode, BSIM4v6gNodePrime); + CREATE_KLU_BINDING_TABLE(BSIM4v6SbpPtr, BSIM4v6SbpBinding, BSIM4v6sNode, BSIM4v6bNodePrime); + } + } + } + + return (OK) ; +} + +int +BSIM4v6bindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + BSIM4v6model *model = (BSIM4v6model *)inModel ; + BSIM4v6instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the BSIM4v6 models */ + for ( ; model != NULL ; model = BSIM4v6nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = BSIM4v6instances(model); here != NULL ; here = BSIM4v6nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6DPbpPtr, BSIM4v6DPbpBinding, BSIM4v6dNodePrime, BSIM4v6bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6GPbpPtr, BSIM4v6GPbpBinding, BSIM4v6gNodePrime, BSIM4v6bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6SPbpPtr, BSIM4v6SPbpBinding, BSIM4v6sNodePrime, BSIM4v6bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6BPdpPtr, BSIM4v6BPdpBinding, BSIM4v6bNodePrime, BSIM4v6dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6BPgpPtr, BSIM4v6BPgpBinding, BSIM4v6bNodePrime, BSIM4v6gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6BPspPtr, BSIM4v6BPspBinding, BSIM4v6bNodePrime, BSIM4v6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6BPbpPtr, BSIM4v6BPbpBinding, BSIM4v6bNodePrime, BSIM4v6bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6DdPtr, BSIM4v6DdBinding, BSIM4v6dNode, BSIM4v6dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6GPgpPtr, BSIM4v6GPgpBinding, BSIM4v6gNodePrime, BSIM4v6gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6SsPtr, BSIM4v6SsBinding, BSIM4v6sNode, BSIM4v6sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6DPdpPtr, BSIM4v6DPdpBinding, BSIM4v6dNodePrime, BSIM4v6dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6SPspPtr, BSIM4v6SPspBinding, BSIM4v6sNodePrime, BSIM4v6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6DdpPtr, BSIM4v6DdpBinding, BSIM4v6dNode, BSIM4v6dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6GPdpPtr, BSIM4v6GPdpBinding, BSIM4v6gNodePrime, BSIM4v6dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6GPspPtr, BSIM4v6GPspBinding, BSIM4v6gNodePrime, BSIM4v6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6SspPtr, BSIM4v6SspBinding, BSIM4v6sNode, BSIM4v6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6DPspPtr, BSIM4v6DPspBinding, BSIM4v6dNodePrime, BSIM4v6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6DPdPtr, BSIM4v6DPdBinding, BSIM4v6dNodePrime, BSIM4v6dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6DPgpPtr, BSIM4v6DPgpBinding, BSIM4v6dNodePrime, BSIM4v6gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6SPgpPtr, BSIM4v6SPgpBinding, BSIM4v6sNodePrime, BSIM4v6gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6SPsPtr, BSIM4v6SPsBinding, BSIM4v6sNodePrime, BSIM4v6sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6SPdpPtr, BSIM4v6SPdpBinding, BSIM4v6sNodePrime, BSIM4v6dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6QqPtr, BSIM4v6QqBinding, BSIM4v6qNode, BSIM4v6qNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6QbpPtr, BSIM4v6QbpBinding, BSIM4v6qNode, BSIM4v6bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6QdpPtr, BSIM4v6QdpBinding, BSIM4v6qNode, BSIM4v6dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6QspPtr, BSIM4v6QspBinding, BSIM4v6qNode, BSIM4v6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6QgpPtr, BSIM4v6QgpBinding, BSIM4v6qNode, BSIM4v6gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6DPqPtr, BSIM4v6DPqBinding, BSIM4v6dNodePrime, BSIM4v6qNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6SPqPtr, BSIM4v6SPqBinding, BSIM4v6sNodePrime, BSIM4v6qNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6GPqPtr, BSIM4v6GPqBinding, BSIM4v6gNodePrime, BSIM4v6qNode); + if (here->BSIM4v6rgateMod != 0) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6GEgePtr, BSIM4v6GEgeBinding, BSIM4v6gNodeExt, BSIM4v6gNodeExt); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6GEgpPtr, BSIM4v6GEgpBinding, BSIM4v6gNodeExt, BSIM4v6gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6GPgePtr, BSIM4v6GPgeBinding, BSIM4v6gNodePrime, BSIM4v6gNodeExt); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6GEdpPtr, BSIM4v6GEdpBinding, BSIM4v6gNodeExt, BSIM4v6dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6GEspPtr, BSIM4v6GEspBinding, BSIM4v6gNodeExt, BSIM4v6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6GEbpPtr, BSIM4v6GEbpBinding, BSIM4v6gNodeExt, BSIM4v6bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6GMdpPtr, BSIM4v6GMdpBinding, BSIM4v6gNodeMid, BSIM4v6dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6GMgpPtr, BSIM4v6GMgpBinding, BSIM4v6gNodeMid, BSIM4v6gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6GMgmPtr, BSIM4v6GMgmBinding, BSIM4v6gNodeMid, BSIM4v6gNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6GMgePtr, BSIM4v6GMgeBinding, BSIM4v6gNodeMid, BSIM4v6gNodeExt); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6GMspPtr, BSIM4v6GMspBinding, BSIM4v6gNodeMid, BSIM4v6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6GMbpPtr, BSIM4v6GMbpBinding, BSIM4v6gNodeMid, BSIM4v6bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6DPgmPtr, BSIM4v6DPgmBinding, BSIM4v6dNodePrime, BSIM4v6gNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6GPgmPtr, BSIM4v6GPgmBinding, BSIM4v6gNodePrime, BSIM4v6gNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6GEgmPtr, BSIM4v6GEgmBinding, BSIM4v6gNodeExt, BSIM4v6gNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6SPgmPtr, BSIM4v6SPgmBinding, BSIM4v6sNodePrime, BSIM4v6gNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6BPgmPtr, BSIM4v6BPgmBinding, BSIM4v6bNodePrime, BSIM4v6gNodeMid); + } + if ((here->BSIM4v6rbodyMod == 1) || (here->BSIM4v6rbodyMod == 2)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6DPdbPtr, BSIM4v6DPdbBinding, BSIM4v6dNodePrime, BSIM4v6dbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6SPsbPtr, BSIM4v6SPsbBinding, BSIM4v6sNodePrime, BSIM4v6sbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6DBdpPtr, BSIM4v6DBdpBinding, BSIM4v6dbNode, BSIM4v6dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6DBdbPtr, BSIM4v6DBdbBinding, BSIM4v6dbNode, BSIM4v6dbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6DBbpPtr, BSIM4v6DBbpBinding, BSIM4v6dbNode, BSIM4v6bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6DBbPtr, BSIM4v6DBbBinding, BSIM4v6dbNode, BSIM4v6bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6BPdbPtr, BSIM4v6BPdbBinding, BSIM4v6bNodePrime, BSIM4v6dbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6BPbPtr, BSIM4v6BPbBinding, BSIM4v6bNodePrime, BSIM4v6bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6BPsbPtr, BSIM4v6BPsbBinding, BSIM4v6bNodePrime, BSIM4v6sbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6SBspPtr, BSIM4v6SBspBinding, BSIM4v6sbNode, BSIM4v6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6SBbpPtr, BSIM4v6SBbpBinding, BSIM4v6sbNode, BSIM4v6bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6SBbPtr, BSIM4v6SBbBinding, BSIM4v6sbNode, BSIM4v6bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6SBsbPtr, BSIM4v6SBsbBinding, BSIM4v6sbNode, BSIM4v6sbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6BdbPtr, BSIM4v6BdbBinding, BSIM4v6bNode, BSIM4v6dbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6BbpPtr, BSIM4v6BbpBinding, BSIM4v6bNode, BSIM4v6bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6BsbPtr, BSIM4v6BsbBinding, BSIM4v6bNode, BSIM4v6sbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6BbPtr, BSIM4v6BbBinding, BSIM4v6bNode, BSIM4v6bNode); + } + if (model->BSIM4v6rdsMod) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6DgpPtr, BSIM4v6DgpBinding, BSIM4v6dNode, BSIM4v6gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6DspPtr, BSIM4v6DspBinding, BSIM4v6dNode, BSIM4v6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6DbpPtr, BSIM4v6DbpBinding, BSIM4v6dNode, BSIM4v6bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6SdpPtr, BSIM4v6SdpBinding, BSIM4v6sNode, BSIM4v6dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6SgpPtr, BSIM4v6SgpBinding, BSIM4v6sNode, BSIM4v6gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(BSIM4v6SbpPtr, BSIM4v6SbpBinding, BSIM4v6sNode, BSIM4v6bNodePrime); + } + } + } + + return (OK) ; +} + +int +BSIM4v6bindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + BSIM4v6model *model = (BSIM4v6model *)inModel ; + BSIM4v6instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the BSIM4v6 models */ + for ( ; model != NULL ; model = BSIM4v6nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = BSIM4v6instances(model); here != NULL ; here = BSIM4v6nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6DPbpPtr, BSIM4v6DPbpBinding, BSIM4v6dNodePrime, BSIM4v6bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6GPbpPtr, BSIM4v6GPbpBinding, BSIM4v6gNodePrime, BSIM4v6bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6SPbpPtr, BSIM4v6SPbpBinding, BSIM4v6sNodePrime, BSIM4v6bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6BPdpPtr, BSIM4v6BPdpBinding, BSIM4v6bNodePrime, BSIM4v6dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6BPgpPtr, BSIM4v6BPgpBinding, BSIM4v6bNodePrime, BSIM4v6gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6BPspPtr, BSIM4v6BPspBinding, BSIM4v6bNodePrime, BSIM4v6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6BPbpPtr, BSIM4v6BPbpBinding, BSIM4v6bNodePrime, BSIM4v6bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6DdPtr, BSIM4v6DdBinding, BSIM4v6dNode, BSIM4v6dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6GPgpPtr, BSIM4v6GPgpBinding, BSIM4v6gNodePrime, BSIM4v6gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6SsPtr, BSIM4v6SsBinding, BSIM4v6sNode, BSIM4v6sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6DPdpPtr, BSIM4v6DPdpBinding, BSIM4v6dNodePrime, BSIM4v6dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6SPspPtr, BSIM4v6SPspBinding, BSIM4v6sNodePrime, BSIM4v6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6DdpPtr, BSIM4v6DdpBinding, BSIM4v6dNode, BSIM4v6dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6GPdpPtr, BSIM4v6GPdpBinding, BSIM4v6gNodePrime, BSIM4v6dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6GPspPtr, BSIM4v6GPspBinding, BSIM4v6gNodePrime, BSIM4v6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6SspPtr, BSIM4v6SspBinding, BSIM4v6sNode, BSIM4v6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6DPspPtr, BSIM4v6DPspBinding, BSIM4v6dNodePrime, BSIM4v6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6DPdPtr, BSIM4v6DPdBinding, BSIM4v6dNodePrime, BSIM4v6dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6DPgpPtr, BSIM4v6DPgpBinding, BSIM4v6dNodePrime, BSIM4v6gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6SPgpPtr, BSIM4v6SPgpBinding, BSIM4v6sNodePrime, BSIM4v6gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6SPsPtr, BSIM4v6SPsBinding, BSIM4v6sNodePrime, BSIM4v6sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6SPdpPtr, BSIM4v6SPdpBinding, BSIM4v6sNodePrime, BSIM4v6dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6QqPtr, BSIM4v6QqBinding, BSIM4v6qNode, BSIM4v6qNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6QbpPtr, BSIM4v6QbpBinding, BSIM4v6qNode, BSIM4v6bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6QdpPtr, BSIM4v6QdpBinding, BSIM4v6qNode, BSIM4v6dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6QspPtr, BSIM4v6QspBinding, BSIM4v6qNode, BSIM4v6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6QgpPtr, BSIM4v6QgpBinding, BSIM4v6qNode, BSIM4v6gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6DPqPtr, BSIM4v6DPqBinding, BSIM4v6dNodePrime, BSIM4v6qNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6SPqPtr, BSIM4v6SPqBinding, BSIM4v6sNodePrime, BSIM4v6qNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6GPqPtr, BSIM4v6GPqBinding, BSIM4v6gNodePrime, BSIM4v6qNode); + if (here->BSIM4v6rgateMod != 0) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6GEgePtr, BSIM4v6GEgeBinding, BSIM4v6gNodeExt, BSIM4v6gNodeExt); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6GEgpPtr, BSIM4v6GEgpBinding, BSIM4v6gNodeExt, BSIM4v6gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6GPgePtr, BSIM4v6GPgeBinding, BSIM4v6gNodePrime, BSIM4v6gNodeExt); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6GEdpPtr, BSIM4v6GEdpBinding, BSIM4v6gNodeExt, BSIM4v6dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6GEspPtr, BSIM4v6GEspBinding, BSIM4v6gNodeExt, BSIM4v6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6GEbpPtr, BSIM4v6GEbpBinding, BSIM4v6gNodeExt, BSIM4v6bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6GMdpPtr, BSIM4v6GMdpBinding, BSIM4v6gNodeMid, BSIM4v6dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6GMgpPtr, BSIM4v6GMgpBinding, BSIM4v6gNodeMid, BSIM4v6gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6GMgmPtr, BSIM4v6GMgmBinding, BSIM4v6gNodeMid, BSIM4v6gNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6GMgePtr, BSIM4v6GMgeBinding, BSIM4v6gNodeMid, BSIM4v6gNodeExt); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6GMspPtr, BSIM4v6GMspBinding, BSIM4v6gNodeMid, BSIM4v6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6GMbpPtr, BSIM4v6GMbpBinding, BSIM4v6gNodeMid, BSIM4v6bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6DPgmPtr, BSIM4v6DPgmBinding, BSIM4v6dNodePrime, BSIM4v6gNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6GPgmPtr, BSIM4v6GPgmBinding, BSIM4v6gNodePrime, BSIM4v6gNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6GEgmPtr, BSIM4v6GEgmBinding, BSIM4v6gNodeExt, BSIM4v6gNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6SPgmPtr, BSIM4v6SPgmBinding, BSIM4v6sNodePrime, BSIM4v6gNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6BPgmPtr, BSIM4v6BPgmBinding, BSIM4v6bNodePrime, BSIM4v6gNodeMid); + } + if ((here->BSIM4v6rbodyMod == 1) || (here->BSIM4v6rbodyMod == 2)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6DPdbPtr, BSIM4v6DPdbBinding, BSIM4v6dNodePrime, BSIM4v6dbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6SPsbPtr, BSIM4v6SPsbBinding, BSIM4v6sNodePrime, BSIM4v6sbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6DBdpPtr, BSIM4v6DBdpBinding, BSIM4v6dbNode, BSIM4v6dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6DBdbPtr, BSIM4v6DBdbBinding, BSIM4v6dbNode, BSIM4v6dbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6DBbpPtr, BSIM4v6DBbpBinding, BSIM4v6dbNode, BSIM4v6bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6DBbPtr, BSIM4v6DBbBinding, BSIM4v6dbNode, BSIM4v6bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6BPdbPtr, BSIM4v6BPdbBinding, BSIM4v6bNodePrime, BSIM4v6dbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6BPbPtr, BSIM4v6BPbBinding, BSIM4v6bNodePrime, BSIM4v6bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6BPsbPtr, BSIM4v6BPsbBinding, BSIM4v6bNodePrime, BSIM4v6sbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6SBspPtr, BSIM4v6SBspBinding, BSIM4v6sbNode, BSIM4v6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6SBbpPtr, BSIM4v6SBbpBinding, BSIM4v6sbNode, BSIM4v6bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6SBbPtr, BSIM4v6SBbBinding, BSIM4v6sbNode, BSIM4v6bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6SBsbPtr, BSIM4v6SBsbBinding, BSIM4v6sbNode, BSIM4v6sbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6BdbPtr, BSIM4v6BdbBinding, BSIM4v6bNode, BSIM4v6dbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6BbpPtr, BSIM4v6BbpBinding, BSIM4v6bNode, BSIM4v6bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6BsbPtr, BSIM4v6BsbBinding, BSIM4v6bNode, BSIM4v6sbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6BbPtr, BSIM4v6BbBinding, BSIM4v6bNode, BSIM4v6bNode); + } + if (model->BSIM4v6rdsMod) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6DgpPtr, BSIM4v6DgpBinding, BSIM4v6dNode, BSIM4v6gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6DspPtr, BSIM4v6DspBinding, BSIM4v6dNode, BSIM4v6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6DbpPtr, BSIM4v6DbpBinding, BSIM4v6dNode, BSIM4v6bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6SdpPtr, BSIM4v6SdpBinding, BSIM4v6sNode, BSIM4v6dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6SgpPtr, BSIM4v6SgpBinding, BSIM4v6sNode, BSIM4v6gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(BSIM4v6SbpPtr, BSIM4v6SbpBinding, BSIM4v6sNode, BSIM4v6bNodePrime); + } + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/bsim4v6/bsim4v6def.h b/src/spicelib/devices/bsim4v6/bsim4v6def.h index 62de645f5..abd97f3c2 100644 --- a/src/spicelib/devices/bsim4v6/bsim4v6def.h +++ b/src/spicelib/devices/bsim4v6/bsim4v6def.h @@ -570,6 +570,79 @@ typedef struct sBSIM4v6instance double **BSIM4v6nVar; #endif /* NONOISE */ +#ifdef KLU + BindElement *BSIM4v6DPbpBinding ; + BindElement *BSIM4v6GPbpBinding ; + BindElement *BSIM4v6SPbpBinding ; + BindElement *BSIM4v6BPdpBinding ; + BindElement *BSIM4v6BPgpBinding ; + BindElement *BSIM4v6BPspBinding ; + BindElement *BSIM4v6BPbpBinding ; + BindElement *BSIM4v6DdBinding ; + BindElement *BSIM4v6GPgpBinding ; + BindElement *BSIM4v6SsBinding ; + BindElement *BSIM4v6DPdpBinding ; + BindElement *BSIM4v6SPspBinding ; + BindElement *BSIM4v6DdpBinding ; + BindElement *BSIM4v6GPdpBinding ; + BindElement *BSIM4v6GPspBinding ; + BindElement *BSIM4v6SspBinding ; + BindElement *BSIM4v6DPspBinding ; + BindElement *BSIM4v6DPdBinding ; + BindElement *BSIM4v6DPgpBinding ; + BindElement *BSIM4v6SPgpBinding ; + BindElement *BSIM4v6SPsBinding ; + BindElement *BSIM4v6SPdpBinding ; + BindElement *BSIM4v6QqBinding ; + BindElement *BSIM4v6QbpBinding ; + BindElement *BSIM4v6QdpBinding ; + BindElement *BSIM4v6QspBinding ; + BindElement *BSIM4v6QgpBinding ; + BindElement *BSIM4v6DPqBinding ; + BindElement *BSIM4v6SPqBinding ; + BindElement *BSIM4v6GPqBinding ; + BindElement *BSIM4v6GEgeBinding ; + BindElement *BSIM4v6GEgpBinding ; + BindElement *BSIM4v6GPgeBinding ; + BindElement *BSIM4v6GEdpBinding ; + BindElement *BSIM4v6GEspBinding ; + BindElement *BSIM4v6GEbpBinding ; + BindElement *BSIM4v6GMdpBinding ; + BindElement *BSIM4v6GMgpBinding ; + BindElement *BSIM4v6GMgmBinding ; + BindElement *BSIM4v6GMgeBinding ; + BindElement *BSIM4v6GMspBinding ; + BindElement *BSIM4v6GMbpBinding ; + BindElement *BSIM4v6DPgmBinding ; + BindElement *BSIM4v6GPgmBinding ; + BindElement *BSIM4v6GEgmBinding ; + BindElement *BSIM4v6SPgmBinding ; + BindElement *BSIM4v6BPgmBinding ; + BindElement *BSIM4v6DPdbBinding ; + BindElement *BSIM4v6SPsbBinding ; + BindElement *BSIM4v6DBdpBinding ; + BindElement *BSIM4v6DBdbBinding ; + BindElement *BSIM4v6DBbpBinding ; + BindElement *BSIM4v6DBbBinding ; + BindElement *BSIM4v6BPdbBinding ; + BindElement *BSIM4v6BPbBinding ; + BindElement *BSIM4v6BPsbBinding ; + BindElement *BSIM4v6SBspBinding ; + BindElement *BSIM4v6SBbpBinding ; + BindElement *BSIM4v6SBbBinding ; + BindElement *BSIM4v6SBsbBinding ; + BindElement *BSIM4v6BdbBinding ; + BindElement *BSIM4v6BbpBinding ; + BindElement *BSIM4v6BsbBinding ; + BindElement *BSIM4v6BbBinding ; + BindElement *BSIM4v6DgpBinding ; + BindElement *BSIM4v6DspBinding ; + BindElement *BSIM4v6DbpBinding ; + BindElement *BSIM4v6SdpBinding ; + BindElement *BSIM4v6SgpBinding ; + BindElement *BSIM4v6SbpBinding ; +#endif + } BSIM4v6instance ; struct bsim4v6SizeDependParam diff --git a/src/spicelib/devices/bsim4v6/bsim4v6ext.h b/src/spicelib/devices/bsim4v6/bsim4v6ext.h index 814262b33..00dab9d70 100644 --- a/src/spicelib/devices/bsim4v6/bsim4v6ext.h +++ b/src/spicelib/devices/bsim4v6/bsim4v6ext.h @@ -29,3 +29,9 @@ extern int BSIM4v6trunc(GENmodel*,CKTcircuit*,double*); extern int BSIM4v6noise(int,int,GENmodel*,CKTcircuit*,Ndata*,double*); extern int BSIM4v6unsetup(GENmodel*,CKTcircuit*); extern int BSIM4v6soaCheck(CKTcircuit *, GENmodel *); + +#ifdef KLU +extern int BSIM4v6bindCSC (GENmodel*, CKTcircuit*) ; +extern int BSIM4v6bindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int BSIM4v6bindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/bsim4v6/bsim4v6init.c b/src/spicelib/devices/bsim4v6/bsim4v6init.c index 6e25377d4..29ca2102e 100644 --- a/src/spicelib/devices/bsim4v6/bsim4v6init.c +++ b/src/spicelib/devices/bsim4v6/bsim4v6init.c @@ -66,6 +66,11 @@ SPICEdev BSIM4v6info = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = BSIM4v6bindCSC, + .DEVbindCSCComplex = BSIM4v6bindCSCComplex, + .DEVbindCSCComplexToReal = BSIM4v6bindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/bsimsoi/Makefile.am b/src/spicelib/devices/bsimsoi/Makefile.am index ba4676815..7ef42475a 100644 --- a/src/spicelib/devices/bsimsoi/Makefile.am +++ b/src/spicelib/devices/bsimsoi/Makefile.am @@ -29,6 +29,9 @@ libbsim4soi_la_SOURCES = \ b4soiitf.h +if KLU_WANTED +libbsim4soi_la_SOURCES += b4soibindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) diff --git a/src/spicelib/devices/bsimsoi/b4soibindCSC.c b/src/spicelib/devices/bsimsoi/b4soibindCSC.c new file mode 100644 index 000000000..cf4854bb6 --- /dev/null +++ b/src/spicelib/devices/bsimsoi/b4soibindCSC.c @@ -0,0 +1,506 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "b4soidef.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +B4SOIbindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + B4SOImodel *model = (B4SOImodel *)inModel ; + B4SOIinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the B4SOI models */ + for ( ; model != NULL ; model = B4SOInextModel(model)) + { + /* loop through all the instances of the model */ + for (here = B4SOIinstances(model); here != NULL ; here = B4SOInextInstance(here)) + { + if ((model->B4SOIshMod == 1) && (here->B4SOIrth0 != 0.0)) + { + CREATE_KLU_BINDING_TABLE(B4SOITemptempPtr, B4SOITemptempBinding, B4SOItempNode, B4SOItempNode); + CREATE_KLU_BINDING_TABLE(B4SOITempdpPtr, B4SOITempdpBinding, B4SOItempNode, B4SOIdNodePrime); + CREATE_KLU_BINDING_TABLE(B4SOITempspPtr, B4SOITempspBinding, B4SOItempNode, B4SOIsNodePrime); + CREATE_KLU_BINDING_TABLE(B4SOITempgPtr, B4SOITempgBinding, B4SOItempNode, B4SOIgNode); + CREATE_KLU_BINDING_TABLE(B4SOITempbPtr, B4SOITempbBinding, B4SOItempNode, B4SOIbNode); + CREATE_KLU_BINDING_TABLE(B4SOIGtempPtr, B4SOIGtempBinding, B4SOIgNode, B4SOItempNode); + CREATE_KLU_BINDING_TABLE(B4SOIDPtempPtr, B4SOIDPtempBinding, B4SOIdNodePrime, B4SOItempNode); + CREATE_KLU_BINDING_TABLE(B4SOISPtempPtr, B4SOISPtempBinding, B4SOIsNodePrime, B4SOItempNode); + CREATE_KLU_BINDING_TABLE(B4SOIEtempPtr, B4SOIEtempBinding, B4SOIeNode, B4SOItempNode); + CREATE_KLU_BINDING_TABLE(B4SOIBtempPtr, B4SOIBtempBinding, B4SOIbNode, B4SOItempNode); + if (here->B4SOIbodyMod == 1) + { + CREATE_KLU_BINDING_TABLE(B4SOIPtempPtr, B4SOIPtempBinding, B4SOIpNode, B4SOItempNode); + } + if (here->B4SOIsoiMod != 0) + { + CREATE_KLU_BINDING_TABLE(B4SOITempePtr, B4SOITempeBinding, B4SOItempNode, B4SOIeNode); + } + } + if (here->B4SOIbodyMod == 2) + { + } + else if (here->B4SOIbodyMod == 1) + { + CREATE_KLU_BINDING_TABLE(B4SOIBpPtr, B4SOIBpBinding, B4SOIbNode, B4SOIpNode); + CREATE_KLU_BINDING_TABLE(B4SOIPbPtr, B4SOIPbBinding, B4SOIpNode, B4SOIbNode); + CREATE_KLU_BINDING_TABLE(B4SOIPpPtr, B4SOIPpBinding, B4SOIpNode, B4SOIpNode); + CREATE_KLU_BINDING_TABLE(B4SOIPgPtr, B4SOIPgBinding, B4SOIpNode, B4SOIgNode); + CREATE_KLU_BINDING_TABLE(B4SOIGpPtr, B4SOIGpBinding, B4SOIgNode, B4SOIpNode); + } + if (here->B4SOIrgateMod != 0) + { + CREATE_KLU_BINDING_TABLE(B4SOIGEgePtr, B4SOIGEgeBinding, B4SOIgNodeExt, B4SOIgNodeExt); + CREATE_KLU_BINDING_TABLE(B4SOIGEgPtr, B4SOIGEgBinding, B4SOIgNodeExt, B4SOIgNode); + CREATE_KLU_BINDING_TABLE(B4SOIGgePtr, B4SOIGgeBinding, B4SOIgNode, B4SOIgNodeExt); + CREATE_KLU_BINDING_TABLE(B4SOIGEdpPtr, B4SOIGEdpBinding, B4SOIgNodeExt, B4SOIdNodePrime); + CREATE_KLU_BINDING_TABLE(B4SOIGEspPtr, B4SOIGEspBinding, B4SOIgNodeExt, B4SOIsNodePrime); + if (here->B4SOIsoiMod != 2) + { + CREATE_KLU_BINDING_TABLE(B4SOIGEbPtr, B4SOIGEbBinding, B4SOIgNodeExt, B4SOIbNode); + } + CREATE_KLU_BINDING_TABLE(B4SOIGMdpPtr, B4SOIGMdpBinding, B4SOIgNodeMid, B4SOIdNodePrime); + CREATE_KLU_BINDING_TABLE(B4SOIGMgPtr, B4SOIGMgBinding, B4SOIgNodeMid, B4SOIgNode); + CREATE_KLU_BINDING_TABLE(B4SOIGMgmPtr, B4SOIGMgmBinding, B4SOIgNodeMid, B4SOIgNodeMid); + CREATE_KLU_BINDING_TABLE(B4SOIGMgePtr, B4SOIGMgeBinding, B4SOIgNodeMid, B4SOIgNodeExt); + CREATE_KLU_BINDING_TABLE(B4SOIGMspPtr, B4SOIGMspBinding, B4SOIgNodeMid, B4SOIsNodePrime); + if (here->B4SOIsoiMod != 2) + { + CREATE_KLU_BINDING_TABLE(B4SOIGMbPtr, B4SOIGMbBinding, B4SOIgNodeMid, B4SOIbNode); + } + CREATE_KLU_BINDING_TABLE(B4SOIGMePtr, B4SOIGMeBinding, B4SOIgNodeMid, B4SOIeNode); + CREATE_KLU_BINDING_TABLE(B4SOIDPgmPtr, B4SOIDPgmBinding, B4SOIdNodePrime, B4SOIgNodeMid); + CREATE_KLU_BINDING_TABLE(B4SOIGgmPtr, B4SOIGgmBinding, B4SOIgNode, B4SOIgNodeMid); + CREATE_KLU_BINDING_TABLE(B4SOIGEgmPtr, B4SOIGEgmBinding, B4SOIgNodeExt, B4SOIgNodeMid); + CREATE_KLU_BINDING_TABLE(B4SOISPgmPtr, B4SOISPgmBinding, B4SOIsNodePrime, B4SOIgNodeMid); + CREATE_KLU_BINDING_TABLE(B4SOIEgmPtr, B4SOIEgmBinding, B4SOIeNode, B4SOIgNodeMid); + } + if (here->B4SOIsoiMod != 2) /* v3.2 */ + { + CREATE_KLU_BINDING_TABLE(B4SOIEbPtr, B4SOIEbBinding, B4SOIeNode, B4SOIbNode); + CREATE_KLU_BINDING_TABLE(B4SOIGbPtr, B4SOIGbBinding, B4SOIgNode, B4SOIbNode); + CREATE_KLU_BINDING_TABLE(B4SOIDPbPtr, B4SOIDPbBinding, B4SOIdNodePrime, B4SOIbNode); + CREATE_KLU_BINDING_TABLE(B4SOISPbPtr, B4SOISPbBinding, B4SOIsNodePrime, B4SOIbNode); + CREATE_KLU_BINDING_TABLE(B4SOIBePtr, B4SOIBeBinding, B4SOIbNode, B4SOIeNode); + CREATE_KLU_BINDING_TABLE(B4SOIBgPtr, B4SOIBgBinding, B4SOIbNode, B4SOIgNode); + CREATE_KLU_BINDING_TABLE(B4SOIBdpPtr, B4SOIBdpBinding, B4SOIbNode, B4SOIdNodePrime); + CREATE_KLU_BINDING_TABLE(B4SOIBspPtr, B4SOIBspBinding, B4SOIbNode, B4SOIsNodePrime); + CREATE_KLU_BINDING_TABLE(B4SOIBbPtr, B4SOIBbBinding, B4SOIbNode, B4SOIbNode); + } + CREATE_KLU_BINDING_TABLE(B4SOIEgPtr, B4SOIEgBinding, B4SOIeNode, B4SOIgNode); + CREATE_KLU_BINDING_TABLE(B4SOIEdpPtr, B4SOIEdpBinding, B4SOIeNode, B4SOIdNodePrime); + CREATE_KLU_BINDING_TABLE(B4SOIEspPtr, B4SOIEspBinding, B4SOIeNode, B4SOIsNodePrime); + CREATE_KLU_BINDING_TABLE(B4SOIGePtr, B4SOIGeBinding, B4SOIgNode, B4SOIeNode); + CREATE_KLU_BINDING_TABLE(B4SOIDPePtr, B4SOIDPeBinding, B4SOIdNodePrime, B4SOIeNode); + CREATE_KLU_BINDING_TABLE(B4SOISPePtr, B4SOISPeBinding, B4SOIsNodePrime, B4SOIeNode); + CREATE_KLU_BINDING_TABLE(B4SOIEePtr, B4SOIEeBinding, B4SOIeNode, B4SOIeNode); + CREATE_KLU_BINDING_TABLE(B4SOIGgPtr, B4SOIGgBinding, B4SOIgNode, B4SOIgNode); + CREATE_KLU_BINDING_TABLE(B4SOIGdpPtr, B4SOIGdpBinding, B4SOIgNode, B4SOIdNodePrime); + CREATE_KLU_BINDING_TABLE(B4SOIGspPtr, B4SOIGspBinding, B4SOIgNode, B4SOIsNodePrime); + CREATE_KLU_BINDING_TABLE(B4SOIDPgPtr, B4SOIDPgBinding, B4SOIdNodePrime, B4SOIgNode); + CREATE_KLU_BINDING_TABLE(B4SOIDPdpPtr, B4SOIDPdpBinding, B4SOIdNodePrime, B4SOIdNodePrime); + CREATE_KLU_BINDING_TABLE(B4SOIDPspPtr, B4SOIDPspBinding, B4SOIdNodePrime, B4SOIsNodePrime); + CREATE_KLU_BINDING_TABLE(B4SOIDPdPtr, B4SOIDPdBinding, B4SOIdNodePrime, B4SOIdNode); + CREATE_KLU_BINDING_TABLE(B4SOISPgPtr, B4SOISPgBinding, B4SOIsNodePrime, B4SOIgNode); + CREATE_KLU_BINDING_TABLE(B4SOISPdpPtr, B4SOISPdpBinding, B4SOIsNodePrime, B4SOIdNodePrime); + CREATE_KLU_BINDING_TABLE(B4SOISPspPtr, B4SOISPspBinding, B4SOIsNodePrime, B4SOIsNodePrime); + CREATE_KLU_BINDING_TABLE(B4SOISPsPtr, B4SOISPsBinding, B4SOIsNodePrime, B4SOIsNode); + CREATE_KLU_BINDING_TABLE(B4SOIDdPtr, B4SOIDdBinding, B4SOIdNode, B4SOIdNode); + CREATE_KLU_BINDING_TABLE(B4SOIDdpPtr, B4SOIDdpBinding, B4SOIdNode, B4SOIdNodePrime); + CREATE_KLU_BINDING_TABLE(B4SOISsPtr, B4SOISsBinding, B4SOIsNode, B4SOIsNode); + CREATE_KLU_BINDING_TABLE(B4SOISspPtr, B4SOISspBinding, B4SOIsNode, B4SOIsNodePrime); + if (here->B4SOIrbodyMod == 1) + { + CREATE_KLU_BINDING_TABLE(B4SOIDPdbPtr, B4SOIDPdbBinding, B4SOIdNodePrime, B4SOIdbNode); + CREATE_KLU_BINDING_TABLE(B4SOISPsbPtr, B4SOISPsbBinding, B4SOIsNodePrime, B4SOIsbNode); + CREATE_KLU_BINDING_TABLE(B4SOIDBdpPtr, B4SOIDBdpBinding, B4SOIdbNode, B4SOIdNodePrime); + CREATE_KLU_BINDING_TABLE(B4SOIDBdbPtr, B4SOIDBdbBinding, B4SOIdbNode, B4SOIdbNode); + CREATE_KLU_BINDING_TABLE(B4SOIDBbPtr, B4SOIDBbBinding, B4SOIdbNode, B4SOIbNode); + CREATE_KLU_BINDING_TABLE(B4SOISBspPtr, B4SOISBspBinding, B4SOIsbNode, B4SOIsNodePrime); + CREATE_KLU_BINDING_TABLE(B4SOISBsbPtr, B4SOISBsbBinding, B4SOIsbNode, B4SOIsbNode); + CREATE_KLU_BINDING_TABLE(B4SOISBbPtr, B4SOISBbBinding, B4SOIsbNode, B4SOIbNode); + CREATE_KLU_BINDING_TABLE(B4SOIBdbPtr, B4SOIBdbBinding, B4SOIbNode, B4SOIdbNode); + CREATE_KLU_BINDING_TABLE(B4SOIBsbPtr, B4SOIBsbBinding, B4SOIbNode, B4SOIsbNode); + } + if (model->B4SOIrdsMod) + { + CREATE_KLU_BINDING_TABLE(B4SOIDgPtr, B4SOIDgBinding, B4SOIdNode, B4SOIgNode); + CREATE_KLU_BINDING_TABLE(B4SOIDspPtr, B4SOIDspBinding, B4SOIdNode, B4SOIsNodePrime); + CREATE_KLU_BINDING_TABLE(B4SOISdpPtr, B4SOISdpBinding, B4SOIsNode, B4SOIdNodePrime); + CREATE_KLU_BINDING_TABLE(B4SOISgPtr, B4SOISgBinding, B4SOIsNode, B4SOIgNode); + if (model->B4SOIsoiMod != 2) + { + CREATE_KLU_BINDING_TABLE(B4SOIDbPtr, B4SOIDbBinding, B4SOIdNode, B4SOIbNode); + CREATE_KLU_BINDING_TABLE(B4SOISbPtr, B4SOISbBinding, B4SOIsNode, B4SOIbNode); + } + } + if (here->B4SOIdebugMod != 0) + { + CREATE_KLU_BINDING_TABLE(B4SOIVbsPtr, B4SOIVbsBinding, B4SOIvbsNode, B4SOIvbsNode); + CREATE_KLU_BINDING_TABLE(B4SOIIdsPtr, B4SOIIdsBinding, B4SOIidsNode, B4SOIidsNode); + CREATE_KLU_BINDING_TABLE(B4SOIIcPtr, B4SOIIcBinding, B4SOIicNode, B4SOIicNode); + CREATE_KLU_BINDING_TABLE(B4SOIIbsPtr, B4SOIIbsBinding, B4SOIibsNode, B4SOIibsNode); + CREATE_KLU_BINDING_TABLE(B4SOIIbdPtr, B4SOIIbdBinding, B4SOIibdNode, B4SOIibdNode); + CREATE_KLU_BINDING_TABLE(B4SOIIiiPtr, B4SOIIiiBinding, B4SOIiiiNode, B4SOIiiiNode); + CREATE_KLU_BINDING_TABLE(B4SOIIgPtr, B4SOIIgBinding, B4SOIigNode, B4SOIigNode); + CREATE_KLU_BINDING_TABLE(B4SOIGiggPtr, B4SOIGiggBinding, B4SOIgiggNode, B4SOIgiggNode); + CREATE_KLU_BINDING_TABLE(B4SOIGigdPtr, B4SOIGigdBinding, B4SOIgigdNode, B4SOIgigdNode); + CREATE_KLU_BINDING_TABLE(B4SOIGigbPtr, B4SOIGigbBinding, B4SOIgigbNode, B4SOIgigbNode); + CREATE_KLU_BINDING_TABLE(B4SOIIgidlPtr, B4SOIIgidlBinding, B4SOIigidlNode, B4SOIigidlNode); + CREATE_KLU_BINDING_TABLE(B4SOIItunPtr, B4SOIItunBinding, B4SOIitunNode, B4SOIitunNode); + CREATE_KLU_BINDING_TABLE(B4SOIIbpPtr, B4SOIIbpBinding, B4SOIibpNode, B4SOIibpNode); + CREATE_KLU_BINDING_TABLE(B4SOICbbPtr, B4SOICbbBinding, B4SOIcbbNode, B4SOIcbbNode); + CREATE_KLU_BINDING_TABLE(B4SOICbdPtr, B4SOICbdBinding, B4SOIcbdNode, B4SOIcbdNode); + CREATE_KLU_BINDING_TABLE(B4SOICbgPtr, B4SOICbgBinding, B4SOIcbgNode, B4SOIcbgNode); + CREATE_KLU_BINDING_TABLE(B4SOIQbfPtr, B4SOIQbfBinding, B4SOIqbfNode, B4SOIqbfNode); + CREATE_KLU_BINDING_TABLE(B4SOIQjsPtr, B4SOIQjsBinding, B4SOIqjsNode, B4SOIqjsNode); + CREATE_KLU_BINDING_TABLE(B4SOIQjdPtr, B4SOIQjdBinding, B4SOIqjdNode, B4SOIqjdNode); + } + } + } + + return (OK) ; +} + +int +B4SOIbindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + B4SOImodel *model = (B4SOImodel *)inModel ; + B4SOIinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the B4SOI models */ + for ( ; model != NULL ; model = B4SOInextModel(model)) + { + /* loop through all the instances of the model */ + for (here = B4SOIinstances(model); here != NULL ; here = B4SOInextInstance(here)) + { + if ((model->B4SOIshMod == 1) && (here->B4SOIrth0 != 0.0)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOITemptempPtr, B4SOITemptempBinding, B4SOItempNode, B4SOItempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOITempdpPtr, B4SOITempdpBinding, B4SOItempNode, B4SOIdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOITempspPtr, B4SOITempspBinding, B4SOItempNode, B4SOIsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOITempgPtr, B4SOITempgBinding, B4SOItempNode, B4SOIgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOITempbPtr, B4SOITempbBinding, B4SOItempNode, B4SOIbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIGtempPtr, B4SOIGtempBinding, B4SOIgNode, B4SOItempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIDPtempPtr, B4SOIDPtempBinding, B4SOIdNodePrime, B4SOItempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOISPtempPtr, B4SOISPtempBinding, B4SOIsNodePrime, B4SOItempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIEtempPtr, B4SOIEtempBinding, B4SOIeNode, B4SOItempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIBtempPtr, B4SOIBtempBinding, B4SOIbNode, B4SOItempNode); + if (here->B4SOIbodyMod == 1) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIPtempPtr, B4SOIPtempBinding, B4SOIpNode, B4SOItempNode); + } + if (here->B4SOIsoiMod != 0) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOITempePtr, B4SOITempeBinding, B4SOItempNode, B4SOIeNode); + } + } + if (here->B4SOIbodyMod == 2) + { + } + else if (here->B4SOIbodyMod == 1) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIBpPtr, B4SOIBpBinding, B4SOIbNode, B4SOIpNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIPbPtr, B4SOIPbBinding, B4SOIpNode, B4SOIbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIPpPtr, B4SOIPpBinding, B4SOIpNode, B4SOIpNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIPgPtr, B4SOIPgBinding, B4SOIpNode, B4SOIgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIGpPtr, B4SOIGpBinding, B4SOIgNode, B4SOIpNode); + } + if (here->B4SOIrgateMod != 0) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIGEgePtr, B4SOIGEgeBinding, B4SOIgNodeExt, B4SOIgNodeExt); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIGEgPtr, B4SOIGEgBinding, B4SOIgNodeExt, B4SOIgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIGgePtr, B4SOIGgeBinding, B4SOIgNode, B4SOIgNodeExt); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIGEdpPtr, B4SOIGEdpBinding, B4SOIgNodeExt, B4SOIdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIGEspPtr, B4SOIGEspBinding, B4SOIgNodeExt, B4SOIsNodePrime); + if (here->B4SOIsoiMod != 2) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIGEbPtr, B4SOIGEbBinding, B4SOIgNodeExt, B4SOIbNode); + } + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIGMdpPtr, B4SOIGMdpBinding, B4SOIgNodeMid, B4SOIdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIGMgPtr, B4SOIGMgBinding, B4SOIgNodeMid, B4SOIgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIGMgmPtr, B4SOIGMgmBinding, B4SOIgNodeMid, B4SOIgNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIGMgePtr, B4SOIGMgeBinding, B4SOIgNodeMid, B4SOIgNodeExt); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIGMspPtr, B4SOIGMspBinding, B4SOIgNodeMid, B4SOIsNodePrime); + if (here->B4SOIsoiMod != 2) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIGMbPtr, B4SOIGMbBinding, B4SOIgNodeMid, B4SOIbNode); + } + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIGMePtr, B4SOIGMeBinding, B4SOIgNodeMid, B4SOIeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIDPgmPtr, B4SOIDPgmBinding, B4SOIdNodePrime, B4SOIgNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIGgmPtr, B4SOIGgmBinding, B4SOIgNode, B4SOIgNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIGEgmPtr, B4SOIGEgmBinding, B4SOIgNodeExt, B4SOIgNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOISPgmPtr, B4SOISPgmBinding, B4SOIsNodePrime, B4SOIgNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIEgmPtr, B4SOIEgmBinding, B4SOIeNode, B4SOIgNodeMid); + } + if (here->B4SOIsoiMod != 2) /* v3.2 */ + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIEbPtr, B4SOIEbBinding, B4SOIeNode, B4SOIbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIGbPtr, B4SOIGbBinding, B4SOIgNode, B4SOIbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIDPbPtr, B4SOIDPbBinding, B4SOIdNodePrime, B4SOIbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOISPbPtr, B4SOISPbBinding, B4SOIsNodePrime, B4SOIbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIBePtr, B4SOIBeBinding, B4SOIbNode, B4SOIeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIBgPtr, B4SOIBgBinding, B4SOIbNode, B4SOIgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIBdpPtr, B4SOIBdpBinding, B4SOIbNode, B4SOIdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIBspPtr, B4SOIBspBinding, B4SOIbNode, B4SOIsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIBbPtr, B4SOIBbBinding, B4SOIbNode, B4SOIbNode); + } + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIEgPtr, B4SOIEgBinding, B4SOIeNode, B4SOIgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIEdpPtr, B4SOIEdpBinding, B4SOIeNode, B4SOIdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIEspPtr, B4SOIEspBinding, B4SOIeNode, B4SOIsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIGePtr, B4SOIGeBinding, B4SOIgNode, B4SOIeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIDPePtr, B4SOIDPeBinding, B4SOIdNodePrime, B4SOIeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOISPePtr, B4SOISPeBinding, B4SOIsNodePrime, B4SOIeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIEePtr, B4SOIEeBinding, B4SOIeNode, B4SOIeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIGgPtr, B4SOIGgBinding, B4SOIgNode, B4SOIgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIGdpPtr, B4SOIGdpBinding, B4SOIgNode, B4SOIdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIGspPtr, B4SOIGspBinding, B4SOIgNode, B4SOIsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIDPgPtr, B4SOIDPgBinding, B4SOIdNodePrime, B4SOIgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIDPdpPtr, B4SOIDPdpBinding, B4SOIdNodePrime, B4SOIdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIDPspPtr, B4SOIDPspBinding, B4SOIdNodePrime, B4SOIsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIDPdPtr, B4SOIDPdBinding, B4SOIdNodePrime, B4SOIdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOISPgPtr, B4SOISPgBinding, B4SOIsNodePrime, B4SOIgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOISPdpPtr, B4SOISPdpBinding, B4SOIsNodePrime, B4SOIdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOISPspPtr, B4SOISPspBinding, B4SOIsNodePrime, B4SOIsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOISPsPtr, B4SOISPsBinding, B4SOIsNodePrime, B4SOIsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIDdPtr, B4SOIDdBinding, B4SOIdNode, B4SOIdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIDdpPtr, B4SOIDdpBinding, B4SOIdNode, B4SOIdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOISsPtr, B4SOISsBinding, B4SOIsNode, B4SOIsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOISspPtr, B4SOISspBinding, B4SOIsNode, B4SOIsNodePrime); + if (here->B4SOIrbodyMod == 1) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIDPdbPtr, B4SOIDPdbBinding, B4SOIdNodePrime, B4SOIdbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOISPsbPtr, B4SOISPsbBinding, B4SOIsNodePrime, B4SOIsbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIDBdpPtr, B4SOIDBdpBinding, B4SOIdbNode, B4SOIdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIDBdbPtr, B4SOIDBdbBinding, B4SOIdbNode, B4SOIdbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIDBbPtr, B4SOIDBbBinding, B4SOIdbNode, B4SOIbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOISBspPtr, B4SOISBspBinding, B4SOIsbNode, B4SOIsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOISBsbPtr, B4SOISBsbBinding, B4SOIsbNode, B4SOIsbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOISBbPtr, B4SOISBbBinding, B4SOIsbNode, B4SOIbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIBdbPtr, B4SOIBdbBinding, B4SOIbNode, B4SOIdbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIBsbPtr, B4SOIBsbBinding, B4SOIbNode, B4SOIsbNode); + } + if (model->B4SOIrdsMod) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIDgPtr, B4SOIDgBinding, B4SOIdNode, B4SOIgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIDspPtr, B4SOIDspBinding, B4SOIdNode, B4SOIsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOISdpPtr, B4SOISdpBinding, B4SOIsNode, B4SOIdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOISgPtr, B4SOISgBinding, B4SOIsNode, B4SOIgNode); + if (model->B4SOIsoiMod != 2) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIDbPtr, B4SOIDbBinding, B4SOIdNode, B4SOIbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOISbPtr, B4SOISbBinding, B4SOIsNode, B4SOIbNode); + } + } + if (here->B4SOIdebugMod != 0) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIVbsPtr, B4SOIVbsBinding, B4SOIvbsNode, B4SOIvbsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIIdsPtr, B4SOIIdsBinding, B4SOIidsNode, B4SOIidsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIIcPtr, B4SOIIcBinding, B4SOIicNode, B4SOIicNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIIbsPtr, B4SOIIbsBinding, B4SOIibsNode, B4SOIibsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIIbdPtr, B4SOIIbdBinding, B4SOIibdNode, B4SOIibdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIIiiPtr, B4SOIIiiBinding, B4SOIiiiNode, B4SOIiiiNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIIgPtr, B4SOIIgBinding, B4SOIigNode, B4SOIigNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIGiggPtr, B4SOIGiggBinding, B4SOIgiggNode, B4SOIgiggNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIGigdPtr, B4SOIGigdBinding, B4SOIgigdNode, B4SOIgigdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIGigbPtr, B4SOIGigbBinding, B4SOIgigbNode, B4SOIgigbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIIgidlPtr, B4SOIIgidlBinding, B4SOIigidlNode, B4SOIigidlNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIItunPtr, B4SOIItunBinding, B4SOIitunNode, B4SOIitunNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIIbpPtr, B4SOIIbpBinding, B4SOIibpNode, B4SOIibpNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOICbbPtr, B4SOICbbBinding, B4SOIcbbNode, B4SOIcbbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOICbdPtr, B4SOICbdBinding, B4SOIcbdNode, B4SOIcbdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOICbgPtr, B4SOICbgBinding, B4SOIcbgNode, B4SOIcbgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIQbfPtr, B4SOIQbfBinding, B4SOIqbfNode, B4SOIqbfNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIQjsPtr, B4SOIQjsBinding, B4SOIqjsNode, B4SOIqjsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(B4SOIQjdPtr, B4SOIQjdBinding, B4SOIqjdNode, B4SOIqjdNode); + } + } + } + + return (OK) ; +} + +int +B4SOIbindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + B4SOImodel *model = (B4SOImodel *)inModel ; + B4SOIinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the B4SOI models */ + for ( ; model != NULL ; model = B4SOInextModel(model)) + { + /* loop through all the instances of the model */ + for (here = B4SOIinstances(model); here != NULL ; here = B4SOInextInstance(here)) + { + if ((model->B4SOIshMod == 1) && (here->B4SOIrth0 != 0.0)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOITemptempPtr, B4SOITemptempBinding, B4SOItempNode, B4SOItempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOITempdpPtr, B4SOITempdpBinding, B4SOItempNode, B4SOIdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOITempspPtr, B4SOITempspBinding, B4SOItempNode, B4SOIsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOITempgPtr, B4SOITempgBinding, B4SOItempNode, B4SOIgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOITempbPtr, B4SOITempbBinding, B4SOItempNode, B4SOIbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIGtempPtr, B4SOIGtempBinding, B4SOIgNode, B4SOItempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIDPtempPtr, B4SOIDPtempBinding, B4SOIdNodePrime, B4SOItempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOISPtempPtr, B4SOISPtempBinding, B4SOIsNodePrime, B4SOItempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIEtempPtr, B4SOIEtempBinding, B4SOIeNode, B4SOItempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIBtempPtr, B4SOIBtempBinding, B4SOIbNode, B4SOItempNode); + if (here->B4SOIbodyMod == 1) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIPtempPtr, B4SOIPtempBinding, B4SOIpNode, B4SOItempNode); + } + if (here->B4SOIsoiMod != 0) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOITempePtr, B4SOITempeBinding, B4SOItempNode, B4SOIeNode); + } + } + if (here->B4SOIbodyMod == 2) + { + } + else if (here->B4SOIbodyMod == 1) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIBpPtr, B4SOIBpBinding, B4SOIbNode, B4SOIpNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIPbPtr, B4SOIPbBinding, B4SOIpNode, B4SOIbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIPpPtr, B4SOIPpBinding, B4SOIpNode, B4SOIpNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIPgPtr, B4SOIPgBinding, B4SOIpNode, B4SOIgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIGpPtr, B4SOIGpBinding, B4SOIgNode, B4SOIpNode); + } + if (here->B4SOIrgateMod != 0) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIGEgePtr, B4SOIGEgeBinding, B4SOIgNodeExt, B4SOIgNodeExt); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIGEgPtr, B4SOIGEgBinding, B4SOIgNodeExt, B4SOIgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIGgePtr, B4SOIGgeBinding, B4SOIgNode, B4SOIgNodeExt); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIGEdpPtr, B4SOIGEdpBinding, B4SOIgNodeExt, B4SOIdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIGEspPtr, B4SOIGEspBinding, B4SOIgNodeExt, B4SOIsNodePrime); + if (here->B4SOIsoiMod != 2) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIGEbPtr, B4SOIGEbBinding, B4SOIgNodeExt, B4SOIbNode); + } + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIGMdpPtr, B4SOIGMdpBinding, B4SOIgNodeMid, B4SOIdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIGMgPtr, B4SOIGMgBinding, B4SOIgNodeMid, B4SOIgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIGMgmPtr, B4SOIGMgmBinding, B4SOIgNodeMid, B4SOIgNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIGMgePtr, B4SOIGMgeBinding, B4SOIgNodeMid, B4SOIgNodeExt); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIGMspPtr, B4SOIGMspBinding, B4SOIgNodeMid, B4SOIsNodePrime); + if (here->B4SOIsoiMod != 2) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIGMbPtr, B4SOIGMbBinding, B4SOIgNodeMid, B4SOIbNode); + } + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIGMePtr, B4SOIGMeBinding, B4SOIgNodeMid, B4SOIeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIDPgmPtr, B4SOIDPgmBinding, B4SOIdNodePrime, B4SOIgNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIGgmPtr, B4SOIGgmBinding, B4SOIgNode, B4SOIgNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIGEgmPtr, B4SOIGEgmBinding, B4SOIgNodeExt, B4SOIgNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOISPgmPtr, B4SOISPgmBinding, B4SOIsNodePrime, B4SOIgNodeMid); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIEgmPtr, B4SOIEgmBinding, B4SOIeNode, B4SOIgNodeMid); + } + if (here->B4SOIsoiMod != 2) /* v3.2 */ + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIEbPtr, B4SOIEbBinding, B4SOIeNode, B4SOIbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIGbPtr, B4SOIGbBinding, B4SOIgNode, B4SOIbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIDPbPtr, B4SOIDPbBinding, B4SOIdNodePrime, B4SOIbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOISPbPtr, B4SOISPbBinding, B4SOIsNodePrime, B4SOIbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIBePtr, B4SOIBeBinding, B4SOIbNode, B4SOIeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIBgPtr, B4SOIBgBinding, B4SOIbNode, B4SOIgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIBdpPtr, B4SOIBdpBinding, B4SOIbNode, B4SOIdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIBspPtr, B4SOIBspBinding, B4SOIbNode, B4SOIsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIBbPtr, B4SOIBbBinding, B4SOIbNode, B4SOIbNode); + } + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIEgPtr, B4SOIEgBinding, B4SOIeNode, B4SOIgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIEdpPtr, B4SOIEdpBinding, B4SOIeNode, B4SOIdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIEspPtr, B4SOIEspBinding, B4SOIeNode, B4SOIsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIGePtr, B4SOIGeBinding, B4SOIgNode, B4SOIeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIDPePtr, B4SOIDPeBinding, B4SOIdNodePrime, B4SOIeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOISPePtr, B4SOISPeBinding, B4SOIsNodePrime, B4SOIeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIEePtr, B4SOIEeBinding, B4SOIeNode, B4SOIeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIGgPtr, B4SOIGgBinding, B4SOIgNode, B4SOIgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIGdpPtr, B4SOIGdpBinding, B4SOIgNode, B4SOIdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIGspPtr, B4SOIGspBinding, B4SOIgNode, B4SOIsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIDPgPtr, B4SOIDPgBinding, B4SOIdNodePrime, B4SOIgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIDPdpPtr, B4SOIDPdpBinding, B4SOIdNodePrime, B4SOIdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIDPspPtr, B4SOIDPspBinding, B4SOIdNodePrime, B4SOIsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIDPdPtr, B4SOIDPdBinding, B4SOIdNodePrime, B4SOIdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOISPgPtr, B4SOISPgBinding, B4SOIsNodePrime, B4SOIgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOISPdpPtr, B4SOISPdpBinding, B4SOIsNodePrime, B4SOIdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOISPspPtr, B4SOISPspBinding, B4SOIsNodePrime, B4SOIsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOISPsPtr, B4SOISPsBinding, B4SOIsNodePrime, B4SOIsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIDdPtr, B4SOIDdBinding, B4SOIdNode, B4SOIdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIDdpPtr, B4SOIDdpBinding, B4SOIdNode, B4SOIdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOISsPtr, B4SOISsBinding, B4SOIsNode, B4SOIsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOISspPtr, B4SOISspBinding, B4SOIsNode, B4SOIsNodePrime); + if (here->B4SOIrbodyMod == 1) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIDPdbPtr, B4SOIDPdbBinding, B4SOIdNodePrime, B4SOIdbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOISPsbPtr, B4SOISPsbBinding, B4SOIsNodePrime, B4SOIsbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIDBdpPtr, B4SOIDBdpBinding, B4SOIdbNode, B4SOIdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIDBdbPtr, B4SOIDBdbBinding, B4SOIdbNode, B4SOIdbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIDBbPtr, B4SOIDBbBinding, B4SOIdbNode, B4SOIbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOISBspPtr, B4SOISBspBinding, B4SOIsbNode, B4SOIsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOISBsbPtr, B4SOISBsbBinding, B4SOIsbNode, B4SOIsbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOISBbPtr, B4SOISBbBinding, B4SOIsbNode, B4SOIbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIBdbPtr, B4SOIBdbBinding, B4SOIbNode, B4SOIdbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIBsbPtr, B4SOIBsbBinding, B4SOIbNode, B4SOIsbNode); + } + if (model->B4SOIrdsMod) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIDgPtr, B4SOIDgBinding, B4SOIdNode, B4SOIgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIDspPtr, B4SOIDspBinding, B4SOIdNode, B4SOIsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOISdpPtr, B4SOISdpBinding, B4SOIsNode, B4SOIdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOISgPtr, B4SOISgBinding, B4SOIsNode, B4SOIgNode); + if (model->B4SOIsoiMod != 2) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIDbPtr, B4SOIDbBinding, B4SOIdNode, B4SOIbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOISbPtr, B4SOISbBinding, B4SOIsNode, B4SOIbNode); + } + } + if (here->B4SOIdebugMod != 0) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIVbsPtr, B4SOIVbsBinding, B4SOIvbsNode, B4SOIvbsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIIdsPtr, B4SOIIdsBinding, B4SOIidsNode, B4SOIidsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIIcPtr, B4SOIIcBinding, B4SOIicNode, B4SOIicNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIIbsPtr, B4SOIIbsBinding, B4SOIibsNode, B4SOIibsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIIbdPtr, B4SOIIbdBinding, B4SOIibdNode, B4SOIibdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIIiiPtr, B4SOIIiiBinding, B4SOIiiiNode, B4SOIiiiNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIIgPtr, B4SOIIgBinding, B4SOIigNode, B4SOIigNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIGiggPtr, B4SOIGiggBinding, B4SOIgiggNode, B4SOIgiggNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIGigdPtr, B4SOIGigdBinding, B4SOIgigdNode, B4SOIgigdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIGigbPtr, B4SOIGigbBinding, B4SOIgigbNode, B4SOIgigbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIIgidlPtr, B4SOIIgidlBinding, B4SOIigidlNode, B4SOIigidlNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIItunPtr, B4SOIItunBinding, B4SOIitunNode, B4SOIitunNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIIbpPtr, B4SOIIbpBinding, B4SOIibpNode, B4SOIibpNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOICbbPtr, B4SOICbbBinding, B4SOIcbbNode, B4SOIcbbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOICbdPtr, B4SOICbdBinding, B4SOIcbdNode, B4SOIcbdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOICbgPtr, B4SOICbgBinding, B4SOIcbgNode, B4SOIcbgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIQbfPtr, B4SOIQbfBinding, B4SOIqbfNode, B4SOIqbfNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIQjsPtr, B4SOIQjsBinding, B4SOIqjsNode, B4SOIqjsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(B4SOIQjdPtr, B4SOIQjdBinding, B4SOIqjdNode, B4SOIqjdNode); + } + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/bsimsoi/b4soidef.h b/src/spicelib/devices/bsimsoi/b4soidef.h index 96913736a..2a3497120 100644 --- a/src/spicelib/devices/bsimsoi/b4soidef.h +++ b/src/spicelib/devices/bsimsoi/b4soidef.h @@ -742,6 +742,110 @@ typedef struct sB4SOIinstance double **B4SOInVar; #endif /* NONOISE */ +#ifdef KLU + BindElement *B4SOITemptempBinding ; + BindElement *B4SOITempdpBinding ; + BindElement *B4SOITempspBinding ; + BindElement *B4SOITempgBinding ; + BindElement *B4SOITempbBinding ; + BindElement *B4SOIGtempBinding ; + BindElement *B4SOIDPtempBinding ; + BindElement *B4SOISPtempBinding ; + BindElement *B4SOIEtempBinding ; + BindElement *B4SOIBtempBinding ; + BindElement *B4SOIPtempBinding ; + BindElement *B4SOITempeBinding ; + BindElement *B4SOIBpBinding ; + BindElement *B4SOIPbBinding ; + BindElement *B4SOIPpBinding ; + BindElement *B4SOIPgBinding ; + BindElement *B4SOIGpBinding ; + BindElement *B4SOIGEgeBinding ; + BindElement *B4SOIGEgBinding ; + BindElement *B4SOIGgeBinding ; + BindElement *B4SOIGEdpBinding ; + BindElement *B4SOIGEspBinding ; + BindElement *B4SOIGEbBinding ; + BindElement *B4SOIGMdpBinding ; + BindElement *B4SOIGMgBinding ; + BindElement *B4SOIGMgmBinding ; + BindElement *B4SOIGMgeBinding ; + BindElement *B4SOIGMspBinding ; + BindElement *B4SOIGMbBinding ; + BindElement *B4SOIGMeBinding ; + BindElement *B4SOIDPgmBinding ; + BindElement *B4SOIGgmBinding ; + BindElement *B4SOIGEgmBinding ; + BindElement *B4SOISPgmBinding ; + BindElement *B4SOIEgmBinding ; + BindElement *B4SOIEbBinding ; + BindElement *B4SOIGbBinding ; + BindElement *B4SOIDPbBinding ; + BindElement *B4SOISPbBinding ; + BindElement *B4SOIBeBinding ; + BindElement *B4SOIBgBinding ; + BindElement *B4SOIBdpBinding ; + BindElement *B4SOIBspBinding ; + BindElement *B4SOIBbBinding ; + BindElement *B4SOIEgBinding ; + BindElement *B4SOIEdpBinding ; + BindElement *B4SOIEspBinding ; + BindElement *B4SOIGeBinding ; + BindElement *B4SOIDPeBinding ; + BindElement *B4SOISPeBinding ; + BindElement *B4SOIEeBinding ; + BindElement *B4SOIGgBinding ; + BindElement *B4SOIGdpBinding ; + BindElement *B4SOIGspBinding ; + BindElement *B4SOIDPgBinding ; + BindElement *B4SOIDPdpBinding ; + BindElement *B4SOIDPspBinding ; + BindElement *B4SOIDPdBinding ; + BindElement *B4SOISPgBinding ; + BindElement *B4SOISPdpBinding ; + BindElement *B4SOISPspBinding ; + BindElement *B4SOISPsBinding ; + BindElement *B4SOIDdBinding ; + BindElement *B4SOIDdpBinding ; + BindElement *B4SOISsBinding ; + BindElement *B4SOISspBinding ; + BindElement *B4SOIDPdbBinding ; + BindElement *B4SOISPsbBinding ; + BindElement *B4SOIDBdpBinding ; + BindElement *B4SOIDBdbBinding ; + BindElement *B4SOIDBbBinding ; + BindElement *B4SOISBspBinding ; + BindElement *B4SOISBsbBinding ; + BindElement *B4SOISBbBinding ; + BindElement *B4SOIBdbBinding ; + BindElement *B4SOIBsbBinding ; + BindElement *B4SOIDgBinding ; + BindElement *B4SOIDspBinding ; + BindElement *B4SOISdpBinding ; + BindElement *B4SOISgBinding ; + BindElement *B4SOIDbBinding ; + BindElement *B4SOISbBinding ; + BindElement *B4SOIVbsBinding ; + BindElement *B4SOIIdsBinding ; + BindElement *B4SOIIcBinding ; + BindElement *B4SOIIbsBinding ; + BindElement *B4SOIIbdBinding ; + BindElement *B4SOIIiiBinding ; + BindElement *B4SOIIgBinding ; + BindElement *B4SOIGiggBinding ; + BindElement *B4SOIGigdBinding ; + BindElement *B4SOIGigbBinding ; + BindElement *B4SOIIgidlBinding ; + BindElement *B4SOIItunBinding ; + BindElement *B4SOIIbpBinding ; + BindElement *B4SOICbbBinding ; + BindElement *B4SOICbdBinding ; + BindElement *B4SOICbgBinding ; + BindElement *B4SOIQbfBinding ; + BindElement *B4SOIQjsBinding ; + BindElement *B4SOIQjdBinding ; +#endif + } B4SOIinstance ; struct b4soiSizeDependParam diff --git a/src/spicelib/devices/bsimsoi/b4soiext.h b/src/spicelib/devices/bsimsoi/b4soiext.h index 014baab32..429647045 100644 --- a/src/spicelib/devices/bsimsoi/b4soiext.h +++ b/src/spicelib/devices/bsimsoi/b4soiext.h @@ -31,3 +31,9 @@ extern int B4SOItrunc(GENmodel*,CKTcircuit*,double*); extern int B4SOInoise(int,int,GENmodel*,CKTcircuit*,Ndata*,double*); extern int B4SOIunsetup(GENmodel*,CKTcircuit*); extern int B4SOIsoaCheck(CKTcircuit *, GENmodel *); + +#ifdef KLU +extern int B4SOIbindCSC (GENmodel*, CKTcircuit*) ; +extern int B4SOIbindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int B4SOIbindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/bsimsoi/b4soiinit.c b/src/spicelib/devices/bsimsoi/b4soiinit.c index 3cdc3c117..fe110e4f0 100644 --- a/src/spicelib/devices/bsimsoi/b4soiinit.c +++ b/src/spicelib/devices/bsimsoi/b4soiinit.c @@ -64,6 +64,11 @@ SPICEdev B4SOIinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = B4SOIbindCSC, + .DEVbindCSCComplex = B4SOIbindCSCComplex, + .DEVbindCSCComplexToReal = B4SOIbindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/cap/Makefile.am b/src/spicelib/devices/cap/Makefile.am index 4205040ae..e0916e32b 100644 --- a/src/spicelib/devices/cap/Makefile.am +++ b/src/spicelib/devices/cap/Makefile.am @@ -31,6 +31,9 @@ libcap_la_SOURCES = \ captrunc.c +if KLU_WANTED +libcap_la_SOURCES += capbindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) diff --git a/src/spicelib/devices/cap/capbindCSC.c b/src/spicelib/devices/cap/capbindCSC.c new file mode 100644 index 000000000..77a37f7fc --- /dev/null +++ b/src/spicelib/devices/cap/capbindCSC.c @@ -0,0 +1,98 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "capdefs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +CAPbindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + CAPmodel *model = (CAPmodel *)inModel ; + CAPinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the CAP models */ + for ( ; model != NULL ; model = CAPnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = CAPinstances(model); here != NULL ; here = CAPnextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(CAPposPosPtr, CAPposPosBinding, CAPposNode, CAPposNode); + CREATE_KLU_BINDING_TABLE(CAPnegNegPtr, CAPnegNegBinding, CAPnegNode, CAPnegNode); + CREATE_KLU_BINDING_TABLE(CAPposNegPtr, CAPposNegBinding, CAPposNode, CAPnegNode); + CREATE_KLU_BINDING_TABLE(CAPnegPosPtr, CAPnegPosBinding, CAPnegNode, CAPposNode); + } + } + + return (OK) ; +} + +int +CAPbindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + CAPmodel *model = (CAPmodel *)inModel ; + CAPinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the CAP models */ + for ( ; model != NULL ; model = CAPnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = CAPinstances(model); here != NULL ; here = CAPnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(CAPposPosPtr, CAPposPosBinding, CAPposNode, CAPposNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(CAPnegNegPtr, CAPnegNegBinding, CAPnegNode, CAPnegNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(CAPposNegPtr, CAPposNegBinding, CAPposNode, CAPnegNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(CAPnegPosPtr, CAPnegPosBinding, CAPnegNode, CAPposNode); + } + } + + return (OK) ; +} + +int +CAPbindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + CAPmodel *model = (CAPmodel *)inModel ; + CAPinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the CAP models */ + for ( ; model != NULL ; model = CAPnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = CAPinstances(model); here != NULL ; here = CAPnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(CAPposPosPtr, CAPposPosBinding, CAPposNode, CAPposNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(CAPnegNegPtr, CAPnegNegBinding, CAPnegNode, CAPnegNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(CAPposNegPtr, CAPposNegBinding, CAPposNode, CAPnegNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(CAPnegPosPtr, CAPnegPosBinding, CAPnegNode, CAPposNode); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/cap/capdefs.h b/src/spicelib/devices/cap/capdefs.h index c6fe2959e..af355cb54 100644 --- a/src/spicelib/devices/cap/capdefs.h +++ b/src/spicelib/devices/cap/capdefs.h @@ -64,6 +64,13 @@ typedef struct sCAPinstance { int CAPsenParmNo; /* parameter # for sensitivity use; set equal to 0 if not a design parameter*/ +#ifdef KLU + BindElement *CAPposPosBinding ; + BindElement *CAPnegNegBinding ; + BindElement *CAPposNegBinding ; + BindElement *CAPnegPosBinding ; +#endif + } CAPinstance ; #define CAPqcap CAPstate /* charge on the capacitor */ diff --git a/src/spicelib/devices/cap/capext.h b/src/spicelib/devices/cap/capext.h index c4e55d0b1..51308524d 100644 --- a/src/spicelib/devices/cap/capext.h +++ b/src/spicelib/devices/cap/capext.h @@ -24,3 +24,8 @@ extern int CAPtemp(GENmodel*,CKTcircuit*); extern int CAPtrunc(GENmodel*,CKTcircuit*,double*); extern int CAPsoaCheck(CKTcircuit *, GENmodel *); +#ifdef KLU +extern int CAPbindCSC (GENmodel*, CKTcircuit*) ; +extern int CAPbindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int CAPbindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/cap/capinit.c b/src/spicelib/devices/cap/capinit.c index b467bce5a..cab0599ba 100644 --- a/src/spicelib/devices/cap/capinit.c +++ b/src/spicelib/devices/cap/capinit.c @@ -66,6 +66,11 @@ SPICEdev CAPinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = CAPbindCSC, + .DEVbindCSCComplex = CAPbindCSCComplex, + .DEVbindCSCComplexToReal = CAPbindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/cccs/Makefile.am b/src/spicelib/devices/cccs/Makefile.am index 566cb2774..57c62b60a 100644 --- a/src/spicelib/devices/cccs/Makefile.am +++ b/src/spicelib/devices/cccs/Makefile.am @@ -23,7 +23,11 @@ libcccs_la_SOURCES = \ cccssset.c +if KLU_WANTED +libcccs_la_SOURCES += cccsbindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) + MAINTAINERCLEANFILES = Makefile.in diff --git a/src/spicelib/devices/cccs/cccsbindCSC.c b/src/spicelib/devices/cccs/cccsbindCSC.c new file mode 100644 index 000000000..e706a4d73 --- /dev/null +++ b/src/spicelib/devices/cccs/cccsbindCSC.c @@ -0,0 +1,92 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "cccsdefs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +CCCSbindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + CCCSmodel *model = (CCCSmodel *)inModel ; + CCCSinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the CCCS models */ + for ( ; model != NULL ; model = CCCSnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = CCCSinstances(model); here != NULL ; here = CCCSnextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(CCCSposContBrPtr, CCCSposContBrBinding, CCCSposNode, CCCScontBranch); + CREATE_KLU_BINDING_TABLE(CCCSnegContBrPtr, CCCSnegContBrBinding, CCCSnegNode, CCCScontBranch); + } + } + + return (OK) ; +} + +int +CCCSbindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + CCCSmodel *model = (CCCSmodel *)inModel ; + CCCSinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the CCCS models */ + for ( ; model != NULL ; model = CCCSnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = CCCSinstances(model); here != NULL ; here = CCCSnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(CCCSposContBrPtr, CCCSposContBrBinding, CCCSposNode, CCCScontBranch); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(CCCSnegContBrPtr, CCCSnegContBrBinding, CCCSnegNode, CCCScontBranch); + } + } + + return (OK) ; +} + +int +CCCSbindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + CCCSmodel *model = (CCCSmodel *)inModel ; + CCCSinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the CCCS models */ + for ( ; model != NULL ; model = CCCSnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = CCCSinstances(model); here != NULL ; here = CCCSnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(CCCSposContBrPtr, CCCSposContBrBinding, CCCSposNode, CCCScontBranch); + CONVERT_KLU_BINDING_TABLE_TO_REAL(CCCSnegContBrPtr, CCCSnegContBrBinding, CCCSnegNode, CCCScontBranch); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/cccs/cccsdefs.h b/src/spicelib/devices/cccs/cccsdefs.h index c64e9cba0..37a6de0ce 100644 --- a/src/spicelib/devices/cccs/cccsdefs.h +++ b/src/spicelib/devices/cccs/cccsdefs.h @@ -44,6 +44,11 @@ typedef struct sCCCSinstance { int CCCSsenParmNo; /* parameter # for sensitivity use; set equal to 0 if not a design parameter*/ +#ifdef KLU + BindElement *CCCSposContBrBinding ; + BindElement *CCCSnegContBrBinding ; +#endif + } CCCSinstance ; /* per model data */ diff --git a/src/spicelib/devices/cccs/cccsext.h b/src/spicelib/devices/cccs/cccsext.h index e04166d76..e66f94d0e 100644 --- a/src/spicelib/devices/cccs/cccsext.h +++ b/src/spicelib/devices/cccs/cccsext.h @@ -17,3 +17,8 @@ extern void CCCSsPrint(GENmodel*,CKTcircuit*); extern int CCCSsSetup(SENstruct*,GENmodel*); extern int CCCSsetup(SMPmatrix*,GENmodel*,CKTcircuit*,int*); +#ifdef KLU +extern int CCCSbindCSC (GENmodel*, CKTcircuit*) ; +extern int CCCSbindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int CCCSbindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/cccs/cccsinit.c b/src/spicelib/devices/cccs/cccsinit.c index 98be7bf4f..16235b406 100644 --- a/src/spicelib/devices/cccs/cccsinit.c +++ b/src/spicelib/devices/cccs/cccsinit.c @@ -66,6 +66,11 @@ SPICEdev CCCSinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = CCCSbindCSC, + .DEVbindCSCComplex = CCCSbindCSCComplex, + .DEVbindCSCComplexToReal = CCCSbindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/ccvs/Makefile.am b/src/spicelib/devices/ccvs/Makefile.am index 3e72d2145..0faa88b17 100644 --- a/src/spicelib/devices/ccvs/Makefile.am +++ b/src/spicelib/devices/ccvs/Makefile.am @@ -24,6 +24,9 @@ libccvs_la_SOURCES = \ ccvssset.c +if KLU_WANTED +libccvs_la_SOURCES += ccvsbindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) diff --git a/src/spicelib/devices/ccvs/ccvsbindCSC.c b/src/spicelib/devices/ccvs/ccvsbindCSC.c new file mode 100644 index 000000000..2e737c1ba --- /dev/null +++ b/src/spicelib/devices/ccvs/ccvsbindCSC.c @@ -0,0 +1,101 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "ccvsdefs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +CCVSbindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + CCVSmodel *model = (CCVSmodel *)inModel ; + CCVSinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the CCVS models */ + for ( ; model != NULL ; model = CCVSnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = CCVSinstances(model); here != NULL ; here = CCVSnextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(CCVSposIbrPtr, CCVSposIbrBinding, CCVSposNode, CCVSbranch); + CREATE_KLU_BINDING_TABLE(CCVSnegIbrPtr, CCVSnegIbrBinding, CCVSnegNode, CCVSbranch); + CREATE_KLU_BINDING_TABLE(CCVSibrNegPtr, CCVSibrNegBinding, CCVSbranch, CCVSnegNode); + CREATE_KLU_BINDING_TABLE(CCVSibrPosPtr, CCVSibrPosBinding, CCVSbranch, CCVSposNode); + CREATE_KLU_BINDING_TABLE(CCVSibrContBrPtr, CCVSibrContBrBinding, CCVSbranch, CCVScontBranch); + } + } + + return (OK) ; +} + +int +CCVSbindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + CCVSmodel *model = (CCVSmodel *)inModel ; + CCVSinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the CCVS models */ + for ( ; model != NULL ; model = CCVSnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = CCVSinstances(model); here != NULL ; here = CCVSnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(CCVSposIbrPtr, CCVSposIbrBinding, CCVSposNode, CCVSbranch); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(CCVSnegIbrPtr, CCVSnegIbrBinding, CCVSnegNode, CCVSbranch); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(CCVSibrNegPtr, CCVSibrNegBinding, CCVSbranch, CCVSnegNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(CCVSibrPosPtr, CCVSibrPosBinding, CCVSbranch, CCVSposNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(CCVSibrContBrPtr, CCVSibrContBrBinding, CCVSbranch, CCVScontBranch); + } + } + + return (OK) ; +} + +int +CCVSbindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + CCVSmodel *model = (CCVSmodel *)inModel ; + CCVSinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the CCVS models */ + for ( ; model != NULL ; model = CCVSnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = CCVSinstances(model); here != NULL ; here = CCVSnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(CCVSposIbrPtr, CCVSposIbrBinding, CCVSposNode, CCVSbranch); + CONVERT_KLU_BINDING_TABLE_TO_REAL(CCVSnegIbrPtr, CCVSnegIbrBinding, CCVSnegNode, CCVSbranch); + CONVERT_KLU_BINDING_TABLE_TO_REAL(CCVSibrNegPtr, CCVSibrNegBinding, CCVSbranch, CCVSnegNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(CCVSibrPosPtr, CCVSibrPosBinding, CCVSbranch, CCVSposNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(CCVSibrContBrPtr, CCVSibrContBrBinding, CCVSbranch, CCVScontBranch); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/ccvs/ccvsdefs.h b/src/spicelib/devices/ccvs/ccvsdefs.h index 09c42fd3c..9b4acb36e 100644 --- a/src/spicelib/devices/ccvs/ccvsdefs.h +++ b/src/spicelib/devices/ccvs/ccvsdefs.h @@ -48,6 +48,14 @@ typedef struct sCCVSinstance { int CCVSsenParmNo; /* parameter # for sensitivity use; set equal to 0 if not a design parameter*/ +#ifdef KLU + BindElement *CCVSposIbrBinding ; + BindElement *CCVSnegIbrBinding ; + BindElement *CCVSibrNegBinding ; + BindElement *CCVSibrPosBinding ; + BindElement *CCVSibrContBrBinding ; +#endif + } CCVSinstance ; /* per model data */ diff --git a/src/spicelib/devices/ccvs/ccvsext.h b/src/spicelib/devices/ccvs/ccvsext.h index 7dd27e30a..eb551ee36 100644 --- a/src/spicelib/devices/ccvs/ccvsext.h +++ b/src/spicelib/devices/ccvs/ccvsext.h @@ -17,3 +17,9 @@ extern void CCVSsPrint(GENmodel*,CKTcircuit*); extern int CCVSsSetup(SENstruct*,GENmodel*); extern int CCVSsetup(SMPmatrix*,GENmodel*,CKTcircuit*,int*); extern int CCVSunsetup(GENmodel*,CKTcircuit*); + +#ifdef KLU +extern int CCVSbindCSC (GENmodel*, CKTcircuit*) ; +extern int CCVSbindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int CCVSbindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/ccvs/ccvsinit.c b/src/spicelib/devices/ccvs/ccvsinit.c index e779e6fc1..57b4d8083 100644 --- a/src/spicelib/devices/ccvs/ccvsinit.c +++ b/src/spicelib/devices/ccvs/ccvsinit.c @@ -66,6 +66,11 @@ SPICEdev CCVSinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = CCVSbindCSC, + .DEVbindCSCComplex = CCVSbindCSCComplex, + .DEVbindCSCComplexToReal = CCVSbindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/cpl/cplinit.c b/src/spicelib/devices/cpl/cplinit.c index 1e3dc3e9e..62472a3da 100644 --- a/src/spicelib/devices/cpl/cplinit.c +++ b/src/spicelib/devices/cpl/cplinit.c @@ -66,6 +66,11 @@ SPICEdev CPLinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = NULL, + .DEVbindCSCComplex = NULL, + .DEVbindCSCComplexToReal = NULL, +#endif }; diff --git a/src/spicelib/devices/csw/Makefile.am b/src/spicelib/devices/csw/Makefile.am index 715d29da5..c2886f90d 100644 --- a/src/spicelib/devices/csw/Makefile.am +++ b/src/spicelib/devices/csw/Makefile.am @@ -24,7 +24,11 @@ libcsw_la_SOURCES = \ cswtrunc.c +if KLU_WANTED +libcsw_la_SOURCES += cswbindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) + MAINTAINERCLEANFILES = Makefile.in diff --git a/src/spicelib/devices/csw/cswbindCSC.c b/src/spicelib/devices/csw/cswbindCSC.c new file mode 100644 index 000000000..7df35ae53 --- /dev/null +++ b/src/spicelib/devices/csw/cswbindCSC.c @@ -0,0 +1,98 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "cswdefs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +CSWbindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + CSWmodel *model = (CSWmodel *)inModel ; + CSWinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the CSW models */ + for ( ; model != NULL ; model = CSWnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = CSWinstances(model); here != NULL ; here = CSWnextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(CSWposPosPtr, CSWposPosBinding, CSWposNode, CSWposNode); + CREATE_KLU_BINDING_TABLE(CSWposNegPtr, CSWposNegBinding, CSWposNode, CSWnegNode); + CREATE_KLU_BINDING_TABLE(CSWnegPosPtr, CSWnegPosBinding, CSWnegNode, CSWposNode); + CREATE_KLU_BINDING_TABLE(CSWnegNegPtr, CSWnegNegBinding, CSWnegNode, CSWnegNode); + } + } + + return (OK) ; +} + +int +CSWbindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + CSWmodel *model = (CSWmodel *)inModel ; + CSWinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the CSW models */ + for ( ; model != NULL ; model = CSWnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = CSWinstances(model); here != NULL ; here = CSWnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(CSWposPosPtr, CSWposPosBinding, CSWposNode, CSWposNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(CSWposNegPtr, CSWposNegBinding, CSWposNode, CSWnegNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(CSWnegPosPtr, CSWnegPosBinding, CSWnegNode, CSWposNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(CSWnegNegPtr, CSWnegNegBinding, CSWnegNode, CSWnegNode); + } + } + + return (OK) ; +} + +int +CSWbindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + CSWmodel *model = (CSWmodel *)inModel ; + CSWinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the CSW models */ + for ( ; model != NULL ; model = CSWnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = CSWinstances(model); here != NULL ; here = CSWnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(CSWposPosPtr, CSWposPosBinding, CSWposNode, CSWposNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(CSWposNegPtr, CSWposNegBinding, CSWposNode, CSWnegNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(CSWnegPosPtr, CSWnegPosBinding, CSWnegNode, CSWposNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(CSWnegNegPtr, CSWnegNegBinding, CSWnegNode, CSWnegNode); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/csw/cswdefs.h b/src/spicelib/devices/csw/cswdefs.h index 7a5737361..722b68ce7 100644 --- a/src/spicelib/devices/csw/cswdefs.h +++ b/src/spicelib/devices/csw/cswdefs.h @@ -50,6 +50,14 @@ typedef struct sCSWinstance { #else /* NONOISE */ double *CSWnVar; #endif /* NONOISE */ + +#ifdef KLU + BindElement *CSWposPosBinding ; + BindElement *CSWposNegBinding ; + BindElement *CSWnegPosBinding ; + BindElement *CSWnegNegBinding ; +#endif + } CSWinstance ; /* data per model */ diff --git a/src/spicelib/devices/csw/cswext.h b/src/spicelib/devices/csw/cswext.h index 22d74de49..0f81b1e10 100644 --- a/src/spicelib/devices/csw/cswext.h +++ b/src/spicelib/devices/csw/cswext.h @@ -17,3 +17,9 @@ extern int CSWpzLoad(GENmodel*,CKTcircuit*,SPcomplex*); extern int CSWsetup(SMPmatrix*,GENmodel*,CKTcircuit*,int*); extern int CSWnoise(int,int,GENmodel*,CKTcircuit*,Ndata*,double*); extern int CSWtrunc(GENmodel*,CKTcircuit*,double*); + +#ifdef KLU +extern int CSWbindCSC (GENmodel*, CKTcircuit*) ; +extern int CSWbindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int CSWbindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/csw/cswinit.c b/src/spicelib/devices/csw/cswinit.c index 6a724dbc0..65e1b3a07 100644 --- a/src/spicelib/devices/csw/cswinit.c +++ b/src/spicelib/devices/csw/cswinit.c @@ -68,6 +68,11 @@ SPICEdev CSWinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = CSWbindCSC, + .DEVbindCSCComplex = CSWbindCSCComplex, + .DEVbindCSCComplexToReal = CSWbindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/dio/Makefile.am b/src/spicelib/devices/dio/Makefile.am index abb29045e..e0a06564d 100644 --- a/src/spicelib/devices/dio/Makefile.am +++ b/src/spicelib/devices/dio/Makefile.am @@ -35,6 +35,11 @@ libdio_la_SOURCES = \ diotrunc.c +if KLU_WANTED +libdio_la_SOURCES += diobindCSC.c +endif + AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) + MAINTAINERCLEANFILES = Makefile.in diff --git a/src/spicelib/devices/dio/diobindCSC.c b/src/spicelib/devices/dio/diobindCSC.c new file mode 100644 index 000000000..28aba6450 --- /dev/null +++ b/src/spicelib/devices/dio/diobindCSC.c @@ -0,0 +1,107 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "diodefs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +DIObindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + DIOmodel *model = (DIOmodel *)inModel ; + DIOinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the DIO models */ + for ( ; model != NULL ; model = DIOnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = DIOinstances(model); here != NULL ; here = DIOnextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(DIOposPosPrimePtr, DIOposPosPrimeBinding, DIOposNode, DIOposPrimeNode); + CREATE_KLU_BINDING_TABLE(DIOnegPosPrimePtr, DIOnegPosPrimeBinding, DIOnegNode, DIOposPrimeNode); + CREATE_KLU_BINDING_TABLE(DIOposPrimePosPtr, DIOposPrimePosBinding, DIOposPrimeNode, DIOposNode); + CREATE_KLU_BINDING_TABLE(DIOposPrimeNegPtr, DIOposPrimeNegBinding, DIOposPrimeNode, DIOnegNode); + CREATE_KLU_BINDING_TABLE(DIOposPosPtr, DIOposPosBinding, DIOposNode, DIOposNode); + CREATE_KLU_BINDING_TABLE(DIOnegNegPtr, DIOnegNegBinding, DIOnegNode, DIOnegNode); + CREATE_KLU_BINDING_TABLE(DIOposPrimePosPrimePtr, DIOposPrimePosPrimeBinding, DIOposPrimeNode, DIOposPrimeNode); + } + } + + return (OK) ; +} + +int +DIObindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + DIOmodel *model = (DIOmodel *)inModel ; + DIOinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the DIO models */ + for ( ; model != NULL ; model = DIOnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = DIOinstances(model); here != NULL ; here = DIOnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(DIOposPosPrimePtr, DIOposPosPrimeBinding, DIOposNode, DIOposPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(DIOnegPosPrimePtr, DIOnegPosPrimeBinding, DIOnegNode, DIOposPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(DIOposPrimePosPtr, DIOposPrimePosBinding, DIOposPrimeNode, DIOposNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(DIOposPrimeNegPtr, DIOposPrimeNegBinding, DIOposPrimeNode, DIOnegNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(DIOposPosPtr, DIOposPosBinding, DIOposNode, DIOposNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(DIOnegNegPtr, DIOnegNegBinding, DIOnegNode, DIOnegNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(DIOposPrimePosPrimePtr, DIOposPrimePosPrimeBinding, DIOposPrimeNode, DIOposPrimeNode); + } + } + + return (OK) ; +} + +int +DIObindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + DIOmodel *model = (DIOmodel *)inModel ; + DIOinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the DIO models */ + for ( ; model != NULL ; model = DIOnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = DIOinstances(model); here != NULL ; here = DIOnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(DIOposPosPrimePtr, DIOposPosPrimeBinding, DIOposNode, DIOposPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(DIOnegPosPrimePtr, DIOnegPosPrimeBinding, DIOnegNode, DIOposPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(DIOposPrimePosPtr, DIOposPrimePosBinding, DIOposPrimeNode, DIOposNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(DIOposPrimeNegPtr, DIOposPrimeNegBinding, DIOposPrimeNode, DIOnegNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(DIOposPosPtr, DIOposPosBinding, DIOposNode, DIOposNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(DIOnegNegPtr, DIOnegNegBinding, DIOnegNode, DIOnegNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(DIOposPrimePosPrimePtr, DIOposPrimePosPrimeBinding, DIOposPrimeNode, DIOposPrimeNode); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/dio/diodefs.h b/src/spicelib/devices/dio/diodefs.h index 280a1e0ce..97f7cf65f 100644 --- a/src/spicelib/devices/dio/diodefs.h +++ b/src/spicelib/devices/dio/diodefs.h @@ -147,6 +147,16 @@ typedef struct sDIOinstance { double **DIOnVar; #endif /* NONOISE */ +#ifdef KLU + BindElement *DIOposPosPrimeBinding ; + BindElement *DIOnegPosPrimeBinding ; + BindElement *DIOposPrimePosBinding ; + BindElement *DIOposPrimeNegBinding ; + BindElement *DIOposPosBinding ; + BindElement *DIOnegNegBinding ; + BindElement *DIOposPrimePosPrimeBinding ; +#endif + } DIOinstance ; #define DIOsenGeq DIOsens /* stores the perturbed values of geq */ diff --git a/src/spicelib/devices/dio/dioext.h b/src/spicelib/devices/dio/dioext.h index 94a493da4..9626dc9f4 100644 --- a/src/spicelib/devices/dio/dioext.h +++ b/src/spicelib/devices/dio/dioext.h @@ -30,3 +30,8 @@ extern int DIOnoise(int,int,GENmodel*,CKTcircuit*,Ndata*,double*); extern int DIOdSetup(DIOmodel*,CKTcircuit*); extern int DIOsoaCheck(CKTcircuit *, GENmodel *); +#ifdef KLU +extern int DIObindCSC (GENmodel*, CKTcircuit*) ; +extern int DIObindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int DIObindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/dio/dioinit.c b/src/spicelib/devices/dio/dioinit.c index 64d64be7d..6cd494b81 100644 --- a/src/spicelib/devices/dio/dioinit.c +++ b/src/spicelib/devices/dio/dioinit.c @@ -67,6 +67,11 @@ SPICEdev DIOinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = DIObindCSC, + .DEVbindCSCComplex = DIObindCSCComplex, + .DEVbindCSCComplexToReal = DIObindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/hfet1/Makefile.am b/src/spicelib/devices/hfet1/Makefile.am index 5d9ef9eee..7a6ccddf6 100644 --- a/src/spicelib/devices/hfet1/Makefile.am +++ b/src/spicelib/devices/hfet1/Makefile.am @@ -25,7 +25,11 @@ libhfet_la_SOURCES = \ hfettrunc.c +if KLU_WANTED +libhfet_la_SOURCES += hfetbindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) + MAINTAINERCLEANFILES = Makefile.in diff --git a/src/spicelib/devices/hfet1/hfetbindCSC.c b/src/spicelib/devices/hfet1/hfetbindCSC.c new file mode 100644 index 000000000..06f7df87d --- /dev/null +++ b/src/spicelib/devices/hfet1/hfetbindCSC.c @@ -0,0 +1,170 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "hfetdefs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +HFETAbindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + HFETAmodel *model = (HFETAmodel *)inModel ; + HFETAinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the HFETA models */ + for ( ; model != NULL ; model = HFETAnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = HFETAinstances(model); here != NULL ; here = HFETAnextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(HFETAdrainDrainPrimePtr, HFETAdrainDrainPrimeBinding, HFETAdrainNode, HFETAdrainPrimeNode); + CREATE_KLU_BINDING_TABLE(HFETAgatePrimeDrainPrimePtr, HFETAgatePrimeDrainPrimeBinding, HFETAgatePrimeNode, HFETAdrainPrimeNode); + CREATE_KLU_BINDING_TABLE(HFETAgatePrimeSourcePrimePtr, HFETAgatePrimeSourcePrimeBinding, HFETAgatePrimeNode, HFETAsourcePrimeNode); + CREATE_KLU_BINDING_TABLE(HFETAsourceSourcePrimePtr, HFETAsourceSourcePrimeBinding, HFETAsourceNode, HFETAsourcePrimeNode); + CREATE_KLU_BINDING_TABLE(HFETAdrainPrimeDrainPtr, HFETAdrainPrimeDrainBinding, HFETAdrainPrimeNode, HFETAdrainNode); + CREATE_KLU_BINDING_TABLE(HFETAdrainPrimeGatePrimePtr, HFETAdrainPrimeGatePrimeBinding, HFETAdrainPrimeNode, HFETAgatePrimeNode); + CREATE_KLU_BINDING_TABLE(HFETAdrainPrimeSourcePrimePtr, HFETAdrainPrimeSourcePrimeBinding, HFETAdrainPrimeNode, HFETAsourcePrimeNode); + CREATE_KLU_BINDING_TABLE(HFETAsourcePrimeGatePrimePtr, HFETAsourcePrimeGatePrimeBinding, HFETAsourcePrimeNode, HFETAgatePrimeNode); + CREATE_KLU_BINDING_TABLE(HFETAsourcePrimeSourcePtr, HFETAsourcePrimeSourceBinding, HFETAsourcePrimeNode, HFETAsourceNode); + CREATE_KLU_BINDING_TABLE(HFETAsourcePrimeDrainPrimePtr, HFETAsourcePrimeDrainPrimeBinding, HFETAsourcePrimeNode, HFETAdrainPrimeNode); + CREATE_KLU_BINDING_TABLE(HFETAdrainDrainPtr, HFETAdrainDrainBinding, HFETAdrainNode, HFETAdrainNode); + CREATE_KLU_BINDING_TABLE(HFETAgatePrimeGatePrimePtr, HFETAgatePrimeGatePrimeBinding, HFETAgatePrimeNode, HFETAgatePrimeNode); + CREATE_KLU_BINDING_TABLE(HFETAsourceSourcePtr, HFETAsourceSourceBinding, HFETAsourceNode, HFETAsourceNode); + CREATE_KLU_BINDING_TABLE(HFETAdrainPrimeDrainPrimePtr, HFETAdrainPrimeDrainPrimeBinding, HFETAdrainPrimeNode, HFETAdrainPrimeNode); + CREATE_KLU_BINDING_TABLE(HFETAsourcePrimeSourcePrimePtr, HFETAsourcePrimeSourcePrimeBinding, HFETAsourcePrimeNode, HFETAsourcePrimeNode); + CREATE_KLU_BINDING_TABLE(HFETAdrainPrimeDrainPrmPrmPtr, HFETAdrainPrimeDrainPrmPrmBinding, HFETAdrainPrimeNode, HFETAdrainPrmPrmNode); + CREATE_KLU_BINDING_TABLE(HFETAdrainPrmPrmDrainPrimePtr, HFETAdrainPrmPrmDrainPrimeBinding, HFETAdrainPrmPrmNode, HFETAdrainPrimeNode); + CREATE_KLU_BINDING_TABLE(HFETAdrainPrmPrmGatePrimePtr, HFETAdrainPrmPrmGatePrimeBinding, HFETAdrainPrmPrmNode, HFETAgatePrimeNode); + CREATE_KLU_BINDING_TABLE(HFETAgatePrimeDrainPrmPrmPtr, HFETAgatePrimeDrainPrmPrmBinding, HFETAgatePrimeNode, HFETAdrainPrmPrmNode); + CREATE_KLU_BINDING_TABLE(HFETAdrainPrmPrmDrainPrmPrmPtr, HFETAdrainPrmPrmDrainPrmPrmBinding, HFETAdrainPrmPrmNode, HFETAdrainPrmPrmNode); + CREATE_KLU_BINDING_TABLE(HFETAsourcePrimeSourcePrmPrmPtr, HFETAsourcePrimeSourcePrmPrmBinding, HFETAsourcePrimeNode, HFETAsourcePrmPrmNode); + CREATE_KLU_BINDING_TABLE(HFETAsourcePrmPrmSourcePrimePtr, HFETAsourcePrmPrmSourcePrimeBinding, HFETAsourcePrmPrmNode, HFETAsourcePrimeNode); + CREATE_KLU_BINDING_TABLE(HFETAsourcePrmPrmGatePrimePtr, HFETAsourcePrmPrmGatePrimeBinding, HFETAsourcePrmPrmNode, HFETAgatePrimeNode); + CREATE_KLU_BINDING_TABLE(HFETAgatePrimeSourcePrmPrmPtr, HFETAgatePrimeSourcePrmPrmBinding, HFETAgatePrimeNode, HFETAsourcePrmPrmNode); + CREATE_KLU_BINDING_TABLE(HFETAsourcePrmPrmSourcePrmPrmPtr, HFETAsourcePrmPrmSourcePrmPrmBinding, HFETAsourcePrmPrmNode, HFETAsourcePrmPrmNode); + CREATE_KLU_BINDING_TABLE(HFETAgateGatePtr, HFETAgateGateBinding, HFETAgateNode, HFETAgateNode); + CREATE_KLU_BINDING_TABLE(HFETAgateGatePrimePtr, HFETAgateGatePrimeBinding, HFETAgateNode, HFETAgatePrimeNode); + CREATE_KLU_BINDING_TABLE(HFETAgatePrimeGatePtr, HFETAgatePrimeGateBinding, HFETAgatePrimeNode, HFETAgateNode); + } + } + + return (OK) ; +} + +int +HFETAbindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + HFETAmodel *model = (HFETAmodel *)inModel ; + HFETAinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the HFETA models */ + for ( ; model != NULL ; model = HFETAnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = HFETAinstances(model); here != NULL ; here = HFETAnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFETAdrainDrainPrimePtr, HFETAdrainDrainPrimeBinding, HFETAdrainNode, HFETAdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFETAgatePrimeDrainPrimePtr, HFETAgatePrimeDrainPrimeBinding, HFETAgatePrimeNode, HFETAdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFETAgatePrimeSourcePrimePtr, HFETAgatePrimeSourcePrimeBinding, HFETAgatePrimeNode, HFETAsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFETAsourceSourcePrimePtr, HFETAsourceSourcePrimeBinding, HFETAsourceNode, HFETAsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFETAdrainPrimeDrainPtr, HFETAdrainPrimeDrainBinding, HFETAdrainPrimeNode, HFETAdrainNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFETAdrainPrimeGatePrimePtr, HFETAdrainPrimeGatePrimeBinding, HFETAdrainPrimeNode, HFETAgatePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFETAdrainPrimeSourcePrimePtr, HFETAdrainPrimeSourcePrimeBinding, HFETAdrainPrimeNode, HFETAsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFETAsourcePrimeGatePrimePtr, HFETAsourcePrimeGatePrimeBinding, HFETAsourcePrimeNode, HFETAgatePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFETAsourcePrimeSourcePtr, HFETAsourcePrimeSourceBinding, HFETAsourcePrimeNode, HFETAsourceNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFETAsourcePrimeDrainPrimePtr, HFETAsourcePrimeDrainPrimeBinding, HFETAsourcePrimeNode, HFETAdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFETAdrainDrainPtr, HFETAdrainDrainBinding, HFETAdrainNode, HFETAdrainNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFETAgatePrimeGatePrimePtr, HFETAgatePrimeGatePrimeBinding, HFETAgatePrimeNode, HFETAgatePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFETAsourceSourcePtr, HFETAsourceSourceBinding, HFETAsourceNode, HFETAsourceNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFETAdrainPrimeDrainPrimePtr, HFETAdrainPrimeDrainPrimeBinding, HFETAdrainPrimeNode, HFETAdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFETAsourcePrimeSourcePrimePtr, HFETAsourcePrimeSourcePrimeBinding, HFETAsourcePrimeNode, HFETAsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFETAdrainPrimeDrainPrmPrmPtr, HFETAdrainPrimeDrainPrmPrmBinding, HFETAdrainPrimeNode, HFETAdrainPrmPrmNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFETAdrainPrmPrmDrainPrimePtr, HFETAdrainPrmPrmDrainPrimeBinding, HFETAdrainPrmPrmNode, HFETAdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFETAdrainPrmPrmGatePrimePtr, HFETAdrainPrmPrmGatePrimeBinding, HFETAdrainPrmPrmNode, HFETAgatePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFETAgatePrimeDrainPrmPrmPtr, HFETAgatePrimeDrainPrmPrmBinding, HFETAgatePrimeNode, HFETAdrainPrmPrmNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFETAdrainPrmPrmDrainPrmPrmPtr, HFETAdrainPrmPrmDrainPrmPrmBinding, HFETAdrainPrmPrmNode, HFETAdrainPrmPrmNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFETAsourcePrimeSourcePrmPrmPtr, HFETAsourcePrimeSourcePrmPrmBinding, HFETAsourcePrimeNode, HFETAsourcePrmPrmNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFETAsourcePrmPrmSourcePrimePtr, HFETAsourcePrmPrmSourcePrimeBinding, HFETAsourcePrmPrmNode, HFETAsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFETAsourcePrmPrmGatePrimePtr, HFETAsourcePrmPrmGatePrimeBinding, HFETAsourcePrmPrmNode, HFETAgatePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFETAgatePrimeSourcePrmPrmPtr, HFETAgatePrimeSourcePrmPrmBinding, HFETAgatePrimeNode, HFETAsourcePrmPrmNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFETAsourcePrmPrmSourcePrmPrmPtr, HFETAsourcePrmPrmSourcePrmPrmBinding, HFETAsourcePrmPrmNode, HFETAsourcePrmPrmNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFETAgateGatePtr, HFETAgateGateBinding, HFETAgateNode, HFETAgateNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFETAgateGatePrimePtr, HFETAgateGatePrimeBinding, HFETAgateNode, HFETAgatePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFETAgatePrimeGatePtr, HFETAgatePrimeGateBinding, HFETAgatePrimeNode, HFETAgateNode); + } + } + + return (OK) ; +} + +int +HFETAbindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + HFETAmodel *model = (HFETAmodel *)inModel ; + HFETAinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the HFETA models */ + for ( ; model != NULL ; model = HFETAnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = HFETAinstances(model); here != NULL ; here = HFETAnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFETAdrainDrainPrimePtr, HFETAdrainDrainPrimeBinding, HFETAdrainNode, HFETAdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFETAgatePrimeDrainPrimePtr, HFETAgatePrimeDrainPrimeBinding, HFETAgatePrimeNode, HFETAdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFETAgatePrimeSourcePrimePtr, HFETAgatePrimeSourcePrimeBinding, HFETAgatePrimeNode, HFETAsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFETAsourceSourcePrimePtr, HFETAsourceSourcePrimeBinding, HFETAsourceNode, HFETAsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFETAdrainPrimeDrainPtr, HFETAdrainPrimeDrainBinding, HFETAdrainPrimeNode, HFETAdrainNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFETAdrainPrimeGatePrimePtr, HFETAdrainPrimeGatePrimeBinding, HFETAdrainPrimeNode, HFETAgatePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFETAdrainPrimeSourcePrimePtr, HFETAdrainPrimeSourcePrimeBinding, HFETAdrainPrimeNode, HFETAsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFETAsourcePrimeGatePrimePtr, HFETAsourcePrimeGatePrimeBinding, HFETAsourcePrimeNode, HFETAgatePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFETAsourcePrimeSourcePtr, HFETAsourcePrimeSourceBinding, HFETAsourcePrimeNode, HFETAsourceNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFETAsourcePrimeDrainPrimePtr, HFETAsourcePrimeDrainPrimeBinding, HFETAsourcePrimeNode, HFETAdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFETAdrainDrainPtr, HFETAdrainDrainBinding, HFETAdrainNode, HFETAdrainNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFETAgatePrimeGatePrimePtr, HFETAgatePrimeGatePrimeBinding, HFETAgatePrimeNode, HFETAgatePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFETAsourceSourcePtr, HFETAsourceSourceBinding, HFETAsourceNode, HFETAsourceNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFETAdrainPrimeDrainPrimePtr, HFETAdrainPrimeDrainPrimeBinding, HFETAdrainPrimeNode, HFETAdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFETAsourcePrimeSourcePrimePtr, HFETAsourcePrimeSourcePrimeBinding, HFETAsourcePrimeNode, HFETAsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFETAdrainPrimeDrainPrmPrmPtr, HFETAdrainPrimeDrainPrmPrmBinding, HFETAdrainPrimeNode, HFETAdrainPrmPrmNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFETAdrainPrmPrmDrainPrimePtr, HFETAdrainPrmPrmDrainPrimeBinding, HFETAdrainPrmPrmNode, HFETAdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFETAdrainPrmPrmGatePrimePtr, HFETAdrainPrmPrmGatePrimeBinding, HFETAdrainPrmPrmNode, HFETAgatePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFETAgatePrimeDrainPrmPrmPtr, HFETAgatePrimeDrainPrmPrmBinding, HFETAgatePrimeNode, HFETAdrainPrmPrmNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFETAdrainPrmPrmDrainPrmPrmPtr, HFETAdrainPrmPrmDrainPrmPrmBinding, HFETAdrainPrmPrmNode, HFETAdrainPrmPrmNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFETAsourcePrimeSourcePrmPrmPtr, HFETAsourcePrimeSourcePrmPrmBinding, HFETAsourcePrimeNode, HFETAsourcePrmPrmNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFETAsourcePrmPrmSourcePrimePtr, HFETAsourcePrmPrmSourcePrimeBinding, HFETAsourcePrmPrmNode, HFETAsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFETAsourcePrmPrmGatePrimePtr, HFETAsourcePrmPrmGatePrimeBinding, HFETAsourcePrmPrmNode, HFETAgatePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFETAgatePrimeSourcePrmPrmPtr, HFETAgatePrimeSourcePrmPrmBinding, HFETAgatePrimeNode, HFETAsourcePrmPrmNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFETAsourcePrmPrmSourcePrmPrmPtr, HFETAsourcePrmPrmSourcePrmPrmBinding, HFETAsourcePrmPrmNode, HFETAsourcePrmPrmNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFETAgateGatePtr, HFETAgateGateBinding, HFETAgateNode, HFETAgateNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFETAgateGatePrimePtr, HFETAgateGatePrimeBinding, HFETAgateNode, HFETAgatePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFETAgatePrimeGatePtr, HFETAgatePrimeGateBinding, HFETAgatePrimeNode, HFETAgateNode); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/hfet1/hfetdefs.h b/src/spicelib/devices/hfet1/hfetdefs.h index 1c3ac5ce4..0a08d892b 100644 --- a/src/spicelib/devices/hfet1/hfetdefs.h +++ b/src/spicelib/devices/hfet1/hfetdefs.h @@ -125,6 +125,37 @@ typedef struct sHFETAinstance { double HFETAfgds; double HFETAggrwl; +#ifdef KLU + BindElement *HFETAdrainDrainPrimeBinding ; + BindElement *HFETAgatePrimeDrainPrimeBinding ; + BindElement *HFETAgatePrimeSourcePrimeBinding ; + BindElement *HFETAsourceSourcePrimeBinding ; + BindElement *HFETAdrainPrimeDrainBinding ; + BindElement *HFETAdrainPrimeGatePrimeBinding ; + BindElement *HFETAdrainPrimeSourcePrimeBinding ; + BindElement *HFETAsourcePrimeGatePrimeBinding ; + BindElement *HFETAsourcePrimeSourceBinding ; + BindElement *HFETAsourcePrimeDrainPrimeBinding ; + BindElement *HFETAdrainDrainBinding ; + BindElement *HFETAgatePrimeGatePrimeBinding ; + BindElement *HFETAsourceSourceBinding ; + BindElement *HFETAdrainPrimeDrainPrimeBinding ; + BindElement *HFETAsourcePrimeSourcePrimeBinding ; + BindElement *HFETAdrainPrimeDrainPrmPrmBinding ; + BindElement *HFETAdrainPrmPrmDrainPrimeBinding ; + BindElement *HFETAdrainPrmPrmGatePrimeBinding ; + BindElement *HFETAgatePrimeDrainPrmPrmBinding ; + BindElement *HFETAdrainPrmPrmDrainPrmPrmBinding ; + BindElement *HFETAsourcePrimeSourcePrmPrmBinding ; + BindElement *HFETAsourcePrmPrmSourcePrimeBinding ; + BindElement *HFETAsourcePrmPrmGatePrimeBinding ; + BindElement *HFETAgatePrimeSourcePrmPrmBinding ; + BindElement *HFETAsourcePrmPrmSourcePrmPrmBinding ; + BindElement *HFETAgateGateBinding ; + BindElement *HFETAgateGatePrimeBinding ; + BindElement *HFETAgatePrimeGateBinding ; +#endif + } HFETAinstance ; diff --git a/src/spicelib/devices/hfet1/hfetext.h b/src/spicelib/devices/hfet1/hfetext.h index ee499df29..98cb43b0d 100644 --- a/src/spicelib/devices/hfet1/hfetext.h +++ b/src/spicelib/devices/hfet1/hfetext.h @@ -18,3 +18,9 @@ extern int HFETAsetup(SMPmatrix*,GENmodel*,CKTcircuit*,int*); extern int HFETAtemp(GENmodel*,CKTcircuit*); extern int HFETAtrunc(GENmodel*,CKTcircuit*,double*); extern int HFETAunsetup(GENmodel*,CKTcircuit*); + +#ifdef KLU +extern int HFETAbindCSC (GENmodel*, CKTcircuit*) ; +extern int HFETAbindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int HFETAbindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/hfet1/hfetinit.c b/src/spicelib/devices/hfet1/hfetinit.c index 802eb0b00..422dafe35 100644 --- a/src/spicelib/devices/hfet1/hfetinit.c +++ b/src/spicelib/devices/hfet1/hfetinit.c @@ -66,6 +66,11 @@ SPICEdev HFETAinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = HFETAbindCSC, + .DEVbindCSCComplex = HFETAbindCSC, + .DEVbindCSCComplexToReal = HFETAbindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/hfet2/Makefile.am b/src/spicelib/devices/hfet2/Makefile.am index 743fae0a2..14f1ad5c1 100644 --- a/src/spicelib/devices/hfet2/Makefile.am +++ b/src/spicelib/devices/hfet2/Makefile.am @@ -25,7 +25,11 @@ libhfet2_la_SOURCES = \ hfet2trunc.c +if KLU_WANTED +libhfet2_la_SOURCES += hfet2bindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) + MAINTAINERCLEANFILES = Makefile.in diff --git a/src/spicelib/devices/hfet2/hfet2bindCSC.c b/src/spicelib/devices/hfet2/hfet2bindCSC.c new file mode 100644 index 000000000..37ab4836d --- /dev/null +++ b/src/spicelib/devices/hfet2/hfet2bindCSC.c @@ -0,0 +1,131 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "hfet2defs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +HFET2bindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + HFET2model *model = (HFET2model *)inModel ; + HFET2instance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the HFET2 models */ + for ( ; model != NULL ; model = HFET2nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = HFET2instances(model); here != NULL ; here = HFET2nextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(HFET2drainDrainPrimePtr, HFET2drainDrainPrimeBinding, HFET2drainNode, HFET2drainPrimeNode); + CREATE_KLU_BINDING_TABLE(HFET2gateDrainPrimePtr, HFET2gateDrainPrimeBinding, HFET2gateNode, HFET2drainPrimeNode); + CREATE_KLU_BINDING_TABLE(HFET2gateSourcePrimePtr, HFET2gateSourcePrimeBinding, HFET2gateNode, HFET2sourcePrimeNode); + CREATE_KLU_BINDING_TABLE(HFET2sourceSourcePrimePtr, HFET2sourceSourcePrimeBinding, HFET2sourceNode, HFET2sourcePrimeNode); + CREATE_KLU_BINDING_TABLE(HFET2drainPrimeDrainPtr, HFET2drainPrimeDrainBinding, HFET2drainPrimeNode, HFET2drainNode); + CREATE_KLU_BINDING_TABLE(HFET2drainPrimeGatePtr, HFET2drainPrimeGateBinding, HFET2drainPrimeNode, HFET2gateNode); + CREATE_KLU_BINDING_TABLE(HFET2drainPriHFET2ourcePrimePtr, HFET2drainPriHFET2ourcePrimeBinding, HFET2drainPrimeNode, HFET2sourcePrimeNode); + CREATE_KLU_BINDING_TABLE(HFET2sourcePrimeGatePtr, HFET2sourcePrimeGateBinding, HFET2sourcePrimeNode, HFET2gateNode); + CREATE_KLU_BINDING_TABLE(HFET2sourcePriHFET2ourcePtr, HFET2sourcePriHFET2ourceBinding, HFET2sourcePrimeNode, HFET2sourceNode); + CREATE_KLU_BINDING_TABLE(HFET2sourcePrimeDrainPrimePtr, HFET2sourcePrimeDrainPrimeBinding, HFET2sourcePrimeNode, HFET2drainPrimeNode); + CREATE_KLU_BINDING_TABLE(HFET2drainDrainPtr, HFET2drainDrainBinding, HFET2drainNode, HFET2drainNode); + CREATE_KLU_BINDING_TABLE(HFET2gateGatePtr, HFET2gateGateBinding, HFET2gateNode, HFET2gateNode); + CREATE_KLU_BINDING_TABLE(HFET2sourceSourcePtr, HFET2sourceSourceBinding, HFET2sourceNode, HFET2sourceNode); + CREATE_KLU_BINDING_TABLE(HFET2drainPrimeDrainPrimePtr, HFET2drainPrimeDrainPrimeBinding, HFET2drainPrimeNode, HFET2drainPrimeNode); + CREATE_KLU_BINDING_TABLE(HFET2sourcePriHFET2ourcePrimePtr, HFET2sourcePriHFET2ourcePrimeBinding, HFET2sourcePrimeNode, HFET2sourcePrimeNode); + } + } + + return (OK) ; +} + +int +HFET2bindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + HFET2model *model = (HFET2model *)inModel ; + HFET2instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the HFET2 models */ + for ( ; model != NULL ; model = HFET2nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = HFET2instances(model); here != NULL ; here = HFET2nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFET2drainDrainPrimePtr, HFET2drainDrainPrimeBinding, HFET2drainNode, HFET2drainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFET2gateDrainPrimePtr, HFET2gateDrainPrimeBinding, HFET2gateNode, HFET2drainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFET2gateSourcePrimePtr, HFET2gateSourcePrimeBinding, HFET2gateNode, HFET2sourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFET2sourceSourcePrimePtr, HFET2sourceSourcePrimeBinding, HFET2sourceNode, HFET2sourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFET2drainPrimeDrainPtr, HFET2drainPrimeDrainBinding, HFET2drainPrimeNode, HFET2drainNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFET2drainPrimeGatePtr, HFET2drainPrimeGateBinding, HFET2drainPrimeNode, HFET2gateNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFET2drainPriHFET2ourcePrimePtr, HFET2drainPriHFET2ourcePrimeBinding, HFET2drainPrimeNode, HFET2sourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFET2sourcePrimeGatePtr, HFET2sourcePrimeGateBinding, HFET2sourcePrimeNode, HFET2gateNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFET2sourcePriHFET2ourcePtr, HFET2sourcePriHFET2ourceBinding, HFET2sourcePrimeNode, HFET2sourceNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFET2sourcePrimeDrainPrimePtr, HFET2sourcePrimeDrainPrimeBinding, HFET2sourcePrimeNode, HFET2drainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFET2drainDrainPtr, HFET2drainDrainBinding, HFET2drainNode, HFET2drainNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFET2gateGatePtr, HFET2gateGateBinding, HFET2gateNode, HFET2gateNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFET2sourceSourcePtr, HFET2sourceSourceBinding, HFET2sourceNode, HFET2sourceNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFET2drainPrimeDrainPrimePtr, HFET2drainPrimeDrainPrimeBinding, HFET2drainPrimeNode, HFET2drainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HFET2sourcePriHFET2ourcePrimePtr, HFET2sourcePriHFET2ourcePrimeBinding, HFET2sourcePrimeNode, HFET2sourcePrimeNode); + } + } + + return (OK) ; +} + +int +HFET2bindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + HFET2model *model = (HFET2model *)inModel ; + HFET2instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the HFET2 models */ + for ( ; model != NULL ; model = HFET2nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = HFET2instances(model); here != NULL ; here = HFET2nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFET2drainDrainPrimePtr, HFET2drainDrainPrimeBinding, HFET2drainNode, HFET2drainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFET2gateDrainPrimePtr, HFET2gateDrainPrimeBinding, HFET2gateNode, HFET2drainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFET2gateSourcePrimePtr, HFET2gateSourcePrimeBinding, HFET2gateNode, HFET2sourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFET2sourceSourcePrimePtr, HFET2sourceSourcePrimeBinding, HFET2sourceNode, HFET2sourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFET2drainPrimeDrainPtr, HFET2drainPrimeDrainBinding, HFET2drainPrimeNode, HFET2drainNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFET2drainPrimeGatePtr, HFET2drainPrimeGateBinding, HFET2drainPrimeNode, HFET2gateNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFET2drainPriHFET2ourcePrimePtr, HFET2drainPriHFET2ourcePrimeBinding, HFET2drainPrimeNode, HFET2sourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFET2sourcePrimeGatePtr, HFET2sourcePrimeGateBinding, HFET2sourcePrimeNode, HFET2gateNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFET2sourcePriHFET2ourcePtr, HFET2sourcePriHFET2ourceBinding, HFET2sourcePrimeNode, HFET2sourceNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFET2sourcePrimeDrainPrimePtr, HFET2sourcePrimeDrainPrimeBinding, HFET2sourcePrimeNode, HFET2drainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFET2drainDrainPtr, HFET2drainDrainBinding, HFET2drainNode, HFET2drainNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFET2gateGatePtr, HFET2gateGateBinding, HFET2gateNode, HFET2gateNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFET2sourceSourcePtr, HFET2sourceSourceBinding, HFET2sourceNode, HFET2sourceNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFET2drainPrimeDrainPrimePtr, HFET2drainPrimeDrainPrimeBinding, HFET2drainPrimeNode, HFET2drainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HFET2sourcePriHFET2ourcePrimePtr, HFET2sourcePriHFET2ourcePrimeBinding, HFET2sourcePrimeNode, HFET2sourcePrimeNode); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/hfet2/hfet2defs.h b/src/spicelib/devices/hfet2/hfet2defs.h index 5e938c7f2..a41e952e3 100644 --- a/src/spicelib/devices/hfet2/hfet2defs.h +++ b/src/spicelib/devices/hfet2/hfet2defs.h @@ -83,7 +83,25 @@ typedef struct sHFET2instance { double HFET2vcrit; double HFET2ggrlw; double HFET2jslw; - + +#ifdef KLU + BindElement *HFET2drainDrainPrimeBinding ; + BindElement *HFET2gateDrainPrimeBinding ; + BindElement *HFET2gateSourcePrimeBinding ; + BindElement *HFET2sourceSourcePrimeBinding ; + BindElement *HFET2drainPrimeDrainBinding ; + BindElement *HFET2drainPrimeGateBinding ; + BindElement *HFET2drainPriHFET2ourcePrimeBinding ; + BindElement *HFET2sourcePrimeGateBinding ; + BindElement *HFET2sourcePriHFET2ourceBinding ; + BindElement *HFET2sourcePrimeDrainPrimeBinding ; + BindElement *HFET2drainDrainBinding ; + BindElement *HFET2gateGateBinding ; + BindElement *HFET2sourceSourceBinding ; + BindElement *HFET2drainPrimeDrainPrimeBinding ; + BindElement *HFET2sourcePriHFET2ourcePrimeBinding ; +#endif + } HFET2instance ; diff --git a/src/spicelib/devices/hfet2/hfet2ext.h b/src/spicelib/devices/hfet2/hfet2ext.h index 760e03256..50aa89397 100644 --- a/src/spicelib/devices/hfet2/hfet2ext.h +++ b/src/spicelib/devices/hfet2/hfet2ext.h @@ -18,3 +18,9 @@ extern int HFET2setup(SMPmatrix*,GENmodel*,CKTcircuit*,int*); extern int HFET2temp(GENmodel*,CKTcircuit*); extern int HFET2trunc(GENmodel*,CKTcircuit*,double*); extern int HFET2unsetup( GENmodel*,CKTcircuit*); + +#ifdef KLU +extern int HFET2bindCSC (GENmodel*, CKTcircuit*) ; +extern int HFET2bindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int HFET2bindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/hfet2/hfet2init.c b/src/spicelib/devices/hfet2/hfet2init.c index 1c8f3ca30..c29dc8407 100644 --- a/src/spicelib/devices/hfet2/hfet2init.c +++ b/src/spicelib/devices/hfet2/hfet2init.c @@ -66,6 +66,11 @@ SPICEdev HFET2info = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = HFET2bindCSC, + .DEVbindCSCComplex = HFET2bindCSCComplex, + .DEVbindCSCComplexToReal = HFET2bindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/hisim2/Makefile.am b/src/spicelib/devices/hisim2/Makefile.am index f5e8106e8..25e31f277 100644 --- a/src/spicelib/devices/hisim2/Makefile.am +++ b/src/spicelib/devices/hisim2/Makefile.am @@ -33,6 +33,10 @@ libhisim2_la_SOURCES = hisim2.h \ hsm2trunc.c +if KLU_WANTED +libhisim2_la_SOURCES += hsm2bindCSC.c +endif + AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) diff --git a/src/spicelib/devices/hisim2/hsm2bindCSC.c b/src/spicelib/devices/hisim2/hsm2bindCSC.c new file mode 100644 index 000000000..28dcc10f7 --- /dev/null +++ b/src/spicelib/devices/hisim2/hsm2bindCSC.c @@ -0,0 +1,239 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "hsm2def.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +HSM2bindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + HSM2model *model = (HSM2model *)inModel ; + HSM2instance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the HSM2 models */ + for ( ; model != NULL ; model = HSM2nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = HSM2instances(model); here != NULL ; here = HSM2nextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(HSM2DPbpPtr, HSM2DPbpBinding, HSM2dNodePrime, HSM2bNodePrime); + CREATE_KLU_BINDING_TABLE(HSM2SPbpPtr, HSM2SPbpBinding, HSM2sNodePrime, HSM2bNodePrime); + CREATE_KLU_BINDING_TABLE(HSM2GPbpPtr, HSM2GPbpBinding, HSM2gNodePrime, HSM2bNodePrime); + CREATE_KLU_BINDING_TABLE(HSM2BPdpPtr, HSM2BPdpBinding, HSM2bNodePrime, HSM2dNodePrime); + CREATE_KLU_BINDING_TABLE(HSM2BPspPtr, HSM2BPspBinding, HSM2bNodePrime, HSM2sNodePrime); + CREATE_KLU_BINDING_TABLE(HSM2BPgpPtr, HSM2BPgpBinding, HSM2bNodePrime, HSM2gNodePrime); + CREATE_KLU_BINDING_TABLE(HSM2BPbpPtr, HSM2BPbpBinding, HSM2bNodePrime, HSM2bNodePrime); + CREATE_KLU_BINDING_TABLE(HSM2DdPtr, HSM2DdBinding, HSM2dNode, HSM2dNode); + CREATE_KLU_BINDING_TABLE(HSM2GPgpPtr, HSM2GPgpBinding, HSM2gNodePrime, HSM2gNodePrime); + CREATE_KLU_BINDING_TABLE(HSM2SsPtr, HSM2SsBinding, HSM2sNode, HSM2sNode); + CREATE_KLU_BINDING_TABLE(HSM2DPdpPtr, HSM2DPdpBinding, HSM2dNodePrime, HSM2dNodePrime); + CREATE_KLU_BINDING_TABLE(HSM2SPspPtr, HSM2SPspBinding, HSM2sNodePrime, HSM2sNodePrime); + CREATE_KLU_BINDING_TABLE(HSM2DdpPtr, HSM2DdpBinding, HSM2dNode, HSM2dNodePrime); + CREATE_KLU_BINDING_TABLE(HSM2GPdpPtr, HSM2GPdpBinding, HSM2gNodePrime, HSM2dNodePrime); + CREATE_KLU_BINDING_TABLE(HSM2GPspPtr, HSM2GPspBinding, HSM2gNodePrime, HSM2sNodePrime); + CREATE_KLU_BINDING_TABLE(HSM2SspPtr, HSM2SspBinding, HSM2sNode, HSM2sNodePrime); + CREATE_KLU_BINDING_TABLE(HSM2DPspPtr, HSM2DPspBinding, HSM2dNodePrime, HSM2sNodePrime); + CREATE_KLU_BINDING_TABLE(HSM2DPdPtr, HSM2DPdBinding, HSM2dNodePrime, HSM2dNode); + CREATE_KLU_BINDING_TABLE(HSM2DPgpPtr, HSM2DPgpBinding, HSM2dNodePrime, HSM2gNodePrime); + CREATE_KLU_BINDING_TABLE(HSM2SPgpPtr, HSM2SPgpBinding, HSM2sNodePrime, HSM2gNodePrime); + CREATE_KLU_BINDING_TABLE(HSM2SPsPtr, HSM2SPsBinding, HSM2sNodePrime, HSM2sNode); + CREATE_KLU_BINDING_TABLE(HSM2SPdpPtr, HSM2SPdpBinding, HSM2sNodePrime, HSM2dNodePrime); + if (here->HSM2_corg == 1) + { + CREATE_KLU_BINDING_TABLE(HSM2GgPtr, HSM2GgBinding, HSM2gNode, HSM2gNode); + CREATE_KLU_BINDING_TABLE(HSM2GgpPtr, HSM2GgpBinding, HSM2gNode, HSM2gNodePrime); + CREATE_KLU_BINDING_TABLE(HSM2GPgPtr, HSM2GPgBinding, HSM2gNodePrime, HSM2gNode); + CREATE_KLU_BINDING_TABLE(HSM2GdpPtr, HSM2GdpBinding, HSM2gNode, HSM2dNodePrime); + CREATE_KLU_BINDING_TABLE(HSM2GspPtr, HSM2GspBinding, HSM2gNode, HSM2sNodePrime); + CREATE_KLU_BINDING_TABLE(HSM2GbpPtr, HSM2GbpBinding, HSM2gNode, HSM2bNodePrime); + } + if (here->HSM2_corbnet == 1) + { + CREATE_KLU_BINDING_TABLE(HSM2DPdbPtr, HSM2DPdbBinding, HSM2dNodePrime, HSM2dbNode); + CREATE_KLU_BINDING_TABLE(HSM2SPsbPtr, HSM2SPsbBinding, HSM2sNodePrime, HSM2sbNode); + CREATE_KLU_BINDING_TABLE(HSM2DBdpPtr, HSM2DBdpBinding, HSM2dbNode, HSM2dNodePrime); + CREATE_KLU_BINDING_TABLE(HSM2DBdbPtr, HSM2DBdbBinding, HSM2dbNode, HSM2dbNode); + CREATE_KLU_BINDING_TABLE(HSM2DBbpPtr, HSM2DBbpBinding, HSM2dbNode, HSM2bNodePrime); + CREATE_KLU_BINDING_TABLE(HSM2DBbPtr, HSM2DBbBinding, HSM2dbNode, HSM2bNode); + CREATE_KLU_BINDING_TABLE(HSM2BPdbPtr, HSM2BPdbBinding, HSM2bNodePrime, HSM2dbNode); + CREATE_KLU_BINDING_TABLE(HSM2BPbPtr, HSM2BPbBinding, HSM2bNodePrime, HSM2bNode); + CREATE_KLU_BINDING_TABLE(HSM2BPsbPtr, HSM2BPsbBinding, HSM2bNodePrime, HSM2sbNode); + CREATE_KLU_BINDING_TABLE(HSM2SBspPtr, HSM2SBspBinding, HSM2sbNode, HSM2sNodePrime); + CREATE_KLU_BINDING_TABLE(HSM2SBbpPtr, HSM2SBbpBinding, HSM2sbNode, HSM2bNodePrime); + CREATE_KLU_BINDING_TABLE(HSM2SBbPtr, HSM2SBbBinding, HSM2sbNode, HSM2bNode); + CREATE_KLU_BINDING_TABLE(HSM2SBsbPtr, HSM2SBsbBinding, HSM2sbNode, HSM2sbNode); + CREATE_KLU_BINDING_TABLE(HSM2BdbPtr, HSM2BdbBinding, HSM2bNode, HSM2dbNode); + CREATE_KLU_BINDING_TABLE(HSM2BbpPtr, HSM2BbpBinding, HSM2bNode, HSM2bNodePrime); + CREATE_KLU_BINDING_TABLE(HSM2BsbPtr, HSM2BsbBinding, HSM2bNode, HSM2sbNode); + CREATE_KLU_BINDING_TABLE(HSM2BbPtr, HSM2BbBinding, HSM2bNode, HSM2bNode); + } + } + } + + return (OK) ; +} + +int +HSM2bindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + HSM2model *model = (HSM2model *)inModel ; + HSM2instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the HSM2 models */ + for ( ; model != NULL ; model = HSM2nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = HSM2instances(model); here != NULL ; here = HSM2nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2DPbpPtr, HSM2DPbpBinding, HSM2dNodePrime, HSM2bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2SPbpPtr, HSM2SPbpBinding, HSM2sNodePrime, HSM2bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2GPbpPtr, HSM2GPbpBinding, HSM2gNodePrime, HSM2bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2BPdpPtr, HSM2BPdpBinding, HSM2bNodePrime, HSM2dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2BPspPtr, HSM2BPspBinding, HSM2bNodePrime, HSM2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2BPgpPtr, HSM2BPgpBinding, HSM2bNodePrime, HSM2gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2BPbpPtr, HSM2BPbpBinding, HSM2bNodePrime, HSM2bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2DdPtr, HSM2DdBinding, HSM2dNode, HSM2dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2GPgpPtr, HSM2GPgpBinding, HSM2gNodePrime, HSM2gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2SsPtr, HSM2SsBinding, HSM2sNode, HSM2sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2DPdpPtr, HSM2DPdpBinding, HSM2dNodePrime, HSM2dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2SPspPtr, HSM2SPspBinding, HSM2sNodePrime, HSM2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2DdpPtr, HSM2DdpBinding, HSM2dNode, HSM2dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2GPdpPtr, HSM2GPdpBinding, HSM2gNodePrime, HSM2dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2GPspPtr, HSM2GPspBinding, HSM2gNodePrime, HSM2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2SspPtr, HSM2SspBinding, HSM2sNode, HSM2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2DPspPtr, HSM2DPspBinding, HSM2dNodePrime, HSM2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2DPdPtr, HSM2DPdBinding, HSM2dNodePrime, HSM2dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2DPgpPtr, HSM2DPgpBinding, HSM2dNodePrime, HSM2gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2SPgpPtr, HSM2SPgpBinding, HSM2sNodePrime, HSM2gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2SPsPtr, HSM2SPsBinding, HSM2sNodePrime, HSM2sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2SPdpPtr, HSM2SPdpBinding, HSM2sNodePrime, HSM2dNodePrime); + if (here->HSM2_corg == 1) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2GgPtr, HSM2GgBinding, HSM2gNode, HSM2gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2GgpPtr, HSM2GgpBinding, HSM2gNode, HSM2gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2GPgPtr, HSM2GPgBinding, HSM2gNodePrime, HSM2gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2GdpPtr, HSM2GdpBinding, HSM2gNode, HSM2dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2GspPtr, HSM2GspBinding, HSM2gNode, HSM2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2GbpPtr, HSM2GbpBinding, HSM2gNode, HSM2bNodePrime); + } + if (here->HSM2_corbnet == 1) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2DPdbPtr, HSM2DPdbBinding, HSM2dNodePrime, HSM2dbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2SPsbPtr, HSM2SPsbBinding, HSM2sNodePrime, HSM2sbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2DBdpPtr, HSM2DBdpBinding, HSM2dbNode, HSM2dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2DBdbPtr, HSM2DBdbBinding, HSM2dbNode, HSM2dbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2DBbpPtr, HSM2DBbpBinding, HSM2dbNode, HSM2bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2DBbPtr, HSM2DBbBinding, HSM2dbNode, HSM2bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2BPdbPtr, HSM2BPdbBinding, HSM2bNodePrime, HSM2dbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2BPbPtr, HSM2BPbBinding, HSM2bNodePrime, HSM2bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2BPsbPtr, HSM2BPsbBinding, HSM2bNodePrime, HSM2sbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2SBspPtr, HSM2SBspBinding, HSM2sbNode, HSM2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2SBbpPtr, HSM2SBbpBinding, HSM2sbNode, HSM2bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2SBbPtr, HSM2SBbBinding, HSM2sbNode, HSM2bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2SBsbPtr, HSM2SBsbBinding, HSM2sbNode, HSM2sbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2BdbPtr, HSM2BdbBinding, HSM2bNode, HSM2dbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2BbpPtr, HSM2BbpBinding, HSM2bNode, HSM2bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2BsbPtr, HSM2BsbBinding, HSM2bNode, HSM2sbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSM2BbPtr, HSM2BbBinding, HSM2bNode, HSM2bNode); + } + } + } + + return (OK) ; +} + +int +HSM2bindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + HSM2model *model = (HSM2model *)inModel ; + HSM2instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the HSM2 models */ + for ( ; model != NULL ; model = HSM2nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = HSM2instances(model); here != NULL ; here = HSM2nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2DPbpPtr, HSM2DPbpBinding, HSM2dNodePrime, HSM2bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2SPbpPtr, HSM2SPbpBinding, HSM2sNodePrime, HSM2bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2GPbpPtr, HSM2GPbpBinding, HSM2gNodePrime, HSM2bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2BPdpPtr, HSM2BPdpBinding, HSM2bNodePrime, HSM2dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2BPspPtr, HSM2BPspBinding, HSM2bNodePrime, HSM2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2BPgpPtr, HSM2BPgpBinding, HSM2bNodePrime, HSM2gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2BPbpPtr, HSM2BPbpBinding, HSM2bNodePrime, HSM2bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2DdPtr, HSM2DdBinding, HSM2dNode, HSM2dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2GPgpPtr, HSM2GPgpBinding, HSM2gNodePrime, HSM2gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2SsPtr, HSM2SsBinding, HSM2sNode, HSM2sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2DPdpPtr, HSM2DPdpBinding, HSM2dNodePrime, HSM2dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2SPspPtr, HSM2SPspBinding, HSM2sNodePrime, HSM2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2DdpPtr, HSM2DdpBinding, HSM2dNode, HSM2dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2GPdpPtr, HSM2GPdpBinding, HSM2gNodePrime, HSM2dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2GPspPtr, HSM2GPspBinding, HSM2gNodePrime, HSM2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2SspPtr, HSM2SspBinding, HSM2sNode, HSM2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2DPspPtr, HSM2DPspBinding, HSM2dNodePrime, HSM2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2DPdPtr, HSM2DPdBinding, HSM2dNodePrime, HSM2dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2DPgpPtr, HSM2DPgpBinding, HSM2dNodePrime, HSM2gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2SPgpPtr, HSM2SPgpBinding, HSM2sNodePrime, HSM2gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2SPsPtr, HSM2SPsBinding, HSM2sNodePrime, HSM2sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2SPdpPtr, HSM2SPdpBinding, HSM2sNodePrime, HSM2dNodePrime); + if (here->HSM2_corg == 1) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2GgPtr, HSM2GgBinding, HSM2gNode, HSM2gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2GgpPtr, HSM2GgpBinding, HSM2gNode, HSM2gNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2GPgPtr, HSM2GPgBinding, HSM2gNodePrime, HSM2gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2GdpPtr, HSM2GdpBinding, HSM2gNode, HSM2dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2GspPtr, HSM2GspBinding, HSM2gNode, HSM2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2GbpPtr, HSM2GbpBinding, HSM2gNode, HSM2bNodePrime); + } + if (here->HSM2_corbnet == 1) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2DPdbPtr, HSM2DPdbBinding, HSM2dNodePrime, HSM2dbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2SPsbPtr, HSM2SPsbBinding, HSM2sNodePrime, HSM2sbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2DBdpPtr, HSM2DBdpBinding, HSM2dbNode, HSM2dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2DBdbPtr, HSM2DBdbBinding, HSM2dbNode, HSM2dbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2DBbpPtr, HSM2DBbpBinding, HSM2dbNode, HSM2bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2DBbPtr, HSM2DBbBinding, HSM2dbNode, HSM2bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2BPdbPtr, HSM2BPdbBinding, HSM2bNodePrime, HSM2dbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2BPbPtr, HSM2BPbBinding, HSM2bNodePrime, HSM2bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2BPsbPtr, HSM2BPsbBinding, HSM2bNodePrime, HSM2sbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2SBspPtr, HSM2SBspBinding, HSM2sbNode, HSM2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2SBbpPtr, HSM2SBbpBinding, HSM2sbNode, HSM2bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2SBbPtr, HSM2SBbBinding, HSM2sbNode, HSM2bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2SBsbPtr, HSM2SBsbBinding, HSM2sbNode, HSM2sbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2BdbPtr, HSM2BdbBinding, HSM2bNode, HSM2dbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2BbpPtr, HSM2BbpBinding, HSM2bNode, HSM2bNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2BsbPtr, HSM2BsbBinding, HSM2bNode, HSM2sbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSM2BbPtr, HSM2BbBinding, HSM2bNode, HSM2bNode); + } + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/hisim2/hsm2def.h b/src/spicelib/devices/hisim2/hsm2def.h index 1ffe6f8b1..026dda2d0 100644 --- a/src/spicelib/devices/hisim2/hsm2def.h +++ b/src/spicelib/devices/hisim2/hsm2def.h @@ -677,6 +677,54 @@ typedef struct sHSM2instance { double **HSM2nVar; #endif /* NONOISE */ +#ifdef KLU + BindElement *HSM2DPbpBinding ; + BindElement *HSM2SPbpBinding ; + BindElement *HSM2GPbpBinding ; + BindElement *HSM2BPdpBinding ; + BindElement *HSM2BPspBinding ; + BindElement *HSM2BPgpBinding ; + BindElement *HSM2BPbpBinding ; + BindElement *HSM2DdBinding ; + BindElement *HSM2GPgpBinding ; + BindElement *HSM2SsBinding ; + BindElement *HSM2DPdpBinding ; + BindElement *HSM2SPspBinding ; + BindElement *HSM2DdpBinding ; + BindElement *HSM2GPdpBinding ; + BindElement *HSM2GPspBinding ; + BindElement *HSM2SspBinding ; + BindElement *HSM2DPspBinding ; + BindElement *HSM2DPdBinding ; + BindElement *HSM2DPgpBinding ; + BindElement *HSM2SPgpBinding ; + BindElement *HSM2SPsBinding ; + BindElement *HSM2SPdpBinding ; + BindElement *HSM2GgBinding ; + BindElement *HSM2GgpBinding ; + BindElement *HSM2GPgBinding ; + BindElement *HSM2GdpBinding ; + BindElement *HSM2GspBinding ; + BindElement *HSM2GbpBinding ; + BindElement *HSM2DPdbBinding ; + BindElement *HSM2SPsbBinding ; + BindElement *HSM2DBdpBinding ; + BindElement *HSM2DBdbBinding ; + BindElement *HSM2DBbpBinding ; + BindElement *HSM2DBbBinding ; + BindElement *HSM2BPdbBinding ; + BindElement *HSM2BPbBinding ; + BindElement *HSM2BPsbBinding ; + BindElement *HSM2SBspBinding ; + BindElement *HSM2SBbpBinding ; + BindElement *HSM2SBbBinding ; + BindElement *HSM2SBsbBinding ; + BindElement *HSM2BdbBinding ; + BindElement *HSM2BbpBinding ; + BindElement *HSM2BsbBinding ; + BindElement *HSM2BbBinding ; +#endif + } HSM2instance ; diff --git a/src/spicelib/devices/hisim2/hsm2ext.h b/src/spicelib/devices/hisim2/hsm2ext.h index 8a84cddd8..2ee6a72e3 100644 --- a/src/spicelib/devices/hisim2/hsm2ext.h +++ b/src/spicelib/devices/hisim2/hsm2ext.h @@ -38,3 +38,9 @@ extern int HSM2temp(GENmodel*,CKTcircuit*); extern int HSM2trunc(GENmodel*,CKTcircuit*,double*); extern int HSM2noise(int,int,GENmodel*,CKTcircuit*,Ndata*,double*); extern int HSM2soaCheck(CKTcircuit *, GENmodel *); + +#ifdef KLU +extern int HSM2bindCSC (GENmodel*, CKTcircuit*) ; +extern int HSM2bindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int HSM2bindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/hisim2/hsm2init.c b/src/spicelib/devices/hisim2/hsm2init.c index c51b87549..b887560a4 100644 --- a/src/spicelib/devices/hisim2/hsm2init.c +++ b/src/spicelib/devices/hisim2/hsm2init.c @@ -66,6 +66,11 @@ SPICEdev HSM2info = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = HSM2bindCSC, + .DEVbindCSCComplex = HSM2bindCSCComplex, + .DEVbindCSCComplexToReal = HSM2bindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/hisimhv1/Makefile.am b/src/spicelib/devices/hisimhv1/Makefile.am index 44b121f18..84f0f516e 100644 --- a/src/spicelib/devices/hisimhv1/Makefile.am +++ b/src/spicelib/devices/hisimhv1/Makefile.am @@ -32,6 +32,11 @@ libhisimhv1_la_SOURCES = hisimhv.h \ hsmhvtemp_eval.h \ hsmhvtrunc.c + +if KLU_WANTED +libhisimhv1_la_SOURCES += hsmhvbindCSC.c +endif + AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) diff --git a/src/spicelib/devices/hisimhv1/hsmhvbindCSC.c b/src/spicelib/devices/hisimhv1/hsmhvbindCSC.c new file mode 100644 index 000000000..cc39dc1da --- /dev/null +++ b/src/spicelib/devices/hisimhv1/hsmhvbindCSC.c @@ -0,0 +1,386 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "hsmhvdef.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +HSMHVbindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + HSMHVmodel *model = (HSMHVmodel *)inModel ; + HSMHVinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the HSMHV models */ + for ( ; model != NULL ; model = HSMHVnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = HSMHVinstances(model); here != NULL ; here = HSMHVnextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(HSMHVDPbpPtr, HSMHVDPbpBinding, HSMHVdNodePrime, HSMHVbNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVSPbpPtr, HSMHVSPbpBinding, HSMHVsNodePrime, HSMHVbNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVGPbpPtr, HSMHVGPbpBinding, HSMHVgNodePrime, HSMHVbNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVBPdPtr, HSMHVBPdBinding, HSMHVbNodePrime, HSMHVdNode); + CREATE_KLU_BINDING_TABLE(HSMHVBPsPtr, HSMHVBPsBinding, HSMHVbNodePrime, HSMHVsNode); + CREATE_KLU_BINDING_TABLE(HSMHVBPdpPtr, HSMHVBPdpBinding, HSMHVbNodePrime, HSMHVdNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVBPspPtr, HSMHVBPspBinding, HSMHVbNodePrime, HSMHVsNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVBPgpPtr, HSMHVBPgpBinding, HSMHVbNodePrime, HSMHVgNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVBPbpPtr, HSMHVBPbpBinding, HSMHVbNodePrime, HSMHVbNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVDdPtr, HSMHVDdBinding, HSMHVdNode, HSMHVdNode); + CREATE_KLU_BINDING_TABLE(HSMHVGPgpPtr, HSMHVGPgpBinding, HSMHVgNodePrime, HSMHVgNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVSsPtr, HSMHVSsBinding, HSMHVsNode, HSMHVsNode); + CREATE_KLU_BINDING_TABLE(HSMHVDPdpPtr, HSMHVDPdpBinding, HSMHVdNodePrime, HSMHVdNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVSPspPtr, HSMHVSPspBinding, HSMHVsNodePrime, HSMHVsNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVDdpPtr, HSMHVDdpBinding, HSMHVdNode, HSMHVdNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVGPdpPtr, HSMHVGPdpBinding, HSMHVgNodePrime, HSMHVdNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVGPspPtr, HSMHVGPspBinding, HSMHVgNodePrime, HSMHVsNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVSspPtr, HSMHVSspBinding, HSMHVsNode, HSMHVsNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVDPspPtr, HSMHVDPspBinding, HSMHVdNodePrime, HSMHVsNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVDPdPtr, HSMHVDPdBinding, HSMHVdNodePrime, HSMHVdNode); + CREATE_KLU_BINDING_TABLE(HSMHVDPgpPtr, HSMHVDPgpBinding, HSMHVdNodePrime, HSMHVgNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVSPgpPtr, HSMHVSPgpBinding, HSMHVsNodePrime, HSMHVgNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVSPsPtr, HSMHVSPsBinding, HSMHVsNodePrime, HSMHVsNode); + CREATE_KLU_BINDING_TABLE(HSMHVSPdpPtr, HSMHVSPdpBinding, HSMHVsNodePrime, HSMHVdNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVGgPtr, HSMHVGgBinding, HSMHVgNode, HSMHVgNode); + CREATE_KLU_BINDING_TABLE(HSMHVGgpPtr, HSMHVGgpBinding, HSMHVgNode, HSMHVgNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVGPgPtr, HSMHVGPgBinding, HSMHVgNodePrime, HSMHVgNode); + CREATE_KLU_BINDING_TABLE(HSMHVDdbPtr, HSMHVDdbBinding, HSMHVdNode, HSMHVdbNode); + CREATE_KLU_BINDING_TABLE(HSMHVSsbPtr, HSMHVSsbBinding, HSMHVsNode, HSMHVsbNode); + CREATE_KLU_BINDING_TABLE(HSMHVDBdPtr, HSMHVDBdBinding, HSMHVdbNode, HSMHVdNode); + CREATE_KLU_BINDING_TABLE(HSMHVDBdbPtr, HSMHVDBdbBinding, HSMHVdbNode, HSMHVdbNode); + CREATE_KLU_BINDING_TABLE(HSMHVDBbpPtr, HSMHVDBbpBinding, HSMHVdbNode, HSMHVbNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVBPdbPtr, HSMHVBPdbBinding, HSMHVbNodePrime, HSMHVdbNode); + CREATE_KLU_BINDING_TABLE(HSMHVBPbPtr, HSMHVBPbBinding, HSMHVbNodePrime, HSMHVbNode); + CREATE_KLU_BINDING_TABLE(HSMHVBPsbPtr, HSMHVBPsbBinding, HSMHVbNodePrime, HSMHVsbNode); + CREATE_KLU_BINDING_TABLE(HSMHVSBsPtr, HSMHVSBsBinding, HSMHVsbNode, HSMHVsNode); + CREATE_KLU_BINDING_TABLE(HSMHVSBbpPtr, HSMHVSBbpBinding, HSMHVsbNode, HSMHVbNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVSBsbPtr, HSMHVSBsbBinding, HSMHVsbNode, HSMHVsbNode); + CREATE_KLU_BINDING_TABLE(HSMHVBbpPtr, HSMHVBbpBinding, HSMHVbNode, HSMHVbNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVBbPtr, HSMHVBbBinding, HSMHVbNode, HSMHVbNode); + CREATE_KLU_BINDING_TABLE(HSMHVDgpPtr, HSMHVDgpBinding, HSMHVdNode, HSMHVgNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVDsPtr, HSMHVDsBinding, HSMHVdNode, HSMHVsNode); + CREATE_KLU_BINDING_TABLE(HSMHVDbpPtr, HSMHVDbpBinding, HSMHVdNode, HSMHVbNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVDspPtr, HSMHVDspBinding, HSMHVdNode, HSMHVsNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVDPsPtr, HSMHVDPsBinding, HSMHVdNodePrime, HSMHVsNode); + CREATE_KLU_BINDING_TABLE(HSMHVSgpPtr, HSMHVSgpBinding, HSMHVsNode, HSMHVgNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVSdPtr, HSMHVSdBinding, HSMHVsNode, HSMHVdNode); + CREATE_KLU_BINDING_TABLE(HSMHVSbpPtr, HSMHVSbpBinding, HSMHVsNode, HSMHVbNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVSdpPtr, HSMHVSdpBinding, HSMHVsNode, HSMHVdNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVSPdPtr, HSMHVSPdBinding, HSMHVsNodePrime, HSMHVdNode); + CREATE_KLU_BINDING_TABLE(HSMHVGPdPtr, HSMHVGPdBinding, HSMHVgNodePrime, HSMHVdNode); + CREATE_KLU_BINDING_TABLE(HSMHVGPsPtr, HSMHVGPsBinding, HSMHVgNodePrime, HSMHVsNode); + if (here->HSMHVsubNode > 0) + { + CREATE_KLU_BINDING_TABLE(HSMHVDsubPtr, HSMHVDsubBinding, HSMHVdNode, HSMHVsubNode); + CREATE_KLU_BINDING_TABLE(HSMHVDPsubPtr, HSMHVDPsubBinding, HSMHVdNodePrime, HSMHVsubNode); + CREATE_KLU_BINDING_TABLE(HSMHVSsubPtr, HSMHVSsubBinding, HSMHVsNode, HSMHVsubNode); + CREATE_KLU_BINDING_TABLE(HSMHVSPsubPtr, HSMHVSPsubBinding, HSMHVsNodePrime, HSMHVsubNode); + } + if (here->HSMHV_coselfheat > 0) + { + CREATE_KLU_BINDING_TABLE(HSMHVTemptempPtr, HSMHVTemptempBinding, HSMHVtempNode, HSMHVtempNode); + CREATE_KLU_BINDING_TABLE(HSMHVTempdPtr, HSMHVTempdBinding, HSMHVtempNode, HSMHVdNode); + CREATE_KLU_BINDING_TABLE(HSMHVTempdpPtr, HSMHVTempdpBinding, HSMHVtempNode, HSMHVdNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVTempsPtr, HSMHVTempsBinding, HSMHVtempNode, HSMHVsNode); + CREATE_KLU_BINDING_TABLE(HSMHVTempspPtr, HSMHVTempspBinding, HSMHVtempNode, HSMHVsNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVDPtempPtr, HSMHVDPtempBinding, HSMHVdNodePrime, HSMHVtempNode); + CREATE_KLU_BINDING_TABLE(HSMHVSPtempPtr, HSMHVSPtempBinding, HSMHVsNodePrime, HSMHVtempNode); + CREATE_KLU_BINDING_TABLE(HSMHVTempgpPtr, HSMHVTempgpBinding, HSMHVtempNode, HSMHVgNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVTempbpPtr, HSMHVTempbpBinding, HSMHVtempNode, HSMHVbNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVGPtempPtr, HSMHVGPtempBinding, HSMHVgNodePrime, HSMHVtempNode); + CREATE_KLU_BINDING_TABLE(HSMHVBPtempPtr, HSMHVBPtempBinding, HSMHVbNodePrime, HSMHVtempNode); + CREATE_KLU_BINDING_TABLE(HSMHVDBtempPtr, HSMHVDBtempBinding, HSMHVdbNode, HSMHVtempNode); + CREATE_KLU_BINDING_TABLE(HSMHVSBtempPtr, HSMHVSBtempBinding, HSMHVsbNode, HSMHVtempNode); + CREATE_KLU_BINDING_TABLE(HSMHVDtempPtr, HSMHVDtempBinding, HSMHVdNode, HSMHVtempNode); + CREATE_KLU_BINDING_TABLE(HSMHVStempPtr, HSMHVStempBinding, HSMHVsNode, HSMHVtempNode); + } + if (model->HSMHV_conqs) + { + CREATE_KLU_BINDING_TABLE(HSMHVDPqiPtr, HSMHVDPqiBinding, HSMHVdNodePrime, HSMHVqiNode); + CREATE_KLU_BINDING_TABLE(HSMHVGPqiPtr, HSMHVGPqiBinding, HSMHVgNodePrime, HSMHVqiNode); + CREATE_KLU_BINDING_TABLE(HSMHVGPqbPtr, HSMHVGPqbBinding, HSMHVgNodePrime, HSMHVqbNode); + CREATE_KLU_BINDING_TABLE(HSMHVSPqiPtr, HSMHVSPqiBinding, HSMHVsNodePrime, HSMHVqiNode); + CREATE_KLU_BINDING_TABLE(HSMHVBPqbPtr, HSMHVBPqbBinding, HSMHVbNodePrime, HSMHVqbNode); + CREATE_KLU_BINDING_TABLE(HSMHVQIdpPtr, HSMHVQIdpBinding, HSMHVqiNode, HSMHVdNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVQIgpPtr, HSMHVQIgpBinding, HSMHVqiNode, HSMHVgNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVQIspPtr, HSMHVQIspBinding, HSMHVqiNode, HSMHVsNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVQIbpPtr, HSMHVQIbpBinding, HSMHVqiNode, HSMHVbNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVQIqiPtr, HSMHVQIqiBinding, HSMHVqiNode, HSMHVqiNode); + CREATE_KLU_BINDING_TABLE(HSMHVQBdpPtr, HSMHVQBdpBinding, HSMHVqbNode, HSMHVdNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVQBgpPtr, HSMHVQBgpBinding, HSMHVqbNode, HSMHVgNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVQBspPtr, HSMHVQBspBinding, HSMHVqbNode, HSMHVsNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVQBbpPtr, HSMHVQBbpBinding, HSMHVqbNode, HSMHVbNodePrime); + CREATE_KLU_BINDING_TABLE(HSMHVQBqbPtr, HSMHVQBqbBinding, HSMHVqbNode, HSMHVqbNode); + if (here->HSMHV_coselfheat > 0) + { + CREATE_KLU_BINDING_TABLE(HSMHVQItempPtr, HSMHVQItempBinding, HSMHVqiNode, HSMHVtempNode); + CREATE_KLU_BINDING_TABLE(HSMHVQBtempPtr, HSMHVQBtempBinding, HSMHVqbNode, HSMHVtempNode); + } + } + } + } + + return (OK) ; +} + +int +HSMHVbindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + HSMHVmodel *model = (HSMHVmodel *)inModel ; + HSMHVinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the HSMHV models */ + for ( ; model != NULL ; model = HSMHVnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = HSMHVinstances(model); here != NULL ; here = HSMHVnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVDPbpPtr, HSMHVDPbpBinding, HSMHVdNodePrime, HSMHVbNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVSPbpPtr, HSMHVSPbpBinding, HSMHVsNodePrime, HSMHVbNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVGPbpPtr, HSMHVGPbpBinding, HSMHVgNodePrime, HSMHVbNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVBPdPtr, HSMHVBPdBinding, HSMHVbNodePrime, HSMHVdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVBPsPtr, HSMHVBPsBinding, HSMHVbNodePrime, HSMHVsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVBPdpPtr, HSMHVBPdpBinding, HSMHVbNodePrime, HSMHVdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVBPspPtr, HSMHVBPspBinding, HSMHVbNodePrime, HSMHVsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVBPgpPtr, HSMHVBPgpBinding, HSMHVbNodePrime, HSMHVgNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVBPbpPtr, HSMHVBPbpBinding, HSMHVbNodePrime, HSMHVbNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVDdPtr, HSMHVDdBinding, HSMHVdNode, HSMHVdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVGPgpPtr, HSMHVGPgpBinding, HSMHVgNodePrime, HSMHVgNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVSsPtr, HSMHVSsBinding, HSMHVsNode, HSMHVsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVDPdpPtr, HSMHVDPdpBinding, HSMHVdNodePrime, HSMHVdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVSPspPtr, HSMHVSPspBinding, HSMHVsNodePrime, HSMHVsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVDdpPtr, HSMHVDdpBinding, HSMHVdNode, HSMHVdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVGPdpPtr, HSMHVGPdpBinding, HSMHVgNodePrime, HSMHVdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVGPspPtr, HSMHVGPspBinding, HSMHVgNodePrime, HSMHVsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVSspPtr, HSMHVSspBinding, HSMHVsNode, HSMHVsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVDPspPtr, HSMHVDPspBinding, HSMHVdNodePrime, HSMHVsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVDPdPtr, HSMHVDPdBinding, HSMHVdNodePrime, HSMHVdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVDPgpPtr, HSMHVDPgpBinding, HSMHVdNodePrime, HSMHVgNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVSPgpPtr, HSMHVSPgpBinding, HSMHVsNodePrime, HSMHVgNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVSPsPtr, HSMHVSPsBinding, HSMHVsNodePrime, HSMHVsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVSPdpPtr, HSMHVSPdpBinding, HSMHVsNodePrime, HSMHVdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVGgPtr, HSMHVGgBinding, HSMHVgNode, HSMHVgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVGgpPtr, HSMHVGgpBinding, HSMHVgNode, HSMHVgNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVGPgPtr, HSMHVGPgBinding, HSMHVgNodePrime, HSMHVgNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVDdbPtr, HSMHVDdbBinding, HSMHVdNode, HSMHVdbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVSsbPtr, HSMHVSsbBinding, HSMHVsNode, HSMHVsbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVDBdPtr, HSMHVDBdBinding, HSMHVdbNode, HSMHVdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVDBdbPtr, HSMHVDBdbBinding, HSMHVdbNode, HSMHVdbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVDBbpPtr, HSMHVDBbpBinding, HSMHVdbNode, HSMHVbNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVBPdbPtr, HSMHVBPdbBinding, HSMHVbNodePrime, HSMHVdbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVBPbPtr, HSMHVBPbBinding, HSMHVbNodePrime, HSMHVbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVBPsbPtr, HSMHVBPsbBinding, HSMHVbNodePrime, HSMHVsbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVSBsPtr, HSMHVSBsBinding, HSMHVsbNode, HSMHVsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVSBbpPtr, HSMHVSBbpBinding, HSMHVsbNode, HSMHVbNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVSBsbPtr, HSMHVSBsbBinding, HSMHVsbNode, HSMHVsbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVBbpPtr, HSMHVBbpBinding, HSMHVbNode, HSMHVbNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVBbPtr, HSMHVBbBinding, HSMHVbNode, HSMHVbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVDgpPtr, HSMHVDgpBinding, HSMHVdNode, HSMHVgNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVDsPtr, HSMHVDsBinding, HSMHVdNode, HSMHVsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVDbpPtr, HSMHVDbpBinding, HSMHVdNode, HSMHVbNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVDspPtr, HSMHVDspBinding, HSMHVdNode, HSMHVsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVDPsPtr, HSMHVDPsBinding, HSMHVdNodePrime, HSMHVsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVSgpPtr, HSMHVSgpBinding, HSMHVsNode, HSMHVgNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVSdPtr, HSMHVSdBinding, HSMHVsNode, HSMHVdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVSbpPtr, HSMHVSbpBinding, HSMHVsNode, HSMHVbNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVSdpPtr, HSMHVSdpBinding, HSMHVsNode, HSMHVdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVSPdPtr, HSMHVSPdBinding, HSMHVsNodePrime, HSMHVdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVGPdPtr, HSMHVGPdBinding, HSMHVgNodePrime, HSMHVdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVGPsPtr, HSMHVGPsBinding, HSMHVgNodePrime, HSMHVsNode); + if (here->HSMHVsubNode > 0) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVDsubPtr, HSMHVDsubBinding, HSMHVdNode, HSMHVsubNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVDPsubPtr, HSMHVDPsubBinding, HSMHVdNodePrime, HSMHVsubNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVSsubPtr, HSMHVSsubBinding, HSMHVsNode, HSMHVsubNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVSPsubPtr, HSMHVSPsubBinding, HSMHVsNodePrime, HSMHVsubNode); + } + if (here->HSMHV_coselfheat > 0) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVTemptempPtr, HSMHVTemptempBinding, HSMHVtempNode, HSMHVtempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVTempdPtr, HSMHVTempdBinding, HSMHVtempNode, HSMHVdNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVTempdpPtr, HSMHVTempdpBinding, HSMHVtempNode, HSMHVdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVTempsPtr, HSMHVTempsBinding, HSMHVtempNode, HSMHVsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVTempspPtr, HSMHVTempspBinding, HSMHVtempNode, HSMHVsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVDPtempPtr, HSMHVDPtempBinding, HSMHVdNodePrime, HSMHVtempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVSPtempPtr, HSMHVSPtempBinding, HSMHVsNodePrime, HSMHVtempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVTempgpPtr, HSMHVTempgpBinding, HSMHVtempNode, HSMHVgNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVTempbpPtr, HSMHVTempbpBinding, HSMHVtempNode, HSMHVbNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVGPtempPtr, HSMHVGPtempBinding, HSMHVgNodePrime, HSMHVtempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVBPtempPtr, HSMHVBPtempBinding, HSMHVbNodePrime, HSMHVtempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVDBtempPtr, HSMHVDBtempBinding, HSMHVdbNode, HSMHVtempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVSBtempPtr, HSMHVSBtempBinding, HSMHVsbNode, HSMHVtempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVDtempPtr, HSMHVDtempBinding, HSMHVdNode, HSMHVtempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVStempPtr, HSMHVStempBinding, HSMHVsNode, HSMHVtempNode); + } + if (model->HSMHV_conqs) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVDPqiPtr, HSMHVDPqiBinding, HSMHVdNodePrime, HSMHVqiNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVGPqiPtr, HSMHVGPqiBinding, HSMHVgNodePrime, HSMHVqiNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVGPqbPtr, HSMHVGPqbBinding, HSMHVgNodePrime, HSMHVqbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVSPqiPtr, HSMHVSPqiBinding, HSMHVsNodePrime, HSMHVqiNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVBPqbPtr, HSMHVBPqbBinding, HSMHVbNodePrime, HSMHVqbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVQIdpPtr, HSMHVQIdpBinding, HSMHVqiNode, HSMHVdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVQIgpPtr, HSMHVQIgpBinding, HSMHVqiNode, HSMHVgNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVQIspPtr, HSMHVQIspBinding, HSMHVqiNode, HSMHVsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVQIbpPtr, HSMHVQIbpBinding, HSMHVqiNode, HSMHVbNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVQIqiPtr, HSMHVQIqiBinding, HSMHVqiNode, HSMHVqiNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVQBdpPtr, HSMHVQBdpBinding, HSMHVqbNode, HSMHVdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVQBgpPtr, HSMHVQBgpBinding, HSMHVqbNode, HSMHVgNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVQBspPtr, HSMHVQBspBinding, HSMHVqbNode, HSMHVsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVQBbpPtr, HSMHVQBbpBinding, HSMHVqbNode, HSMHVbNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVQBqbPtr, HSMHVQBqbBinding, HSMHVqbNode, HSMHVqbNode); + if (here->HSMHV_coselfheat > 0) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVQItempPtr, HSMHVQItempBinding, HSMHVqiNode, HSMHVtempNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(HSMHVQBtempPtr, HSMHVQBtempBinding, HSMHVqbNode, HSMHVtempNode); + } + } + } + } + + return (OK) ; +} + +int +HSMHVbindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + HSMHVmodel *model = (HSMHVmodel *)inModel ; + HSMHVinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the HSMHV models */ + for ( ; model != NULL ; model = HSMHVnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = HSMHVinstances(model); here != NULL ; here = HSMHVnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVDPbpPtr, HSMHVDPbpBinding, HSMHVdNodePrime, HSMHVbNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVSPbpPtr, HSMHVSPbpBinding, HSMHVsNodePrime, HSMHVbNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVGPbpPtr, HSMHVGPbpBinding, HSMHVgNodePrime, HSMHVbNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVBPdPtr, HSMHVBPdBinding, HSMHVbNodePrime, HSMHVdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVBPsPtr, HSMHVBPsBinding, HSMHVbNodePrime, HSMHVsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVBPdpPtr, HSMHVBPdpBinding, HSMHVbNodePrime, HSMHVdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVBPspPtr, HSMHVBPspBinding, HSMHVbNodePrime, HSMHVsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVBPgpPtr, HSMHVBPgpBinding, HSMHVbNodePrime, HSMHVgNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVBPbpPtr, HSMHVBPbpBinding, HSMHVbNodePrime, HSMHVbNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVDdPtr, HSMHVDdBinding, HSMHVdNode, HSMHVdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVGPgpPtr, HSMHVGPgpBinding, HSMHVgNodePrime, HSMHVgNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVSsPtr, HSMHVSsBinding, HSMHVsNode, HSMHVsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVDPdpPtr, HSMHVDPdpBinding, HSMHVdNodePrime, HSMHVdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVSPspPtr, HSMHVSPspBinding, HSMHVsNodePrime, HSMHVsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVDdpPtr, HSMHVDdpBinding, HSMHVdNode, HSMHVdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVGPdpPtr, HSMHVGPdpBinding, HSMHVgNodePrime, HSMHVdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVGPspPtr, HSMHVGPspBinding, HSMHVgNodePrime, HSMHVsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVSspPtr, HSMHVSspBinding, HSMHVsNode, HSMHVsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVDPspPtr, HSMHVDPspBinding, HSMHVdNodePrime, HSMHVsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVDPdPtr, HSMHVDPdBinding, HSMHVdNodePrime, HSMHVdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVDPgpPtr, HSMHVDPgpBinding, HSMHVdNodePrime, HSMHVgNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVSPgpPtr, HSMHVSPgpBinding, HSMHVsNodePrime, HSMHVgNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVSPsPtr, HSMHVSPsBinding, HSMHVsNodePrime, HSMHVsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVSPdpPtr, HSMHVSPdpBinding, HSMHVsNodePrime, HSMHVdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVGgPtr, HSMHVGgBinding, HSMHVgNode, HSMHVgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVGgpPtr, HSMHVGgpBinding, HSMHVgNode, HSMHVgNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVGPgPtr, HSMHVGPgBinding, HSMHVgNodePrime, HSMHVgNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVDdbPtr, HSMHVDdbBinding, HSMHVdNode, HSMHVdbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVSsbPtr, HSMHVSsbBinding, HSMHVsNode, HSMHVsbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVDBdPtr, HSMHVDBdBinding, HSMHVdbNode, HSMHVdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVDBdbPtr, HSMHVDBdbBinding, HSMHVdbNode, HSMHVdbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVDBbpPtr, HSMHVDBbpBinding, HSMHVdbNode, HSMHVbNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVBPdbPtr, HSMHVBPdbBinding, HSMHVbNodePrime, HSMHVdbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVBPbPtr, HSMHVBPbBinding, HSMHVbNodePrime, HSMHVbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVBPsbPtr, HSMHVBPsbBinding, HSMHVbNodePrime, HSMHVsbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVSBsPtr, HSMHVSBsBinding, HSMHVsbNode, HSMHVsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVSBbpPtr, HSMHVSBbpBinding, HSMHVsbNode, HSMHVbNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVSBsbPtr, HSMHVSBsbBinding, HSMHVsbNode, HSMHVsbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVBbpPtr, HSMHVBbpBinding, HSMHVbNode, HSMHVbNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVBbPtr, HSMHVBbBinding, HSMHVbNode, HSMHVbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVDgpPtr, HSMHVDgpBinding, HSMHVdNode, HSMHVgNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVDsPtr, HSMHVDsBinding, HSMHVdNode, HSMHVsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVDbpPtr, HSMHVDbpBinding, HSMHVdNode, HSMHVbNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVDspPtr, HSMHVDspBinding, HSMHVdNode, HSMHVsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVDPsPtr, HSMHVDPsBinding, HSMHVdNodePrime, HSMHVsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVSgpPtr, HSMHVSgpBinding, HSMHVsNode, HSMHVgNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVSdPtr, HSMHVSdBinding, HSMHVsNode, HSMHVdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVSbpPtr, HSMHVSbpBinding, HSMHVsNode, HSMHVbNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVSdpPtr, HSMHVSdpBinding, HSMHVsNode, HSMHVdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVSPdPtr, HSMHVSPdBinding, HSMHVsNodePrime, HSMHVdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVGPdPtr, HSMHVGPdBinding, HSMHVgNodePrime, HSMHVdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVGPsPtr, HSMHVGPsBinding, HSMHVgNodePrime, HSMHVsNode); + if (here->HSMHVsubNode > 0) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVDsubPtr, HSMHVDsubBinding, HSMHVdNode, HSMHVsubNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVDPsubPtr, HSMHVDPsubBinding, HSMHVdNodePrime, HSMHVsubNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVSsubPtr, HSMHVSsubBinding, HSMHVsNode, HSMHVsubNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVSPsubPtr, HSMHVSPsubBinding, HSMHVsNodePrime, HSMHVsubNode); + } + if (here->HSMHV_coselfheat > 0) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVTemptempPtr, HSMHVTemptempBinding, HSMHVtempNode, HSMHVtempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVTempdPtr, HSMHVTempdBinding, HSMHVtempNode, HSMHVdNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVTempdpPtr, HSMHVTempdpBinding, HSMHVtempNode, HSMHVdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVTempsPtr, HSMHVTempsBinding, HSMHVtempNode, HSMHVsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVTempspPtr, HSMHVTempspBinding, HSMHVtempNode, HSMHVsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVDPtempPtr, HSMHVDPtempBinding, HSMHVdNodePrime, HSMHVtempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVSPtempPtr, HSMHVSPtempBinding, HSMHVsNodePrime, HSMHVtempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVTempgpPtr, HSMHVTempgpBinding, HSMHVtempNode, HSMHVgNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVTempbpPtr, HSMHVTempbpBinding, HSMHVtempNode, HSMHVbNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVGPtempPtr, HSMHVGPtempBinding, HSMHVgNodePrime, HSMHVtempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVBPtempPtr, HSMHVBPtempBinding, HSMHVbNodePrime, HSMHVtempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVDBtempPtr, HSMHVDBtempBinding, HSMHVdbNode, HSMHVtempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVSBtempPtr, HSMHVSBtempBinding, HSMHVsbNode, HSMHVtempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVDtempPtr, HSMHVDtempBinding, HSMHVdNode, HSMHVtempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVStempPtr, HSMHVStempBinding, HSMHVsNode, HSMHVtempNode); + } + if (model->HSMHV_conqs) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVDPqiPtr, HSMHVDPqiBinding, HSMHVdNodePrime, HSMHVqiNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVGPqiPtr, HSMHVGPqiBinding, HSMHVgNodePrime, HSMHVqiNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVGPqbPtr, HSMHVGPqbBinding, HSMHVgNodePrime, HSMHVqbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVSPqiPtr, HSMHVSPqiBinding, HSMHVsNodePrime, HSMHVqiNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVBPqbPtr, HSMHVBPqbBinding, HSMHVbNodePrime, HSMHVqbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVQIdpPtr, HSMHVQIdpBinding, HSMHVqiNode, HSMHVdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVQIgpPtr, HSMHVQIgpBinding, HSMHVqiNode, HSMHVgNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVQIspPtr, HSMHVQIspBinding, HSMHVqiNode, HSMHVsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVQIbpPtr, HSMHVQIbpBinding, HSMHVqiNode, HSMHVbNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVQIqiPtr, HSMHVQIqiBinding, HSMHVqiNode, HSMHVqiNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVQBdpPtr, HSMHVQBdpBinding, HSMHVqbNode, HSMHVdNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVQBgpPtr, HSMHVQBgpBinding, HSMHVqbNode, HSMHVgNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVQBspPtr, HSMHVQBspBinding, HSMHVqbNode, HSMHVsNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVQBbpPtr, HSMHVQBbpBinding, HSMHVqbNode, HSMHVbNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVQBqbPtr, HSMHVQBqbBinding, HSMHVqbNode, HSMHVqbNode); + if (here->HSMHV_coselfheat > 0) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVQItempPtr, HSMHVQItempBinding, HSMHVqiNode, HSMHVtempNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(HSMHVQBtempPtr, HSMHVQBtempBinding, HSMHVqbNode, HSMHVtempNode); + } + } + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/hisimhv1/hsmhvdef.h b/src/spicelib/devices/hisimhv1/hsmhvdef.h index d93015c53..1e4a4bf0d 100644 --- a/src/spicelib/devices/hisimhv1/hsmhvdef.h +++ b/src/spicelib/devices/hisimhv1/hsmhvdef.h @@ -907,6 +907,97 @@ typedef struct sHSMHVinstance { double **HSMHVnVar; #endif /* NONOISE */ +#ifdef KLU + BindElement *HSMHVDPbpBinding ; + BindElement *HSMHVSPbpBinding ; + BindElement *HSMHVGPbpBinding ; + BindElement *HSMHVBPdBinding ; + BindElement *HSMHVBPsBinding ; + BindElement *HSMHVBPdpBinding ; + BindElement *HSMHVBPspBinding ; + BindElement *HSMHVBPgpBinding ; + BindElement *HSMHVBPbpBinding ; + BindElement *HSMHVDdBinding ; + BindElement *HSMHVGPgpBinding ; + BindElement *HSMHVSsBinding ; + BindElement *HSMHVDPdpBinding ; + BindElement *HSMHVSPspBinding ; + BindElement *HSMHVDdpBinding ; + BindElement *HSMHVGPdpBinding ; + BindElement *HSMHVGPspBinding ; + BindElement *HSMHVSspBinding ; + BindElement *HSMHVDPspBinding ; + BindElement *HSMHVDPdBinding ; + BindElement *HSMHVDPgpBinding ; + BindElement *HSMHVSPgpBinding ; + BindElement *HSMHVSPsBinding ; + BindElement *HSMHVSPdpBinding ; + BindElement *HSMHVGgBinding ; + BindElement *HSMHVGgpBinding ; + BindElement *HSMHVGPgBinding ; + BindElement *HSMHVDdbBinding ; + BindElement *HSMHVSsbBinding ; + BindElement *HSMHVDBdBinding ; + BindElement *HSMHVDBdbBinding ; + BindElement *HSMHVDBbpBinding ; + BindElement *HSMHVBPdbBinding ; + BindElement *HSMHVBPbBinding ; + BindElement *HSMHVBPsbBinding ; + BindElement *HSMHVSBsBinding ; + BindElement *HSMHVSBbpBinding ; + BindElement *HSMHVSBsbBinding ; + BindElement *HSMHVBbpBinding ; + BindElement *HSMHVBbBinding ; + BindElement *HSMHVDgpBinding ; + BindElement *HSMHVDsBinding ; + BindElement *HSMHVDbpBinding ; + BindElement *HSMHVDspBinding ; + BindElement *HSMHVDPsBinding ; + BindElement *HSMHVSgpBinding ; + BindElement *HSMHVSdBinding ; + BindElement *HSMHVSbpBinding ; + BindElement *HSMHVSdpBinding ; + BindElement *HSMHVSPdBinding ; + BindElement *HSMHVGPdBinding ; + BindElement *HSMHVGPsBinding ; + BindElement *HSMHVDsubBinding ; + BindElement *HSMHVDPsubBinding ; + BindElement *HSMHVSsubBinding ; + BindElement *HSMHVSPsubBinding ; + BindElement *HSMHVTemptempBinding ; + BindElement *HSMHVTempdBinding ; + BindElement *HSMHVTempdpBinding ; + BindElement *HSMHVTempsBinding ; + BindElement *HSMHVTempspBinding ; + BindElement *HSMHVDPtempBinding ; + BindElement *HSMHVSPtempBinding ; + BindElement *HSMHVTempgpBinding ; + BindElement *HSMHVTempbpBinding ; + BindElement *HSMHVGPtempBinding ; + BindElement *HSMHVBPtempBinding ; + BindElement *HSMHVDBtempBinding ; + BindElement *HSMHVSBtempBinding ; + BindElement *HSMHVDtempBinding ; + BindElement *HSMHVStempBinding ; + BindElement *HSMHVDPqiBinding ; + BindElement *HSMHVGPqiBinding ; + BindElement *HSMHVGPqbBinding ; + BindElement *HSMHVSPqiBinding ; + BindElement *HSMHVBPqbBinding ; + BindElement *HSMHVQIdpBinding ; + BindElement *HSMHVQIgpBinding ; + BindElement *HSMHVQIspBinding ; + BindElement *HSMHVQIbpBinding ; + BindElement *HSMHVQIqiBinding ; + BindElement *HSMHVQBdpBinding ; + BindElement *HSMHVQBgpBinding ; + BindElement *HSMHVQBspBinding ; + BindElement *HSMHVQBbpBinding ; + BindElement *HSMHVQBqbBinding ; + BindElement *HSMHVQItempBinding ; + BindElement *HSMHVQBtempBinding ; +#endif + } HSMHVinstance ; diff --git a/src/spicelib/devices/hisimhv1/hsmhvext.h b/src/spicelib/devices/hisimhv1/hsmhvext.h index 780c7a3cf..3be866846 100644 --- a/src/spicelib/devices/hisimhv1/hsmhvext.h +++ b/src/spicelib/devices/hisimhv1/hsmhvext.h @@ -38,3 +38,9 @@ extern int HSMHVtemp(GENmodel*,CKTcircuit*); extern int HSMHVtrunc(GENmodel*,CKTcircuit*,double*); extern int HSMHVnoise(int,int,GENmodel*,CKTcircuit*,Ndata*,double*); extern int HSMHVsoaCheck(CKTcircuit *, GENmodel *); + +#ifdef KLU +extern int HSMHVbindCSC (GENmodel*, CKTcircuit*); +extern int HSMHVbindCSCComplex (GENmodel*, CKTcircuit*); +extern int HSMHVbindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/hisimhv1/hsmhvinit.c b/src/spicelib/devices/hisimhv1/hsmhvinit.c index 40cd4a561..e79ce69e4 100644 --- a/src/spicelib/devices/hisimhv1/hsmhvinit.c +++ b/src/spicelib/devices/hisimhv1/hsmhvinit.c @@ -66,6 +66,11 @@ SPICEdev HSMHVinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = HSMHVbindCSC, + .DEVbindCSCComplex = HSMHVbindCSCComplex, + .DEVbindCSCComplexToReal = HSMHVbindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/ind/Makefile.am b/src/spicelib/devices/ind/Makefile.am index 5a05ee97b..dfbc0442f 100644 --- a/src/spicelib/devices/ind/Makefile.am +++ b/src/spicelib/devices/ind/Makefile.am @@ -40,7 +40,12 @@ libind_la_SOURCES = \ muttemp.c +if KLU_WANTED +libind_la_SOURCES += indbindCSC.c +libind_la_SOURCES += mutbindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) + MAINTAINERCLEANFILES = Makefile.in diff --git a/src/spicelib/devices/ind/indbindCSC.c b/src/spicelib/devices/ind/indbindCSC.c new file mode 100644 index 000000000..609c0ed2c --- /dev/null +++ b/src/spicelib/devices/ind/indbindCSC.c @@ -0,0 +1,101 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "inddefs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +INDbindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + INDmodel *model = (INDmodel *)inModel ; + INDinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the IND models */ + for ( ; model != NULL ; model = INDnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = INDinstances(model); here != NULL ; here = INDnextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(INDposIbrPtr, INDposIbrBinding, INDposNode, INDbrEq); + CREATE_KLU_BINDING_TABLE(INDnegIbrPtr, INDnegIbrBinding, INDnegNode, INDbrEq); + CREATE_KLU_BINDING_TABLE(INDibrNegPtr, INDibrNegBinding, INDbrEq, INDnegNode); + CREATE_KLU_BINDING_TABLE(INDibrPosPtr, INDibrPosBinding, INDbrEq, INDposNode); + CREATE_KLU_BINDING_TABLE(INDibrIbrPtr, INDibrIbrBinding, INDbrEq, INDbrEq); + } + } + + return (OK) ; +} + +int +INDbindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + INDmodel *model = (INDmodel *)inModel ; + INDinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the IND models */ + for ( ; model != NULL ; model = INDnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = INDinstances(model); here != NULL ; here = INDnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(INDposIbrPtr, INDposIbrBinding, INDposNode, INDbrEq); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(INDnegIbrPtr, INDnegIbrBinding, INDnegNode, INDbrEq); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(INDibrNegPtr, INDibrNegBinding, INDbrEq, INDnegNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(INDibrPosPtr, INDibrPosBinding, INDbrEq, INDposNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(INDibrIbrPtr, INDibrIbrBinding, INDbrEq, INDbrEq); + } + } + + return (OK) ; +} + +int +INDbindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + INDmodel *model = (INDmodel *)inModel ; + INDinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the IND models */ + for ( ; model != NULL ; model = INDnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = INDinstances(model); here != NULL ; here = INDnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(INDposIbrPtr, INDposIbrBinding, INDposNode, INDbrEq); + CONVERT_KLU_BINDING_TABLE_TO_REAL(INDnegIbrPtr, INDnegIbrBinding, INDnegNode, INDbrEq); + CONVERT_KLU_BINDING_TABLE_TO_REAL(INDibrNegPtr, INDibrNegBinding, INDbrEq, INDnegNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(INDibrPosPtr, INDibrPosBinding, INDbrEq, INDposNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(INDibrIbrPtr, INDibrIbrBinding, INDbrEq, INDbrEq); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/ind/inddefs.h b/src/spicelib/devices/ind/inddefs.h index e987bc4cb..29d86207c 100644 --- a/src/spicelib/devices/ind/inddefs.h +++ b/src/spicelib/devices/ind/inddefs.h @@ -75,6 +75,14 @@ struct sINDinstance { struct INDsystem *system; INDinstance *system_next_ind; int system_idx; + +#ifdef KLU + BindElement *INDposIbrBinding; + BindElement *INDnegIbrBinding; + BindElement *INDibrNegBinding; + BindElement *INDibrPosBinding; + BindElement *INDibrIbrBinding; +#endif }; #define INDflux INDstate /* flux in the inductor */ @@ -147,6 +155,11 @@ struct sMUTinstance { * set equal to 0 if not a design parameter */ MUTinstance *system_next_mut; + +#ifdef KLU + BindElement *MUTbr1br2Binding; + BindElement *MUTbr2br1Binding; +#endif }; diff --git a/src/spicelib/devices/ind/indext.h b/src/spicelib/devices/ind/indext.h index 3fd334818..e7adf53f8 100644 --- a/src/spicelib/devices/ind/indext.h +++ b/src/spicelib/devices/ind/indext.h @@ -36,4 +36,14 @@ extern void MUTsPrint(GENmodel*,CKTcircuit*); extern int MUTsSetup(SENstruct*,GENmodel*); extern int MUTsetup(SMPmatrix*,GENmodel*,CKTcircuit*,int*); extern int MUTtemp(GENmodel *inModel, CKTcircuit *ckt); + +#ifdef KLU +extern int INDbindCSC (GENmodel*, CKTcircuit*) ; +extern int INDbindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int INDbindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +extern int MUTbindCSC (GENmodel*, CKTcircuit*) ; +extern int MUTbindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int MUTbindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif + #endif diff --git a/src/spicelib/devices/ind/indinit.c b/src/spicelib/devices/ind/indinit.c index 517a79e3f..86bd698d3 100644 --- a/src/spicelib/devices/ind/indinit.c +++ b/src/spicelib/devices/ind/indinit.c @@ -66,6 +66,11 @@ SPICEdev INDinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = INDbindCSC, + .DEVbindCSCComplex = INDbindCSCComplex, + .DEVbindCSCComplexToReal = INDbindCSCComplexToReal, +#endif }; @@ -128,6 +133,11 @@ SPICEdev MUTinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = MUTbindCSC, + .DEVbindCSCComplex = MUTbindCSCComplex, + .DEVbindCSCComplexToReal = MUTbindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/ind/mutbindCSC.c b/src/spicelib/devices/ind/mutbindCSC.c new file mode 100644 index 000000000..d17ebf640 --- /dev/null +++ b/src/spicelib/devices/ind/mutbindCSC.c @@ -0,0 +1,92 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "inddefs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +MUTbindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + MUTmodel *model = (MUTmodel *)inModel ; + MUTinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the MUT models */ + for ( ; model != NULL ; model = MUTnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = MUTinstances(model); here != NULL ; here = MUTnextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(MUTbr1br2Ptr, MUTbr1br2Binding, MUTind1->INDbrEq, MUTind2->INDbrEq); + CREATE_KLU_BINDING_TABLE(MUTbr2br1Ptr, MUTbr2br1Binding, MUTind2->INDbrEq, MUTind1->INDbrEq); + } + } + + return (OK) ; +} + +int +MUTbindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + MUTmodel *model = (MUTmodel *)inModel ; + MUTinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the MUT models */ + for ( ; model != NULL ; model = MUTnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = MUTinstances(model); here != NULL ; here = MUTnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MUTbr1br2Ptr, MUTbr1br2Binding, MUTind1->INDbrEq, MUTind2->INDbrEq); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MUTbr2br1Ptr, MUTbr2br1Binding, MUTind2->INDbrEq, MUTind1->INDbrEq); + } + } + + return (OK) ; +} + +int +MUTbindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + MUTmodel *model = (MUTmodel *)inModel ; + MUTinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the MUT models */ + for ( ; model != NULL ; model = MUTnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = MUTinstances(model); here != NULL ; here = MUTnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(MUTbr1br2Ptr, MUTbr1br2Binding, MUTind1->INDbrEq, MUTind2->INDbrEq); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MUTbr2br1Ptr, MUTbr2br1Binding, MUTind2->INDbrEq, MUTind1->INDbrEq); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/isrc/isrcinit.c b/src/spicelib/devices/isrc/isrcinit.c index f5a8a6744..10366f40f 100644 --- a/src/spicelib/devices/isrc/isrcinit.c +++ b/src/spicelib/devices/isrc/isrcinit.c @@ -66,6 +66,11 @@ SPICEdev ISRCinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = NULL, + .DEVbindCSCComplex = NULL, + .DEVbindCSCComplexToReal = NULL, +#endif }; diff --git a/src/spicelib/devices/jfet/Makefile.am b/src/spicelib/devices/jfet/Makefile.am index fc4907373..2f7947dfe 100644 --- a/src/spicelib/devices/jfet/Makefile.am +++ b/src/spicelib/devices/jfet/Makefile.am @@ -28,7 +28,11 @@ libjfet_la_SOURCES = \ jfettrun.c +if KLU_WANTED +libjfet_la_SOURCES += jfetbindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) + MAINTAINERCLEANFILES = Makefile.in diff --git a/src/spicelib/devices/jfet/jfetbindCSC.c b/src/spicelib/devices/jfet/jfetbindCSC.c new file mode 100644 index 000000000..c1b79e182 --- /dev/null +++ b/src/spicelib/devices/jfet/jfetbindCSC.c @@ -0,0 +1,131 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "jfetdefs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +JFETbindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + JFETmodel *model = (JFETmodel *)inModel ; + JFETinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the JFET models */ + for ( ; model != NULL ; model = JFETnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = JFETinstances(model); here != NULL ; here = JFETnextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(JFETdrainDrainPrimePtr, JFETdrainDrainPrimeBinding, JFETdrainNode, JFETdrainPrimeNode); + CREATE_KLU_BINDING_TABLE(JFETgateDrainPrimePtr, JFETgateDrainPrimeBinding, JFETgateNode, JFETdrainPrimeNode); + CREATE_KLU_BINDING_TABLE(JFETgateSourcePrimePtr, JFETgateSourcePrimeBinding, JFETgateNode, JFETsourcePrimeNode); + CREATE_KLU_BINDING_TABLE(JFETsourceSourcePrimePtr, JFETsourceSourcePrimeBinding, JFETsourceNode, JFETsourcePrimeNode); + CREATE_KLU_BINDING_TABLE(JFETdrainPrimeDrainPtr, JFETdrainPrimeDrainBinding, JFETdrainPrimeNode, JFETdrainNode); + CREATE_KLU_BINDING_TABLE(JFETdrainPrimeGatePtr, JFETdrainPrimeGateBinding, JFETdrainPrimeNode, JFETgateNode); + CREATE_KLU_BINDING_TABLE(JFETdrainPrimeSourcePrimePtr, JFETdrainPrimeSourcePrimeBinding, JFETdrainPrimeNode, JFETsourcePrimeNode); + CREATE_KLU_BINDING_TABLE(JFETsourcePrimeGatePtr, JFETsourcePrimeGateBinding, JFETsourcePrimeNode, JFETgateNode); + CREATE_KLU_BINDING_TABLE(JFETsourcePrimeSourcePtr, JFETsourcePrimeSourceBinding, JFETsourcePrimeNode, JFETsourceNode); + CREATE_KLU_BINDING_TABLE(JFETsourcePrimeDrainPrimePtr, JFETsourcePrimeDrainPrimeBinding, JFETsourcePrimeNode, JFETdrainPrimeNode); + CREATE_KLU_BINDING_TABLE(JFETdrainDrainPtr, JFETdrainDrainBinding, JFETdrainNode, JFETdrainNode); + CREATE_KLU_BINDING_TABLE(JFETgateGatePtr, JFETgateGateBinding, JFETgateNode, JFETgateNode); + CREATE_KLU_BINDING_TABLE(JFETsourceSourcePtr, JFETsourceSourceBinding, JFETsourceNode, JFETsourceNode); + CREATE_KLU_BINDING_TABLE(JFETdrainPrimeDrainPrimePtr, JFETdrainPrimeDrainPrimeBinding, JFETdrainPrimeNode, JFETdrainPrimeNode); + CREATE_KLU_BINDING_TABLE(JFETsourcePrimeSourcePrimePtr, JFETsourcePrimeSourcePrimeBinding, JFETsourcePrimeNode, JFETsourcePrimeNode); + } + } + + return (OK) ; +} + +int +JFETbindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + JFETmodel *model = (JFETmodel *)inModel ; + JFETinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the JFET models */ + for ( ; model != NULL ; model = JFETnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = JFETinstances(model); here != NULL ; here = JFETnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFETdrainDrainPrimePtr, JFETdrainDrainPrimeBinding, JFETdrainNode, JFETdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFETgateDrainPrimePtr, JFETgateDrainPrimeBinding, JFETgateNode, JFETdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFETgateSourcePrimePtr, JFETgateSourcePrimeBinding, JFETgateNode, JFETsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFETsourceSourcePrimePtr, JFETsourceSourcePrimeBinding, JFETsourceNode, JFETsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFETdrainPrimeDrainPtr, JFETdrainPrimeDrainBinding, JFETdrainPrimeNode, JFETdrainNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFETdrainPrimeGatePtr, JFETdrainPrimeGateBinding, JFETdrainPrimeNode, JFETgateNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFETdrainPrimeSourcePrimePtr, JFETdrainPrimeSourcePrimeBinding, JFETdrainPrimeNode, JFETsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFETsourcePrimeGatePtr, JFETsourcePrimeGateBinding, JFETsourcePrimeNode, JFETgateNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFETsourcePrimeSourcePtr, JFETsourcePrimeSourceBinding, JFETsourcePrimeNode, JFETsourceNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFETsourcePrimeDrainPrimePtr, JFETsourcePrimeDrainPrimeBinding, JFETsourcePrimeNode, JFETdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFETdrainDrainPtr, JFETdrainDrainBinding, JFETdrainNode, JFETdrainNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFETgateGatePtr, JFETgateGateBinding, JFETgateNode, JFETgateNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFETsourceSourcePtr, JFETsourceSourceBinding, JFETsourceNode, JFETsourceNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFETdrainPrimeDrainPrimePtr, JFETdrainPrimeDrainPrimeBinding, JFETdrainPrimeNode, JFETdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFETsourcePrimeSourcePrimePtr, JFETsourcePrimeSourcePrimeBinding, JFETsourcePrimeNode, JFETsourcePrimeNode); + } + } + + return (OK) ; +} + +int +JFETbindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + JFETmodel *model = (JFETmodel *)inModel ; + JFETinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the JFET models */ + for ( ; model != NULL ; model = JFETnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = JFETinstances(model); here != NULL ; here = JFETnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFETdrainDrainPrimePtr, JFETdrainDrainPrimeBinding, JFETdrainNode, JFETdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFETgateDrainPrimePtr, JFETgateDrainPrimeBinding, JFETgateNode, JFETdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFETgateSourcePrimePtr, JFETgateSourcePrimeBinding, JFETgateNode, JFETsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFETsourceSourcePrimePtr, JFETsourceSourcePrimeBinding, JFETsourceNode, JFETsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFETdrainPrimeDrainPtr, JFETdrainPrimeDrainBinding, JFETdrainPrimeNode, JFETdrainNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFETdrainPrimeGatePtr, JFETdrainPrimeGateBinding, JFETdrainPrimeNode, JFETgateNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFETdrainPrimeSourcePrimePtr, JFETdrainPrimeSourcePrimeBinding, JFETdrainPrimeNode, JFETsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFETsourcePrimeGatePtr, JFETsourcePrimeGateBinding, JFETsourcePrimeNode, JFETgateNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFETsourcePrimeSourcePtr, JFETsourcePrimeSourceBinding, JFETsourcePrimeNode, JFETsourceNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFETsourcePrimeDrainPrimePtr, JFETsourcePrimeDrainPrimeBinding, JFETsourcePrimeNode, JFETdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFETdrainDrainPtr, JFETdrainDrainBinding, JFETdrainNode, JFETdrainNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFETgateGatePtr, JFETgateGateBinding, JFETgateNode, JFETgateNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFETsourceSourcePtr, JFETsourceSourceBinding, JFETsourceNode, JFETsourceNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFETdrainPrimeDrainPrimePtr, JFETdrainPrimeDrainPrimeBinding, JFETdrainPrimeNode, JFETdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFETsourcePrimeSourcePrimePtr, JFETsourcePrimeSourcePrimeBinding, JFETsourcePrimeNode, JFETsourcePrimeNode); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/jfet/jfetdefs.h b/src/spicelib/devices/jfet/jfetdefs.h index 2dbc79b29..701dc0375 100644 --- a/src/spicelib/devices/jfet/jfetdefs.h +++ b/src/spicelib/devices/jfet/jfetdefs.h @@ -152,6 +152,24 @@ typedef struct sJFETinstance { double JFETtThreshold; /* temperature adjusted threshold voltage */ double JFETtBeta; /* temperature adjusted beta */ +#ifdef KLU + BindElement *JFETdrainDrainPrimeBinding ; + BindElement *JFETgateDrainPrimeBinding ; + BindElement *JFETgateSourcePrimeBinding ; + BindElement *JFETsourceSourcePrimeBinding ; + BindElement *JFETdrainPrimeDrainBinding ; + BindElement *JFETdrainPrimeGateBinding ; + BindElement *JFETdrainPrimeSourcePrimeBinding ; + BindElement *JFETsourcePrimeGateBinding ; + BindElement *JFETsourcePrimeSourceBinding ; + BindElement *JFETsourcePrimeDrainPrimeBinding ; + BindElement *JFETdrainDrainBinding ; + BindElement *JFETgateGateBinding ; + BindElement *JFETsourceSourceBinding ; + BindElement *JFETdrainPrimeDrainPrimeBinding ; + BindElement *JFETsourcePrimeSourcePrimeBinding ; +#endif + } JFETinstance ; #define JFETvgs JFETstate diff --git a/src/spicelib/devices/jfet/jfetext.h b/src/spicelib/devices/jfet/jfetext.h index d90800e75..4c84249b1 100644 --- a/src/spicelib/devices/jfet/jfetext.h +++ b/src/spicelib/devices/jfet/jfetext.h @@ -22,3 +22,9 @@ extern int JFETtrunc(GENmodel*,CKTcircuit*,double*); extern int JFETdisto(int,GENmodel*,CKTcircuit*); extern int JFETnoise(int,int,GENmodel*,CKTcircuit*,Ndata*,double*); extern int JFETdSetup(GENmodel*,CKTcircuit*); + +#ifdef KLU +extern int JFETbindCSC (GENmodel*, CKTcircuit*) ; +extern int JFETbindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int JFETbindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/jfet/jfetinit.c b/src/spicelib/devices/jfet/jfetinit.c index 0e47b487c..d36dd556f 100644 --- a/src/spicelib/devices/jfet/jfetinit.c +++ b/src/spicelib/devices/jfet/jfetinit.c @@ -66,6 +66,11 @@ SPICEdev JFETinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = JFETbindCSC, + .DEVbindCSCComplex = JFETbindCSCComplex, + .DEVbindCSCComplexToReal = JFETbindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/jfet2/Makefile.am b/src/spicelib/devices/jfet2/Makefile.am index f8789cd9b..c0f9dd189 100644 --- a/src/spicelib/devices/jfet2/Makefile.am +++ b/src/spicelib/devices/jfet2/Makefile.am @@ -28,8 +28,11 @@ libjfet2_la_SOURCES = \ psmodel.h - +if KLU_WANTED +libjfet2_la_SOURCES += jfet2bindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) + MAINTAINERCLEANFILES = Makefile.in diff --git a/src/spicelib/devices/jfet2/jfet2bindCSC.c b/src/spicelib/devices/jfet2/jfet2bindCSC.c new file mode 100644 index 000000000..2213b3be1 --- /dev/null +++ b/src/spicelib/devices/jfet2/jfet2bindCSC.c @@ -0,0 +1,131 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "jfet2defs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +JFET2bindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + JFET2model *model = (JFET2model *)inModel ; + JFET2instance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the JFET2 models */ + for ( ; model != NULL ; model = JFET2nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = JFET2instances(model); here != NULL ; here = JFET2nextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(JFET2drainDrainPrimePtr, JFET2drainDrainPrimeBinding, JFET2drainNode, JFET2drainPrimeNode); + CREATE_KLU_BINDING_TABLE(JFET2gateDrainPrimePtr, JFET2gateDrainPrimeBinding, JFET2gateNode, JFET2drainPrimeNode); + CREATE_KLU_BINDING_TABLE(JFET2gateSourcePrimePtr, JFET2gateSourcePrimeBinding, JFET2gateNode, JFET2sourcePrimeNode); + CREATE_KLU_BINDING_TABLE(JFET2sourceSourcePrimePtr, JFET2sourceSourcePrimeBinding, JFET2sourceNode, JFET2sourcePrimeNode); + CREATE_KLU_BINDING_TABLE(JFET2drainPrimeDrainPtr, JFET2drainPrimeDrainBinding, JFET2drainPrimeNode, JFET2drainNode); + CREATE_KLU_BINDING_TABLE(JFET2drainPrimeGatePtr, JFET2drainPrimeGateBinding, JFET2drainPrimeNode, JFET2gateNode); + CREATE_KLU_BINDING_TABLE(JFET2drainPrimeSourcePrimePtr, JFET2drainPrimeSourcePrimeBinding, JFET2drainPrimeNode, JFET2sourcePrimeNode); + CREATE_KLU_BINDING_TABLE(JFET2sourcePrimeGatePtr, JFET2sourcePrimeGateBinding, JFET2sourcePrimeNode, JFET2gateNode); + CREATE_KLU_BINDING_TABLE(JFET2sourcePrimeSourcePtr, JFET2sourcePrimeSourceBinding, JFET2sourcePrimeNode, JFET2sourceNode); + CREATE_KLU_BINDING_TABLE(JFET2sourcePrimeDrainPrimePtr, JFET2sourcePrimeDrainPrimeBinding, JFET2sourcePrimeNode, JFET2drainPrimeNode); + CREATE_KLU_BINDING_TABLE(JFET2drainDrainPtr, JFET2drainDrainBinding, JFET2drainNode, JFET2drainNode); + CREATE_KLU_BINDING_TABLE(JFET2gateGatePtr, JFET2gateGateBinding, JFET2gateNode, JFET2gateNode); + CREATE_KLU_BINDING_TABLE(JFET2sourceSourcePtr, JFET2sourceSourceBinding, JFET2sourceNode, JFET2sourceNode); + CREATE_KLU_BINDING_TABLE(JFET2drainPrimeDrainPrimePtr, JFET2drainPrimeDrainPrimeBinding, JFET2drainPrimeNode, JFET2drainPrimeNode); + CREATE_KLU_BINDING_TABLE(JFET2sourcePrimeSourcePrimePtr, JFET2sourcePrimeSourcePrimeBinding, JFET2sourcePrimeNode, JFET2sourcePrimeNode); + } + } + + return (OK) ; +} + +int +JFET2bindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + JFET2model *model = (JFET2model *)inModel ; + JFET2instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the JFET2 models */ + for ( ; model != NULL ; model = JFET2nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = JFET2instances(model); here != NULL ; here = JFET2nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFET2drainDrainPrimePtr, JFET2drainDrainPrimeBinding, JFET2drainNode, JFET2drainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFET2gateDrainPrimePtr, JFET2gateDrainPrimeBinding, JFET2gateNode, JFET2drainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFET2gateSourcePrimePtr, JFET2gateSourcePrimeBinding, JFET2gateNode, JFET2sourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFET2sourceSourcePrimePtr, JFET2sourceSourcePrimeBinding, JFET2sourceNode, JFET2sourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFET2drainPrimeDrainPtr, JFET2drainPrimeDrainBinding, JFET2drainPrimeNode, JFET2drainNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFET2drainPrimeGatePtr, JFET2drainPrimeGateBinding, JFET2drainPrimeNode, JFET2gateNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFET2drainPrimeSourcePrimePtr, JFET2drainPrimeSourcePrimeBinding, JFET2drainPrimeNode, JFET2sourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFET2sourcePrimeGatePtr, JFET2sourcePrimeGateBinding, JFET2sourcePrimeNode, JFET2gateNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFET2sourcePrimeSourcePtr, JFET2sourcePrimeSourceBinding, JFET2sourcePrimeNode, JFET2sourceNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFET2sourcePrimeDrainPrimePtr, JFET2sourcePrimeDrainPrimeBinding, JFET2sourcePrimeNode, JFET2drainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFET2drainDrainPtr, JFET2drainDrainBinding, JFET2drainNode, JFET2drainNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFET2gateGatePtr, JFET2gateGateBinding, JFET2gateNode, JFET2gateNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFET2sourceSourcePtr, JFET2sourceSourceBinding, JFET2sourceNode, JFET2sourceNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFET2drainPrimeDrainPrimePtr, JFET2drainPrimeDrainPrimeBinding, JFET2drainPrimeNode, JFET2drainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(JFET2sourcePrimeSourcePrimePtr, JFET2sourcePrimeSourcePrimeBinding, JFET2sourcePrimeNode, JFET2sourcePrimeNode); + } + } + + return (OK) ; +} + +int +JFET2bindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + JFET2model *model = (JFET2model *)inModel ; + JFET2instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the JFET2 models */ + for ( ; model != NULL ; model = JFET2nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = JFET2instances(model); here != NULL ; here = JFET2nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFET2drainDrainPrimePtr, JFET2drainDrainPrimeBinding, JFET2drainNode, JFET2drainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFET2gateDrainPrimePtr, JFET2gateDrainPrimeBinding, JFET2gateNode, JFET2drainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFET2gateSourcePrimePtr, JFET2gateSourcePrimeBinding, JFET2gateNode, JFET2sourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFET2sourceSourcePrimePtr, JFET2sourceSourcePrimeBinding, JFET2sourceNode, JFET2sourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFET2drainPrimeDrainPtr, JFET2drainPrimeDrainBinding, JFET2drainPrimeNode, JFET2drainNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFET2drainPrimeGatePtr, JFET2drainPrimeGateBinding, JFET2drainPrimeNode, JFET2gateNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFET2drainPrimeSourcePrimePtr, JFET2drainPrimeSourcePrimeBinding, JFET2drainPrimeNode, JFET2sourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFET2sourcePrimeGatePtr, JFET2sourcePrimeGateBinding, JFET2sourcePrimeNode, JFET2gateNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFET2sourcePrimeSourcePtr, JFET2sourcePrimeSourceBinding, JFET2sourcePrimeNode, JFET2sourceNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFET2sourcePrimeDrainPrimePtr, JFET2sourcePrimeDrainPrimeBinding, JFET2sourcePrimeNode, JFET2drainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFET2drainDrainPtr, JFET2drainDrainBinding, JFET2drainNode, JFET2drainNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFET2gateGatePtr, JFET2gateGateBinding, JFET2gateNode, JFET2gateNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFET2sourceSourcePtr, JFET2sourceSourceBinding, JFET2sourceNode, JFET2sourceNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFET2drainPrimeDrainPrimePtr, JFET2drainPrimeDrainPrimeBinding, JFET2drainPrimeNode, JFET2drainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(JFET2sourcePrimeSourcePrimePtr, JFET2sourcePrimeSourcePrimeBinding, JFET2sourcePrimeNode, JFET2sourcePrimeNode); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/jfet2/jfet2defs.h b/src/spicelib/devices/jfet2/jfet2defs.h index 320c96608..f8b2a230b 100644 --- a/src/spicelib/devices/jfet2/jfet2defs.h +++ b/src/spicelib/devices/jfet2/jfet2defs.h @@ -158,6 +158,24 @@ typedef struct sJFET2instance { double JFET2d3; /* Dual Power-law parameter */ double JFET2alpha; /* capacitance model transition parameter */ +#ifdef KLU + BindElement *JFET2drainDrainPrimeBinding ; + BindElement *JFET2gateDrainPrimeBinding ; + BindElement *JFET2gateSourcePrimeBinding ; + BindElement *JFET2sourceSourcePrimeBinding ; + BindElement *JFET2drainPrimeDrainBinding ; + BindElement *JFET2drainPrimeGateBinding ; + BindElement *JFET2drainPrimeSourcePrimeBinding ; + BindElement *JFET2sourcePrimeGateBinding ; + BindElement *JFET2sourcePrimeSourceBinding ; + BindElement *JFET2sourcePrimeDrainPrimeBinding ; + BindElement *JFET2drainDrainBinding ; + BindElement *JFET2gateGateBinding ; + BindElement *JFET2sourceSourceBinding ; + BindElement *JFET2drainPrimeDrainPrimeBinding ; + BindElement *JFET2sourcePrimeSourcePrimeBinding ; +#endif + } JFET2instance ; #define JFET2vgs JFET2state diff --git a/src/spicelib/devices/jfet2/jfet2ext.h b/src/spicelib/devices/jfet2/jfet2ext.h index de9d6b4e1..128424625 100644 --- a/src/spicelib/devices/jfet2/jfet2ext.h +++ b/src/spicelib/devices/jfet2/jfet2ext.h @@ -22,3 +22,9 @@ extern int JFET2unsetup(GENmodel*,CKTcircuit*); extern int JFET2temp(GENmodel*,CKTcircuit*); extern int JFET2trunc(GENmodel*,CKTcircuit*,double*); extern int JFET2noise(int,int,GENmodel*,CKTcircuit*,Ndata*,double*); + +#ifdef KLU +extern int JFET2bindCSC (GENmodel*, CKTcircuit*) ; +extern int JFET2bindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int JFET2bindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/jfet2/jfet2init.c b/src/spicelib/devices/jfet2/jfet2init.c index 857706f4a..7fa2600d5 100644 --- a/src/spicelib/devices/jfet2/jfet2init.c +++ b/src/spicelib/devices/jfet2/jfet2init.c @@ -66,6 +66,11 @@ SPICEdev JFET2info = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = JFET2bindCSC, + .DEVbindCSCComplex = JFET2bindCSCComplex, + .DEVbindCSCComplexToReal = JFET2bindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/ltra/Makefile.am b/src/spicelib/devices/ltra/Makefile.am index 42a9c042a..c65eb5fff 100644 --- a/src/spicelib/devices/ltra/Makefile.am +++ b/src/spicelib/devices/ltra/Makefile.am @@ -25,7 +25,11 @@ libltra_la_SOURCES = \ ltratrun.c +if KLU_WANTED +libltra_la_SOURCES += ltrabindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) + MAINTAINERCLEANFILES = Makefile.in diff --git a/src/spicelib/devices/ltra/ltrabindCSC.c b/src/spicelib/devices/ltra/ltrabindCSC.c new file mode 100644 index 000000000..676e80d31 --- /dev/null +++ b/src/spicelib/devices/ltra/ltrabindCSC.c @@ -0,0 +1,146 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "ltradefs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +LTRAbindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + LTRAmodel *model = (LTRAmodel *)inModel ; + LTRAinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the LTRA models */ + for ( ; model != NULL ; model = LTRAnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = LTRAinstances(model); here != NULL ; here = LTRAnextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(LTRAibr1Pos1Ptr, LTRAibr1Pos1Binding, LTRAbrEq1, LTRAposNode1); + CREATE_KLU_BINDING_TABLE(LTRAibr1Neg1Ptr, LTRAibr1Neg1Binding, LTRAbrEq1, LTRAnegNode1); + CREATE_KLU_BINDING_TABLE(LTRAibr1Pos2Ptr, LTRAibr1Pos2Binding, LTRAbrEq1, LTRAposNode2); + CREATE_KLU_BINDING_TABLE(LTRAibr1Neg2Ptr, LTRAibr1Neg2Binding, LTRAbrEq1, LTRAnegNode2); + CREATE_KLU_BINDING_TABLE(LTRAibr1Ibr1Ptr, LTRAibr1Ibr1Binding, LTRAbrEq1, LTRAbrEq1); + CREATE_KLU_BINDING_TABLE(LTRAibr1Ibr2Ptr, LTRAibr1Ibr2Binding, LTRAbrEq1, LTRAbrEq2); + CREATE_KLU_BINDING_TABLE(LTRAibr2Pos1Ptr, LTRAibr2Pos1Binding, LTRAbrEq2, LTRAposNode1); + CREATE_KLU_BINDING_TABLE(LTRAibr2Neg1Ptr, LTRAibr2Neg1Binding, LTRAbrEq2, LTRAnegNode1); + CREATE_KLU_BINDING_TABLE(LTRAibr2Pos2Ptr, LTRAibr2Pos2Binding, LTRAbrEq2, LTRAposNode2); + CREATE_KLU_BINDING_TABLE(LTRAibr2Neg2Ptr, LTRAibr2Neg2Binding, LTRAbrEq2, LTRAnegNode2); + CREATE_KLU_BINDING_TABLE(LTRAibr2Ibr1Ptr, LTRAibr2Ibr1Binding, LTRAbrEq2, LTRAbrEq1); + CREATE_KLU_BINDING_TABLE(LTRAibr2Ibr2Ptr, LTRAibr2Ibr2Binding, LTRAbrEq2, LTRAbrEq2); + CREATE_KLU_BINDING_TABLE(LTRApos1Ibr1Ptr, LTRApos1Ibr1Binding, LTRAposNode1, LTRAbrEq1); + CREATE_KLU_BINDING_TABLE(LTRAneg1Ibr1Ptr, LTRAneg1Ibr1Binding, LTRAnegNode1, LTRAbrEq1); + CREATE_KLU_BINDING_TABLE(LTRApos2Ibr2Ptr, LTRApos2Ibr2Binding, LTRAposNode2, LTRAbrEq2); + CREATE_KLU_BINDING_TABLE(LTRAneg2Ibr2Ptr, LTRAneg2Ibr2Binding, LTRAnegNode2, LTRAbrEq2); + CREATE_KLU_BINDING_TABLE(LTRApos1Pos1Ptr, LTRApos1Pos1Binding, LTRAposNode1, LTRAposNode1); + CREATE_KLU_BINDING_TABLE(LTRAneg1Neg1Ptr, LTRAneg1Neg1Binding, LTRAnegNode1, LTRAnegNode1); + CREATE_KLU_BINDING_TABLE(LTRApos2Pos2Ptr, LTRApos2Pos2Binding, LTRAposNode2, LTRAposNode2); + CREATE_KLU_BINDING_TABLE(LTRAneg2Neg2Ptr, LTRAneg2Neg2Binding, LTRAnegNode2, LTRAnegNode2); + } + } + + return (OK) ; +} + +int +LTRAbindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + LTRAmodel *model = (LTRAmodel *)inModel ; + LTRAinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the LTRA models */ + for ( ; model != NULL ; model = LTRAnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = LTRAinstances(model); here != NULL ; here = LTRAnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(LTRAibr1Pos1Ptr, LTRAibr1Pos1Binding, LTRAbrEq1, LTRAposNode1); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(LTRAibr1Neg1Ptr, LTRAibr1Neg1Binding, LTRAbrEq1, LTRAnegNode1); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(LTRAibr1Pos2Ptr, LTRAibr1Pos2Binding, LTRAbrEq1, LTRAposNode2); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(LTRAibr1Neg2Ptr, LTRAibr1Neg2Binding, LTRAbrEq1, LTRAnegNode2); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(LTRAibr1Ibr1Ptr, LTRAibr1Ibr1Binding, LTRAbrEq1, LTRAbrEq1); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(LTRAibr1Ibr2Ptr, LTRAibr1Ibr2Binding, LTRAbrEq1, LTRAbrEq2); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(LTRAibr2Pos1Ptr, LTRAibr2Pos1Binding, LTRAbrEq2, LTRAposNode1); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(LTRAibr2Neg1Ptr, LTRAibr2Neg1Binding, LTRAbrEq2, LTRAnegNode1); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(LTRAibr2Pos2Ptr, LTRAibr2Pos2Binding, LTRAbrEq2, LTRAposNode2); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(LTRAibr2Neg2Ptr, LTRAibr2Neg2Binding, LTRAbrEq2, LTRAnegNode2); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(LTRAibr2Ibr1Ptr, LTRAibr2Ibr1Binding, LTRAbrEq2, LTRAbrEq1); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(LTRAibr2Ibr2Ptr, LTRAibr2Ibr2Binding, LTRAbrEq2, LTRAbrEq2); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(LTRApos1Ibr1Ptr, LTRApos1Ibr1Binding, LTRAposNode1, LTRAbrEq1); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(LTRAneg1Ibr1Ptr, LTRAneg1Ibr1Binding, LTRAnegNode1, LTRAbrEq1); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(LTRApos2Ibr2Ptr, LTRApos2Ibr2Binding, LTRAposNode2, LTRAbrEq2); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(LTRAneg2Ibr2Ptr, LTRAneg2Ibr2Binding, LTRAnegNode2, LTRAbrEq2); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(LTRApos1Pos1Ptr, LTRApos1Pos1Binding, LTRAposNode1, LTRAposNode1); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(LTRAneg1Neg1Ptr, LTRAneg1Neg1Binding, LTRAnegNode1, LTRAnegNode1); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(LTRApos2Pos2Ptr, LTRApos2Pos2Binding, LTRAposNode2, LTRAposNode2); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(LTRAneg2Neg2Ptr, LTRAneg2Neg2Binding, LTRAnegNode2, LTRAnegNode2); + } + } + + return (OK) ; +} + +int +LTRAbindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + LTRAmodel *model = (LTRAmodel *)inModel ; + LTRAinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the LTRA models */ + for ( ; model != NULL ; model = LTRAnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = LTRAinstances(model); here != NULL ; here = LTRAnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(LTRAibr1Pos1Ptr, LTRAibr1Pos1Binding, LTRAbrEq1, LTRAposNode1); + CONVERT_KLU_BINDING_TABLE_TO_REAL(LTRAibr1Neg1Ptr, LTRAibr1Neg1Binding, LTRAbrEq1, LTRAnegNode1); + CONVERT_KLU_BINDING_TABLE_TO_REAL(LTRAibr1Pos2Ptr, LTRAibr1Pos2Binding, LTRAbrEq1, LTRAposNode2); + CONVERT_KLU_BINDING_TABLE_TO_REAL(LTRAibr1Neg2Ptr, LTRAibr1Neg2Binding, LTRAbrEq1, LTRAnegNode2); + CONVERT_KLU_BINDING_TABLE_TO_REAL(LTRAibr1Ibr1Ptr, LTRAibr1Ibr1Binding, LTRAbrEq1, LTRAbrEq1); + CONVERT_KLU_BINDING_TABLE_TO_REAL(LTRAibr1Ibr2Ptr, LTRAibr1Ibr2Binding, LTRAbrEq1, LTRAbrEq2); + CONVERT_KLU_BINDING_TABLE_TO_REAL(LTRAibr2Pos1Ptr, LTRAibr2Pos1Binding, LTRAbrEq2, LTRAposNode1); + CONVERT_KLU_BINDING_TABLE_TO_REAL(LTRAibr2Neg1Ptr, LTRAibr2Neg1Binding, LTRAbrEq2, LTRAnegNode1); + CONVERT_KLU_BINDING_TABLE_TO_REAL(LTRAibr2Pos2Ptr, LTRAibr2Pos2Binding, LTRAbrEq2, LTRAposNode2); + CONVERT_KLU_BINDING_TABLE_TO_REAL(LTRAibr2Neg2Ptr, LTRAibr2Neg2Binding, LTRAbrEq2, LTRAnegNode2); + CONVERT_KLU_BINDING_TABLE_TO_REAL(LTRAibr2Ibr1Ptr, LTRAibr2Ibr1Binding, LTRAbrEq2, LTRAbrEq1); + CONVERT_KLU_BINDING_TABLE_TO_REAL(LTRAibr2Ibr2Ptr, LTRAibr2Ibr2Binding, LTRAbrEq2, LTRAbrEq2); + CONVERT_KLU_BINDING_TABLE_TO_REAL(LTRApos1Ibr1Ptr, LTRApos1Ibr1Binding, LTRAposNode1, LTRAbrEq1); + CONVERT_KLU_BINDING_TABLE_TO_REAL(LTRAneg1Ibr1Ptr, LTRAneg1Ibr1Binding, LTRAnegNode1, LTRAbrEq1); + CONVERT_KLU_BINDING_TABLE_TO_REAL(LTRApos2Ibr2Ptr, LTRApos2Ibr2Binding, LTRAposNode2, LTRAbrEq2); + CONVERT_KLU_BINDING_TABLE_TO_REAL(LTRAneg2Ibr2Ptr, LTRAneg2Ibr2Binding, LTRAnegNode2, LTRAbrEq2); + CONVERT_KLU_BINDING_TABLE_TO_REAL(LTRApos1Pos1Ptr, LTRApos1Pos1Binding, LTRAposNode1, LTRAposNode1); + CONVERT_KLU_BINDING_TABLE_TO_REAL(LTRAneg1Neg1Ptr, LTRAneg1Neg1Binding, LTRAnegNode1, LTRAnegNode1); + CONVERT_KLU_BINDING_TABLE_TO_REAL(LTRApos2Pos2Ptr, LTRApos2Pos2Binding, LTRAposNode2, LTRAposNode2); + CONVERT_KLU_BINDING_TABLE_TO_REAL(LTRAneg2Neg2Ptr, LTRAneg2Neg2Binding, LTRAnegNode2, LTRAnegNode2); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/ltra/ltradefs.h b/src/spicelib/devices/ltra/ltradefs.h index f1f0e3d2e..08e6baeb7 100644 --- a/src/spicelib/devices/ltra/ltradefs.h +++ b/src/spicelib/devices/ltra/ltradefs.h @@ -70,6 +70,30 @@ typedef struct sLTRAinstance { unsigned LTRAicC1Given : 1; /* flag to ind. init. current at port 1 given */ unsigned LTRAicV2Given : 1; /* flag to ind. init. voltage at port 2 given */ unsigned LTRAicC2Given : 1; /* flag to ind. init. current at port 2 given */ + +#ifdef KLU + BindElement *LTRAibr1Pos1Binding ; + BindElement *LTRAibr1Neg1Binding ; + BindElement *LTRAibr1Pos2Binding ; + BindElement *LTRAibr1Neg2Binding ; + BindElement *LTRAibr1Ibr1Binding ; + BindElement *LTRAibr1Ibr2Binding ; + BindElement *LTRAibr2Pos1Binding ; + BindElement *LTRAibr2Neg1Binding ; + BindElement *LTRAibr2Pos2Binding ; + BindElement *LTRAibr2Neg2Binding ; + BindElement *LTRAibr2Ibr1Binding ; + BindElement *LTRAibr2Ibr2Binding ; + BindElement *LTRApos1Ibr1Binding ; + BindElement *LTRAneg1Ibr1Binding ; + BindElement *LTRApos2Ibr2Binding ; + BindElement *LTRAneg2Ibr2Binding ; + BindElement *LTRApos1Pos1Binding ; + BindElement *LTRAneg1Neg1Binding ; + BindElement *LTRApos2Pos2Binding ; + BindElement *LTRAneg2Neg2Binding ; +#endif + } LTRAinstance ; diff --git a/src/spicelib/devices/ltra/ltraext.h b/src/spicelib/devices/ltra/ltraext.h index b0b93c341..595352301 100644 --- a/src/spicelib/devices/ltra/ltraext.h +++ b/src/spicelib/devices/ltra/ltraext.h @@ -44,3 +44,9 @@ extern double LTRAh3dashCoeffSetup(double*,int,double,double,double,double*,int, extern void LTRArcCoeffsSetup(double*,double*,double*,double*,double*,double*,int,double,double,double,double*,int,double); extern void LTRArlcCoeffsSetup(double*,double*,double*,double*,double*,double*,int,double,double,double,double,double*,int,double,int*); extern int LTRAstraightLineCheck(double,double,double,double,double,double,double,double); + +#ifdef KLU +extern int LTRAbindCSC (GENmodel*, CKTcircuit*) ; +extern int LTRAbindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int LTRAbindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/ltra/ltrainit.c b/src/spicelib/devices/ltra/ltrainit.c index 97988e7e2..47f64ccd5 100644 --- a/src/spicelib/devices/ltra/ltrainit.c +++ b/src/spicelib/devices/ltra/ltrainit.c @@ -66,6 +66,11 @@ SPICEdev LTRAinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = LTRAbindCSC, + .DEVbindCSCComplex = LTRAbindCSCComplex, + .DEVbindCSCComplexToReal = LTRAbindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/mes/Makefile.am b/src/spicelib/devices/mes/Makefile.am index 3d0c3b3d5..adbdfc555 100644 --- a/src/spicelib/devices/mes/Makefile.am +++ b/src/spicelib/devices/mes/Makefile.am @@ -28,7 +28,11 @@ libmes_la_SOURCES = \ mestrunc.c +if KLU_WANTED +libmes_la_SOURCES += mesbindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) + MAINTAINERCLEANFILES = Makefile.in diff --git a/src/spicelib/devices/mes/mesbindCSC.c b/src/spicelib/devices/mes/mesbindCSC.c new file mode 100644 index 000000000..0f0bad066 --- /dev/null +++ b/src/spicelib/devices/mes/mesbindCSC.c @@ -0,0 +1,131 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "mesdefs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +MESbindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + MESmodel *model = (MESmodel *)inModel ; + MESinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the MES models */ + for ( ; model != NULL ; model = MESnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = MESinstances(model); here != NULL ; here = MESnextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(MESdrainDrainPrimePtr, MESdrainDrainPrimeBinding, MESdrainNode, MESdrainPrimeNode); + CREATE_KLU_BINDING_TABLE(MESgateDrainPrimePtr, MESgateDrainPrimeBinding, MESgateNode, MESdrainPrimeNode); + CREATE_KLU_BINDING_TABLE(MESgateSourcePrimePtr, MESgateSourcePrimeBinding, MESgateNode, MESsourcePrimeNode); + CREATE_KLU_BINDING_TABLE(MESsourceSourcePrimePtr, MESsourceSourcePrimeBinding, MESsourceNode, MESsourcePrimeNode); + CREATE_KLU_BINDING_TABLE(MESdrainPrimeDrainPtr, MESdrainPrimeDrainBinding, MESdrainPrimeNode, MESdrainNode); + CREATE_KLU_BINDING_TABLE(MESdrainPrimeGatePtr, MESdrainPrimeGateBinding, MESdrainPrimeNode, MESgateNode); + CREATE_KLU_BINDING_TABLE(MESdrainPrimeSourcePrimePtr, MESdrainPrimeSourcePrimeBinding, MESdrainPrimeNode, MESsourcePrimeNode); + CREATE_KLU_BINDING_TABLE(MESsourcePrimeGatePtr, MESsourcePrimeGateBinding, MESsourcePrimeNode, MESgateNode); + CREATE_KLU_BINDING_TABLE(MESsourcePrimeSourcePtr, MESsourcePrimeSourceBinding, MESsourcePrimeNode, MESsourceNode); + CREATE_KLU_BINDING_TABLE(MESsourcePrimeDrainPrimePtr, MESsourcePrimeDrainPrimeBinding, MESsourcePrimeNode, MESdrainPrimeNode); + CREATE_KLU_BINDING_TABLE(MESdrainDrainPtr, MESdrainDrainBinding, MESdrainNode, MESdrainNode); + CREATE_KLU_BINDING_TABLE(MESgateGatePtr, MESgateGateBinding, MESgateNode, MESgateNode); + CREATE_KLU_BINDING_TABLE(MESsourceSourcePtr, MESsourceSourceBinding, MESsourceNode, MESsourceNode); + CREATE_KLU_BINDING_TABLE(MESdrainPrimeDrainPrimePtr, MESdrainPrimeDrainPrimeBinding, MESdrainPrimeNode, MESdrainPrimeNode); + CREATE_KLU_BINDING_TABLE(MESsourcePrimeSourcePrimePtr, MESsourcePrimeSourcePrimeBinding, MESsourcePrimeNode, MESsourcePrimeNode); + } + } + + return (OK) ; +} + +int +MESbindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + MESmodel *model = (MESmodel *)inModel ; + MESinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the MES models */ + for ( ; model != NULL ; model = MESnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = MESinstances(model); here != NULL ; here = MESnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESdrainDrainPrimePtr, MESdrainDrainPrimeBinding, MESdrainNode, MESdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESgateDrainPrimePtr, MESgateDrainPrimeBinding, MESgateNode, MESdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESgateSourcePrimePtr, MESgateSourcePrimeBinding, MESgateNode, MESsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESsourceSourcePrimePtr, MESsourceSourcePrimeBinding, MESsourceNode, MESsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESdrainPrimeDrainPtr, MESdrainPrimeDrainBinding, MESdrainPrimeNode, MESdrainNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESdrainPrimeGatePtr, MESdrainPrimeGateBinding, MESdrainPrimeNode, MESgateNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESdrainPrimeSourcePrimePtr, MESdrainPrimeSourcePrimeBinding, MESdrainPrimeNode, MESsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESsourcePrimeGatePtr, MESsourcePrimeGateBinding, MESsourcePrimeNode, MESgateNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESsourcePrimeSourcePtr, MESsourcePrimeSourceBinding, MESsourcePrimeNode, MESsourceNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESsourcePrimeDrainPrimePtr, MESsourcePrimeDrainPrimeBinding, MESsourcePrimeNode, MESdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESdrainDrainPtr, MESdrainDrainBinding, MESdrainNode, MESdrainNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESgateGatePtr, MESgateGateBinding, MESgateNode, MESgateNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESsourceSourcePtr, MESsourceSourceBinding, MESsourceNode, MESsourceNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESdrainPrimeDrainPrimePtr, MESdrainPrimeDrainPrimeBinding, MESdrainPrimeNode, MESdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESsourcePrimeSourcePrimePtr, MESsourcePrimeSourcePrimeBinding, MESsourcePrimeNode, MESsourcePrimeNode); + } + } + + return (OK) ; +} + +int +MESbindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + MESmodel *model = (MESmodel *)inModel ; + MESinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the MES models */ + for ( ; model != NULL ; model = MESnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = MESinstances(model); here != NULL ; here = MESnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESdrainDrainPrimePtr, MESdrainDrainPrimeBinding, MESdrainNode, MESdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESgateDrainPrimePtr, MESgateDrainPrimeBinding, MESgateNode, MESdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESgateSourcePrimePtr, MESgateSourcePrimeBinding, MESgateNode, MESsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESsourceSourcePrimePtr, MESsourceSourcePrimeBinding, MESsourceNode, MESsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESdrainPrimeDrainPtr, MESdrainPrimeDrainBinding, MESdrainPrimeNode, MESdrainNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESdrainPrimeGatePtr, MESdrainPrimeGateBinding, MESdrainPrimeNode, MESgateNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESdrainPrimeSourcePrimePtr, MESdrainPrimeSourcePrimeBinding, MESdrainPrimeNode, MESsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESsourcePrimeGatePtr, MESsourcePrimeGateBinding, MESsourcePrimeNode, MESgateNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESsourcePrimeSourcePtr, MESsourcePrimeSourceBinding, MESsourcePrimeNode, MESsourceNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESsourcePrimeDrainPrimePtr, MESsourcePrimeDrainPrimeBinding, MESsourcePrimeNode, MESdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESdrainDrainPtr, MESdrainDrainBinding, MESdrainNode, MESdrainNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESgateGatePtr, MESgateGateBinding, MESgateNode, MESgateNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESsourceSourcePtr, MESsourceSourceBinding, MESsourceNode, MESsourceNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESdrainPrimeDrainPrimePtr, MESdrainPrimeDrainPrimeBinding, MESdrainPrimeNode, MESdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESsourcePrimeSourcePrimePtr, MESsourcePrimeSourcePrimeBinding, MESsourcePrimeNode, MESsourcePrimeNode); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/mes/mesdefs.h b/src/spicelib/devices/mes/mesdefs.h index c0bb29556..24fa8b443 100644 --- a/src/spicelib/devices/mes/mesdefs.h +++ b/src/spicelib/devices/mes/mesdefs.h @@ -144,6 +144,24 @@ int MESmode; double **MESnVar; #endif /* NONOISE */ +#ifdef KLU + BindElement *MESdrainDrainPrimeBinding ; + BindElement *MESgateDrainPrimeBinding ; + BindElement *MESgateSourcePrimeBinding ; + BindElement *MESsourceSourcePrimeBinding ; + BindElement *MESdrainPrimeDrainBinding ; + BindElement *MESdrainPrimeGateBinding ; + BindElement *MESdrainPrimeSourcePrimeBinding ; + BindElement *MESsourcePrimeGateBinding ; + BindElement *MESsourcePrimeSourceBinding ; + BindElement *MESsourcePrimeDrainPrimeBinding ; + BindElement *MESdrainDrainBinding ; + BindElement *MESgateGateBinding ; + BindElement *MESsourceSourceBinding ; + BindElement *MESdrainPrimeDrainPrimeBinding ; + BindElement *MESsourcePrimeSourcePrimeBinding ; +#endif + } MESinstance ; #define MESvgs MESstate diff --git a/src/spicelib/devices/mes/mesext.h b/src/spicelib/devices/mes/mesext.h index 94e896484..ce436a4ed 100644 --- a/src/spicelib/devices/mes/mesext.h +++ b/src/spicelib/devices/mes/mesext.h @@ -23,3 +23,8 @@ extern int MESdisto(int,GENmodel*,CKTcircuit*); extern int MESnoise(int,int,GENmodel*,CKTcircuit*,Ndata*,double*); extern int MESdSetup(GENmodel*,CKTcircuit*); +#ifdef KLU +extern int MESbindCSC (GENmodel*, CKTcircuit*) ; +extern int MESbindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int MESbindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/mes/mesinit.c b/src/spicelib/devices/mes/mesinit.c index 151e5aafe..8b22406df 100644 --- a/src/spicelib/devices/mes/mesinit.c +++ b/src/spicelib/devices/mes/mesinit.c @@ -66,6 +66,11 @@ SPICEdev MESinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = MESbindCSC, + .DEVbindCSCComplex = MESbindCSCComplex, + .DEVbindCSCComplexToReal = MESbindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/mesa/Makefile.am b/src/spicelib/devices/mesa/Makefile.am index 79e6f7555..07218b37b 100644 --- a/src/spicelib/devices/mesa/Makefile.am +++ b/src/spicelib/devices/mesa/Makefile.am @@ -25,7 +25,11 @@ libmesa_la_SOURCES = \ mesatrunc.c +if KLU_WANTED +libmesa_la_SOURCES += mesabindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) + MAINTAINERCLEANFILES = Makefile.in diff --git a/src/spicelib/devices/mesa/mesabindCSC.c b/src/spicelib/devices/mesa/mesabindCSC.c new file mode 100644 index 000000000..39dce6c1f --- /dev/null +++ b/src/spicelib/devices/mesa/mesabindCSC.c @@ -0,0 +1,170 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "mesadefs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +MESAbindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + MESAmodel *model = (MESAmodel *)inModel ; + MESAinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the MESA models */ + for ( ; model != NULL ; model = MESAnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = MESAinstances(model); here != NULL ; here = MESAnextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(MESAdrainDrainPtr, MESAdrainDrainBinding, MESAdrainNode, MESAdrainNode); + CREATE_KLU_BINDING_TABLE(MESAdrainPrimeDrainPrimePtr, MESAdrainPrimeDrainPrimeBinding, MESAdrainPrimeNode, MESAdrainPrimeNode); + CREATE_KLU_BINDING_TABLE(MESAdrainPrmPrmDrainPrmPrmPtr, MESAdrainPrmPrmDrainPrmPrmBinding, MESAdrainPrmPrmNode, MESAdrainPrmPrmNode); + CREATE_KLU_BINDING_TABLE(MESAgateGatePtr, MESAgateGateBinding, MESAgateNode, MESAgateNode); + CREATE_KLU_BINDING_TABLE(MESAgatePrimeGatePrimePtr, MESAgatePrimeGatePrimeBinding, MESAgatePrimeNode, MESAgatePrimeNode); + CREATE_KLU_BINDING_TABLE(MESAsourceSourcePtr, MESAsourceSourceBinding, MESAsourceNode, MESAsourceNode); + CREATE_KLU_BINDING_TABLE(MESAsourcePrimeSourcePrimePtr, MESAsourcePrimeSourcePrimeBinding, MESAsourcePrimeNode, MESAsourcePrimeNode); + CREATE_KLU_BINDING_TABLE(MESAsourcePrmPrmSourcePrmPrmPtr, MESAsourcePrmPrmSourcePrmPrmBinding, MESAsourcePrmPrmNode, MESAsourcePrmPrmNode); + CREATE_KLU_BINDING_TABLE(MESAdrainDrainPrimePtr, MESAdrainDrainPrimeBinding, MESAdrainNode, MESAdrainPrimeNode); + CREATE_KLU_BINDING_TABLE(MESAdrainPrimeDrainPtr, MESAdrainPrimeDrainBinding, MESAdrainPrimeNode, MESAdrainNode); + CREATE_KLU_BINDING_TABLE(MESAgatePrimeDrainPrimePtr, MESAgatePrimeDrainPrimeBinding, MESAgatePrimeNode, MESAdrainPrimeNode); + CREATE_KLU_BINDING_TABLE(MESAdrainPrimeGatePrimePtr, MESAdrainPrimeGatePrimeBinding, MESAdrainPrimeNode, MESAgatePrimeNode); + CREATE_KLU_BINDING_TABLE(MESAgatePrimeSourcePrimePtr, MESAgatePrimeSourcePrimeBinding, MESAgatePrimeNode, MESAsourcePrimeNode); + CREATE_KLU_BINDING_TABLE(MESAsourcePrimeGatePrimePtr, MESAsourcePrimeGatePrimeBinding, MESAsourcePrimeNode, MESAgatePrimeNode); + CREATE_KLU_BINDING_TABLE(MESAsourceSourcePrimePtr, MESAsourceSourcePrimeBinding, MESAsourceNode, MESAsourcePrimeNode); + CREATE_KLU_BINDING_TABLE(MESAsourcePrimeSourcePtr, MESAsourcePrimeSourceBinding, MESAsourcePrimeNode, MESAsourceNode); + CREATE_KLU_BINDING_TABLE(MESAdrainPrimeSourcePrimePtr, MESAdrainPrimeSourcePrimeBinding, MESAdrainPrimeNode, MESAsourcePrimeNode); + CREATE_KLU_BINDING_TABLE(MESAsourcePrimeDrainPrimePtr, MESAsourcePrimeDrainPrimeBinding, MESAsourcePrimeNode, MESAdrainPrimeNode); + CREATE_KLU_BINDING_TABLE(MESAgatePrimeGatePtr, MESAgatePrimeGateBinding, MESAgatePrimeNode, MESAgateNode); + CREATE_KLU_BINDING_TABLE(MESAgateGatePrimePtr, MESAgateGatePrimeBinding, MESAgateNode, MESAgatePrimeNode); + CREATE_KLU_BINDING_TABLE(MESAsourcePrmPrmSourcePrimePtr, MESAsourcePrmPrmSourcePrimeBinding, MESAsourcePrmPrmNode, MESAsourcePrimeNode); + CREATE_KLU_BINDING_TABLE(MESAsourcePrimeSourcePrmPrmPtr, MESAsourcePrimeSourcePrmPrmBinding, MESAsourcePrimeNode, MESAsourcePrmPrmNode); + CREATE_KLU_BINDING_TABLE(MESAsourcePrmPrmGatePrimePtr, MESAsourcePrmPrmGatePrimeBinding, MESAsourcePrmPrmNode, MESAgatePrimeNode); + CREATE_KLU_BINDING_TABLE(MESAgatePrimeSourcePrmPrmPtr, MESAgatePrimeSourcePrmPrmBinding, MESAgatePrimeNode, MESAsourcePrmPrmNode); + CREATE_KLU_BINDING_TABLE(MESAdrainPrmPrmDrainPrimePtr, MESAdrainPrmPrmDrainPrimeBinding, MESAdrainPrmPrmNode, MESAdrainPrimeNode); + CREATE_KLU_BINDING_TABLE(MESAdrainPrimeDrainPrmPrmPtr, MESAdrainPrimeDrainPrmPrmBinding, MESAdrainPrimeNode, MESAdrainPrmPrmNode); + CREATE_KLU_BINDING_TABLE(MESAdrainPrmPrmGatePrimePtr, MESAdrainPrmPrmGatePrimeBinding, MESAdrainPrmPrmNode, MESAgatePrimeNode); + CREATE_KLU_BINDING_TABLE(MESAgatePrimeDrainPrmPrmPtr, MESAgatePrimeDrainPrmPrmBinding, MESAgatePrimeNode, MESAdrainPrmPrmNode); + } + } + + return (OK) ; +} + +int +MESAbindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + MESAmodel *model = (MESAmodel *)inModel ; + MESAinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the MESA models */ + for ( ; model != NULL ; model = MESAnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = MESAinstances(model); here != NULL ; here = MESAnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESAdrainDrainPtr, MESAdrainDrainBinding, MESAdrainNode, MESAdrainNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESAdrainPrimeDrainPrimePtr, MESAdrainPrimeDrainPrimeBinding, MESAdrainPrimeNode, MESAdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESAdrainPrmPrmDrainPrmPrmPtr, MESAdrainPrmPrmDrainPrmPrmBinding, MESAdrainPrmPrmNode, MESAdrainPrmPrmNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESAgateGatePtr, MESAgateGateBinding, MESAgateNode, MESAgateNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESAgatePrimeGatePrimePtr, MESAgatePrimeGatePrimeBinding, MESAgatePrimeNode, MESAgatePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESAsourceSourcePtr, MESAsourceSourceBinding, MESAsourceNode, MESAsourceNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESAsourcePrimeSourcePrimePtr, MESAsourcePrimeSourcePrimeBinding, MESAsourcePrimeNode, MESAsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESAsourcePrmPrmSourcePrmPrmPtr, MESAsourcePrmPrmSourcePrmPrmBinding, MESAsourcePrmPrmNode, MESAsourcePrmPrmNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESAdrainDrainPrimePtr, MESAdrainDrainPrimeBinding, MESAdrainNode, MESAdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESAdrainPrimeDrainPtr, MESAdrainPrimeDrainBinding, MESAdrainPrimeNode, MESAdrainNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESAgatePrimeDrainPrimePtr, MESAgatePrimeDrainPrimeBinding, MESAgatePrimeNode, MESAdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESAdrainPrimeGatePrimePtr, MESAdrainPrimeGatePrimeBinding, MESAdrainPrimeNode, MESAgatePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESAgatePrimeSourcePrimePtr, MESAgatePrimeSourcePrimeBinding, MESAgatePrimeNode, MESAsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESAsourcePrimeGatePrimePtr, MESAsourcePrimeGatePrimeBinding, MESAsourcePrimeNode, MESAgatePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESAsourceSourcePrimePtr, MESAsourceSourcePrimeBinding, MESAsourceNode, MESAsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESAsourcePrimeSourcePtr, MESAsourcePrimeSourceBinding, MESAsourcePrimeNode, MESAsourceNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESAdrainPrimeSourcePrimePtr, MESAdrainPrimeSourcePrimeBinding, MESAdrainPrimeNode, MESAsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESAsourcePrimeDrainPrimePtr, MESAsourcePrimeDrainPrimeBinding, MESAsourcePrimeNode, MESAdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESAgatePrimeGatePtr, MESAgatePrimeGateBinding, MESAgatePrimeNode, MESAgateNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESAgateGatePrimePtr, MESAgateGatePrimeBinding, MESAgateNode, MESAgatePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESAsourcePrmPrmSourcePrimePtr, MESAsourcePrmPrmSourcePrimeBinding, MESAsourcePrmPrmNode, MESAsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESAsourcePrimeSourcePrmPrmPtr, MESAsourcePrimeSourcePrmPrmBinding, MESAsourcePrimeNode, MESAsourcePrmPrmNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESAsourcePrmPrmGatePrimePtr, MESAsourcePrmPrmGatePrimeBinding, MESAsourcePrmPrmNode, MESAgatePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESAgatePrimeSourcePrmPrmPtr, MESAgatePrimeSourcePrmPrmBinding, MESAgatePrimeNode, MESAsourcePrmPrmNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESAdrainPrmPrmDrainPrimePtr, MESAdrainPrmPrmDrainPrimeBinding, MESAdrainPrmPrmNode, MESAdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESAdrainPrimeDrainPrmPrmPtr, MESAdrainPrimeDrainPrmPrmBinding, MESAdrainPrimeNode, MESAdrainPrmPrmNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESAdrainPrmPrmGatePrimePtr, MESAdrainPrmPrmGatePrimeBinding, MESAdrainPrmPrmNode, MESAgatePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MESAgatePrimeDrainPrmPrmPtr, MESAgatePrimeDrainPrmPrmBinding, MESAgatePrimeNode, MESAdrainPrmPrmNode); + } + } + + return (OK) ; +} + +int +MESAbindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + MESAmodel *model = (MESAmodel *)inModel ; + MESAinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the MESA models */ + for ( ; model != NULL ; model = MESAnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = MESAinstances(model); here != NULL ; here = MESAnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESAdrainDrainPtr, MESAdrainDrainBinding, MESAdrainNode, MESAdrainNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESAdrainPrimeDrainPrimePtr, MESAdrainPrimeDrainPrimeBinding, MESAdrainPrimeNode, MESAdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESAdrainPrmPrmDrainPrmPrmPtr, MESAdrainPrmPrmDrainPrmPrmBinding, MESAdrainPrmPrmNode, MESAdrainPrmPrmNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESAgateGatePtr, MESAgateGateBinding, MESAgateNode, MESAgateNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESAgatePrimeGatePrimePtr, MESAgatePrimeGatePrimeBinding, MESAgatePrimeNode, MESAgatePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESAsourceSourcePtr, MESAsourceSourceBinding, MESAsourceNode, MESAsourceNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESAsourcePrimeSourcePrimePtr, MESAsourcePrimeSourcePrimeBinding, MESAsourcePrimeNode, MESAsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESAsourcePrmPrmSourcePrmPrmPtr, MESAsourcePrmPrmSourcePrmPrmBinding, MESAsourcePrmPrmNode, MESAsourcePrmPrmNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESAdrainDrainPrimePtr, MESAdrainDrainPrimeBinding, MESAdrainNode, MESAdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESAdrainPrimeDrainPtr, MESAdrainPrimeDrainBinding, MESAdrainPrimeNode, MESAdrainNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESAgatePrimeDrainPrimePtr, MESAgatePrimeDrainPrimeBinding, MESAgatePrimeNode, MESAdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESAdrainPrimeGatePrimePtr, MESAdrainPrimeGatePrimeBinding, MESAdrainPrimeNode, MESAgatePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESAgatePrimeSourcePrimePtr, MESAgatePrimeSourcePrimeBinding, MESAgatePrimeNode, MESAsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESAsourcePrimeGatePrimePtr, MESAsourcePrimeGatePrimeBinding, MESAsourcePrimeNode, MESAgatePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESAsourceSourcePrimePtr, MESAsourceSourcePrimeBinding, MESAsourceNode, MESAsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESAsourcePrimeSourcePtr, MESAsourcePrimeSourceBinding, MESAsourcePrimeNode, MESAsourceNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESAdrainPrimeSourcePrimePtr, MESAdrainPrimeSourcePrimeBinding, MESAdrainPrimeNode, MESAsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESAsourcePrimeDrainPrimePtr, MESAsourcePrimeDrainPrimeBinding, MESAsourcePrimeNode, MESAdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESAgatePrimeGatePtr, MESAgatePrimeGateBinding, MESAgatePrimeNode, MESAgateNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESAgateGatePrimePtr, MESAgateGatePrimeBinding, MESAgateNode, MESAgatePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESAsourcePrmPrmSourcePrimePtr, MESAsourcePrmPrmSourcePrimeBinding, MESAsourcePrmPrmNode, MESAsourcePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESAsourcePrimeSourcePrmPrmPtr, MESAsourcePrimeSourcePrmPrmBinding, MESAsourcePrimeNode, MESAsourcePrmPrmNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESAsourcePrmPrmGatePrimePtr, MESAsourcePrmPrmGatePrimeBinding, MESAsourcePrmPrmNode, MESAgatePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESAgatePrimeSourcePrmPrmPtr, MESAgatePrimeSourcePrmPrmBinding, MESAgatePrimeNode, MESAsourcePrmPrmNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESAdrainPrmPrmDrainPrimePtr, MESAdrainPrmPrmDrainPrimeBinding, MESAdrainPrmPrmNode, MESAdrainPrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESAdrainPrimeDrainPrmPrmPtr, MESAdrainPrimeDrainPrmPrmBinding, MESAdrainPrimeNode, MESAdrainPrmPrmNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESAdrainPrmPrmGatePrimePtr, MESAdrainPrmPrmGatePrimeBinding, MESAdrainPrmPrmNode, MESAgatePrimeNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MESAgatePrimeDrainPrmPrmPtr, MESAgatePrimeDrainPrmPrmBinding, MESAgatePrimeNode, MESAdrainPrmPrmNode); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/mesa/mesadefs.h b/src/spicelib/devices/mesa/mesadefs.h index 1f6c652cd..50bdcece4 100644 --- a/src/spicelib/devices/mesa/mesadefs.h +++ b/src/spicelib/devices/mesa/mesadefs.h @@ -210,6 +210,38 @@ int MESAmode; double MESAnsb0; double MESAvcrits; double MESAvcritd; + +#ifdef KLU + BindElement *MESAdrainDrainBinding ; + BindElement *MESAdrainPrimeDrainPrimeBinding ; + BindElement *MESAdrainPrmPrmDrainPrmPrmBinding ; + BindElement *MESAgateGateBinding ; + BindElement *MESAgatePrimeGatePrimeBinding ; + BindElement *MESAsourceSourceBinding ; + BindElement *MESAsourcePrimeSourcePrimeBinding ; + BindElement *MESAsourcePrmPrmSourcePrmPrmBinding ; + BindElement *MESAdrainDrainPrimeBinding ; + BindElement *MESAdrainPrimeDrainBinding ; + BindElement *MESAgatePrimeDrainPrimeBinding ; + BindElement *MESAdrainPrimeGatePrimeBinding ; + BindElement *MESAgatePrimeSourcePrimeBinding ; + BindElement *MESAsourcePrimeGatePrimeBinding ; + BindElement *MESAsourceSourcePrimeBinding ; + BindElement *MESAsourcePrimeSourceBinding ; + BindElement *MESAdrainPrimeSourcePrimeBinding ; + BindElement *MESAsourcePrimeDrainPrimeBinding ; + BindElement *MESAgatePrimeGateBinding ; + BindElement *MESAgateGatePrimeBinding ; + BindElement *MESAsourcePrmPrmSourcePrimeBinding ; + BindElement *MESAsourcePrimeSourcePrmPrmBinding ; + BindElement *MESAsourcePrmPrmGatePrimeBinding ; + BindElement *MESAgatePrimeSourcePrmPrmBinding ; + BindElement *MESAdrainPrmPrmDrainPrimeBinding ; + BindElement *MESAdrainPrimeDrainPrmPrmBinding ; + BindElement *MESAdrainPrmPrmGatePrimeBinding ; + BindElement *MESAgatePrimeDrainPrmPrmBinding ; +#endif + } MESAinstance ; diff --git a/src/spicelib/devices/mesa/mesaext.h b/src/spicelib/devices/mesa/mesaext.h index 2b322d611..65ff368f4 100644 --- a/src/spicelib/devices/mesa/mesaext.h +++ b/src/spicelib/devices/mesa/mesaext.h @@ -18,3 +18,9 @@ extern int MESAsetup(SMPmatrix*,GENmodel*,CKTcircuit*,int*); extern int MESAtemp(GENmodel*,CKTcircuit*); extern int MESAtrunc(GENmodel*,CKTcircuit*,double*); extern int MESAunsetup(GENmodel*,CKTcircuit*); + +#ifdef KLU +extern int MESAbindCSC (GENmodel*, CKTcircuit*) ; +extern int MESAbindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int MESAbindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/mesa/mesainit.c b/src/spicelib/devices/mesa/mesainit.c index 8d632347d..10e518227 100644 --- a/src/spicelib/devices/mesa/mesainit.c +++ b/src/spicelib/devices/mesa/mesainit.c @@ -66,6 +66,11 @@ SPICEdev MESAinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = MESAbindCSC, + .DEVbindCSCComplex = MESAbindCSCComplex, + .DEVbindCSCComplexToReal = MESAbindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/mos1/Makefile.am b/src/spicelib/devices/mos1/Makefile.am index e523c113c..a0e3eff13 100644 --- a/src/spicelib/devices/mos1/Makefile.am +++ b/src/spicelib/devices/mos1/Makefile.am @@ -34,7 +34,11 @@ libmos1_la_SOURCES = \ mos1trun.c +if KLU_WANTED +libmos1_la_SOURCES += mos1bindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) + MAINTAINERCLEANFILES = Makefile.in diff --git a/src/spicelib/devices/mos1/mos1bindCSC.c b/src/spicelib/devices/mos1/mos1bindCSC.c new file mode 100644 index 000000000..48542af39 --- /dev/null +++ b/src/spicelib/devices/mos1/mos1bindCSC.c @@ -0,0 +1,152 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "mos1defs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +MOS1bindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + MOS1model *model = (MOS1model *)inModel ; + MOS1instance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the MOS1 models */ + for ( ; model != NULL ; model = MOS1nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = MOS1instances(model); here != NULL ; here = MOS1nextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(MOS1DdPtr, MOS1DdBinding, MOS1dNode, MOS1dNode); + CREATE_KLU_BINDING_TABLE(MOS1GgPtr, MOS1GgBinding, MOS1gNode, MOS1gNode); + CREATE_KLU_BINDING_TABLE(MOS1SsPtr, MOS1SsBinding, MOS1sNode, MOS1sNode); + CREATE_KLU_BINDING_TABLE(MOS1BbPtr, MOS1BbBinding, MOS1bNode, MOS1bNode); + CREATE_KLU_BINDING_TABLE(MOS1DPdpPtr, MOS1DPdpBinding, MOS1dNodePrime, MOS1dNodePrime); + CREATE_KLU_BINDING_TABLE(MOS1SPspPtr, MOS1SPspBinding, MOS1sNodePrime, MOS1sNodePrime); + CREATE_KLU_BINDING_TABLE(MOS1DdpPtr, MOS1DdpBinding, MOS1dNode, MOS1dNodePrime); + CREATE_KLU_BINDING_TABLE(MOS1GbPtr, MOS1GbBinding, MOS1gNode, MOS1bNode); + CREATE_KLU_BINDING_TABLE(MOS1GdpPtr, MOS1GdpBinding, MOS1gNode, MOS1dNodePrime); + CREATE_KLU_BINDING_TABLE(MOS1GspPtr, MOS1GspBinding, MOS1gNode, MOS1sNodePrime); + CREATE_KLU_BINDING_TABLE(MOS1SspPtr, MOS1SspBinding, MOS1sNode, MOS1sNodePrime); + CREATE_KLU_BINDING_TABLE(MOS1BdpPtr, MOS1BdpBinding, MOS1bNode, MOS1dNodePrime); + CREATE_KLU_BINDING_TABLE(MOS1BspPtr, MOS1BspBinding, MOS1bNode, MOS1sNodePrime); + CREATE_KLU_BINDING_TABLE(MOS1DPspPtr, MOS1DPspBinding, MOS1dNodePrime, MOS1sNodePrime); + CREATE_KLU_BINDING_TABLE(MOS1DPdPtr, MOS1DPdBinding, MOS1dNodePrime, MOS1dNode); + CREATE_KLU_BINDING_TABLE(MOS1BgPtr, MOS1BgBinding, MOS1bNode, MOS1gNode); + CREATE_KLU_BINDING_TABLE(MOS1DPgPtr, MOS1DPgBinding, MOS1dNodePrime, MOS1gNode); + CREATE_KLU_BINDING_TABLE(MOS1SPgPtr, MOS1SPgBinding, MOS1sNodePrime, MOS1gNode); + CREATE_KLU_BINDING_TABLE(MOS1SPsPtr, MOS1SPsBinding, MOS1sNodePrime, MOS1sNode); + CREATE_KLU_BINDING_TABLE(MOS1DPbPtr, MOS1DPbBinding, MOS1dNodePrime, MOS1bNode); + CREATE_KLU_BINDING_TABLE(MOS1SPbPtr, MOS1SPbBinding, MOS1sNodePrime, MOS1bNode); + CREATE_KLU_BINDING_TABLE(MOS1SPdpPtr, MOS1SPdpBinding, MOS1sNodePrime, MOS1dNodePrime); + } + } + + return (OK) ; +} + +int +MOS1bindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + MOS1model *model = (MOS1model *)inModel ; + MOS1instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the MOS1 models */ + for ( ; model != NULL ; model = MOS1nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = MOS1instances(model); here != NULL ; here = MOS1nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS1DdPtr, MOS1DdBinding, MOS1dNode, MOS1dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS1GgPtr, MOS1GgBinding, MOS1gNode, MOS1gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS1SsPtr, MOS1SsBinding, MOS1sNode, MOS1sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS1BbPtr, MOS1BbBinding, MOS1bNode, MOS1bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS1DPdpPtr, MOS1DPdpBinding, MOS1dNodePrime, MOS1dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS1SPspPtr, MOS1SPspBinding, MOS1sNodePrime, MOS1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS1DdpPtr, MOS1DdpBinding, MOS1dNode, MOS1dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS1GbPtr, MOS1GbBinding, MOS1gNode, MOS1bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS1GdpPtr, MOS1GdpBinding, MOS1gNode, MOS1dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS1GspPtr, MOS1GspBinding, MOS1gNode, MOS1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS1SspPtr, MOS1SspBinding, MOS1sNode, MOS1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS1BdpPtr, MOS1BdpBinding, MOS1bNode, MOS1dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS1BspPtr, MOS1BspBinding, MOS1bNode, MOS1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS1DPspPtr, MOS1DPspBinding, MOS1dNodePrime, MOS1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS1DPdPtr, MOS1DPdBinding, MOS1dNodePrime, MOS1dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS1BgPtr, MOS1BgBinding, MOS1bNode, MOS1gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS1DPgPtr, MOS1DPgBinding, MOS1dNodePrime, MOS1gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS1SPgPtr, MOS1SPgBinding, MOS1sNodePrime, MOS1gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS1SPsPtr, MOS1SPsBinding, MOS1sNodePrime, MOS1sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS1DPbPtr, MOS1DPbBinding, MOS1dNodePrime, MOS1bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS1SPbPtr, MOS1SPbBinding, MOS1sNodePrime, MOS1bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS1SPdpPtr, MOS1SPdpBinding, MOS1sNodePrime, MOS1dNodePrime); + } + } + + return (OK) ; +} + +int +MOS1bindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + MOS1model *model = (MOS1model *)inModel ; + MOS1instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the MOS1 models */ + for ( ; model != NULL ; model = MOS1nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = MOS1instances(model); here != NULL ; here = MOS1nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS1DdPtr, MOS1DdBinding, MOS1dNode, MOS1dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS1GgPtr, MOS1GgBinding, MOS1gNode, MOS1gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS1SsPtr, MOS1SsBinding, MOS1sNode, MOS1sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS1BbPtr, MOS1BbBinding, MOS1bNode, MOS1bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS1DPdpPtr, MOS1DPdpBinding, MOS1dNodePrime, MOS1dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS1SPspPtr, MOS1SPspBinding, MOS1sNodePrime, MOS1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS1DdpPtr, MOS1DdpBinding, MOS1dNode, MOS1dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS1GbPtr, MOS1GbBinding, MOS1gNode, MOS1bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS1GdpPtr, MOS1GdpBinding, MOS1gNode, MOS1dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS1GspPtr, MOS1GspBinding, MOS1gNode, MOS1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS1SspPtr, MOS1SspBinding, MOS1sNode, MOS1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS1BdpPtr, MOS1BdpBinding, MOS1bNode, MOS1dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS1BspPtr, MOS1BspBinding, MOS1bNode, MOS1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS1DPspPtr, MOS1DPspBinding, MOS1dNodePrime, MOS1sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS1DPdPtr, MOS1DPdBinding, MOS1dNodePrime, MOS1dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS1BgPtr, MOS1BgBinding, MOS1bNode, MOS1gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS1DPgPtr, MOS1DPgBinding, MOS1dNodePrime, MOS1gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS1SPgPtr, MOS1SPgBinding, MOS1sNodePrime, MOS1gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS1SPsPtr, MOS1SPsBinding, MOS1sNodePrime, MOS1sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS1DPbPtr, MOS1DPbBinding, MOS1dNodePrime, MOS1bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS1SPbPtr, MOS1SPbBinding, MOS1sNodePrime, MOS1bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS1SPdpPtr, MOS1SPdpBinding, MOS1sNodePrime, MOS1dNodePrime); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/mos1/mos1defs.h b/src/spicelib/devices/mos1/mos1defs.h index 81b79c7f4..8117bf655 100644 --- a/src/spicelib/devices/mos1/mos1defs.h +++ b/src/spicelib/devices/mos1/mos1defs.h @@ -266,6 +266,31 @@ typedef struct sMOS1instance { #define MOS1dphibs_dw MOS1sens + 68 #define MOS1dphibd_dw MOS1sens + 69 +#ifdef KLU + BindElement *MOS1DdBinding ; + BindElement *MOS1GgBinding ; + BindElement *MOS1SsBinding ; + BindElement *MOS1BbBinding ; + BindElement *MOS1DPdpBinding ; + BindElement *MOS1SPspBinding ; + BindElement *MOS1DdpBinding ; + BindElement *MOS1GbBinding ; + BindElement *MOS1GdpBinding ; + BindElement *MOS1GspBinding ; + BindElement *MOS1SspBinding ; + BindElement *MOS1BdpBinding ; + BindElement *MOS1BspBinding ; + BindElement *MOS1DPspBinding ; + BindElement *MOS1DPdBinding ; + BindElement *MOS1BgBinding ; + BindElement *MOS1DPgBinding ; + BindElement *MOS1SPgBinding ; + BindElement *MOS1SPsBinding ; + BindElement *MOS1DPbBinding ; + BindElement *MOS1SPbBinding ; + BindElement *MOS1SPdpBinding ; +#endif + } MOS1instance ; #define MOS1vbd MOS1states+ 0 /* bulk-drain voltage */ diff --git a/src/spicelib/devices/mos1/mos1ext.h b/src/spicelib/devices/mos1/mos1ext.h index a81756679..7aa3a2d4b 100644 --- a/src/spicelib/devices/mos1/mos1ext.h +++ b/src/spicelib/devices/mos1/mos1ext.h @@ -28,3 +28,9 @@ extern int MOS1convTest(GENmodel*,CKTcircuit*); extern int MOS1disto(int,GENmodel*,CKTcircuit*); extern int MOS1noise(int,int,GENmodel*,CKTcircuit*,Ndata*,double*); extern int MOS1dSetup(GENmodel*,CKTcircuit*); + +#ifdef KLU +extern int MOS1bindCSC (GENmodel*, CKTcircuit*) ; +extern int MOS1bindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int MOS1bindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/mos1/mos1init.c b/src/spicelib/devices/mos1/mos1init.c index 6f1923164..4d25c32e6 100644 --- a/src/spicelib/devices/mos1/mos1init.c +++ b/src/spicelib/devices/mos1/mos1init.c @@ -66,6 +66,11 @@ SPICEdev MOS1info = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = MOS1bindCSC, + .DEVbindCSCComplex = MOS1bindCSCComplex, + .DEVbindCSCComplexToReal = MOS1bindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/mos2/Makefile.am b/src/spicelib/devices/mos2/Makefile.am index a27ddc9d2..a3d439759 100644 --- a/src/spicelib/devices/mos2/Makefile.am +++ b/src/spicelib/devices/mos2/Makefile.am @@ -33,7 +33,11 @@ libmos2_la_SOURCES = \ mos2temp.c \ mos2trun.c +if KLU_WANTED +libmos2_la_SOURCES += mos2bindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) + MAINTAINERCLEANFILES = Makefile.in diff --git a/src/spicelib/devices/mos2/mos2bindCSC.c b/src/spicelib/devices/mos2/mos2bindCSC.c new file mode 100644 index 000000000..b3eb6334c --- /dev/null +++ b/src/spicelib/devices/mos2/mos2bindCSC.c @@ -0,0 +1,152 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "mos2defs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +MOS2bindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + MOS2model *model = (MOS2model *)inModel ; + MOS2instance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the MOS2 models */ + for ( ; model != NULL ; model = MOS2nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = MOS2instances(model); here != NULL ; here = MOS2nextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(MOS2DdPtr, MOS2DdBinding, MOS2dNode, MOS2dNode); + CREATE_KLU_BINDING_TABLE(MOS2GgPtr, MOS2GgBinding, MOS2gNode, MOS2gNode); + CREATE_KLU_BINDING_TABLE(MOS2SsPtr, MOS2SsBinding, MOS2sNode, MOS2sNode); + CREATE_KLU_BINDING_TABLE(MOS2BbPtr, MOS2BbBinding, MOS2bNode, MOS2bNode); + CREATE_KLU_BINDING_TABLE(MOS2DPdpPtr, MOS2DPdpBinding, MOS2dNodePrime, MOS2dNodePrime); + CREATE_KLU_BINDING_TABLE(MOS2SPspPtr, MOS2SPspBinding, MOS2sNodePrime, MOS2sNodePrime); + CREATE_KLU_BINDING_TABLE(MOS2DdpPtr, MOS2DdpBinding, MOS2dNode, MOS2dNodePrime); + CREATE_KLU_BINDING_TABLE(MOS2GbPtr, MOS2GbBinding, MOS2gNode, MOS2bNode); + CREATE_KLU_BINDING_TABLE(MOS2GdpPtr, MOS2GdpBinding, MOS2gNode, MOS2dNodePrime); + CREATE_KLU_BINDING_TABLE(MOS2GspPtr, MOS2GspBinding, MOS2gNode, MOS2sNodePrime); + CREATE_KLU_BINDING_TABLE(MOS2SspPtr, MOS2SspBinding, MOS2sNode, MOS2sNodePrime); + CREATE_KLU_BINDING_TABLE(MOS2BdpPtr, MOS2BdpBinding, MOS2bNode, MOS2dNodePrime); + CREATE_KLU_BINDING_TABLE(MOS2BspPtr, MOS2BspBinding, MOS2bNode, MOS2sNodePrime); + CREATE_KLU_BINDING_TABLE(MOS2DPspPtr, MOS2DPspBinding, MOS2dNodePrime, MOS2sNodePrime); + CREATE_KLU_BINDING_TABLE(MOS2DPdPtr, MOS2DPdBinding, MOS2dNodePrime, MOS2dNode); + CREATE_KLU_BINDING_TABLE(MOS2BgPtr, MOS2BgBinding, MOS2bNode, MOS2gNode); + CREATE_KLU_BINDING_TABLE(MOS2DPgPtr, MOS2DPgBinding, MOS2dNodePrime, MOS2gNode); + CREATE_KLU_BINDING_TABLE(MOS2SPgPtr, MOS2SPgBinding, MOS2sNodePrime, MOS2gNode); + CREATE_KLU_BINDING_TABLE(MOS2SPsPtr, MOS2SPsBinding, MOS2sNodePrime, MOS2sNode); + CREATE_KLU_BINDING_TABLE(MOS2DPbPtr, MOS2DPbBinding, MOS2dNodePrime, MOS2bNode); + CREATE_KLU_BINDING_TABLE(MOS2SPbPtr, MOS2SPbBinding, MOS2sNodePrime, MOS2bNode); + CREATE_KLU_BINDING_TABLE(MOS2SPdpPtr, MOS2SPdpBinding, MOS2sNodePrime, MOS2dNodePrime); + } + } + + return (OK) ; +} + +int +MOS2bindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + MOS2model *model = (MOS2model *)inModel ; + MOS2instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the MOS2 models */ + for ( ; model != NULL ; model = MOS2nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = MOS2instances(model); here != NULL ; here = MOS2nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS2DdPtr, MOS2DdBinding, MOS2dNode, MOS2dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS2GgPtr, MOS2GgBinding, MOS2gNode, MOS2gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS2SsPtr, MOS2SsBinding, MOS2sNode, MOS2sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS2BbPtr, MOS2BbBinding, MOS2bNode, MOS2bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS2DPdpPtr, MOS2DPdpBinding, MOS2dNodePrime, MOS2dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS2SPspPtr, MOS2SPspBinding, MOS2sNodePrime, MOS2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS2DdpPtr, MOS2DdpBinding, MOS2dNode, MOS2dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS2GbPtr, MOS2GbBinding, MOS2gNode, MOS2bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS2GdpPtr, MOS2GdpBinding, MOS2gNode, MOS2dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS2GspPtr, MOS2GspBinding, MOS2gNode, MOS2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS2SspPtr, MOS2SspBinding, MOS2sNode, MOS2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS2BdpPtr, MOS2BdpBinding, MOS2bNode, MOS2dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS2BspPtr, MOS2BspBinding, MOS2bNode, MOS2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS2DPspPtr, MOS2DPspBinding, MOS2dNodePrime, MOS2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS2DPdPtr, MOS2DPdBinding, MOS2dNodePrime, MOS2dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS2BgPtr, MOS2BgBinding, MOS2bNode, MOS2gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS2DPgPtr, MOS2DPgBinding, MOS2dNodePrime, MOS2gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS2SPgPtr, MOS2SPgBinding, MOS2sNodePrime, MOS2gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS2SPsPtr, MOS2SPsBinding, MOS2sNodePrime, MOS2sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS2DPbPtr, MOS2DPbBinding, MOS2dNodePrime, MOS2bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS2SPbPtr, MOS2SPbBinding, MOS2sNodePrime, MOS2bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS2SPdpPtr, MOS2SPdpBinding, MOS2sNodePrime, MOS2dNodePrime); + } + } + + return (OK) ; +} + +int +MOS2bindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + MOS2model *model = (MOS2model *)inModel ; + MOS2instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the MOS2 models */ + for ( ; model != NULL ; model = MOS2nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = MOS2instances(model); here != NULL ; here = MOS2nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS2DdPtr, MOS2DdBinding, MOS2dNode, MOS2dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS2GgPtr, MOS2GgBinding, MOS2gNode, MOS2gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS2SsPtr, MOS2SsBinding, MOS2sNode, MOS2sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS2BbPtr, MOS2BbBinding, MOS2bNode, MOS2bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS2DPdpPtr, MOS2DPdpBinding, MOS2dNodePrime, MOS2dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS2SPspPtr, MOS2SPspBinding, MOS2sNodePrime, MOS2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS2DdpPtr, MOS2DdpBinding, MOS2dNode, MOS2dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS2GbPtr, MOS2GbBinding, MOS2gNode, MOS2bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS2GdpPtr, MOS2GdpBinding, MOS2gNode, MOS2dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS2GspPtr, MOS2GspBinding, MOS2gNode, MOS2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS2SspPtr, MOS2SspBinding, MOS2sNode, MOS2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS2BdpPtr, MOS2BdpBinding, MOS2bNode, MOS2dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS2BspPtr, MOS2BspBinding, MOS2bNode, MOS2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS2DPspPtr, MOS2DPspBinding, MOS2dNodePrime, MOS2sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS2DPdPtr, MOS2DPdBinding, MOS2dNodePrime, MOS2dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS2BgPtr, MOS2BgBinding, MOS2bNode, MOS2gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS2DPgPtr, MOS2DPgBinding, MOS2dNodePrime, MOS2gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS2SPgPtr, MOS2SPgBinding, MOS2sNodePrime, MOS2gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS2SPsPtr, MOS2SPsBinding, MOS2sNodePrime, MOS2sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS2DPbPtr, MOS2DPbBinding, MOS2dNodePrime, MOS2bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS2SPbPtr, MOS2SPbBinding, MOS2sNodePrime, MOS2bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS2SPdpPtr, MOS2SPdpBinding, MOS2sNodePrime, MOS2dNodePrime); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/mos2/mos2defs.h b/src/spicelib/devices/mos2/mos2defs.h index 431dc7d35..407ac3026 100644 --- a/src/spicelib/devices/mos2/mos2defs.h +++ b/src/spicelib/devices/mos2/mos2defs.h @@ -270,7 +270,30 @@ typedef struct sMOS2instance { double **MOS2nVar; #endif /* NONOISE */ - +#ifdef KLU + BindElement *MOS2DdBinding ; + BindElement *MOS2GgBinding ; + BindElement *MOS2SsBinding ; + BindElement *MOS2BbBinding ; + BindElement *MOS2DPdpBinding ; + BindElement *MOS2SPspBinding ; + BindElement *MOS2DdpBinding ; + BindElement *MOS2GbBinding ; + BindElement *MOS2GdpBinding ; + BindElement *MOS2GspBinding ; + BindElement *MOS2SspBinding ; + BindElement *MOS2BdpBinding ; + BindElement *MOS2BspBinding ; + BindElement *MOS2DPspBinding ; + BindElement *MOS2DPdBinding ; + BindElement *MOS2BgBinding ; + BindElement *MOS2DPgBinding ; + BindElement *MOS2SPgBinding ; + BindElement *MOS2SPsBinding ; + BindElement *MOS2DPbBinding ; + BindElement *MOS2SPbBinding ; + BindElement *MOS2SPdpBinding ; +#endif } MOS2instance ; diff --git a/src/spicelib/devices/mos2/mos2ext.h b/src/spicelib/devices/mos2/mos2ext.h index 28e46973e..e55e2fea4 100644 --- a/src/spicelib/devices/mos2/mos2ext.h +++ b/src/spicelib/devices/mos2/mos2ext.h @@ -29,3 +29,9 @@ extern int MOS2disto(int,GENmodel*,CKTcircuit*); extern int MOS2noise(int,int,GENmodel*,CKTcircuit*,Ndata*,double*); extern int MOS2dSetup(GENmodel*,CKTcircuit*); + +#ifdef KLU +extern int MOS2bindCSC (GENmodel*, CKTcircuit*) ; +extern int MOS2bindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int MOS2bindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/mos2/mos2init.c b/src/spicelib/devices/mos2/mos2init.c index 297a0edde..e3d0adb9b 100644 --- a/src/spicelib/devices/mos2/mos2init.c +++ b/src/spicelib/devices/mos2/mos2init.c @@ -66,6 +66,11 @@ SPICEdev MOS2info = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = MOS2bindCSC, + .DEVbindCSCComplex = MOS2bindCSCComplex, + .DEVbindCSCComplexToReal = MOS2bindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/mos3/Makefile.am b/src/spicelib/devices/mos3/Makefile.am index 7419051a9..cf08841e1 100644 --- a/src/spicelib/devices/mos3/Makefile.am +++ b/src/spicelib/devices/mos3/Makefile.am @@ -33,7 +33,11 @@ libmos3_la_SOURCES = \ mos3temp.c \ mos3trun.c +if KLU_WANTED +libmos3_la_SOURCES += mos3bindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) + MAINTAINERCLEANFILES = Makefile.in diff --git a/src/spicelib/devices/mos3/mos3bindCSC.c b/src/spicelib/devices/mos3/mos3bindCSC.c new file mode 100644 index 000000000..7cc7df5fe --- /dev/null +++ b/src/spicelib/devices/mos3/mos3bindCSC.c @@ -0,0 +1,152 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "mos3defs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +MOS3bindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + MOS3model *model = (MOS3model *)inModel ; + MOS3instance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the MOS3 models */ + for ( ; model != NULL ; model = MOS3nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = MOS3instances(model); here != NULL ; here = MOS3nextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(MOS3DdPtr, MOS3DdBinding, MOS3dNode, MOS3dNode); + CREATE_KLU_BINDING_TABLE(MOS3GgPtr, MOS3GgBinding, MOS3gNode, MOS3gNode); + CREATE_KLU_BINDING_TABLE(MOS3SsPtr, MOS3SsBinding, MOS3sNode, MOS3sNode); + CREATE_KLU_BINDING_TABLE(MOS3BbPtr, MOS3BbBinding, MOS3bNode, MOS3bNode); + CREATE_KLU_BINDING_TABLE(MOS3DPdpPtr, MOS3DPdpBinding, MOS3dNodePrime, MOS3dNodePrime); + CREATE_KLU_BINDING_TABLE(MOS3SPspPtr, MOS3SPspBinding, MOS3sNodePrime, MOS3sNodePrime); + CREATE_KLU_BINDING_TABLE(MOS3DdpPtr, MOS3DdpBinding, MOS3dNode, MOS3dNodePrime); + CREATE_KLU_BINDING_TABLE(MOS3GbPtr, MOS3GbBinding, MOS3gNode, MOS3bNode); + CREATE_KLU_BINDING_TABLE(MOS3GdpPtr, MOS3GdpBinding, MOS3gNode, MOS3dNodePrime); + CREATE_KLU_BINDING_TABLE(MOS3GspPtr, MOS3GspBinding, MOS3gNode, MOS3sNodePrime); + CREATE_KLU_BINDING_TABLE(MOS3SspPtr, MOS3SspBinding, MOS3sNode, MOS3sNodePrime); + CREATE_KLU_BINDING_TABLE(MOS3BdpPtr, MOS3BdpBinding, MOS3bNode, MOS3dNodePrime); + CREATE_KLU_BINDING_TABLE(MOS3BspPtr, MOS3BspBinding, MOS3bNode, MOS3sNodePrime); + CREATE_KLU_BINDING_TABLE(MOS3DPspPtr, MOS3DPspBinding, MOS3dNodePrime, MOS3sNodePrime); + CREATE_KLU_BINDING_TABLE(MOS3DPdPtr, MOS3DPdBinding, MOS3dNodePrime, MOS3dNode); + CREATE_KLU_BINDING_TABLE(MOS3BgPtr, MOS3BgBinding, MOS3bNode, MOS3gNode); + CREATE_KLU_BINDING_TABLE(MOS3DPgPtr, MOS3DPgBinding, MOS3dNodePrime, MOS3gNode); + CREATE_KLU_BINDING_TABLE(MOS3SPgPtr, MOS3SPgBinding, MOS3sNodePrime, MOS3gNode); + CREATE_KLU_BINDING_TABLE(MOS3SPsPtr, MOS3SPsBinding, MOS3sNodePrime, MOS3sNode); + CREATE_KLU_BINDING_TABLE(MOS3DPbPtr, MOS3DPbBinding, MOS3dNodePrime, MOS3bNode); + CREATE_KLU_BINDING_TABLE(MOS3SPbPtr, MOS3SPbBinding, MOS3sNodePrime, MOS3bNode); + CREATE_KLU_BINDING_TABLE(MOS3SPdpPtr, MOS3SPdpBinding, MOS3sNodePrime, MOS3dNodePrime); + } + } + + return (OK) ; +} + +int +MOS3bindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + MOS3model *model = (MOS3model *)inModel ; + MOS3instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the MOS3 models */ + for ( ; model != NULL ; model = MOS3nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = MOS3instances(model); here != NULL ; here = MOS3nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS3DdPtr, MOS3DdBinding, MOS3dNode, MOS3dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS3GgPtr, MOS3GgBinding, MOS3gNode, MOS3gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS3SsPtr, MOS3SsBinding, MOS3sNode, MOS3sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS3BbPtr, MOS3BbBinding, MOS3bNode, MOS3bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS3DPdpPtr, MOS3DPdpBinding, MOS3dNodePrime, MOS3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS3SPspPtr, MOS3SPspBinding, MOS3sNodePrime, MOS3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS3DdpPtr, MOS3DdpBinding, MOS3dNode, MOS3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS3GbPtr, MOS3GbBinding, MOS3gNode, MOS3bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS3GdpPtr, MOS3GdpBinding, MOS3gNode, MOS3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS3GspPtr, MOS3GspBinding, MOS3gNode, MOS3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS3SspPtr, MOS3SspBinding, MOS3sNode, MOS3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS3BdpPtr, MOS3BdpBinding, MOS3bNode, MOS3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS3BspPtr, MOS3BspBinding, MOS3bNode, MOS3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS3DPspPtr, MOS3DPspBinding, MOS3dNodePrime, MOS3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS3DPdPtr, MOS3DPdBinding, MOS3dNodePrime, MOS3dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS3BgPtr, MOS3BgBinding, MOS3bNode, MOS3gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS3DPgPtr, MOS3DPgBinding, MOS3dNodePrime, MOS3gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS3SPgPtr, MOS3SPgBinding, MOS3sNodePrime, MOS3gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS3SPsPtr, MOS3SPsBinding, MOS3sNodePrime, MOS3sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS3DPbPtr, MOS3DPbBinding, MOS3dNodePrime, MOS3bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS3SPbPtr, MOS3SPbBinding, MOS3sNodePrime, MOS3bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS3SPdpPtr, MOS3SPdpBinding, MOS3sNodePrime, MOS3dNodePrime); + } + } + + return (OK) ; +} + +int +MOS3bindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + MOS3model *model = (MOS3model *)inModel ; + MOS3instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the MOS3 models */ + for ( ; model != NULL ; model = MOS3nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = MOS3instances(model); here != NULL ; here = MOS3nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS3DdPtr, MOS3DdBinding, MOS3dNode, MOS3dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS3GgPtr, MOS3GgBinding, MOS3gNode, MOS3gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS3SsPtr, MOS3SsBinding, MOS3sNode, MOS3sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS3BbPtr, MOS3BbBinding, MOS3bNode, MOS3bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS3DPdpPtr, MOS3DPdpBinding, MOS3dNodePrime, MOS3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS3SPspPtr, MOS3SPspBinding, MOS3sNodePrime, MOS3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS3DdpPtr, MOS3DdpBinding, MOS3dNode, MOS3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS3GbPtr, MOS3GbBinding, MOS3gNode, MOS3bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS3GdpPtr, MOS3GdpBinding, MOS3gNode, MOS3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS3GspPtr, MOS3GspBinding, MOS3gNode, MOS3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS3SspPtr, MOS3SspBinding, MOS3sNode, MOS3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS3BdpPtr, MOS3BdpBinding, MOS3bNode, MOS3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS3BspPtr, MOS3BspBinding, MOS3bNode, MOS3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS3DPspPtr, MOS3DPspBinding, MOS3dNodePrime, MOS3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS3DPdPtr, MOS3DPdBinding, MOS3dNodePrime, MOS3dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS3BgPtr, MOS3BgBinding, MOS3bNode, MOS3gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS3DPgPtr, MOS3DPgBinding, MOS3dNodePrime, MOS3gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS3SPgPtr, MOS3SPgBinding, MOS3sNodePrime, MOS3gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS3SPsPtr, MOS3SPsBinding, MOS3sNodePrime, MOS3sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS3DPbPtr, MOS3DPbBinding, MOS3dNodePrime, MOS3bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS3SPbPtr, MOS3SPbBinding, MOS3sNodePrime, MOS3bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS3SPdpPtr, MOS3SPdpBinding, MOS3sNodePrime, MOS3dNodePrime); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/mos3/mos3defs.h b/src/spicelib/devices/mos3/mos3defs.h index f6159f0a1..268a9b158 100644 --- a/src/spicelib/devices/mos3/mos3defs.h +++ b/src/spicelib/devices/mos3/mos3defs.h @@ -269,6 +269,31 @@ typedef struct sMOS3instance { double **MOS3nVar; #endif /* NONOISE */ +#ifdef KLU + BindElement *MOS3DdBinding ; + BindElement *MOS3GgBinding ; + BindElement *MOS3SsBinding ; + BindElement *MOS3BbBinding ; + BindElement *MOS3DPdpBinding ; + BindElement *MOS3SPspBinding ; + BindElement *MOS3DdpBinding ; + BindElement *MOS3GbBinding ; + BindElement *MOS3GdpBinding ; + BindElement *MOS3GspBinding ; + BindElement *MOS3SspBinding ; + BindElement *MOS3BdpBinding ; + BindElement *MOS3BspBinding ; + BindElement *MOS3DPspBinding ; + BindElement *MOS3DPdBinding ; + BindElement *MOS3BgBinding ; + BindElement *MOS3DPgBinding ; + BindElement *MOS3SPgBinding ; + BindElement *MOS3SPsBinding ; + BindElement *MOS3DPbBinding ; + BindElement *MOS3SPbBinding ; + BindElement *MOS3SPdpBinding ; +#endif + } MOS3instance ; #define MOS3vbd MOS3states+ 0 diff --git a/src/spicelib/devices/mos3/mos3ext.h b/src/spicelib/devices/mos3/mos3ext.h index 12e587f76..bab082bc8 100644 --- a/src/spicelib/devices/mos3/mos3ext.h +++ b/src/spicelib/devices/mos3/mos3ext.h @@ -28,3 +28,9 @@ extern int MOS3trunc(GENmodel*,CKTcircuit*,double*); extern int MOS3disto(int,GENmodel*,CKTcircuit*); extern int MOS3noise(int,int,GENmodel*,CKTcircuit*,Ndata*,double*); extern int MOS3dSetup(GENmodel*,CKTcircuit*); + +#ifdef KLU +extern int MOS3bindCSC (GENmodel*, CKTcircuit*) ; +extern int MOS3bindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int MOS3bindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/mos3/mos3init.c b/src/spicelib/devices/mos3/mos3init.c index d962dd88a..badd06b5c 100644 --- a/src/spicelib/devices/mos3/mos3init.c +++ b/src/spicelib/devices/mos3/mos3init.c @@ -66,6 +66,11 @@ SPICEdev MOS3info = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = MOS3bindCSC, + .DEVbindCSCComplex = MOS3bindCSCComplex, + .DEVbindCSCComplexToReal = MOS3bindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/mos6/Makefile.am b/src/spicelib/devices/mos6/Makefile.am index 324030804..6300e3173 100644 --- a/src/spicelib/devices/mos6/Makefile.am +++ b/src/spicelib/devices/mos6/Makefile.am @@ -24,7 +24,11 @@ libmos6_la_SOURCES = \ mos6trun.c +if KLU_WANTED +libmos6_la_SOURCES += mos6bindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) + MAINTAINERCLEANFILES = Makefile.in diff --git a/src/spicelib/devices/mos6/mos6bindCSC.c b/src/spicelib/devices/mos6/mos6bindCSC.c new file mode 100644 index 000000000..50138968d --- /dev/null +++ b/src/spicelib/devices/mos6/mos6bindCSC.c @@ -0,0 +1,152 @@ +/********** +Author: 2012 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "mos6defs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +MOS6bindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + MOS6model *model = (MOS6model *)inModel ; + MOS6instance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the MOS6 models */ + for ( ; model != NULL ; model = MOS6nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = MOS6instances(model); here != NULL ; here = MOS6nextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(MOS6DdPtr, MOS6DdBinding, MOS6dNode, MOS6dNode); + CREATE_KLU_BINDING_TABLE(MOS6GgPtr, MOS6GgBinding, MOS6gNode, MOS6gNode); + CREATE_KLU_BINDING_TABLE(MOS6SsPtr, MOS6SsBinding, MOS6sNode, MOS6sNode); + CREATE_KLU_BINDING_TABLE(MOS6BbPtr, MOS6BbBinding, MOS6bNode, MOS6bNode); + CREATE_KLU_BINDING_TABLE(MOS6DPdpPtr, MOS6DPdpBinding, MOS6dNodePrime, MOS6dNodePrime); + CREATE_KLU_BINDING_TABLE(MOS6SPspPtr, MOS6SPspBinding, MOS6sNodePrime, MOS6sNodePrime); + CREATE_KLU_BINDING_TABLE(MOS6DdpPtr, MOS6DdpBinding, MOS6dNode, MOS6dNodePrime); + CREATE_KLU_BINDING_TABLE(MOS6GbPtr, MOS6GbBinding, MOS6gNode, MOS6bNode); + CREATE_KLU_BINDING_TABLE(MOS6GdpPtr, MOS6GdpBinding, MOS6gNode, MOS6dNodePrime); + CREATE_KLU_BINDING_TABLE(MOS6GspPtr, MOS6GspBinding, MOS6gNode, MOS6sNodePrime); + CREATE_KLU_BINDING_TABLE(MOS6SspPtr, MOS6SspBinding, MOS6sNode, MOS6sNodePrime); + CREATE_KLU_BINDING_TABLE(MOS6BdpPtr, MOS6BdpBinding, MOS6bNode, MOS6dNodePrime); + CREATE_KLU_BINDING_TABLE(MOS6BspPtr, MOS6BspBinding, MOS6bNode, MOS6sNodePrime); + CREATE_KLU_BINDING_TABLE(MOS6DPspPtr, MOS6DPspBinding, MOS6dNodePrime, MOS6sNodePrime); + CREATE_KLU_BINDING_TABLE(MOS6DPdPtr, MOS6DPdBinding, MOS6dNodePrime, MOS6dNode); + CREATE_KLU_BINDING_TABLE(MOS6BgPtr, MOS6BgBinding, MOS6bNode, MOS6gNode); + CREATE_KLU_BINDING_TABLE(MOS6DPgPtr, MOS6DPgBinding, MOS6dNodePrime, MOS6gNode); + CREATE_KLU_BINDING_TABLE(MOS6SPgPtr, MOS6SPgBinding, MOS6sNodePrime, MOS6gNode); + CREATE_KLU_BINDING_TABLE(MOS6SPsPtr, MOS6SPsBinding, MOS6sNodePrime, MOS6sNode); + CREATE_KLU_BINDING_TABLE(MOS6DPbPtr, MOS6DPbBinding, MOS6dNodePrime, MOS6bNode); + CREATE_KLU_BINDING_TABLE(MOS6SPbPtr, MOS6SPbBinding, MOS6sNodePrime, MOS6bNode); + CREATE_KLU_BINDING_TABLE(MOS6SPdpPtr, MOS6SPdpBinding, MOS6sNodePrime, MOS6dNodePrime); + } + } + + return (OK) ; +} + +int +MOS6bindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + MOS6model *model = (MOS6model *)inModel ; + MOS6instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the MOS6 models */ + for ( ; model != NULL ; model = MOS6nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = MOS6instances(model); here != NULL ; here = MOS6nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS6DdPtr, MOS6DdBinding, MOS6dNode, MOS6dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS6GgPtr, MOS6GgBinding, MOS6gNode, MOS6gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS6SsPtr, MOS6SsBinding, MOS6sNode, MOS6sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS6BbPtr, MOS6BbBinding, MOS6bNode, MOS6bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS6DPdpPtr, MOS6DPdpBinding, MOS6dNodePrime, MOS6dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS6SPspPtr, MOS6SPspBinding, MOS6sNodePrime, MOS6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS6DdpPtr, MOS6DdpBinding, MOS6dNode, MOS6dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS6GbPtr, MOS6GbBinding, MOS6gNode, MOS6bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS6GdpPtr, MOS6GdpBinding, MOS6gNode, MOS6dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS6GspPtr, MOS6GspBinding, MOS6gNode, MOS6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS6SspPtr, MOS6SspBinding, MOS6sNode, MOS6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS6BdpPtr, MOS6BdpBinding, MOS6bNode, MOS6dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS6BspPtr, MOS6BspBinding, MOS6bNode, MOS6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS6DPspPtr, MOS6DPspBinding, MOS6dNodePrime, MOS6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS6DPdPtr, MOS6DPdBinding, MOS6dNodePrime, MOS6dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS6BgPtr, MOS6BgBinding, MOS6bNode, MOS6gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS6DPgPtr, MOS6DPgBinding, MOS6dNodePrime, MOS6gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS6SPgPtr, MOS6SPgBinding, MOS6sNodePrime, MOS6gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS6SPsPtr, MOS6SPsBinding, MOS6sNodePrime, MOS6sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS6DPbPtr, MOS6DPbBinding, MOS6dNodePrime, MOS6bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS6SPbPtr, MOS6SPbBinding, MOS6sNodePrime, MOS6bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS6SPdpPtr, MOS6SPdpBinding, MOS6sNodePrime, MOS6dNodePrime); + } + } + + return (OK) ; +} + +int +MOS6bindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + MOS6model *model = (MOS6model *)inModel ; + MOS6instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the MOS6 models */ + for ( ; model != NULL ; model = MOS6nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = MOS6instances(model); here != NULL ; here = MOS6nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS6DdPtr, MOS6DdBinding, MOS6dNode, MOS6dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS6GgPtr, MOS6GgBinding, MOS6gNode, MOS6gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS6SsPtr, MOS6SsBinding, MOS6sNode, MOS6sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS6BbPtr, MOS6BbBinding, MOS6bNode, MOS6bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS6DPdpPtr, MOS6DPdpBinding, MOS6dNodePrime, MOS6dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS6SPspPtr, MOS6SPspBinding, MOS6sNodePrime, MOS6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS6DdpPtr, MOS6DdpBinding, MOS6dNode, MOS6dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS6GbPtr, MOS6GbBinding, MOS6gNode, MOS6bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS6GdpPtr, MOS6GdpBinding, MOS6gNode, MOS6dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS6GspPtr, MOS6GspBinding, MOS6gNode, MOS6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS6SspPtr, MOS6SspBinding, MOS6sNode, MOS6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS6BdpPtr, MOS6BdpBinding, MOS6bNode, MOS6dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS6BspPtr, MOS6BspBinding, MOS6bNode, MOS6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS6DPspPtr, MOS6DPspBinding, MOS6dNodePrime, MOS6sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS6DPdPtr, MOS6DPdBinding, MOS6dNodePrime, MOS6dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS6BgPtr, MOS6BgBinding, MOS6bNode, MOS6gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS6DPgPtr, MOS6DPgBinding, MOS6dNodePrime, MOS6gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS6SPgPtr, MOS6SPgBinding, MOS6sNodePrime, MOS6gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS6SPsPtr, MOS6SPsBinding, MOS6sNodePrime, MOS6sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS6DPbPtr, MOS6DPbBinding, MOS6dNodePrime, MOS6bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS6SPbPtr, MOS6SPbBinding, MOS6sNodePrime, MOS6bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS6SPdpPtr, MOS6SPdpBinding, MOS6sNodePrime, MOS6dNodePrime); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/mos6/mos6defs.h b/src/spicelib/devices/mos6/mos6defs.h index ba871ac67..580a3b2af 100644 --- a/src/spicelib/devices/mos6/mos6defs.h +++ b/src/spicelib/devices/mos6/mos6defs.h @@ -198,6 +198,31 @@ typedef struct sMOS6instance { #define MOS6dphibs_dw MOS6sens + 68 #define MOS6dphibd_dw MOS6sens + 69 +#ifdef KLU + BindElement *MOS6DdBinding ; + BindElement *MOS6GgBinding ; + BindElement *MOS6SsBinding ; + BindElement *MOS6BbBinding ; + BindElement *MOS6DPdpBinding ; + BindElement *MOS6SPspBinding ; + BindElement *MOS6DdpBinding ; + BindElement *MOS6GbBinding ; + BindElement *MOS6GdpBinding ; + BindElement *MOS6GspBinding ; + BindElement *MOS6SspBinding ; + BindElement *MOS6BdpBinding ; + BindElement *MOS6BspBinding ; + BindElement *MOS6DPspBinding ; + BindElement *MOS6DPdBinding ; + BindElement *MOS6BgBinding ; + BindElement *MOS6DPgBinding ; + BindElement *MOS6SPgBinding ; + BindElement *MOS6SPsBinding ; + BindElement *MOS6DPbBinding ; + BindElement *MOS6SPbBinding ; + BindElement *MOS6SPdpBinding ; +#endif + } MOS6instance ; #define MOS6vbd MOS6states+ 0 /* bulk-drain voltage */ diff --git a/src/spicelib/devices/mos6/mos6ext.h b/src/spicelib/devices/mos6/mos6ext.h index 8bacf5ed0..a7ffd3d2f 100644 --- a/src/spicelib/devices/mos6/mos6ext.h +++ b/src/spicelib/devices/mos6/mos6ext.h @@ -19,3 +19,9 @@ extern int MOS6unsetup(GENmodel*,CKTcircuit*); extern int MOS6temp(GENmodel*,CKTcircuit*); extern int MOS6trunc(GENmodel*,CKTcircuit*,double*); extern int MOS6convTest(GENmodel*,CKTcircuit*); + +#ifdef KLU +extern int MOS6bindCSC (GENmodel*, CKTcircuit*) ; +extern int MOS6bindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int MOS6bindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/mos6/mos6init.c b/src/spicelib/devices/mos6/mos6init.c index a4273df19..008b8443b 100644 --- a/src/spicelib/devices/mos6/mos6init.c +++ b/src/spicelib/devices/mos6/mos6init.c @@ -66,6 +66,11 @@ SPICEdev MOS6info = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = MOS6bindCSC, + .DEVbindCSCComplex = MOS6bindCSCComplex, + .DEVbindCSCComplexToReal = MOS6bindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/mos9/Makefile.am b/src/spicelib/devices/mos9/Makefile.am index 5db83e4c0..564835c93 100644 --- a/src/spicelib/devices/mos9/Makefile.am +++ b/src/spicelib/devices/mos9/Makefile.am @@ -34,7 +34,11 @@ libmos9_la_SOURCES = \ mos9trun.c +if KLU_WANTED +libmos9_la_SOURCES += mos9bindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) + MAINTAINERCLEANFILES = Makefile.in diff --git a/src/spicelib/devices/mos9/mos9bindCSC.c b/src/spicelib/devices/mos9/mos9bindCSC.c new file mode 100644 index 000000000..23eecc5d1 --- /dev/null +++ b/src/spicelib/devices/mos9/mos9bindCSC.c @@ -0,0 +1,152 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "mos9defs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +MOS9bindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + MOS9model *model = (MOS9model *)inModel ; + MOS9instance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the MOS9 models */ + for ( ; model != NULL ; model = MOS9nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = MOS9instances(model); here != NULL ; here = MOS9nextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(MOS9DdPtr, MOS9DdBinding, MOS9dNode, MOS9dNode); + CREATE_KLU_BINDING_TABLE(MOS9GgPtr, MOS9GgBinding, MOS9gNode, MOS9gNode); + CREATE_KLU_BINDING_TABLE(MOS9SsPtr, MOS9SsBinding, MOS9sNode, MOS9sNode); + CREATE_KLU_BINDING_TABLE(MOS9BbPtr, MOS9BbBinding, MOS9bNode, MOS9bNode); + CREATE_KLU_BINDING_TABLE(MOS9DPdpPtr, MOS9DPdpBinding, MOS9dNodePrime, MOS9dNodePrime); + CREATE_KLU_BINDING_TABLE(MOS9SPspPtr, MOS9SPspBinding, MOS9sNodePrime, MOS9sNodePrime); + CREATE_KLU_BINDING_TABLE(MOS9DdpPtr, MOS9DdpBinding, MOS9dNode, MOS9dNodePrime); + CREATE_KLU_BINDING_TABLE(MOS9GbPtr, MOS9GbBinding, MOS9gNode, MOS9bNode); + CREATE_KLU_BINDING_TABLE(MOS9GdpPtr, MOS9GdpBinding, MOS9gNode, MOS9dNodePrime); + CREATE_KLU_BINDING_TABLE(MOS9GspPtr, MOS9GspBinding, MOS9gNode, MOS9sNodePrime); + CREATE_KLU_BINDING_TABLE(MOS9SspPtr, MOS9SspBinding, MOS9sNode, MOS9sNodePrime); + CREATE_KLU_BINDING_TABLE(MOS9BdpPtr, MOS9BdpBinding, MOS9bNode, MOS9dNodePrime); + CREATE_KLU_BINDING_TABLE(MOS9BspPtr, MOS9BspBinding, MOS9bNode, MOS9sNodePrime); + CREATE_KLU_BINDING_TABLE(MOS9DPspPtr, MOS9DPspBinding, MOS9dNodePrime, MOS9sNodePrime); + CREATE_KLU_BINDING_TABLE(MOS9DPdPtr, MOS9DPdBinding, MOS9dNodePrime, MOS9dNode); + CREATE_KLU_BINDING_TABLE(MOS9BgPtr, MOS9BgBinding, MOS9bNode, MOS9gNode); + CREATE_KLU_BINDING_TABLE(MOS9DPgPtr, MOS9DPgBinding, MOS9dNodePrime, MOS9gNode); + CREATE_KLU_BINDING_TABLE(MOS9SPgPtr, MOS9SPgBinding, MOS9sNodePrime, MOS9gNode); + CREATE_KLU_BINDING_TABLE(MOS9SPsPtr, MOS9SPsBinding, MOS9sNodePrime, MOS9sNode); + CREATE_KLU_BINDING_TABLE(MOS9DPbPtr, MOS9DPbBinding, MOS9dNodePrime, MOS9bNode); + CREATE_KLU_BINDING_TABLE(MOS9SPbPtr, MOS9SPbBinding, MOS9sNodePrime, MOS9bNode); + CREATE_KLU_BINDING_TABLE(MOS9SPdpPtr, MOS9SPdpBinding, MOS9sNodePrime, MOS9dNodePrime); + } + } + + return (OK) ; +} + +int +MOS9bindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + MOS9model *model = (MOS9model *)inModel ; + MOS9instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the MOS9 models */ + for ( ; model != NULL ; model = MOS9nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = MOS9instances(model); here != NULL ; here = MOS9nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS9DdPtr, MOS9DdBinding, MOS9dNode, MOS9dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS9GgPtr, MOS9GgBinding, MOS9gNode, MOS9gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS9SsPtr, MOS9SsBinding, MOS9sNode, MOS9sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS9BbPtr, MOS9BbBinding, MOS9bNode, MOS9bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS9DPdpPtr, MOS9DPdpBinding, MOS9dNodePrime, MOS9dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS9SPspPtr, MOS9SPspBinding, MOS9sNodePrime, MOS9sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS9DdpPtr, MOS9DdpBinding, MOS9dNode, MOS9dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS9GbPtr, MOS9GbBinding, MOS9gNode, MOS9bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS9GdpPtr, MOS9GdpBinding, MOS9gNode, MOS9dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS9GspPtr, MOS9GspBinding, MOS9gNode, MOS9sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS9SspPtr, MOS9SspBinding, MOS9sNode, MOS9sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS9BdpPtr, MOS9BdpBinding, MOS9bNode, MOS9dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS9BspPtr, MOS9BspBinding, MOS9bNode, MOS9sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS9DPspPtr, MOS9DPspBinding, MOS9dNodePrime, MOS9sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS9DPdPtr, MOS9DPdBinding, MOS9dNodePrime, MOS9dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS9BgPtr, MOS9BgBinding, MOS9bNode, MOS9gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS9DPgPtr, MOS9DPgBinding, MOS9dNodePrime, MOS9gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS9SPgPtr, MOS9SPgBinding, MOS9sNodePrime, MOS9gNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS9SPsPtr, MOS9SPsBinding, MOS9sNodePrime, MOS9sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS9DPbPtr, MOS9DPbBinding, MOS9dNodePrime, MOS9bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS9SPbPtr, MOS9SPbBinding, MOS9sNodePrime, MOS9bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(MOS9SPdpPtr, MOS9SPdpBinding, MOS9sNodePrime, MOS9dNodePrime); + } + } + + return (OK) ; +} + +int +MOS9bindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + MOS9model *model = (MOS9model *)inModel ; + MOS9instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the MOS9 models */ + for ( ; model != NULL ; model = MOS9nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = MOS9instances(model); here != NULL ; here = MOS9nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS9DdPtr, MOS9DdBinding, MOS9dNode, MOS9dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS9GgPtr, MOS9GgBinding, MOS9gNode, MOS9gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS9SsPtr, MOS9SsBinding, MOS9sNode, MOS9sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS9BbPtr, MOS9BbBinding, MOS9bNode, MOS9bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS9DPdpPtr, MOS9DPdpBinding, MOS9dNodePrime, MOS9dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS9SPspPtr, MOS9SPspBinding, MOS9sNodePrime, MOS9sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS9DdpPtr, MOS9DdpBinding, MOS9dNode, MOS9dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS9GbPtr, MOS9GbBinding, MOS9gNode, MOS9bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS9GdpPtr, MOS9GdpBinding, MOS9gNode, MOS9dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS9GspPtr, MOS9GspBinding, MOS9gNode, MOS9sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS9SspPtr, MOS9SspBinding, MOS9sNode, MOS9sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS9BdpPtr, MOS9BdpBinding, MOS9bNode, MOS9dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS9BspPtr, MOS9BspBinding, MOS9bNode, MOS9sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS9DPspPtr, MOS9DPspBinding, MOS9dNodePrime, MOS9sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS9DPdPtr, MOS9DPdBinding, MOS9dNodePrime, MOS9dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS9BgPtr, MOS9BgBinding, MOS9bNode, MOS9gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS9DPgPtr, MOS9DPgBinding, MOS9dNodePrime, MOS9gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS9SPgPtr, MOS9SPgBinding, MOS9sNodePrime, MOS9gNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS9SPsPtr, MOS9SPsBinding, MOS9sNodePrime, MOS9sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS9DPbPtr, MOS9DPbBinding, MOS9dNodePrime, MOS9bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS9SPbPtr, MOS9SPbBinding, MOS9sNodePrime, MOS9bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(MOS9SPdpPtr, MOS9SPdpBinding, MOS9sNodePrime, MOS9dNodePrime); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/mos9/mos9defs.h b/src/spicelib/devices/mos9/mos9defs.h index 486c41cad..6f673df91 100644 --- a/src/spicelib/devices/mos9/mos9defs.h +++ b/src/spicelib/devices/mos9/mos9defs.h @@ -271,6 +271,31 @@ typedef struct sMOS9instance { double **MOS9nVar; #endif /* NONOISE */ +#ifdef KLU + BindElement *MOS9DdBinding ; + BindElement *MOS9GgBinding ; + BindElement *MOS9SsBinding ; + BindElement *MOS9BbBinding ; + BindElement *MOS9DPdpBinding ; + BindElement *MOS9SPspBinding ; + BindElement *MOS9DdpBinding ; + BindElement *MOS9GbBinding ; + BindElement *MOS9GdpBinding ; + BindElement *MOS9GspBinding ; + BindElement *MOS9SspBinding ; + BindElement *MOS9BdpBinding ; + BindElement *MOS9BspBinding ; + BindElement *MOS9DPspBinding ; + BindElement *MOS9DPdBinding ; + BindElement *MOS9BgBinding ; + BindElement *MOS9DPgBinding ; + BindElement *MOS9SPgBinding ; + BindElement *MOS9SPsBinding ; + BindElement *MOS9DPbBinding ; + BindElement *MOS9SPbBinding ; + BindElement *MOS9SPdpBinding ; +#endif + } MOS9instance ; #define MOS9vbd MOS9states+ 0 diff --git a/src/spicelib/devices/mos9/mos9ext.h b/src/spicelib/devices/mos9/mos9ext.h index 985be5ed8..9f1b42390 100644 --- a/src/spicelib/devices/mos9/mos9ext.h +++ b/src/spicelib/devices/mos9/mos9ext.h @@ -28,3 +28,9 @@ extern int MOS9trunc(GENmodel*,CKTcircuit*,double*); extern int MOS9disto(int,GENmodel*,CKTcircuit*); extern int MOS9noise(int,int,GENmodel*,CKTcircuit*,Ndata*,double*); extern int MOS9dSetup(GENmodel*,CKTcircuit*); + +#ifdef KLU +extern int MOS9bindCSC (GENmodel*, CKTcircuit*) ; +extern int MOS9bindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int MOS9bindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/mos9/mos9init.c b/src/spicelib/devices/mos9/mos9init.c index 292c6bfc6..523c8c61e 100644 --- a/src/spicelib/devices/mos9/mos9init.c +++ b/src/spicelib/devices/mos9/mos9init.c @@ -66,6 +66,11 @@ SPICEdev MOS9info = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = MOS9bindCSC, + .DEVbindCSCComplex = MOS9bindCSCComplex, + .DEVbindCSCComplexToReal = MOS9bindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/nbjt/Makefile.am b/src/spicelib/devices/nbjt/Makefile.am index 4a5c3ee8a..7f18d5b19 100644 --- a/src/spicelib/devices/nbjt/Makefile.am +++ b/src/spicelib/devices/nbjt/Makefile.am @@ -24,6 +24,9 @@ libnbjt_la_SOURCES = \ nbjttrun.c +if KLU_WANTED +libnbjt_la_SOURCES += nbjtbindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) diff --git a/src/spicelib/devices/nbjt/nbjtbindCSC.c b/src/spicelib/devices/nbjt/nbjtbindCSC.c new file mode 100644 index 000000000..a6e150f52 --- /dev/null +++ b/src/spicelib/devices/nbjt/nbjtbindCSC.c @@ -0,0 +1,113 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "nbjtdefs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +NBJTbindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + NBJTmodel *model = (NBJTmodel *)inModel ; + NBJTinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the NBJT models */ + for ( ; model != NULL ; model = NBJTnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = NBJTinstances(model); here != NULL ; here = NBJTnextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(NBJTcolColPtr, NBJTcolColBinding, NBJTcolNode, NBJTcolNode); + CREATE_KLU_BINDING_TABLE(NBJTbaseBasePtr, NBJTbaseBaseBinding, NBJTbaseNode, NBJTbaseNode); + CREATE_KLU_BINDING_TABLE(NBJTemitEmitPtr, NBJTemitEmitBinding, NBJTemitNode, NBJTemitNode); + CREATE_KLU_BINDING_TABLE(NBJTcolBasePtr, NBJTcolBaseBinding, NBJTcolNode, NBJTbaseNode); + CREATE_KLU_BINDING_TABLE(NBJTcolEmitPtr, NBJTcolEmitBinding, NBJTcolNode, NBJTemitNode); + CREATE_KLU_BINDING_TABLE(NBJTbaseColPtr, NBJTbaseColBinding, NBJTbaseNode, NBJTcolNode); + CREATE_KLU_BINDING_TABLE(NBJTbaseEmitPtr, NBJTbaseEmitBinding, NBJTbaseNode, NBJTemitNode); + CREATE_KLU_BINDING_TABLE(NBJTemitColPtr, NBJTemitColBinding, NBJTemitNode, NBJTcolNode); + CREATE_KLU_BINDING_TABLE(NBJTemitBasePtr, NBJTemitBaseBinding, NBJTemitNode, NBJTbaseNode); + } + } + + return (OK) ; +} + +int +NBJTbindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + NBJTmodel *model = (NBJTmodel *)inModel ; + NBJTinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the NBJT models */ + for ( ; model != NULL ; model = NBJTnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = NBJTinstances(model); here != NULL ; here = NBJTnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NBJTcolColPtr, NBJTcolColBinding, NBJTcolNode, NBJTcolNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NBJTbaseBasePtr, NBJTbaseBaseBinding, NBJTbaseNode, NBJTbaseNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NBJTemitEmitPtr, NBJTemitEmitBinding, NBJTemitNode, NBJTemitNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NBJTcolBasePtr, NBJTcolBaseBinding, NBJTcolNode, NBJTbaseNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NBJTcolEmitPtr, NBJTcolEmitBinding, NBJTcolNode, NBJTemitNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NBJTbaseColPtr, NBJTbaseColBinding, NBJTbaseNode, NBJTcolNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NBJTbaseEmitPtr, NBJTbaseEmitBinding, NBJTbaseNode, NBJTemitNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NBJTemitColPtr, NBJTemitColBinding, NBJTemitNode, NBJTcolNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NBJTemitBasePtr, NBJTemitBaseBinding, NBJTemitNode, NBJTbaseNode); + } + } + + return (OK) ; +} + +int +NBJTbindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + NBJTmodel *model = (NBJTmodel *)inModel ; + NBJTinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the NBJT models */ + for ( ; model != NULL ; model = NBJTnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = NBJTinstances(model); here != NULL ; here = NBJTnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(NBJTcolColPtr, NBJTcolColBinding, NBJTcolNode, NBJTcolNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NBJTbaseBasePtr, NBJTbaseBaseBinding, NBJTbaseNode, NBJTbaseNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NBJTemitEmitPtr, NBJTemitEmitBinding, NBJTemitNode, NBJTemitNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NBJTcolBasePtr, NBJTcolBaseBinding, NBJTcolNode, NBJTbaseNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NBJTcolEmitPtr, NBJTcolEmitBinding, NBJTcolNode, NBJTemitNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NBJTbaseColPtr, NBJTbaseColBinding, NBJTbaseNode, NBJTcolNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NBJTbaseEmitPtr, NBJTbaseEmitBinding, NBJTbaseNode, NBJTemitNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NBJTemitColPtr, NBJTemitColBinding, NBJTemitNode, NBJTcolNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NBJTemitBasePtr, NBJTemitBaseBinding, NBJTemitNode, NBJTbaseNode); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/nbjt/nbjtdefs.h b/src/spicelib/devices/nbjt/nbjtdefs.h index 730e3e48c..07a75aa63 100644 --- a/src/spicelib/devices/nbjt/nbjtdefs.h +++ b/src/spicelib/devices/nbjt/nbjtdefs.h @@ -83,6 +83,19 @@ typedef struct sNBJTinstance { unsigned NBJTicFileGiven:1; /* flag to indicate init. cond. file given */ unsigned NBJTprintGiven:1; /* flag to indicate if print was given */ unsigned NBJTtempGiven:1; /* flag to indicate if temp was given */ + +#ifdef KLU + BindElement *NBJTcolColBinding ; + BindElement *NBJTbaseBaseBinding ; + BindElement *NBJTemitEmitBinding ; + BindElement *NBJTcolBaseBinding ; + BindElement *NBJTcolEmitBinding ; + BindElement *NBJTbaseColBinding ; + BindElement *NBJTbaseEmitBinding ; + BindElement *NBJTemitColBinding ; + BindElement *NBJTemitBaseBinding ; +#endif + } NBJTinstance; /* per model data */ diff --git a/src/spicelib/devices/nbjt/nbjtext.h b/src/spicelib/devices/nbjt/nbjtext.h index d2dbf1923..3658f9c28 100644 --- a/src/spicelib/devices/nbjt/nbjtext.h +++ b/src/spicelib/devices/nbjt/nbjtext.h @@ -23,5 +23,10 @@ extern int NBJTtrunc(GENmodel *, CKTcircuit *, double *); extern void NBJTdump(GENmodel *, CKTcircuit *); extern void NBJTacct(GENmodel *, CKTcircuit *, FILE *); +#ifdef KLU +extern int NBJTbindCSC (GENmodel*, CKTcircuit*) ; +extern int NBJTbindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int NBJTbindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif #endif /* NBJT_H */ diff --git a/src/spicelib/devices/nbjt/nbjtinit.c b/src/spicelib/devices/nbjt/nbjtinit.c index af222ffe1..76112f56f 100644 --- a/src/spicelib/devices/nbjt/nbjtinit.c +++ b/src/spicelib/devices/nbjt/nbjtinit.c @@ -66,6 +66,11 @@ SPICEdev NBJTinfo = { .DEVdump = NBJTdump, .DEVacct = NBJTacct, #endif +#ifdef KLU + .DEVbindCSC = NBJTbindCSC, + .DEVbindCSCComplex = NBJTbindCSCComplex, + .DEVbindCSCComplexToReal = NBJTbindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/nbjt2/Makefile.am b/src/spicelib/devices/nbjt2/Makefile.am index 08ed45a07..22e262578 100644 --- a/src/spicelib/devices/nbjt2/Makefile.am +++ b/src/spicelib/devices/nbjt2/Makefile.am @@ -24,6 +24,9 @@ libnbjt2_la_SOURCES = \ nbt2trun.c +if KLU_WANTED +libnbjt2_la_SOURCES += nbjt2bindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) diff --git a/src/spicelib/devices/nbjt2/nbjt2bindCSC.c b/src/spicelib/devices/nbjt2/nbjt2bindCSC.c new file mode 100644 index 000000000..c77cef583 --- /dev/null +++ b/src/spicelib/devices/nbjt2/nbjt2bindCSC.c @@ -0,0 +1,113 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "nbjt2def.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +NBJT2bindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + NBJT2model *model = (NBJT2model *)inModel ; + NBJT2instance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the NBJT2 models */ + for ( ; model != NULL ; model = NBJT2nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = NBJT2instances(model); here != NULL ; here = NBJT2nextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(NBJT2colColPtr, NBJT2colColBinding, NBJT2colNode, NBJT2colNode); + CREATE_KLU_BINDING_TABLE(NBJT2colBasePtr, NBJT2colBaseBinding, NBJT2colNode, NBJT2baseNode); + CREATE_KLU_BINDING_TABLE(NBJT2colEmitPtr, NBJT2colEmitBinding, NBJT2colNode, NBJT2emitNode); + CREATE_KLU_BINDING_TABLE(NBJT2baseColPtr, NBJT2baseColBinding, NBJT2baseNode, NBJT2colNode); + CREATE_KLU_BINDING_TABLE(NBJT2baseBasePtr, NBJT2baseBaseBinding, NBJT2baseNode, NBJT2baseNode); + CREATE_KLU_BINDING_TABLE(NBJT2baseEmitPtr, NBJT2baseEmitBinding, NBJT2baseNode, NBJT2emitNode); + CREATE_KLU_BINDING_TABLE(NBJT2emitColPtr, NBJT2emitColBinding, NBJT2emitNode, NBJT2colNode); + CREATE_KLU_BINDING_TABLE(NBJT2emitBasePtr, NBJT2emitBaseBinding, NBJT2emitNode, NBJT2baseNode); + CREATE_KLU_BINDING_TABLE(NBJT2emitEmitPtr, NBJT2emitEmitBinding, NBJT2emitNode, NBJT2emitNode); + } + } + + return (OK) ; +} + +int +NBJT2bindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + NBJT2model *model = (NBJT2model *)inModel ; + NBJT2instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the NBJT2 models */ + for ( ; model != NULL ; model = NBJT2nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = NBJT2instances(model); here != NULL ; here = NBJT2nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NBJT2colColPtr, NBJT2colColBinding, NBJT2colNode, NBJT2colNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NBJT2colBasePtr, NBJT2colBaseBinding, NBJT2colNode, NBJT2baseNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NBJT2colEmitPtr, NBJT2colEmitBinding, NBJT2colNode, NBJT2emitNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NBJT2baseColPtr, NBJT2baseColBinding, NBJT2baseNode, NBJT2colNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NBJT2baseBasePtr, NBJT2baseBaseBinding, NBJT2baseNode, NBJT2baseNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NBJT2baseEmitPtr, NBJT2baseEmitBinding, NBJT2baseNode, NBJT2emitNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NBJT2emitColPtr, NBJT2emitColBinding, NBJT2emitNode, NBJT2colNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NBJT2emitBasePtr, NBJT2emitBaseBinding, NBJT2emitNode, NBJT2baseNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NBJT2emitEmitPtr, NBJT2emitEmitBinding, NBJT2emitNode, NBJT2emitNode); + } + } + + return (OK) ; +} + +int +NBJT2bindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + NBJT2model *model = (NBJT2model *)inModel ; + NBJT2instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the NBJT2 models */ + for ( ; model != NULL ; model = NBJT2nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = NBJT2instances(model); here != NULL ; here = NBJT2nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(NBJT2colColPtr, NBJT2colColBinding, NBJT2colNode, NBJT2colNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NBJT2colBasePtr, NBJT2colBaseBinding, NBJT2colNode, NBJT2baseNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NBJT2colEmitPtr, NBJT2colEmitBinding, NBJT2colNode, NBJT2emitNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NBJT2baseColPtr, NBJT2baseColBinding, NBJT2baseNode, NBJT2colNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NBJT2baseBasePtr, NBJT2baseBaseBinding, NBJT2baseNode, NBJT2baseNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NBJT2baseEmitPtr, NBJT2baseEmitBinding, NBJT2baseNode, NBJT2emitNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NBJT2emitColPtr, NBJT2emitColBinding, NBJT2emitNode, NBJT2colNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NBJT2emitBasePtr, NBJT2emitBaseBinding, NBJT2emitNode, NBJT2baseNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NBJT2emitEmitPtr, NBJT2emitEmitBinding, NBJT2emitNode, NBJT2emitNode); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/nbjt2/nbjt2def.h b/src/spicelib/devices/nbjt2/nbjt2def.h index d48d080d9..dc2f5b2f7 100644 --- a/src/spicelib/devices/nbjt2/nbjt2def.h +++ b/src/spicelib/devices/nbjt2/nbjt2def.h @@ -85,6 +85,19 @@ typedef struct sNBJT2instance { unsigned NBJT2icFileGiven:1; /* flag to indicate init. cond. file given */ unsigned NBJT2printGiven:1; /* flag to indicate print given */ unsigned NBJT2tempGiven:1; /* flag to indicate temp given */ + +#ifdef KLU + BindElement *NBJT2colColBinding ; + BindElement *NBJT2colBaseBinding ; + BindElement *NBJT2colEmitBinding ; + BindElement *NBJT2baseColBinding ; + BindElement *NBJT2baseBaseBinding ; + BindElement *NBJT2baseEmitBinding ; + BindElement *NBJT2emitColBinding ; + BindElement *NBJT2emitBaseBinding ; + BindElement *NBJT2emitEmitBinding ; +#endif + } NBJT2instance; /* per model data */ diff --git a/src/spicelib/devices/nbjt2/nbjt2ext.h b/src/spicelib/devices/nbjt2/nbjt2ext.h index f7d14d450..294f7a54d 100644 --- a/src/spicelib/devices/nbjt2/nbjt2ext.h +++ b/src/spicelib/devices/nbjt2/nbjt2ext.h @@ -24,4 +24,10 @@ extern int NBJT2trunc(GENmodel *, CKTcircuit *, double *); extern void NBJT2dump(GENmodel *, CKTcircuit *); extern void NBJT2acct(GENmodel *, CKTcircuit *, FILE *); +#ifdef KLU +extern int NBJT2bindCSC (GENmodel*, CKTcircuit*) ; +extern int NBJT2bindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int NBJT2bindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif + #endif /* NBJT2EXT_H */ diff --git a/src/spicelib/devices/nbjt2/nbt2init.c b/src/spicelib/devices/nbjt2/nbt2init.c index a0c9f8653..ff9913f73 100644 --- a/src/spicelib/devices/nbjt2/nbt2init.c +++ b/src/spicelib/devices/nbjt2/nbt2init.c @@ -66,6 +66,11 @@ SPICEdev NBJT2info = { .DEVdump = NBJT2dump, .DEVacct = NBJT2acct, #endif +#ifdef KLU + .DEVbindCSC = NBJT2bindCSC, + .DEVbindCSCComplex = NBJT2bindCSCComplex, + .DEVbindCSCComplexToReal = NBJT2bindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/ndev/ndevinit.c b/src/spicelib/devices/ndev/ndevinit.c index f65046905..922bb4310 100644 --- a/src/spicelib/devices/ndev/ndevinit.c +++ b/src/spicelib/devices/ndev/ndevinit.c @@ -66,6 +66,11 @@ SPICEdev NDEVinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = NULL, + .DEVbindCSCComplex = NULL, + .DEVbindCSCComplexToReal = NULL, +#endif }; diff --git a/src/spicelib/devices/numd/Makefile.am b/src/spicelib/devices/numd/Makefile.am index a9c263e89..9f6b19510 100644 --- a/src/spicelib/devices/numd/Makefile.am +++ b/src/spicelib/devices/numd/Makefile.am @@ -24,6 +24,10 @@ libnumd_la_SOURCES = \ numdtrun.c +if KLU_WANTED +libnumd_la_SOURCES += numdbindCSC.c +endif + AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) diff --git a/src/spicelib/devices/numd/numdbindCSC.c b/src/spicelib/devices/numd/numdbindCSC.c new file mode 100644 index 000000000..d19ef5feb --- /dev/null +++ b/src/spicelib/devices/numd/numdbindCSC.c @@ -0,0 +1,98 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "numddefs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +NUMDbindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + NUMDmodel *model = (NUMDmodel *)inModel ; + NUMDinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the NUMD models */ + for ( ; model != NULL ; model = NUMDnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = NUMDinstances(model); here != NULL ; here = NUMDnextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(NUMDposPosPtr, NUMDposPosBinding, NUMDposNode, NUMDposNode); + CREATE_KLU_BINDING_TABLE(NUMDnegNegPtr, NUMDnegNegBinding, NUMDnegNode, NUMDnegNode); + CREATE_KLU_BINDING_TABLE(NUMDnegPosPtr, NUMDnegPosBinding, NUMDnegNode, NUMDposNode); + CREATE_KLU_BINDING_TABLE(NUMDposNegPtr, NUMDposNegBinding, NUMDposNode, NUMDnegNode); + } + } + + return (OK) ; +} + +int +NUMDbindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + NUMDmodel *model = (NUMDmodel *)inModel ; + NUMDinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the NUMD models */ + for ( ; model != NULL ; model = NUMDnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = NUMDinstances(model); here != NULL ; here = NUMDnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NUMDposPosPtr, NUMDposPosBinding, NUMDposNode, NUMDposNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NUMDnegNegPtr, NUMDnegNegBinding, NUMDnegNode, NUMDnegNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NUMDnegPosPtr, NUMDnegPosBinding, NUMDnegNode, NUMDposNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NUMDposNegPtr, NUMDposNegBinding, NUMDposNode, NUMDnegNode); + } + } + + return (OK) ; +} + +int +NUMDbindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + NUMDmodel *model = (NUMDmodel *)inModel ; + NUMDinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the NUMD models */ + for ( ; model != NULL ; model = NUMDnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = NUMDinstances(model); here != NULL ; here = NUMDnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(NUMDposPosPtr, NUMDposPosBinding, NUMDposNode, NUMDposNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NUMDnegNegPtr, NUMDnegNegBinding, NUMDnegNode, NUMDnegNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NUMDnegPosPtr, NUMDnegPosBinding, NUMDnegNode, NUMDposNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NUMDposNegPtr, NUMDposNegBinding, NUMDposNode, NUMDnegNode); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/numd/numddefs.h b/src/spicelib/devices/numd/numddefs.h index f44640977..c67fd8494 100644 --- a/src/spicelib/devices/numd/numddefs.h +++ b/src/spicelib/devices/numd/numddefs.h @@ -63,6 +63,14 @@ typedef struct sNUMDinstance { unsigned NUMDicFileGiven:1; /* flag to indicate init. cond. file given */ unsigned NUMDtempGiven:1; /* flag to indicate temp was specified */ unsigned NUMDprintGiven:1; /* flag to indicate if print was specified */ + +#ifdef KLU + BindElement *NUMDposPosBinding ; + BindElement *NUMDnegNegBinding ; + BindElement *NUMDnegPosBinding ; + BindElement *NUMDposNegBinding ; +#endif + } NUMDinstance; diff --git a/src/spicelib/devices/numd/numdext.h b/src/spicelib/devices/numd/numdext.h index 27919c0ed..b90f31ce8 100644 --- a/src/spicelib/devices/numd/numdext.h +++ b/src/spicelib/devices/numd/numdext.h @@ -24,4 +24,10 @@ extern int NUMDtrunc(GENmodel *, CKTcircuit *, double *); extern void NUMDdump(GENmodel *, CKTcircuit *); extern void NUMDacct(GENmodel *, CKTcircuit *, FILE *); +#ifdef KLU +extern int NUMDbindCSC (GENmodel*, CKTcircuit*) ; +extern int NUMDbindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int NUMDbindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif + #endif /* NUMDEXT_H */ diff --git a/src/spicelib/devices/numd/numdinit.c b/src/spicelib/devices/numd/numdinit.c index bf036444a..09c7bd9e6 100644 --- a/src/spicelib/devices/numd/numdinit.c +++ b/src/spicelib/devices/numd/numdinit.c @@ -66,6 +66,11 @@ SPICEdev NUMDinfo = { .DEVdump = NUMDdump, .DEVacct = NUMDacct, #endif +#ifdef KLU + .DEVbindCSC = NUMDbindCSC, + .DEVbindCSCComplex = NUMDbindCSCComplex, + .DEVbindCSCComplexToReal = NUMDbindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/numd2/Makefile.am b/src/spicelib/devices/numd2/Makefile.am index d4734642b..bd0dd1cf2 100644 --- a/src/spicelib/devices/numd2/Makefile.am +++ b/src/spicelib/devices/numd2/Makefile.am @@ -24,6 +24,9 @@ libnumd2_la_SOURCES = \ nud2trun.c +if KLU_WANTED +libnumd2_la_SOURCES += numd2bindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) diff --git a/src/spicelib/devices/numd2/numd2bindCSC.c b/src/spicelib/devices/numd2/numd2bindCSC.c new file mode 100644 index 000000000..010a2fa6a --- /dev/null +++ b/src/spicelib/devices/numd2/numd2bindCSC.c @@ -0,0 +1,98 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "numd2def.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +NUMD2bindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + NUMD2model *model = (NUMD2model *)inModel ; + NUMD2instance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the NUMD2 models */ + for ( ; model != NULL ; model = NUMD2nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = NUMD2instances(model); here != NULL ; here = NUMD2nextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(NUMD2posPosPtr, NUMD2posPosBinding, NUMD2posNode, NUMD2posNode); + CREATE_KLU_BINDING_TABLE(NUMD2negNegPtr, NUMD2negNegBinding, NUMD2negNode, NUMD2negNode); + CREATE_KLU_BINDING_TABLE(NUMD2negPosPtr, NUMD2negPosBinding, NUMD2negNode, NUMD2posNode); + CREATE_KLU_BINDING_TABLE(NUMD2posNegPtr, NUMD2posNegBinding, NUMD2posNode, NUMD2negNode); + } + } + + return (OK) ; +} + +int +NUMD2bindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + NUMD2model *model = (NUMD2model *)inModel ; + NUMD2instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the NUMD2 models */ + for ( ; model != NULL ; model = NUMD2nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = NUMD2instances(model); here != NULL ; here = NUMD2nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NUMD2posPosPtr, NUMD2posPosBinding, NUMD2posNode, NUMD2posNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NUMD2negNegPtr, NUMD2negNegBinding, NUMD2negNode, NUMD2negNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NUMD2negPosPtr, NUMD2negPosBinding, NUMD2negNode, NUMD2posNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NUMD2posNegPtr, NUMD2posNegBinding, NUMD2posNode, NUMD2negNode); + } + } + + return (OK) ; +} + +int +NUMD2bindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + NUMD2model *model = (NUMD2model *)inModel ; + NUMD2instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the NUMD2 models */ + for ( ; model != NULL ; model = NUMD2nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = NUMD2instances(model); here != NULL ; here = NUMD2nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(NUMD2posPosPtr, NUMD2posPosBinding, NUMD2posNode, NUMD2posNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NUMD2negNegPtr, NUMD2negNegBinding, NUMD2negNode, NUMD2negNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NUMD2negPosPtr, NUMD2negPosBinding, NUMD2negNode, NUMD2posNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NUMD2posNegPtr, NUMD2posNegBinding, NUMD2posNode, NUMD2negNode); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/numd2/numd2def.h b/src/spicelib/devices/numd2/numd2def.h index 58742da00..1ac9bd9d9 100644 --- a/src/spicelib/devices/numd2/numd2def.h +++ b/src/spicelib/devices/numd2/numd2def.h @@ -65,6 +65,14 @@ typedef struct sNUMD2instance { unsigned NUMD2icFileGiven:1; /* flag to indicate init. cond. file given */ unsigned NUMD2tempGiven:1; /* flag to indicate temp was specified */ unsigned NUMD2printGiven:1; /* flag to indicate if print was specified */ + +#ifdef KLU + BindElement *NUMD2posPosBinding ; + BindElement *NUMD2negNegBinding ; + BindElement *NUMD2negPosBinding ; + BindElement *NUMD2posNegBinding ; +#endif + } NUMD2instance; diff --git a/src/spicelib/devices/numd2/numd2ext.h b/src/spicelib/devices/numd2/numd2ext.h index 50c986417..519201212 100644 --- a/src/spicelib/devices/numd2/numd2ext.h +++ b/src/spicelib/devices/numd2/numd2ext.h @@ -24,5 +24,10 @@ extern int NUMD2trunc(GENmodel *, CKTcircuit *, double *); extern void NUMD2dump(GENmodel *, CKTcircuit *); extern void NUMD2acct(GENmodel *, CKTcircuit *, FILE *); +#ifdef KLU +extern int NUMD2bindCSC (GENmodel*, CKTcircuit*) ; +extern int NUMD2bindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int NUMD2bindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif #endif /* NUMD2EXT_H */ diff --git a/src/spicelib/devices/numd2/numd2init.c b/src/spicelib/devices/numd2/numd2init.c index 9d22900b1..6aaf72ef5 100644 --- a/src/spicelib/devices/numd2/numd2init.c +++ b/src/spicelib/devices/numd2/numd2init.c @@ -66,6 +66,11 @@ SPICEdev NUMD2info = { .DEVdump = NUMD2dump, .DEVacct = NUMD2acct, #endif +#ifdef KLU + .DEVbindCSC = NUMD2bindCSC, + .DEVbindCSCComplex = NUMD2bindCSCComplex, + .DEVbindCSCComplexToReal = NUMD2bindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/numos/Makefile.am b/src/spicelib/devices/numos/Makefile.am index 0517f2552..4f7c315c8 100644 --- a/src/spicelib/devices/numos/Makefile.am +++ b/src/spicelib/devices/numos/Makefile.am @@ -24,6 +24,9 @@ libnumos_la_SOURCES = \ nummtrun.c +if KLU_WANTED +libnumos_la_SOURCES += numosbindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) diff --git a/src/spicelib/devices/numos/numosbindCSC.c b/src/spicelib/devices/numos/numosbindCSC.c new file mode 100644 index 000000000..9ebb76931 --- /dev/null +++ b/src/spicelib/devices/numos/numosbindCSC.c @@ -0,0 +1,134 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "numosdef.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +NUMOSbindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + NUMOSmodel *model = (NUMOSmodel *)inModel ; + NUMOSinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the NUMOS models */ + for ( ; model != NULL ; model = NUMOSnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = NUMOSinstances(model); here != NULL ; here = NUMOSnextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(NUMOSdrainDrainPtr, NUMOSdrainDrainBinding, NUMOSdrainNode, NUMOSdrainNode); + CREATE_KLU_BINDING_TABLE(NUMOSdrainSourcePtr, NUMOSdrainSourceBinding, NUMOSdrainNode, NUMOSsourceNode); + CREATE_KLU_BINDING_TABLE(NUMOSdrainGatePtr, NUMOSdrainGateBinding, NUMOSdrainNode, NUMOSgateNode); + CREATE_KLU_BINDING_TABLE(NUMOSdrainBulkPtr, NUMOSdrainBulkBinding, NUMOSdrainNode, NUMOSbulkNode); + CREATE_KLU_BINDING_TABLE(NUMOSsourceDrainPtr, NUMOSsourceDrainBinding, NUMOSsourceNode, NUMOSdrainNode); + CREATE_KLU_BINDING_TABLE(NUMOSsourceSourcePtr, NUMOSsourceSourceBinding, NUMOSsourceNode, NUMOSsourceNode); + CREATE_KLU_BINDING_TABLE(NUMOSsourceGatePtr, NUMOSsourceGateBinding, NUMOSsourceNode, NUMOSgateNode); + CREATE_KLU_BINDING_TABLE(NUMOSsourceBulkPtr, NUMOSsourceBulkBinding, NUMOSsourceNode, NUMOSbulkNode); + CREATE_KLU_BINDING_TABLE(NUMOSgateDrainPtr, NUMOSgateDrainBinding, NUMOSgateNode, NUMOSdrainNode); + CREATE_KLU_BINDING_TABLE(NUMOSgateSourcePtr, NUMOSgateSourceBinding, NUMOSgateNode, NUMOSsourceNode); + CREATE_KLU_BINDING_TABLE(NUMOSgateGatePtr, NUMOSgateGateBinding, NUMOSgateNode, NUMOSgateNode); + CREATE_KLU_BINDING_TABLE(NUMOSgateBulkPtr, NUMOSgateBulkBinding, NUMOSgateNode, NUMOSbulkNode); + CREATE_KLU_BINDING_TABLE(NUMOSbulkDrainPtr, NUMOSbulkDrainBinding, NUMOSbulkNode, NUMOSdrainNode); + CREATE_KLU_BINDING_TABLE(NUMOSbulkSourcePtr, NUMOSbulkSourceBinding, NUMOSbulkNode, NUMOSsourceNode); + CREATE_KLU_BINDING_TABLE(NUMOSbulkGatePtr, NUMOSbulkGateBinding, NUMOSbulkNode, NUMOSgateNode); + CREATE_KLU_BINDING_TABLE(NUMOSbulkBulkPtr, NUMOSbulkBulkBinding, NUMOSbulkNode, NUMOSbulkNode); + } + } + + return (OK) ; +} + +int +NUMOSbindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + NUMOSmodel *model = (NUMOSmodel *)inModel ; + NUMOSinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the NUMOS models */ + for ( ; model != NULL ; model = NUMOSnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = NUMOSinstances(model); here != NULL ; here = NUMOSnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NUMOSdrainDrainPtr, NUMOSdrainDrainBinding, NUMOSdrainNode, NUMOSdrainNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NUMOSdrainSourcePtr, NUMOSdrainSourceBinding, NUMOSdrainNode, NUMOSsourceNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NUMOSdrainGatePtr, NUMOSdrainGateBinding, NUMOSdrainNode, NUMOSgateNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NUMOSdrainBulkPtr, NUMOSdrainBulkBinding, NUMOSdrainNode, NUMOSbulkNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NUMOSsourceDrainPtr, NUMOSsourceDrainBinding, NUMOSsourceNode, NUMOSdrainNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NUMOSsourceSourcePtr, NUMOSsourceSourceBinding, NUMOSsourceNode, NUMOSsourceNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NUMOSsourceGatePtr, NUMOSsourceGateBinding, NUMOSsourceNode, NUMOSgateNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NUMOSsourceBulkPtr, NUMOSsourceBulkBinding, NUMOSsourceNode, NUMOSbulkNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NUMOSgateDrainPtr, NUMOSgateDrainBinding, NUMOSgateNode, NUMOSdrainNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NUMOSgateSourcePtr, NUMOSgateSourceBinding, NUMOSgateNode, NUMOSsourceNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NUMOSgateGatePtr, NUMOSgateGateBinding, NUMOSgateNode, NUMOSgateNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NUMOSgateBulkPtr, NUMOSgateBulkBinding, NUMOSgateNode, NUMOSbulkNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NUMOSbulkDrainPtr, NUMOSbulkDrainBinding, NUMOSbulkNode, NUMOSdrainNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NUMOSbulkSourcePtr, NUMOSbulkSourceBinding, NUMOSbulkNode, NUMOSsourceNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NUMOSbulkGatePtr, NUMOSbulkGateBinding, NUMOSbulkNode, NUMOSgateNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(NUMOSbulkBulkPtr, NUMOSbulkBulkBinding, NUMOSbulkNode, NUMOSbulkNode); + } + } + + return (OK) ; +} + +int +NUMOSbindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + NUMOSmodel *model = (NUMOSmodel *)inModel ; + NUMOSinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the NUMOS models */ + for ( ; model != NULL ; model = NUMOSnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = NUMOSinstances(model); here != NULL ; here = NUMOSnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(NUMOSdrainDrainPtr, NUMOSdrainDrainBinding, NUMOSdrainNode, NUMOSdrainNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NUMOSdrainSourcePtr, NUMOSdrainSourceBinding, NUMOSdrainNode, NUMOSsourceNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NUMOSdrainGatePtr, NUMOSdrainGateBinding, NUMOSdrainNode, NUMOSgateNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NUMOSdrainBulkPtr, NUMOSdrainBulkBinding, NUMOSdrainNode, NUMOSbulkNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NUMOSsourceDrainPtr, NUMOSsourceDrainBinding, NUMOSsourceNode, NUMOSdrainNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NUMOSsourceSourcePtr, NUMOSsourceSourceBinding, NUMOSsourceNode, NUMOSsourceNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NUMOSsourceGatePtr, NUMOSsourceGateBinding, NUMOSsourceNode, NUMOSgateNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NUMOSsourceBulkPtr, NUMOSsourceBulkBinding, NUMOSsourceNode, NUMOSbulkNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NUMOSgateDrainPtr, NUMOSgateDrainBinding, NUMOSgateNode, NUMOSdrainNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NUMOSgateSourcePtr, NUMOSgateSourceBinding, NUMOSgateNode, NUMOSsourceNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NUMOSgateGatePtr, NUMOSgateGateBinding, NUMOSgateNode, NUMOSgateNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NUMOSgateBulkPtr, NUMOSgateBulkBinding, NUMOSgateNode, NUMOSbulkNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NUMOSbulkDrainPtr, NUMOSbulkDrainBinding, NUMOSbulkNode, NUMOSdrainNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NUMOSbulkSourcePtr, NUMOSbulkSourceBinding, NUMOSbulkNode, NUMOSsourceNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NUMOSbulkGatePtr, NUMOSbulkGateBinding, NUMOSbulkNode, NUMOSgateNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(NUMOSbulkBulkPtr, NUMOSbulkBulkBinding, NUMOSbulkNode, NUMOSbulkNode); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/numos/numosdef.h b/src/spicelib/devices/numos/numosdef.h index 5a5b1ed5d..613841484 100644 --- a/src/spicelib/devices/numos/numosdef.h +++ b/src/spicelib/devices/numos/numosdef.h @@ -113,6 +113,26 @@ typedef struct sNUMOSinstance { unsigned NUMOSicFileGiven:1; /* flag to indicate init. cond. file given */ unsigned NUMOSprintGiven:1; /* flag to indicate print was given */ unsigned NUMOStempGiven:1; /* flag to indicate temp was given */ + +#ifdef KLU + BindElement *NUMOSdrainDrainBinding ; + BindElement *NUMOSdrainSourceBinding ; + BindElement *NUMOSdrainGateBinding ; + BindElement *NUMOSdrainBulkBinding ; + BindElement *NUMOSsourceDrainBinding ; + BindElement *NUMOSsourceSourceBinding ; + BindElement *NUMOSsourceGateBinding ; + BindElement *NUMOSsourceBulkBinding ; + BindElement *NUMOSgateDrainBinding ; + BindElement *NUMOSgateSourceBinding ; + BindElement *NUMOSgateGateBinding ; + BindElement *NUMOSgateBulkBinding ; + BindElement *NUMOSbulkDrainBinding ; + BindElement *NUMOSbulkSourceBinding ; + BindElement *NUMOSbulkGateBinding ; + BindElement *NUMOSbulkBulkBinding ; +#endif + } NUMOSinstance; /* per model data */ diff --git a/src/spicelib/devices/numos/numosext.h b/src/spicelib/devices/numos/numosext.h index db0975ffd..adff061ac 100644 --- a/src/spicelib/devices/numos/numosext.h +++ b/src/spicelib/devices/numos/numosext.h @@ -24,4 +24,10 @@ extern int NUMOStrunc(GENmodel *, CKTcircuit *, double *); extern void NUMOSdump(GENmodel *, CKTcircuit *); extern void NUMOSacct(GENmodel *, CKTcircuit *, FILE *); +#ifdef KLU +extern int NUMOSbindCSC (GENmodel*, CKTcircuit*) ; +extern int NUMOSbindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int NUMOSbindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif + #endif /* NUMOSEXT_H */ diff --git a/src/spicelib/devices/numos/numosinit.c b/src/spicelib/devices/numos/numosinit.c index ee1ef902d..d448ec41f 100644 --- a/src/spicelib/devices/numos/numosinit.c +++ b/src/spicelib/devices/numos/numosinit.c @@ -66,6 +66,11 @@ SPICEdev NUMOSinfo = { .DEVdump = NUMOSdump, .DEVacct = NUMOSacct, #endif +#ifdef KLU + .DEVbindCSC = NUMOSbindCSC, + .DEVbindCSCComplex = NUMOSbindCSCComplex, + .DEVbindCSCComplexToReal = NUMOSbindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/res/Makefile.am b/src/spicelib/devices/res/Makefile.am index ab746263d..c2fd893d9 100644 --- a/src/spicelib/devices/res/Makefile.am +++ b/src/spicelib/devices/res/Makefile.am @@ -28,7 +28,11 @@ libres_la_SOURCES = \ restemp.c +if KLU_WANTED +libres_la_SOURCES += resbindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) + MAINTAINERCLEANFILES = Makefile.in diff --git a/src/spicelib/devices/res/resbindCSC.c b/src/spicelib/devices/res/resbindCSC.c new file mode 100644 index 000000000..99a2b4c27 --- /dev/null +++ b/src/spicelib/devices/res/resbindCSC.c @@ -0,0 +1,98 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "resdefs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +RESbindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + RESmodel *model = (RESmodel *)inModel ; + RESinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the RES models */ + for ( ; model != NULL ; model = RESnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = RESinstances(model); here != NULL ; here = RESnextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(RESposPosPtr, RESposPosBinding, RESposNode, RESposNode); + CREATE_KLU_BINDING_TABLE(RESnegNegPtr, RESnegNegBinding, RESnegNode, RESnegNode); + CREATE_KLU_BINDING_TABLE(RESposNegPtr, RESposNegBinding, RESposNode, RESnegNode); + CREATE_KLU_BINDING_TABLE(RESnegPosPtr, RESnegPosBinding, RESnegNode, RESposNode); + } + } + + return (OK) ; +} + +int +RESbindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + RESmodel *model = (RESmodel *)inModel ; + RESinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the RES models */ + for ( ; model != NULL ; model = RESnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = RESinstances(model); here != NULL ; here = RESnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(RESposPosPtr, RESposPosBinding, RESposNode, RESposNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(RESnegNegPtr, RESnegNegBinding, RESnegNode, RESnegNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(RESposNegPtr, RESposNegBinding, RESposNode, RESnegNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(RESnegPosPtr, RESnegPosBinding, RESnegNode, RESposNode); + } + } + + return (OK) ; +} + +int +RESbindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + RESmodel *model = (RESmodel *)inModel ; + RESinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the RES models */ + for ( ; model != NULL ; model = RESnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = RESinstances(model); here != NULL ; here = RESnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(RESposPosPtr, RESposPosBinding, RESposNode, RESposNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(RESnegNegPtr, RESnegNegBinding, RESnegNode, RESnegNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(RESposNegPtr, RESposNegBinding, RESposNode, RESnegNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(RESnegPosPtr, RESnegPosBinding, RESnegNode, RESposNode); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/res/resdefs.h b/src/spicelib/devices/res/resdefs.h index 52cb7daca..b601d236f 100644 --- a/src/spicelib/devices/res/resdefs.h +++ b/src/spicelib/devices/res/resdefs.h @@ -88,6 +88,13 @@ typedef struct sRESinstance { double **RESnVar; #endif /* NONOISE */ +#ifdef KLU + BindElement *RESposPosBinding ; + BindElement *RESnegNegBinding ; + BindElement *RESposNegBinding ; + BindElement *RESnegPosBinding ; +#endif + } RESinstance ; diff --git a/src/spicelib/devices/res/resext.h b/src/spicelib/devices/res/resext.h index 31c1f3a90..36da842ae 100644 --- a/src/spicelib/devices/res/resext.h +++ b/src/spicelib/devices/res/resext.h @@ -21,3 +21,9 @@ extern int RESsetup(SMPmatrix*,GENmodel*,CKTcircuit*,int*); extern int REStemp(GENmodel*,CKTcircuit*); extern int RESnoise(int,int,GENmodel*,CKTcircuit*,Ndata*,double*); extern int RESsoaCheck(CKTcircuit *, GENmodel *); + +#ifdef KLU +extern int RESbindCSC (GENmodel*, CKTcircuit*) ; +extern int RESbindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int RESbindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/res/resinit.c b/src/spicelib/devices/res/resinit.c index 75dfc13be..739150d1b 100644 --- a/src/spicelib/devices/res/resinit.c +++ b/src/spicelib/devices/res/resinit.c @@ -66,6 +66,11 @@ SPICEdev RESinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = RESbindCSC, + .DEVbindCSCComplex = RESbindCSCComplex, + .DEVbindCSCComplexToReal = RESbindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/soi3/Makefile.am b/src/spicelib/devices/soi3/Makefile.am index 09b1591dd..4081c33fe 100644 --- a/src/spicelib/devices/soi3/Makefile.am +++ b/src/spicelib/devices/soi3/Makefile.am @@ -27,7 +27,11 @@ libsoi3_la_SOURCES = \ soi3trun.c +if KLU_WANTED +libsoi3_la_SOURCES += soi3bindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) + MAINTAINERCLEANFILES = Makefile.in diff --git a/src/spicelib/devices/soi3/soi3bindCSC.c b/src/spicelib/devices/soi3/soi3bindCSC.c new file mode 100644 index 000000000..78eca5d70 --- /dev/null +++ b/src/spicelib/devices/soi3/soi3bindCSC.c @@ -0,0 +1,311 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "soi3defs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +SOI3bindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + SOI3model *model = (SOI3model *)inModel ; + SOI3instance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the SOI3 models */ + for ( ; model != NULL ; model = SOI3nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = SOI3instances(model); here != NULL ; here = SOI3nextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(SOI3D_dPtr, SOI3D_dBinding, SOI3dNode, SOI3dNode); + CREATE_KLU_BINDING_TABLE(SOI3D_dpPtr, SOI3D_dpBinding, SOI3dNode, SOI3dNodePrime); + CREATE_KLU_BINDING_TABLE(SOI3DP_dPtr, SOI3DP_dBinding, SOI3dNodePrime, SOI3dNode); + CREATE_KLU_BINDING_TABLE(SOI3S_sPtr, SOI3S_sBinding, SOI3sNode, SOI3sNode); + CREATE_KLU_BINDING_TABLE(SOI3S_spPtr, SOI3S_spBinding, SOI3sNode, SOI3sNodePrime); + CREATE_KLU_BINDING_TABLE(SOI3SP_sPtr, SOI3SP_sBinding, SOI3sNodePrime, SOI3sNode); + CREATE_KLU_BINDING_TABLE(SOI3GF_gfPtr, SOI3GF_gfBinding, SOI3gfNode, SOI3gfNode); + CREATE_KLU_BINDING_TABLE(SOI3GF_gbPtr, SOI3GF_gbBinding, SOI3gfNode, SOI3gbNode); + CREATE_KLU_BINDING_TABLE(SOI3GF_dpPtr, SOI3GF_dpBinding, SOI3gfNode, SOI3dNodePrime); + CREATE_KLU_BINDING_TABLE(SOI3GF_spPtr, SOI3GF_spBinding, SOI3gfNode, SOI3sNodePrime); + CREATE_KLU_BINDING_TABLE(SOI3GF_bPtr, SOI3GF_bBinding, SOI3gfNode, SOI3bNode); + CREATE_KLU_BINDING_TABLE(SOI3GB_gfPtr, SOI3GB_gfBinding, SOI3gbNode, SOI3gfNode); + CREATE_KLU_BINDING_TABLE(SOI3GB_gbPtr, SOI3GB_gbBinding, SOI3gbNode, SOI3gbNode); + CREATE_KLU_BINDING_TABLE(SOI3GB_dpPtr, SOI3GB_dpBinding, SOI3gbNode, SOI3dNodePrime); + CREATE_KLU_BINDING_TABLE(SOI3GB_spPtr, SOI3GB_spBinding, SOI3gbNode, SOI3sNodePrime); + CREATE_KLU_BINDING_TABLE(SOI3GB_bPtr, SOI3GB_bBinding, SOI3gbNode, SOI3bNode); + CREATE_KLU_BINDING_TABLE(SOI3B_gfPtr, SOI3B_gfBinding, SOI3bNode, SOI3gfNode); + CREATE_KLU_BINDING_TABLE(SOI3B_gbPtr, SOI3B_gbBinding, SOI3bNode, SOI3gbNode); + CREATE_KLU_BINDING_TABLE(SOI3B_dpPtr, SOI3B_dpBinding, SOI3bNode, SOI3dNodePrime); + CREATE_KLU_BINDING_TABLE(SOI3B_spPtr, SOI3B_spBinding, SOI3bNode, SOI3sNodePrime); + CREATE_KLU_BINDING_TABLE(SOI3B_bPtr, SOI3B_bBinding, SOI3bNode, SOI3bNode); + CREATE_KLU_BINDING_TABLE(SOI3DP_gfPtr, SOI3DP_gfBinding, SOI3dNodePrime, SOI3gfNode); + CREATE_KLU_BINDING_TABLE(SOI3DP_gbPtr, SOI3DP_gbBinding, SOI3dNodePrime, SOI3gbNode); + CREATE_KLU_BINDING_TABLE(SOI3DP_dpPtr, SOI3DP_dpBinding, SOI3dNodePrime, SOI3dNodePrime); + CREATE_KLU_BINDING_TABLE(SOI3DP_spPtr, SOI3DP_spBinding, SOI3dNodePrime, SOI3sNodePrime); + CREATE_KLU_BINDING_TABLE(SOI3DP_bPtr, SOI3DP_bBinding, SOI3dNodePrime, SOI3bNode); + CREATE_KLU_BINDING_TABLE(SOI3SP_gfPtr, SOI3SP_gfBinding, SOI3sNodePrime, SOI3gfNode); + CREATE_KLU_BINDING_TABLE(SOI3SP_gbPtr, SOI3SP_gbBinding, SOI3sNodePrime, SOI3gbNode); + CREATE_KLU_BINDING_TABLE(SOI3SP_dpPtr, SOI3SP_dpBinding, SOI3sNodePrime, SOI3dNodePrime); + CREATE_KLU_BINDING_TABLE(SOI3SP_spPtr, SOI3SP_spBinding, SOI3sNodePrime, SOI3sNodePrime); + CREATE_KLU_BINDING_TABLE(SOI3SP_bPtr, SOI3SP_bBinding, SOI3sNodePrime, SOI3bNode); + if (here->SOI3rt == 0) + { + CREATE_KLU_BINDING_TABLE(SOI3TOUT_ibrPtr, SOI3TOUT_ibrBinding, SOI3toutNode, SOI3branch); + CREATE_KLU_BINDING_TABLE(SOI3IBR_toutPtr, SOI3IBR_toutBinding, SOI3branch, SOI3toutNode); + } + else + { + CREATE_KLU_BINDING_TABLE(SOI3TOUT_toutPtr, SOI3TOUT_toutBinding, SOI3toutNode, SOI3toutNode); + if (here->SOI3numThermalNodes > 1) + { + CREATE_KLU_BINDING_TABLE(SOI3TOUT_tout1Ptr, SOI3TOUT_tout1Binding, SOI3toutNode, SOI3tout1Node); + CREATE_KLU_BINDING_TABLE(SOI3TOUT1_toutPtr, SOI3TOUT1_toutBinding, SOI3tout1Node, SOI3toutNode); + CREATE_KLU_BINDING_TABLE(SOI3TOUT1_tout1Ptr, SOI3TOUT1_tout1Binding, SOI3tout1Node, SOI3tout1Node); + } + if (here->SOI3numThermalNodes > 2) + { + CREATE_KLU_BINDING_TABLE(SOI3TOUT1_tout2Ptr, SOI3TOUT1_tout2Binding, SOI3tout1Node, SOI3tout2Node); + CREATE_KLU_BINDING_TABLE(SOI3TOUT2_tout1Ptr, SOI3TOUT2_tout1Binding, SOI3tout2Node, SOI3tout1Node); + CREATE_KLU_BINDING_TABLE(SOI3TOUT2_tout2Ptr, SOI3TOUT2_tout2Binding, SOI3tout2Node, SOI3tout2Node); + } + if (here->SOI3numThermalNodes > 3) + { + CREATE_KLU_BINDING_TABLE(SOI3TOUT2_tout3Ptr, SOI3TOUT2_tout3Binding, SOI3tout2Node, SOI3tout3Node); + CREATE_KLU_BINDING_TABLE(SOI3TOUT3_tout2Ptr, SOI3TOUT3_tout2Binding, SOI3tout3Node, SOI3tout2Node); + CREATE_KLU_BINDING_TABLE(SOI3TOUT3_tout3Ptr, SOI3TOUT3_tout3Binding, SOI3tout3Node, SOI3tout3Node); + } + if (here->SOI3numThermalNodes > 4) + { + CREATE_KLU_BINDING_TABLE(SOI3TOUT3_tout4Ptr, SOI3TOUT3_tout4Binding, SOI3tout3Node, SOI3tout4Node); + CREATE_KLU_BINDING_TABLE(SOI3TOUT4_tout3Ptr, SOI3TOUT4_tout3Binding, SOI3tout4Node, SOI3tout3Node); + CREATE_KLU_BINDING_TABLE(SOI3TOUT4_tout4Ptr, SOI3TOUT4_tout4Binding, SOI3tout4Node, SOI3tout4Node); + } + CREATE_KLU_BINDING_TABLE(SOI3TOUT_toutPtr, SOI3TOUT_toutBinding, SOI3toutNode, SOI3toutNode); + CREATE_KLU_BINDING_TABLE(SOI3TOUT_gfPtr, SOI3TOUT_gfBinding, SOI3toutNode, SOI3gfNode); + CREATE_KLU_BINDING_TABLE(SOI3TOUT_gbPtr, SOI3TOUT_gbBinding, SOI3toutNode, SOI3gbNode); + CREATE_KLU_BINDING_TABLE(SOI3TOUT_dpPtr, SOI3TOUT_dpBinding, SOI3toutNode, SOI3dNodePrime); + CREATE_KLU_BINDING_TABLE(SOI3TOUT_spPtr, SOI3TOUT_spBinding, SOI3toutNode, SOI3sNodePrime); + CREATE_KLU_BINDING_TABLE(SOI3TOUT_bPtr, SOI3TOUT_bBinding, SOI3toutNode, SOI3bNode); + CREATE_KLU_BINDING_TABLE(SOI3GF_toutPtr, SOI3GF_toutBinding, SOI3gfNode, SOI3toutNode); + CREATE_KLU_BINDING_TABLE(SOI3GB_toutPtr, SOI3GB_toutBinding, SOI3gbNode, SOI3toutNode); + CREATE_KLU_BINDING_TABLE(SOI3DP_toutPtr, SOI3DP_toutBinding, SOI3dNodePrime, SOI3toutNode); + CREATE_KLU_BINDING_TABLE(SOI3SP_toutPtr, SOI3SP_toutBinding, SOI3sNodePrime, SOI3toutNode); + CREATE_KLU_BINDING_TABLE(SOI3B_toutPtr, SOI3B_toutBinding, SOI3bNode, SOI3toutNode); + } + } + } + + return (OK) ; +} + +int +SOI3bindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + SOI3model *model = (SOI3model *)inModel ; + SOI3instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the SOI3 models */ + for ( ; model != NULL ; model = SOI3nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = SOI3instances(model); here != NULL ; here = SOI3nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3D_dPtr, SOI3D_dBinding, SOI3dNode, SOI3dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3D_dpPtr, SOI3D_dpBinding, SOI3dNode, SOI3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3DP_dPtr, SOI3DP_dBinding, SOI3dNodePrime, SOI3dNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3S_sPtr, SOI3S_sBinding, SOI3sNode, SOI3sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3S_spPtr, SOI3S_spBinding, SOI3sNode, SOI3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3SP_sPtr, SOI3SP_sBinding, SOI3sNodePrime, SOI3sNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3GF_gfPtr, SOI3GF_gfBinding, SOI3gfNode, SOI3gfNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3GF_gbPtr, SOI3GF_gbBinding, SOI3gfNode, SOI3gbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3GF_dpPtr, SOI3GF_dpBinding, SOI3gfNode, SOI3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3GF_spPtr, SOI3GF_spBinding, SOI3gfNode, SOI3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3GF_bPtr, SOI3GF_bBinding, SOI3gfNode, SOI3bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3GB_gfPtr, SOI3GB_gfBinding, SOI3gbNode, SOI3gfNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3GB_gbPtr, SOI3GB_gbBinding, SOI3gbNode, SOI3gbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3GB_dpPtr, SOI3GB_dpBinding, SOI3gbNode, SOI3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3GB_spPtr, SOI3GB_spBinding, SOI3gbNode, SOI3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3GB_bPtr, SOI3GB_bBinding, SOI3gbNode, SOI3bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3B_gfPtr, SOI3B_gfBinding, SOI3bNode, SOI3gfNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3B_gbPtr, SOI3B_gbBinding, SOI3bNode, SOI3gbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3B_dpPtr, SOI3B_dpBinding, SOI3bNode, SOI3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3B_spPtr, SOI3B_spBinding, SOI3bNode, SOI3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3B_bPtr, SOI3B_bBinding, SOI3bNode, SOI3bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3DP_gfPtr, SOI3DP_gfBinding, SOI3dNodePrime, SOI3gfNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3DP_gbPtr, SOI3DP_gbBinding, SOI3dNodePrime, SOI3gbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3DP_dpPtr, SOI3DP_dpBinding, SOI3dNodePrime, SOI3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3DP_spPtr, SOI3DP_spBinding, SOI3dNodePrime, SOI3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3DP_bPtr, SOI3DP_bBinding, SOI3dNodePrime, SOI3bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3SP_gfPtr, SOI3SP_gfBinding, SOI3sNodePrime, SOI3gfNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3SP_gbPtr, SOI3SP_gbBinding, SOI3sNodePrime, SOI3gbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3SP_dpPtr, SOI3SP_dpBinding, SOI3sNodePrime, SOI3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3SP_spPtr, SOI3SP_spBinding, SOI3sNodePrime, SOI3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3SP_bPtr, SOI3SP_bBinding, SOI3sNodePrime, SOI3bNode); + if (here->SOI3rt == 0) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3TOUT_ibrPtr, SOI3TOUT_ibrBinding, SOI3toutNode, SOI3branch); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3IBR_toutPtr, SOI3IBR_toutBinding, SOI3branch, SOI3toutNode); + } + else + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3TOUT_toutPtr, SOI3TOUT_toutBinding, SOI3toutNode, SOI3toutNode); + if (here->SOI3numThermalNodes > 1) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3TOUT_tout1Ptr, SOI3TOUT_tout1Binding, SOI3toutNode, SOI3tout1Node); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3TOUT1_toutPtr, SOI3TOUT1_toutBinding, SOI3tout1Node, SOI3toutNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3TOUT1_tout1Ptr, SOI3TOUT1_tout1Binding, SOI3tout1Node, SOI3tout1Node); + } + if (here->SOI3numThermalNodes > 2) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3TOUT1_tout2Ptr, SOI3TOUT1_tout2Binding, SOI3tout1Node, SOI3tout2Node); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3TOUT2_tout1Ptr, SOI3TOUT2_tout1Binding, SOI3tout2Node, SOI3tout1Node); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3TOUT2_tout2Ptr, SOI3TOUT2_tout2Binding, SOI3tout2Node, SOI3tout2Node); + } + if (here->SOI3numThermalNodes > 3) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3TOUT2_tout3Ptr, SOI3TOUT2_tout3Binding, SOI3tout2Node, SOI3tout3Node); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3TOUT3_tout2Ptr, SOI3TOUT3_tout2Binding, SOI3tout3Node, SOI3tout2Node); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3TOUT3_tout3Ptr, SOI3TOUT3_tout3Binding, SOI3tout3Node, SOI3tout3Node); + } + if (here->SOI3numThermalNodes > 4) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3TOUT3_tout4Ptr, SOI3TOUT3_tout4Binding, SOI3tout3Node, SOI3tout4Node); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3TOUT4_tout3Ptr, SOI3TOUT4_tout3Binding, SOI3tout4Node, SOI3tout3Node); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3TOUT4_tout4Ptr, SOI3TOUT4_tout4Binding, SOI3tout4Node, SOI3tout4Node); + } + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3TOUT_toutPtr, SOI3TOUT_toutBinding, SOI3toutNode, SOI3toutNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3TOUT_gfPtr, SOI3TOUT_gfBinding, SOI3toutNode, SOI3gfNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3TOUT_gbPtr, SOI3TOUT_gbBinding, SOI3toutNode, SOI3gbNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3TOUT_dpPtr, SOI3TOUT_dpBinding, SOI3toutNode, SOI3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3TOUT_spPtr, SOI3TOUT_spBinding, SOI3toutNode, SOI3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3TOUT_bPtr, SOI3TOUT_bBinding, SOI3toutNode, SOI3bNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3GF_toutPtr, SOI3GF_toutBinding, SOI3gfNode, SOI3toutNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3GB_toutPtr, SOI3GB_toutBinding, SOI3gbNode, SOI3toutNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3DP_toutPtr, SOI3DP_toutBinding, SOI3dNodePrime, SOI3toutNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3SP_toutPtr, SOI3SP_toutBinding, SOI3sNodePrime, SOI3toutNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SOI3B_toutPtr, SOI3B_toutBinding, SOI3bNode, SOI3toutNode); + } + } + } + + return (OK) ; +} + +int +SOI3bindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + SOI3model *model = (SOI3model *)inModel ; + SOI3instance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the SOI3 models */ + for ( ; model != NULL ; model = SOI3nextModel(model)) + { + /* loop through all the instances of the model */ + for (here = SOI3instances(model); here != NULL ; here = SOI3nextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3D_dPtr, SOI3D_dBinding, SOI3dNode, SOI3dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3D_dpPtr, SOI3D_dpBinding, SOI3dNode, SOI3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3DP_dPtr, SOI3DP_dBinding, SOI3dNodePrime, SOI3dNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3S_sPtr, SOI3S_sBinding, SOI3sNode, SOI3sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3S_spPtr, SOI3S_spBinding, SOI3sNode, SOI3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3SP_sPtr, SOI3SP_sBinding, SOI3sNodePrime, SOI3sNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3GF_gfPtr, SOI3GF_gfBinding, SOI3gfNode, SOI3gfNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3GF_gbPtr, SOI3GF_gbBinding, SOI3gfNode, SOI3gbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3GF_dpPtr, SOI3GF_dpBinding, SOI3gfNode, SOI3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3GF_spPtr, SOI3GF_spBinding, SOI3gfNode, SOI3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3GF_bPtr, SOI3GF_bBinding, SOI3gfNode, SOI3bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3GB_gfPtr, SOI3GB_gfBinding, SOI3gbNode, SOI3gfNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3GB_gbPtr, SOI3GB_gbBinding, SOI3gbNode, SOI3gbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3GB_dpPtr, SOI3GB_dpBinding, SOI3gbNode, SOI3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3GB_spPtr, SOI3GB_spBinding, SOI3gbNode, SOI3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3GB_bPtr, SOI3GB_bBinding, SOI3gbNode, SOI3bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3B_gfPtr, SOI3B_gfBinding, SOI3bNode, SOI3gfNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3B_gbPtr, SOI3B_gbBinding, SOI3bNode, SOI3gbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3B_dpPtr, SOI3B_dpBinding, SOI3bNode, SOI3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3B_spPtr, SOI3B_spBinding, SOI3bNode, SOI3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3B_bPtr, SOI3B_bBinding, SOI3bNode, SOI3bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3DP_gfPtr, SOI3DP_gfBinding, SOI3dNodePrime, SOI3gfNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3DP_gbPtr, SOI3DP_gbBinding, SOI3dNodePrime, SOI3gbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3DP_dpPtr, SOI3DP_dpBinding, SOI3dNodePrime, SOI3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3DP_spPtr, SOI3DP_spBinding, SOI3dNodePrime, SOI3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3DP_bPtr, SOI3DP_bBinding, SOI3dNodePrime, SOI3bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3SP_gfPtr, SOI3SP_gfBinding, SOI3sNodePrime, SOI3gfNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3SP_gbPtr, SOI3SP_gbBinding, SOI3sNodePrime, SOI3gbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3SP_dpPtr, SOI3SP_dpBinding, SOI3sNodePrime, SOI3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3SP_spPtr, SOI3SP_spBinding, SOI3sNodePrime, SOI3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3SP_bPtr, SOI3SP_bBinding, SOI3sNodePrime, SOI3bNode); + if (here->SOI3rt == 0) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3TOUT_ibrPtr, SOI3TOUT_ibrBinding, SOI3toutNode, SOI3branch); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3IBR_toutPtr, SOI3IBR_toutBinding, SOI3branch, SOI3toutNode); + } + else + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3TOUT_toutPtr, SOI3TOUT_toutBinding, SOI3toutNode, SOI3toutNode); + if (here->SOI3numThermalNodes > 1) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3TOUT_tout1Ptr, SOI3TOUT_tout1Binding, SOI3toutNode, SOI3tout1Node); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3TOUT1_toutPtr, SOI3TOUT1_toutBinding, SOI3tout1Node, SOI3toutNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3TOUT1_tout1Ptr, SOI3TOUT1_tout1Binding, SOI3tout1Node, SOI3tout1Node); + } + if (here->SOI3numThermalNodes > 2) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3TOUT1_tout2Ptr, SOI3TOUT1_tout2Binding, SOI3tout1Node, SOI3tout2Node); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3TOUT2_tout1Ptr, SOI3TOUT2_tout1Binding, SOI3tout2Node, SOI3tout1Node); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3TOUT2_tout2Ptr, SOI3TOUT2_tout2Binding, SOI3tout2Node, SOI3tout2Node); + } + if (here->SOI3numThermalNodes > 3) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3TOUT2_tout3Ptr, SOI3TOUT2_tout3Binding, SOI3tout2Node, SOI3tout3Node); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3TOUT3_tout2Ptr, SOI3TOUT3_tout2Binding, SOI3tout3Node, SOI3tout2Node); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3TOUT3_tout3Ptr, SOI3TOUT3_tout3Binding, SOI3tout3Node, SOI3tout3Node); + } + if (here->SOI3numThermalNodes > 4) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3TOUT3_tout4Ptr, SOI3TOUT3_tout4Binding, SOI3tout3Node, SOI3tout4Node); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3TOUT4_tout3Ptr, SOI3TOUT4_tout3Binding, SOI3tout4Node, SOI3tout3Node); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3TOUT4_tout4Ptr, SOI3TOUT4_tout4Binding, SOI3tout4Node, SOI3tout4Node); + } + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3TOUT_toutPtr, SOI3TOUT_toutBinding, SOI3toutNode, SOI3toutNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3TOUT_gfPtr, SOI3TOUT_gfBinding, SOI3toutNode, SOI3gfNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3TOUT_gbPtr, SOI3TOUT_gbBinding, SOI3toutNode, SOI3gbNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3TOUT_dpPtr, SOI3TOUT_dpBinding, SOI3toutNode, SOI3dNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3TOUT_spPtr, SOI3TOUT_spBinding, SOI3toutNode, SOI3sNodePrime); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3TOUT_bPtr, SOI3TOUT_bBinding, SOI3toutNode, SOI3bNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3GF_toutPtr, SOI3GF_toutBinding, SOI3gfNode, SOI3toutNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3GB_toutPtr, SOI3GB_toutBinding, SOI3gbNode, SOI3toutNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3DP_toutPtr, SOI3DP_toutBinding, SOI3dNodePrime, SOI3toutNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3SP_toutPtr, SOI3SP_toutBinding, SOI3sNodePrime, SOI3toutNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SOI3B_toutPtr, SOI3B_toutBinding, SOI3bNode, SOI3toutNode); + } + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/soi3/soi3defs.h b/src/spicelib/devices/soi3/soi3defs.h index 77be8b355..465597cf8 100644 --- a/src/spicelib/devices/soi3/soi3defs.h +++ b/src/spicelib/devices/soi3/soi3defs.h @@ -321,6 +321,65 @@ typedef struct sSOI3instance { double **SOI3nVar; #endif /* NONOISE */ +#ifdef KLU + BindElement *SOI3D_dBinding ; + BindElement *SOI3D_dpBinding ; + BindElement *SOI3DP_dBinding ; + BindElement *SOI3S_sBinding ; + BindElement *SOI3S_spBinding ; + BindElement *SOI3SP_sBinding ; + BindElement *SOI3GF_gfBinding ; + BindElement *SOI3GF_gbBinding ; + BindElement *SOI3GF_dpBinding ; + BindElement *SOI3GF_spBinding ; + BindElement *SOI3GF_bBinding ; + BindElement *SOI3GB_gfBinding ; + BindElement *SOI3GB_gbBinding ; + BindElement *SOI3GB_dpBinding ; + BindElement *SOI3GB_spBinding ; + BindElement *SOI3GB_bBinding ; + BindElement *SOI3B_gfBinding ; + BindElement *SOI3B_gbBinding ; + BindElement *SOI3B_dpBinding ; + BindElement *SOI3B_spBinding ; + BindElement *SOI3B_bBinding ; + BindElement *SOI3DP_gfBinding ; + BindElement *SOI3DP_gbBinding ; + BindElement *SOI3DP_dpBinding ; + BindElement *SOI3DP_spBinding ; + BindElement *SOI3DP_bBinding ; + BindElement *SOI3SP_gfBinding ; + BindElement *SOI3SP_gbBinding ; + BindElement *SOI3SP_dpBinding ; + BindElement *SOI3SP_spBinding ; + BindElement *SOI3SP_bBinding ; + BindElement *SOI3TOUT_ibrBinding ; + BindElement *SOI3IBR_toutBinding ; + BindElement *SOI3TOUT_toutBinding ; + BindElement *SOI3TOUT_tout1Binding ; + BindElement *SOI3TOUT1_toutBinding ; + BindElement *SOI3TOUT1_tout1Binding ; + BindElement *SOI3TOUT1_tout2Binding ; + BindElement *SOI3TOUT2_tout1Binding ; + BindElement *SOI3TOUT2_tout2Binding ; + BindElement *SOI3TOUT2_tout3Binding ; + BindElement *SOI3TOUT3_tout2Binding ; + BindElement *SOI3TOUT3_tout3Binding ; + BindElement *SOI3TOUT3_tout4Binding ; + BindElement *SOI3TOUT4_tout3Binding ; + BindElement *SOI3TOUT4_tout4Binding ; + BindElement *SOI3TOUT_gfBinding ; + BindElement *SOI3TOUT_gbBinding ; + BindElement *SOI3TOUT_dpBinding ; + BindElement *SOI3TOUT_spBinding ; + BindElement *SOI3TOUT_bBinding ; + BindElement *SOI3GF_toutBinding ; + BindElement *SOI3GB_toutBinding ; + BindElement *SOI3DP_toutBinding ; + BindElement *SOI3SP_toutBinding ; + BindElement *SOI3B_toutBinding ; +#endif + } SOI3instance ; #define SOI3vbd SOI3states+ 0 /* bulk-drain voltage */ diff --git a/src/spicelib/devices/soi3/soi3ext.h b/src/spicelib/devices/soi3/soi3ext.h index 75f0f2a24..d54c28e0b 100644 --- a/src/spicelib/devices/soi3/soi3ext.h +++ b/src/spicelib/devices/soi3/soi3ext.h @@ -65,3 +65,9 @@ extern int SOI3convTest(GENmodel*,CKTcircuit*); /* extern int SOI3disto(int,GENmodel*,CKTcircuit*); */ extern int SOI3noise(int,int,GENmodel*,CKTcircuit*,Ndata*,double*); + +#ifdef KLU +extern int SOI3bindCSC (GENmodel*, CKTcircuit*) ; +extern int SOI3bindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int SOI3bindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/soi3/soi3init.c b/src/spicelib/devices/soi3/soi3init.c index cb60a76ed..93d748e3d 100644 --- a/src/spicelib/devices/soi3/soi3init.c +++ b/src/spicelib/devices/soi3/soi3init.c @@ -66,6 +66,11 @@ SPICEdev SOI3info = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = SOI3bindCSC, + .DEVbindCSCComplex = SOI3bindCSCComplex, + .DEVbindCSCComplexToReal = SOI3bindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/sw/Makefile.am b/src/spicelib/devices/sw/Makefile.am index 445c1a790..6451924ba 100644 --- a/src/spicelib/devices/sw/Makefile.am +++ b/src/spicelib/devices/sw/Makefile.am @@ -24,7 +24,11 @@ libsw_la_SOURCES = \ swtrunc.c +if KLU_WANTED +libsw_la_SOURCES += swbindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) + MAINTAINERCLEANFILES = Makefile.in diff --git a/src/spicelib/devices/sw/swbindCSC.c b/src/spicelib/devices/sw/swbindCSC.c new file mode 100644 index 000000000..767630fed --- /dev/null +++ b/src/spicelib/devices/sw/swbindCSC.c @@ -0,0 +1,98 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "swdefs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +SWbindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + SWmodel *model = (SWmodel *)inModel ; + SWinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the SW models */ + for ( ; model != NULL ; model = SWnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = SWinstances(model); here != NULL ; here = SWnextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(SWposPosPtr, SWposPosBinding, SWposNode, SWposNode); + CREATE_KLU_BINDING_TABLE(SWposNegPtr, SWposNegBinding, SWposNode, SWnegNode); + CREATE_KLU_BINDING_TABLE(SWnegPosPtr, SWnegPosBinding, SWnegNode, SWposNode); + CREATE_KLU_BINDING_TABLE(SWnegNegPtr, SWnegNegBinding, SWnegNode, SWnegNode); + } + } + + return (OK) ; +} + +int +SWbindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + SWmodel *model = (SWmodel *)inModel ; + SWinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the SW models */ + for ( ; model != NULL ; model = SWnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = SWinstances(model); here != NULL ; here = SWnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SWposPosPtr, SWposPosBinding, SWposNode, SWposNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SWposNegPtr, SWposNegBinding, SWposNode, SWnegNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SWnegPosPtr, SWnegPosBinding, SWnegNode, SWposNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(SWnegNegPtr, SWnegNegBinding, SWnegNode, SWnegNode); + } + } + + return (OK) ; +} + +int +SWbindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + SWmodel *model = (SWmodel *)inModel ; + SWinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the SW models */ + for ( ; model != NULL ; model = SWnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = SWinstances(model); here != NULL ; here = SWnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(SWposPosPtr, SWposPosBinding, SWposNode, SWposNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SWposNegPtr, SWposNegBinding, SWposNode, SWnegNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SWnegPosPtr, SWnegPosBinding, SWnegNode, SWposNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(SWnegNegPtr, SWnegNegBinding, SWnegNode, SWnegNode); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/sw/swdefs.h b/src/spicelib/devices/sw/swdefs.h index 4e73cc4e4..b22f12e6d 100644 --- a/src/spicelib/devices/sw/swdefs.h +++ b/src/spicelib/devices/sw/swdefs.h @@ -49,6 +49,14 @@ typedef struct sSWinstance { #else /* NONOISE */ double *SWnVar; #endif /* NONOISE */ + +#ifdef KLU + BindElement *SWposPosBinding ; + BindElement *SWposNegBinding ; + BindElement *SWnegPosBinding ; + BindElement *SWnegNegBinding ; +#endif + } SWinstance ; /* data per model */ diff --git a/src/spicelib/devices/sw/swext.h b/src/spicelib/devices/sw/swext.h index c134a2c58..2bcdf57d8 100644 --- a/src/spicelib/devices/sw/swext.h +++ b/src/spicelib/devices/sw/swext.h @@ -17,3 +17,9 @@ extern int SWpzLoad(GENmodel*,CKTcircuit*,SPcomplex*); extern int SWsetup(SMPmatrix*,GENmodel*,CKTcircuit*,int*); extern int SWnoise(int,int,GENmodel*,CKTcircuit*,Ndata*,double*); extern int SWtrunc(GENmodel*,CKTcircuit*,double*); + +#ifdef KLU +extern int SWbindCSC (GENmodel*, CKTcircuit*) ; +extern int SWbindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int SWbindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/sw/swinit.c b/src/spicelib/devices/sw/swinit.c index 1222545f1..b3bf4e2d5 100644 --- a/src/spicelib/devices/sw/swinit.c +++ b/src/spicelib/devices/sw/swinit.c @@ -67,6 +67,11 @@ SPICEdev SWinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = SWbindCSC, + .DEVbindCSCComplex = SWbindCSCComplex, + .DEVbindCSCComplexToReal = SWbindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/tra/Makefile.am b/src/spicelib/devices/tra/Makefile.am index de708838f..5fb0a2eeb 100644 --- a/src/spicelib/devices/tra/Makefile.am +++ b/src/spicelib/devices/tra/Makefile.am @@ -22,6 +22,11 @@ libtra_la_SOURCES = \ tratrunc.c +if KLU_WANTED +libtra_la_SOURCES += trabindCSC.c +endif + AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) + MAINTAINERCLEANFILES = Makefile.in diff --git a/src/spicelib/devices/tra/trabindCSC.c b/src/spicelib/devices/tra/trabindCSC.c new file mode 100644 index 000000000..b15459d6d --- /dev/null +++ b/src/spicelib/devices/tra/trabindCSC.c @@ -0,0 +1,152 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "tradefs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +TRAbindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + TRAmodel *model = (TRAmodel *)inModel ; + TRAinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the TRA models */ + for ( ; model != NULL ; model = TRAnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = TRAinstances(model); here != NULL ; here = TRAnextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(TRAibr1Ibr2Ptr, TRAibr1Ibr2Binding, TRAbrEq1, TRAbrEq2); + CREATE_KLU_BINDING_TABLE(TRAibr1Int1Ptr, TRAibr1Int1Binding, TRAbrEq1, TRAintNode1); + CREATE_KLU_BINDING_TABLE(TRAibr1Neg1Ptr, TRAibr1Neg1Binding, TRAbrEq1, TRAnegNode1); + CREATE_KLU_BINDING_TABLE(TRAibr1Neg2Ptr, TRAibr1Neg2Binding, TRAbrEq1, TRAnegNode2); + CREATE_KLU_BINDING_TABLE(TRAibr1Pos2Ptr, TRAibr1Pos2Binding, TRAbrEq1, TRAposNode2); + CREATE_KLU_BINDING_TABLE(TRAibr2Ibr1Ptr, TRAibr2Ibr1Binding, TRAbrEq2, TRAbrEq1); + CREATE_KLU_BINDING_TABLE(TRAibr2Int2Ptr, TRAibr2Int2Binding, TRAbrEq2, TRAintNode2); + CREATE_KLU_BINDING_TABLE(TRAibr2Neg1Ptr, TRAibr2Neg1Binding, TRAbrEq2, TRAnegNode1); + CREATE_KLU_BINDING_TABLE(TRAibr2Neg2Ptr, TRAibr2Neg2Binding, TRAbrEq2, TRAnegNode2); + CREATE_KLU_BINDING_TABLE(TRAibr2Pos1Ptr, TRAibr2Pos1Binding, TRAbrEq2, TRAposNode1); + CREATE_KLU_BINDING_TABLE(TRAint1Ibr1Ptr, TRAint1Ibr1Binding, TRAintNode1, TRAbrEq1); + CREATE_KLU_BINDING_TABLE(TRAint1Int1Ptr, TRAint1Int1Binding, TRAintNode1, TRAintNode1); + CREATE_KLU_BINDING_TABLE(TRAint1Pos1Ptr, TRAint1Pos1Binding, TRAintNode1, TRAposNode1); + CREATE_KLU_BINDING_TABLE(TRAint2Ibr2Ptr, TRAint2Ibr2Binding, TRAintNode2, TRAbrEq2); + CREATE_KLU_BINDING_TABLE(TRAint2Int2Ptr, TRAint2Int2Binding, TRAintNode2, TRAintNode2); + CREATE_KLU_BINDING_TABLE(TRAint2Pos2Ptr, TRAint2Pos2Binding, TRAintNode2, TRAposNode2); + CREATE_KLU_BINDING_TABLE(TRAneg1Ibr1Ptr, TRAneg1Ibr1Binding, TRAnegNode1, TRAbrEq1); + CREATE_KLU_BINDING_TABLE(TRAneg2Ibr2Ptr, TRAneg2Ibr2Binding, TRAnegNode2, TRAbrEq2); + CREATE_KLU_BINDING_TABLE(TRApos1Int1Ptr, TRApos1Int1Binding, TRAposNode1, TRAintNode1); + CREATE_KLU_BINDING_TABLE(TRApos1Pos1Ptr, TRApos1Pos1Binding, TRAposNode1, TRAposNode1); + CREATE_KLU_BINDING_TABLE(TRApos2Int2Ptr, TRApos2Int2Binding, TRAposNode2, TRAintNode2); + CREATE_KLU_BINDING_TABLE(TRApos2Pos2Ptr, TRApos2Pos2Binding, TRAposNode2, TRAposNode2); + } + } + + return (OK) ; +} + +int +TRAbindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + TRAmodel *model = (TRAmodel *)inModel ; + TRAinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the TRA models */ + for ( ; model != NULL ; model = TRAnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = TRAinstances(model); here != NULL ; here = TRAnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TRAibr1Ibr2Ptr, TRAibr1Ibr2Binding, TRAbrEq1, TRAbrEq2); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TRAibr1Int1Ptr, TRAibr1Int1Binding, TRAbrEq1, TRAintNode1); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TRAibr1Neg1Ptr, TRAibr1Neg1Binding, TRAbrEq1, TRAnegNode1); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TRAibr1Neg2Ptr, TRAibr1Neg2Binding, TRAbrEq1, TRAnegNode2); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TRAibr1Pos2Ptr, TRAibr1Pos2Binding, TRAbrEq1, TRAposNode2); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TRAibr2Ibr1Ptr, TRAibr2Ibr1Binding, TRAbrEq2, TRAbrEq1); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TRAibr2Int2Ptr, TRAibr2Int2Binding, TRAbrEq2, TRAintNode2); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TRAibr2Neg1Ptr, TRAibr2Neg1Binding, TRAbrEq2, TRAnegNode1); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TRAibr2Neg2Ptr, TRAibr2Neg2Binding, TRAbrEq2, TRAnegNode2); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TRAibr2Pos1Ptr, TRAibr2Pos1Binding, TRAbrEq2, TRAposNode1); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TRAint1Ibr1Ptr, TRAint1Ibr1Binding, TRAintNode1, TRAbrEq1); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TRAint1Int1Ptr, TRAint1Int1Binding, TRAintNode1, TRAintNode1); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TRAint1Pos1Ptr, TRAint1Pos1Binding, TRAintNode1, TRAposNode1); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TRAint2Ibr2Ptr, TRAint2Ibr2Binding, TRAintNode2, TRAbrEq2); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TRAint2Int2Ptr, TRAint2Int2Binding, TRAintNode2, TRAintNode2); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TRAint2Pos2Ptr, TRAint2Pos2Binding, TRAintNode2, TRAposNode2); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TRAneg1Ibr1Ptr, TRAneg1Ibr1Binding, TRAnegNode1, TRAbrEq1); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TRAneg2Ibr2Ptr, TRAneg2Ibr2Binding, TRAnegNode2, TRAbrEq2); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TRApos1Int1Ptr, TRApos1Int1Binding, TRAposNode1, TRAintNode1); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TRApos1Pos1Ptr, TRApos1Pos1Binding, TRAposNode1, TRAposNode1); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TRApos2Int2Ptr, TRApos2Int2Binding, TRAposNode2, TRAintNode2); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TRApos2Pos2Ptr, TRApos2Pos2Binding, TRAposNode2, TRAposNode2); + } + } + + return (OK) ; +} + +int +TRAbindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + TRAmodel *model = (TRAmodel *)inModel ; + TRAinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the TRA models */ + for ( ; model != NULL ; model = TRAnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = TRAinstances(model); here != NULL ; here = TRAnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(TRAibr1Ibr2Ptr, TRAibr1Ibr2Binding, TRAbrEq1, TRAbrEq2); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TRAibr1Int1Ptr, TRAibr1Int1Binding, TRAbrEq1, TRAintNode1); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TRAibr1Neg1Ptr, TRAibr1Neg1Binding, TRAbrEq1, TRAnegNode1); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TRAibr1Neg2Ptr, TRAibr1Neg2Binding, TRAbrEq1, TRAnegNode2); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TRAibr1Pos2Ptr, TRAibr1Pos2Binding, TRAbrEq1, TRAposNode2); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TRAibr2Ibr1Ptr, TRAibr2Ibr1Binding, TRAbrEq2, TRAbrEq1); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TRAibr2Int2Ptr, TRAibr2Int2Binding, TRAbrEq2, TRAintNode2); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TRAibr2Neg1Ptr, TRAibr2Neg1Binding, TRAbrEq2, TRAnegNode1); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TRAibr2Neg2Ptr, TRAibr2Neg2Binding, TRAbrEq2, TRAnegNode2); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TRAibr2Pos1Ptr, TRAibr2Pos1Binding, TRAbrEq2, TRAposNode1); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TRAint1Ibr1Ptr, TRAint1Ibr1Binding, TRAintNode1, TRAbrEq1); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TRAint1Int1Ptr, TRAint1Int1Binding, TRAintNode1, TRAintNode1); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TRAint1Pos1Ptr, TRAint1Pos1Binding, TRAintNode1, TRAposNode1); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TRAint2Ibr2Ptr, TRAint2Ibr2Binding, TRAintNode2, TRAbrEq2); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TRAint2Int2Ptr, TRAint2Int2Binding, TRAintNode2, TRAintNode2); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TRAint2Pos2Ptr, TRAint2Pos2Binding, TRAintNode2, TRAposNode2); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TRAneg1Ibr1Ptr, TRAneg1Ibr1Binding, TRAnegNode1, TRAbrEq1); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TRAneg2Ibr2Ptr, TRAneg2Ibr2Binding, TRAnegNode2, TRAbrEq2); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TRApos1Int1Ptr, TRApos1Int1Binding, TRAposNode1, TRAintNode1); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TRApos1Pos1Ptr, TRApos1Pos1Binding, TRAposNode1, TRAposNode1); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TRApos2Int2Ptr, TRApos2Int2Binding, TRAposNode2, TRAintNode2); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TRApos2Pos2Ptr, TRApos2Pos2Binding, TRAposNode2, TRAposNode2); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/tra/tradefs.h b/src/spicelib/devices/tra/tradefs.h index d90448f55..7e1df5453 100644 --- a/src/spicelib/devices/tra/tradefs.h +++ b/src/spicelib/devices/tra/tradefs.h @@ -83,6 +83,32 @@ typedef struct sTRAinstance { unsigned TRAicC2Given : 1; /* flag to ind. init. current at port 2 given */ unsigned TRAreltolGiven:1; /* flag to ind. relative deriv. tol. given */ unsigned TRAabstolGiven:1; /* flag to ind. absolute deriv. tol. given */ + +#ifdef KLU + BindElement *TRAibr1Ibr2Binding ; + BindElement *TRAibr1Int1Binding ; + BindElement *TRAibr1Neg1Binding ; + BindElement *TRAibr1Neg2Binding ; + BindElement *TRAibr1Pos2Binding ; + BindElement *TRAibr2Ibr1Binding ; + BindElement *TRAibr2Int2Binding ; + BindElement *TRAibr2Neg1Binding ; + BindElement *TRAibr2Neg2Binding ; + BindElement *TRAibr2Pos1Binding ; + BindElement *TRAint1Ibr1Binding ; + BindElement *TRAint1Int1Binding ; + BindElement *TRAint1Pos1Binding ; + BindElement *TRAint2Ibr2Binding ; + BindElement *TRAint2Int2Binding ; + BindElement *TRAint2Pos2Binding ; + BindElement *TRAneg1Ibr1Binding ; + BindElement *TRAneg2Ibr2Binding ; + BindElement *TRApos1Int1Binding ; + BindElement *TRApos1Pos1Binding ; + BindElement *TRApos2Int2Binding ; + BindElement *TRApos2Pos2Binding ; +#endif + } TRAinstance ; diff --git a/src/spicelib/devices/tra/traext.h b/src/spicelib/devices/tra/traext.h index 43a153249..d7640c353 100644 --- a/src/spicelib/devices/tra/traext.h +++ b/src/spicelib/devices/tra/traext.h @@ -16,3 +16,9 @@ extern int TRAsetup(SMPmatrix*,GENmodel*,CKTcircuit*,int*); extern int TRAunsetup(GENmodel*,CKTcircuit*); extern int TRAtemp(GENmodel*,CKTcircuit*); extern int TRAtrunc(GENmodel*,CKTcircuit*,double*); + +#ifdef KLU +extern int TRAbindCSC (GENmodel*, CKTcircuit*) ; +extern int TRAbindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int TRAbindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/tra/trainit.c b/src/spicelib/devices/tra/trainit.c index ff0853da3..9a0c79658 100644 --- a/src/spicelib/devices/tra/trainit.c +++ b/src/spicelib/devices/tra/trainit.c @@ -66,6 +66,11 @@ SPICEdev TRAinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = TRAbindCSC, + .DEVbindCSCComplex = TRAbindCSCComplex, + .DEVbindCSCComplexToReal = TRAbindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/txl/Makefile.am b/src/spicelib/devices/txl/Makefile.am index 0e07d1a38..25e7c4d9a 100644 --- a/src/spicelib/devices/txl/Makefile.am +++ b/src/spicelib/devices/txl/Makefile.am @@ -21,6 +21,11 @@ libtxl_la_SOURCES = \ txlsetup.c \ txlinit.c + +if KLU_WANTED +libtxl_la_SOURCES += txlbindCSC.c +endif + AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) diff --git a/src/spicelib/devices/txl/txlbindCSC.c b/src/spicelib/devices/txl/txlbindCSC.c new file mode 100644 index 000000000..f8f3dd001 --- /dev/null +++ b/src/spicelib/devices/txl/txlbindCSC.c @@ -0,0 +1,128 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "txldefs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +TXLbindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + TXLmodel *model = (TXLmodel *)inModel ; + TXLinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the TXL models */ + for ( ; model != NULL ; model = TXLnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = TXLinstances(model); here != NULL ; here = TXLnextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(TXLposPosPtr, TXLposPosBinding, TXLposNode, TXLposNode); + CREATE_KLU_BINDING_TABLE(TXLposNegPtr, TXLposNegBinding, TXLposNode, TXLnegNode); + CREATE_KLU_BINDING_TABLE(TXLnegPosPtr, TXLnegPosBinding, TXLnegNode, TXLposNode); + CREATE_KLU_BINDING_TABLE(TXLnegNegPtr, TXLnegNegBinding, TXLnegNode, TXLnegNode); + CREATE_KLU_BINDING_TABLE(TXLibr1PosPtr, TXLibr1PosBinding, TXLibr1, TXLposNode); + CREATE_KLU_BINDING_TABLE(TXLibr2NegPtr, TXLibr2NegBinding, TXLibr2, TXLnegNode); + CREATE_KLU_BINDING_TABLE(TXLnegIbr2Ptr, TXLnegIbr2Binding, TXLnegNode, TXLibr2); + CREATE_KLU_BINDING_TABLE(TXLposIbr1Ptr, TXLposIbr1Binding, TXLposNode, TXLibr1); + CREATE_KLU_BINDING_TABLE(TXLibr1Ibr1Ptr, TXLibr1Ibr1Binding, TXLibr1, TXLibr1); + CREATE_KLU_BINDING_TABLE(TXLibr2Ibr2Ptr, TXLibr2Ibr2Binding, TXLibr2, TXLibr2); + CREATE_KLU_BINDING_TABLE(TXLibr1NegPtr, TXLibr1NegBinding, TXLibr1, TXLnegNode); + CREATE_KLU_BINDING_TABLE(TXLibr2PosPtr, TXLibr2PosBinding, TXLibr2, TXLposNode); + CREATE_KLU_BINDING_TABLE(TXLibr1Ibr2Ptr, TXLibr1Ibr2Binding, TXLibr1, TXLibr2); + CREATE_KLU_BINDING_TABLE(TXLibr2Ibr1Ptr, TXLibr2Ibr1Binding, TXLibr2, TXLibr1); + } + } + + return (OK) ; +} + +int +TXLbindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + TXLmodel *model = (TXLmodel *)inModel ; + TXLinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the TXL models */ + for ( ; model != NULL ; model = TXLnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = TXLinstances(model); here != NULL ; here = TXLnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TXLposPosPtr, TXLposPosBinding, TXLposNode, TXLposNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TXLposNegPtr, TXLposNegBinding, TXLposNode, TXLnegNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TXLnegPosPtr, TXLnegPosBinding, TXLnegNode, TXLposNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TXLnegNegPtr, TXLnegNegBinding, TXLnegNode, TXLnegNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TXLibr1PosPtr, TXLibr1PosBinding, TXLibr1, TXLposNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TXLibr2NegPtr, TXLibr2NegBinding, TXLibr2, TXLnegNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TXLnegIbr2Ptr, TXLnegIbr2Binding, TXLnegNode, TXLibr2); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TXLposIbr1Ptr, TXLposIbr1Binding, TXLposNode, TXLibr1); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TXLibr1Ibr1Ptr, TXLibr1Ibr1Binding, TXLibr1, TXLibr1); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TXLibr2Ibr2Ptr, TXLibr2Ibr2Binding, TXLibr2, TXLibr2); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TXLibr1NegPtr, TXLibr1NegBinding, TXLibr1, TXLnegNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TXLibr2PosPtr, TXLibr2PosBinding, TXLibr2, TXLposNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TXLibr1Ibr2Ptr, TXLibr1Ibr2Binding, TXLibr1, TXLibr2); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(TXLibr2Ibr1Ptr, TXLibr2Ibr1Binding, TXLibr2, TXLibr1); + } + } + + return (OK) ; +} + +int +TXLbindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + TXLmodel *model = (TXLmodel *)inModel ; + TXLinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the TXL models */ + for ( ; model != NULL ; model = TXLnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = TXLinstances(model); here != NULL ; here = TXLnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(TXLposPosPtr, TXLposPosBinding, TXLposNode, TXLposNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TXLposNegPtr, TXLposNegBinding, TXLposNode, TXLnegNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TXLnegPosPtr, TXLnegPosBinding, TXLnegNode, TXLposNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TXLnegNegPtr, TXLnegNegBinding, TXLnegNode, TXLnegNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TXLibr1PosPtr, TXLibr1PosBinding, TXLibr1, TXLposNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TXLibr2NegPtr, TXLibr2NegBinding, TXLibr2, TXLnegNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TXLnegIbr2Ptr, TXLnegIbr2Binding, TXLnegNode, TXLibr2); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TXLposIbr1Ptr, TXLposIbr1Binding, TXLposNode, TXLibr1); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TXLibr1Ibr1Ptr, TXLibr1Ibr1Binding, TXLibr1, TXLibr1); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TXLibr2Ibr2Ptr, TXLibr2Ibr2Binding, TXLibr2, TXLibr2); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TXLibr1NegPtr, TXLibr1NegBinding, TXLibr1, TXLnegNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TXLibr2PosPtr, TXLibr2PosBinding, TXLibr2, TXLposNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TXLibr1Ibr2Ptr, TXLibr1Ibr2Binding, TXLibr1, TXLibr2); + CONVERT_KLU_BINDING_TABLE_TO_REAL(TXLibr2Ibr1Ptr, TXLibr2Ibr1Binding, TXLibr2, TXLibr1); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/txl/txldefs.h b/src/spicelib/devices/txl/txldefs.h index ccdba9838..290074c48 100644 --- a/src/spicelib/devices/txl/txldefs.h +++ b/src/spicelib/devices/txl/txldefs.h @@ -50,6 +50,23 @@ typedef struct sTXLinstance { unsigned TXLdcGiven : 1; unsigned TXLlengthgiven : 1; /* flag to indicate that instance parameter len is specified */ +#ifdef KLU + BindElement *TXLposPosBinding ; + BindElement *TXLposNegBinding ; + BindElement *TXLnegPosBinding ; + BindElement *TXLnegNegBinding ; + BindElement *TXLibr1PosBinding ; + BindElement *TXLibr2NegBinding ; + BindElement *TXLnegIbr2Binding ; + BindElement *TXLposIbr1Binding ; + BindElement *TXLibr1Ibr1Binding ; + BindElement *TXLibr2Ibr2Binding ; + BindElement *TXLibr1NegBinding ; + BindElement *TXLibr2PosBinding ; + BindElement *TXLibr1Ibr2Binding ; + BindElement *TXLibr2Ibr1Binding ; +#endif + } TXLinstance ; diff --git a/src/spicelib/devices/txl/txlext.h b/src/spicelib/devices/txl/txlext.h index bd827956a..11a9fc8b8 100644 --- a/src/spicelib/devices/txl/txlext.h +++ b/src/spicelib/devices/txl/txlext.h @@ -12,3 +12,9 @@ extern int TXLmParam(int,IFvalue*,GENmodel*); extern int TXLparam(int,IFvalue*,GENinstance*,IFvalue*); extern int TXLsetup(SMPmatrix*,GENmodel*,CKTcircuit*,int*); extern int TXLunsetup(GENmodel*, CKTcircuit*); + +#ifdef KLU +extern int TXLbindCSC (GENmodel*, CKTcircuit*) ; +extern int TXLbindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int TXLbindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/txl/txlinit.c b/src/spicelib/devices/txl/txlinit.c index 0a7c06b96..8f76c4741 100644 --- a/src/spicelib/devices/txl/txlinit.c +++ b/src/spicelib/devices/txl/txlinit.c @@ -71,6 +71,11 @@ SPICEdev TXLinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = TXLbindCSC, + .DEVbindCSCComplex = TXLbindCSCComplex, + .DEVbindCSCComplexToReal = TXLbindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/urc/urcinit.c b/src/spicelib/devices/urc/urcinit.c index 181465191..2f9ad074d 100644 --- a/src/spicelib/devices/urc/urcinit.c +++ b/src/spicelib/devices/urc/urcinit.c @@ -66,6 +66,11 @@ SPICEdev URCinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = NULL, + .DEVbindCSCComplex = NULL, + .DEVbindCSCComplexToReal = NULL, +#endif }; diff --git a/src/spicelib/devices/vbic/Makefile.am b/src/spicelib/devices/vbic/Makefile.am index a0aee2cb8..189cdb458 100644 --- a/src/spicelib/devices/vbic/Makefile.am +++ b/src/spicelib/devices/vbic/Makefile.am @@ -28,6 +28,9 @@ libvbic_la_SOURCES = \ vbictrunc.c +if KLU_WANTED +libvbic_la_SOURCES += vbicbindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) diff --git a/src/spicelib/devices/vbic/vbicbindCSC.c b/src/spicelib/devices/vbic/vbicbindCSC.c new file mode 100644 index 000000000..d9aa51ce0 --- /dev/null +++ b/src/spicelib/devices/vbic/vbicbindCSC.c @@ -0,0 +1,239 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "vbicdefs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +VBICbindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + VBICmodel *model = (VBICmodel *)inModel ; + VBICinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the VBIC models */ + for ( ; model != NULL ; model = VBICnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = VBICinstances(model); here != NULL ; here = VBICnextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(VBICcollCollPtr, VBICcollCollBinding, VBICcollNode, VBICcollNode); + CREATE_KLU_BINDING_TABLE(VBICbaseBasePtr, VBICbaseBaseBinding, VBICbaseNode, VBICbaseNode); + CREATE_KLU_BINDING_TABLE(VBICemitEmitPtr, VBICemitEmitBinding, VBICemitNode, VBICemitNode); + CREATE_KLU_BINDING_TABLE(VBICsubsSubsPtr, VBICsubsSubsBinding, VBICsubsNode, VBICsubsNode); + CREATE_KLU_BINDING_TABLE(VBICcollCXCollCXPtr, VBICcollCXCollCXBinding, VBICcollCXNode, VBICcollCXNode); + CREATE_KLU_BINDING_TABLE(VBICcollCICollCIPtr, VBICcollCICollCIBinding, VBICcollCINode, VBICcollCINode); + CREATE_KLU_BINDING_TABLE(VBICbaseBXBaseBXPtr, VBICbaseBXBaseBXBinding, VBICbaseBXNode, VBICbaseBXNode); + CREATE_KLU_BINDING_TABLE(VBICbaseBIBaseBIPtr, VBICbaseBIBaseBIBinding, VBICbaseBINode, VBICbaseBINode); + CREATE_KLU_BINDING_TABLE(VBICemitEIEmitEIPtr, VBICemitEIEmitEIBinding, VBICemitEINode, VBICemitEINode); + CREATE_KLU_BINDING_TABLE(VBICbaseBPBaseBPPtr, VBICbaseBPBaseBPBinding, VBICbaseBPNode, VBICbaseBPNode); + CREATE_KLU_BINDING_TABLE(VBICsubsSISubsSIPtr, VBICsubsSISubsSIBinding, VBICsubsSINode, VBICsubsSINode); + CREATE_KLU_BINDING_TABLE(VBICbaseEmitPtr, VBICbaseEmitBinding, VBICbaseNode, VBICemitNode); + CREATE_KLU_BINDING_TABLE(VBICemitBasePtr, VBICemitBaseBinding, VBICemitNode, VBICbaseNode); + CREATE_KLU_BINDING_TABLE(VBICbaseCollPtr, VBICbaseCollBinding, VBICbaseNode, VBICcollNode); + CREATE_KLU_BINDING_TABLE(VBICcollBasePtr, VBICcollBaseBinding, VBICcollNode, VBICbaseNode); + CREATE_KLU_BINDING_TABLE(VBICcollCollCXPtr, VBICcollCollCXBinding, VBICcollNode, VBICcollCXNode); + CREATE_KLU_BINDING_TABLE(VBICbaseBaseBXPtr, VBICbaseBaseBXBinding, VBICbaseNode, VBICbaseBXNode); + CREATE_KLU_BINDING_TABLE(VBICemitEmitEIPtr, VBICemitEmitEIBinding, VBICemitNode, VBICemitEINode); + CREATE_KLU_BINDING_TABLE(VBICsubsSubsSIPtr, VBICsubsSubsSIBinding, VBICsubsNode, VBICsubsSINode); + CREATE_KLU_BINDING_TABLE(VBICcollCXCollCIPtr, VBICcollCXCollCIBinding, VBICcollCXNode, VBICcollCINode); + CREATE_KLU_BINDING_TABLE(VBICcollCXBaseBXPtr, VBICcollCXBaseBXBinding, VBICcollCXNode, VBICbaseBXNode); + CREATE_KLU_BINDING_TABLE(VBICcollCXBaseBIPtr, VBICcollCXBaseBIBinding, VBICcollCXNode, VBICbaseBINode); + CREATE_KLU_BINDING_TABLE(VBICcollCXBaseBPPtr, VBICcollCXBaseBPBinding, VBICcollCXNode, VBICbaseBPNode); + CREATE_KLU_BINDING_TABLE(VBICcollCIBaseBIPtr, VBICcollCIBaseBIBinding, VBICcollCINode, VBICbaseBINode); + CREATE_KLU_BINDING_TABLE(VBICcollCIEmitEIPtr, VBICcollCIEmitEIBinding, VBICcollCINode, VBICemitEINode); + CREATE_KLU_BINDING_TABLE(VBICbaseBXBaseBIPtr, VBICbaseBXBaseBIBinding, VBICbaseBXNode, VBICbaseBINode); + CREATE_KLU_BINDING_TABLE(VBICbaseBXEmitEIPtr, VBICbaseBXEmitEIBinding, VBICbaseBXNode, VBICemitEINode); + CREATE_KLU_BINDING_TABLE(VBICbaseBXBaseBPPtr, VBICbaseBXBaseBPBinding, VBICbaseBXNode, VBICbaseBPNode); + CREATE_KLU_BINDING_TABLE(VBICbaseBXSubsSIPtr, VBICbaseBXSubsSIBinding, VBICbaseBXNode, VBICsubsSINode); + CREATE_KLU_BINDING_TABLE(VBICbaseBIEmitEIPtr, VBICbaseBIEmitEIBinding, VBICbaseBINode, VBICemitEINode); + CREATE_KLU_BINDING_TABLE(VBICbaseBPSubsSIPtr, VBICbaseBPSubsSIBinding, VBICbaseBPNode, VBICsubsSINode); + CREATE_KLU_BINDING_TABLE(VBICcollCXCollPtr, VBICcollCXCollBinding, VBICcollCXNode, VBICcollNode); + CREATE_KLU_BINDING_TABLE(VBICbaseBXBasePtr, VBICbaseBXBaseBinding, VBICbaseBXNode, VBICbaseNode); + CREATE_KLU_BINDING_TABLE(VBICemitEIEmitPtr, VBICemitEIEmitBinding, VBICemitEINode, VBICemitNode); + CREATE_KLU_BINDING_TABLE(VBICsubsSISubsPtr, VBICsubsSISubsBinding, VBICsubsSINode, VBICsubsNode); + CREATE_KLU_BINDING_TABLE(VBICcollCICollCXPtr, VBICcollCICollCXBinding, VBICcollCINode, VBICcollCXNode); + CREATE_KLU_BINDING_TABLE(VBICbaseBICollCXPtr, VBICbaseBICollCXBinding, VBICbaseBINode, VBICcollCXNode); + CREATE_KLU_BINDING_TABLE(VBICbaseBPCollCXPtr, VBICbaseBPCollCXBinding, VBICbaseBPNode, VBICcollCXNode); + CREATE_KLU_BINDING_TABLE(VBICbaseBXCollCIPtr, VBICbaseBXCollCIBinding, VBICbaseBXNode, VBICcollCINode); + CREATE_KLU_BINDING_TABLE(VBICbaseBICollCIPtr, VBICbaseBICollCIBinding, VBICbaseBINode, VBICcollCINode); + CREATE_KLU_BINDING_TABLE(VBICemitEICollCIPtr, VBICemitEICollCIBinding, VBICemitEINode, VBICcollCINode); + CREATE_KLU_BINDING_TABLE(VBICbaseBPCollCIPtr, VBICbaseBPCollCIBinding, VBICbaseBPNode, VBICcollCINode); + CREATE_KLU_BINDING_TABLE(VBICbaseBIBaseBXPtr, VBICbaseBIBaseBXBinding, VBICbaseBINode, VBICbaseBXNode); + CREATE_KLU_BINDING_TABLE(VBICemitEIBaseBXPtr, VBICemitEIBaseBXBinding, VBICemitEINode, VBICbaseBXNode); + CREATE_KLU_BINDING_TABLE(VBICbaseBPBaseBXPtr, VBICbaseBPBaseBXBinding, VBICbaseBPNode, VBICbaseBXNode); + CREATE_KLU_BINDING_TABLE(VBICsubsSIBaseBXPtr, VBICsubsSIBaseBXBinding, VBICsubsSINode, VBICbaseBXNode); + CREATE_KLU_BINDING_TABLE(VBICemitEIBaseBIPtr, VBICemitEIBaseBIBinding, VBICemitEINode, VBICbaseBINode); + CREATE_KLU_BINDING_TABLE(VBICbaseBPBaseBIPtr, VBICbaseBPBaseBIBinding, VBICbaseBPNode, VBICbaseBINode); + CREATE_KLU_BINDING_TABLE(VBICsubsSICollCIPtr, VBICsubsSICollCIBinding, VBICsubsSINode, VBICcollCINode); + CREATE_KLU_BINDING_TABLE(VBICsubsSIBaseBIPtr, VBICsubsSIBaseBIBinding, VBICsubsSINode, VBICbaseBINode); + CREATE_KLU_BINDING_TABLE(VBICsubsSIBaseBPPtr, VBICsubsSIBaseBPBinding, VBICsubsSINode, VBICbaseBPNode); + } + } + + return (OK) ; +} + +int +VBICbindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + VBICmodel *model = (VBICmodel *)inModel ; + VBICinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the VBIC models */ + for ( ; model != NULL ; model = VBICnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = VBICinstances(model); here != NULL ; here = VBICnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICcollCollPtr, VBICcollCollBinding, VBICcollNode, VBICcollNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICbaseBasePtr, VBICbaseBaseBinding, VBICbaseNode, VBICbaseNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICemitEmitPtr, VBICemitEmitBinding, VBICemitNode, VBICemitNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICsubsSubsPtr, VBICsubsSubsBinding, VBICsubsNode, VBICsubsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICcollCXCollCXPtr, VBICcollCXCollCXBinding, VBICcollCXNode, VBICcollCXNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICcollCICollCIPtr, VBICcollCICollCIBinding, VBICcollCINode, VBICcollCINode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICbaseBXBaseBXPtr, VBICbaseBXBaseBXBinding, VBICbaseBXNode, VBICbaseBXNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICbaseBIBaseBIPtr, VBICbaseBIBaseBIBinding, VBICbaseBINode, VBICbaseBINode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICemitEIEmitEIPtr, VBICemitEIEmitEIBinding, VBICemitEINode, VBICemitEINode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICbaseBPBaseBPPtr, VBICbaseBPBaseBPBinding, VBICbaseBPNode, VBICbaseBPNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICsubsSISubsSIPtr, VBICsubsSISubsSIBinding, VBICsubsSINode, VBICsubsSINode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICbaseEmitPtr, VBICbaseEmitBinding, VBICbaseNode, VBICemitNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICemitBasePtr, VBICemitBaseBinding, VBICemitNode, VBICbaseNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICbaseCollPtr, VBICbaseCollBinding, VBICbaseNode, VBICcollNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICcollBasePtr, VBICcollBaseBinding, VBICcollNode, VBICbaseNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICcollCollCXPtr, VBICcollCollCXBinding, VBICcollNode, VBICcollCXNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICbaseBaseBXPtr, VBICbaseBaseBXBinding, VBICbaseNode, VBICbaseBXNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICemitEmitEIPtr, VBICemitEmitEIBinding, VBICemitNode, VBICemitEINode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICsubsSubsSIPtr, VBICsubsSubsSIBinding, VBICsubsNode, VBICsubsSINode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICcollCXCollCIPtr, VBICcollCXCollCIBinding, VBICcollCXNode, VBICcollCINode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICcollCXBaseBXPtr, VBICcollCXBaseBXBinding, VBICcollCXNode, VBICbaseBXNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICcollCXBaseBIPtr, VBICcollCXBaseBIBinding, VBICcollCXNode, VBICbaseBINode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICcollCXBaseBPPtr, VBICcollCXBaseBPBinding, VBICcollCXNode, VBICbaseBPNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICcollCIBaseBIPtr, VBICcollCIBaseBIBinding, VBICcollCINode, VBICbaseBINode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICcollCIEmitEIPtr, VBICcollCIEmitEIBinding, VBICcollCINode, VBICemitEINode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICbaseBXBaseBIPtr, VBICbaseBXBaseBIBinding, VBICbaseBXNode, VBICbaseBINode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICbaseBXEmitEIPtr, VBICbaseBXEmitEIBinding, VBICbaseBXNode, VBICemitEINode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICbaseBXBaseBPPtr, VBICbaseBXBaseBPBinding, VBICbaseBXNode, VBICbaseBPNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICbaseBXSubsSIPtr, VBICbaseBXSubsSIBinding, VBICbaseBXNode, VBICsubsSINode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICbaseBIEmitEIPtr, VBICbaseBIEmitEIBinding, VBICbaseBINode, VBICemitEINode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICbaseBPSubsSIPtr, VBICbaseBPSubsSIBinding, VBICbaseBPNode, VBICsubsSINode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICcollCXCollPtr, VBICcollCXCollBinding, VBICcollCXNode, VBICcollNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICbaseBXBasePtr, VBICbaseBXBaseBinding, VBICbaseBXNode, VBICbaseNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICemitEIEmitPtr, VBICemitEIEmitBinding, VBICemitEINode, VBICemitNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICsubsSISubsPtr, VBICsubsSISubsBinding, VBICsubsSINode, VBICsubsNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICcollCICollCXPtr, VBICcollCICollCXBinding, VBICcollCINode, VBICcollCXNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICbaseBICollCXPtr, VBICbaseBICollCXBinding, VBICbaseBINode, VBICcollCXNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICbaseBPCollCXPtr, VBICbaseBPCollCXBinding, VBICbaseBPNode, VBICcollCXNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICbaseBXCollCIPtr, VBICbaseBXCollCIBinding, VBICbaseBXNode, VBICcollCINode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICbaseBICollCIPtr, VBICbaseBICollCIBinding, VBICbaseBINode, VBICcollCINode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICemitEICollCIPtr, VBICemitEICollCIBinding, VBICemitEINode, VBICcollCINode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICbaseBPCollCIPtr, VBICbaseBPCollCIBinding, VBICbaseBPNode, VBICcollCINode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICbaseBIBaseBXPtr, VBICbaseBIBaseBXBinding, VBICbaseBINode, VBICbaseBXNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICemitEIBaseBXPtr, VBICemitEIBaseBXBinding, VBICemitEINode, VBICbaseBXNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICbaseBPBaseBXPtr, VBICbaseBPBaseBXBinding, VBICbaseBPNode, VBICbaseBXNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICsubsSIBaseBXPtr, VBICsubsSIBaseBXBinding, VBICsubsSINode, VBICbaseBXNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICemitEIBaseBIPtr, VBICemitEIBaseBIBinding, VBICemitEINode, VBICbaseBINode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICbaseBPBaseBIPtr, VBICbaseBPBaseBIBinding, VBICbaseBPNode, VBICbaseBINode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICsubsSICollCIPtr, VBICsubsSICollCIBinding, VBICsubsSINode, VBICcollCINode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICsubsSIBaseBIPtr, VBICsubsSIBaseBIBinding, VBICsubsSINode, VBICbaseBINode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VBICsubsSIBaseBPPtr, VBICsubsSIBaseBPBinding, VBICsubsSINode, VBICbaseBPNode); + } + } + + return (OK) ; +} + +int +VBICbindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + VBICmodel *model = (VBICmodel *)inModel ; + VBICinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the VBIC models */ + for ( ; model != NULL ; model = VBICnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = VBICinstances(model); here != NULL ; here = VBICnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICcollCollPtr, VBICcollCollBinding, VBICcollNode, VBICcollNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICbaseBasePtr, VBICbaseBaseBinding, VBICbaseNode, VBICbaseNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICemitEmitPtr, VBICemitEmitBinding, VBICemitNode, VBICemitNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICsubsSubsPtr, VBICsubsSubsBinding, VBICsubsNode, VBICsubsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICcollCXCollCXPtr, VBICcollCXCollCXBinding, VBICcollCXNode, VBICcollCXNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICcollCICollCIPtr, VBICcollCICollCIBinding, VBICcollCINode, VBICcollCINode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICbaseBXBaseBXPtr, VBICbaseBXBaseBXBinding, VBICbaseBXNode, VBICbaseBXNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICbaseBIBaseBIPtr, VBICbaseBIBaseBIBinding, VBICbaseBINode, VBICbaseBINode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICemitEIEmitEIPtr, VBICemitEIEmitEIBinding, VBICemitEINode, VBICemitEINode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICbaseBPBaseBPPtr, VBICbaseBPBaseBPBinding, VBICbaseBPNode, VBICbaseBPNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICsubsSISubsSIPtr, VBICsubsSISubsSIBinding, VBICsubsSINode, VBICsubsSINode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICbaseEmitPtr, VBICbaseEmitBinding, VBICbaseNode, VBICemitNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICemitBasePtr, VBICemitBaseBinding, VBICemitNode, VBICbaseNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICbaseCollPtr, VBICbaseCollBinding, VBICbaseNode, VBICcollNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICcollBasePtr, VBICcollBaseBinding, VBICcollNode, VBICbaseNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICcollCollCXPtr, VBICcollCollCXBinding, VBICcollNode, VBICcollCXNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICbaseBaseBXPtr, VBICbaseBaseBXBinding, VBICbaseNode, VBICbaseBXNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICemitEmitEIPtr, VBICemitEmitEIBinding, VBICemitNode, VBICemitEINode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICsubsSubsSIPtr, VBICsubsSubsSIBinding, VBICsubsNode, VBICsubsSINode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICcollCXCollCIPtr, VBICcollCXCollCIBinding, VBICcollCXNode, VBICcollCINode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICcollCXBaseBXPtr, VBICcollCXBaseBXBinding, VBICcollCXNode, VBICbaseBXNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICcollCXBaseBIPtr, VBICcollCXBaseBIBinding, VBICcollCXNode, VBICbaseBINode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICcollCXBaseBPPtr, VBICcollCXBaseBPBinding, VBICcollCXNode, VBICbaseBPNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICcollCIBaseBIPtr, VBICcollCIBaseBIBinding, VBICcollCINode, VBICbaseBINode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICcollCIEmitEIPtr, VBICcollCIEmitEIBinding, VBICcollCINode, VBICemitEINode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICbaseBXBaseBIPtr, VBICbaseBXBaseBIBinding, VBICbaseBXNode, VBICbaseBINode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICbaseBXEmitEIPtr, VBICbaseBXEmitEIBinding, VBICbaseBXNode, VBICemitEINode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICbaseBXBaseBPPtr, VBICbaseBXBaseBPBinding, VBICbaseBXNode, VBICbaseBPNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICbaseBXSubsSIPtr, VBICbaseBXSubsSIBinding, VBICbaseBXNode, VBICsubsSINode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICbaseBIEmitEIPtr, VBICbaseBIEmitEIBinding, VBICbaseBINode, VBICemitEINode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICbaseBPSubsSIPtr, VBICbaseBPSubsSIBinding, VBICbaseBPNode, VBICsubsSINode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICcollCXCollPtr, VBICcollCXCollBinding, VBICcollCXNode, VBICcollNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICbaseBXBasePtr, VBICbaseBXBaseBinding, VBICbaseBXNode, VBICbaseNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICemitEIEmitPtr, VBICemitEIEmitBinding, VBICemitEINode, VBICemitNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICsubsSISubsPtr, VBICsubsSISubsBinding, VBICsubsSINode, VBICsubsNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICcollCICollCXPtr, VBICcollCICollCXBinding, VBICcollCINode, VBICcollCXNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICbaseBICollCXPtr, VBICbaseBICollCXBinding, VBICbaseBINode, VBICcollCXNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICbaseBPCollCXPtr, VBICbaseBPCollCXBinding, VBICbaseBPNode, VBICcollCXNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICbaseBXCollCIPtr, VBICbaseBXCollCIBinding, VBICbaseBXNode, VBICcollCINode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICbaseBICollCIPtr, VBICbaseBICollCIBinding, VBICbaseBINode, VBICcollCINode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICemitEICollCIPtr, VBICemitEICollCIBinding, VBICemitEINode, VBICcollCINode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICbaseBPCollCIPtr, VBICbaseBPCollCIBinding, VBICbaseBPNode, VBICcollCINode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICbaseBIBaseBXPtr, VBICbaseBIBaseBXBinding, VBICbaseBINode, VBICbaseBXNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICemitEIBaseBXPtr, VBICemitEIBaseBXBinding, VBICemitEINode, VBICbaseBXNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICbaseBPBaseBXPtr, VBICbaseBPBaseBXBinding, VBICbaseBPNode, VBICbaseBXNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICsubsSIBaseBXPtr, VBICsubsSIBaseBXBinding, VBICsubsSINode, VBICbaseBXNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICemitEIBaseBIPtr, VBICemitEIBaseBIBinding, VBICemitEINode, VBICbaseBINode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICbaseBPBaseBIPtr, VBICbaseBPBaseBIBinding, VBICbaseBPNode, VBICbaseBINode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICsubsSICollCIPtr, VBICsubsSICollCIBinding, VBICsubsSINode, VBICcollCINode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICsubsSIBaseBIPtr, VBICsubsSIBaseBIBinding, VBICsubsSINode, VBICbaseBINode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VBICsubsSIBaseBPPtr, VBICsubsSIBaseBPBinding, VBICsubsSINode, VBICbaseBPNode); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/vbic/vbicdefs.h b/src/spicelib/devices/vbic/vbicdefs.h index 012bd7e95..1dd356607 100644 --- a/src/spicelib/devices/vbic/vbicdefs.h +++ b/src/spicelib/devices/vbic/vbicdefs.h @@ -245,6 +245,60 @@ typedef struct sVBICinstance { #endif /*NONOISE*/ /* the above to avoid allocating memory when it is not needed */ +#ifdef KLU + BindElement *VBICcollCollBinding ; + BindElement *VBICbaseBaseBinding ; + BindElement *VBICemitEmitBinding ; + BindElement *VBICsubsSubsBinding ; + BindElement *VBICcollCXCollCXBinding ; + BindElement *VBICcollCICollCIBinding ; + BindElement *VBICbaseBXBaseBXBinding ; + BindElement *VBICbaseBIBaseBIBinding ; + BindElement *VBICemitEIEmitEIBinding ; + BindElement *VBICbaseBPBaseBPBinding ; + BindElement *VBICsubsSISubsSIBinding ; + BindElement *VBICbaseEmitBinding ; + BindElement *VBICemitBaseBinding ; + BindElement *VBICbaseCollBinding ; + BindElement *VBICcollBaseBinding ; + BindElement *VBICcollCollCXBinding ; + BindElement *VBICbaseBaseBXBinding ; + BindElement *VBICemitEmitEIBinding ; + BindElement *VBICsubsSubsSIBinding ; + BindElement *VBICcollCXCollCIBinding ; + BindElement *VBICcollCXBaseBXBinding ; + BindElement *VBICcollCXBaseBIBinding ; + BindElement *VBICcollCXBaseBPBinding ; + BindElement *VBICcollCIBaseBIBinding ; + BindElement *VBICcollCIEmitEIBinding ; + BindElement *VBICbaseBXBaseBIBinding ; + BindElement *VBICbaseBXEmitEIBinding ; + BindElement *VBICbaseBXBaseBPBinding ; + BindElement *VBICbaseBXSubsSIBinding ; + BindElement *VBICbaseBIEmitEIBinding ; + BindElement *VBICbaseBPSubsSIBinding ; + BindElement *VBICcollCXCollBinding ; + BindElement *VBICbaseBXBaseBinding ; + BindElement *VBICemitEIEmitBinding ; + BindElement *VBICsubsSISubsBinding ; + BindElement *VBICcollCICollCXBinding ; + BindElement *VBICbaseBICollCXBinding ; + BindElement *VBICbaseBPCollCXBinding ; + BindElement *VBICbaseBXCollCIBinding ; + BindElement *VBICbaseBICollCIBinding ; + BindElement *VBICemitEICollCIBinding ; + BindElement *VBICbaseBPCollCIBinding ; + BindElement *VBICbaseBIBaseBXBinding ; + BindElement *VBICemitEIBaseBXBinding ; + BindElement *VBICbaseBPBaseBXBinding ; + BindElement *VBICsubsSIBaseBXBinding ; + BindElement *VBICemitEIBaseBIBinding ; + BindElement *VBICbaseBPBaseBIBinding ; + BindElement *VBICsubsSICollCIBinding ; + BindElement *VBICsubsSIBaseBIBinding ; + BindElement *VBICsubsSIBaseBPBinding ; +#endif + } VBICinstance ; /* entries in the state vector for vbic: */ diff --git a/src/spicelib/devices/vbic/vbicext.h b/src/spicelib/devices/vbic/vbicext.h index 8a820d3dd..9da7646cc 100644 --- a/src/spicelib/devices/vbic/vbicext.h +++ b/src/spicelib/devices/vbic/vbicext.h @@ -27,4 +27,10 @@ extern int VBICtrunc(GENmodel*,CKTcircuit*,double*); extern int VBICnoise(int,int,GENmodel*,CKTcircuit*,Ndata*,double*); extern int VBICsoaCheck(CKTcircuit *, GENmodel *); +#ifdef KLU +extern int VBICbindCSC (GENmodel*, CKTcircuit*) ; +extern int VBICbindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int VBICbindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif + #endif diff --git a/src/spicelib/devices/vbic/vbicinit.c b/src/spicelib/devices/vbic/vbicinit.c index 77fd2531e..2bdb7cf1e 100644 --- a/src/spicelib/devices/vbic/vbicinit.c +++ b/src/spicelib/devices/vbic/vbicinit.c @@ -71,6 +71,11 @@ SPICEdev VBICinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = VBICbindCSC, + .DEVbindCSCComplex = VBICbindCSCComplex, + .DEVbindCSCComplexToReal = VBICbindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/vccs/Makefile.am b/src/spicelib/devices/vccs/Makefile.am index 145693195..eae86acd7 100644 --- a/src/spicelib/devices/vccs/Makefile.am +++ b/src/spicelib/devices/vccs/Makefile.am @@ -23,7 +23,11 @@ libvccs_la_SOURCES = \ vccssset.c +if KLU_WANTED +libvccs_la_SOURCES += vccsbindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) + MAINTAINERCLEANFILES = Makefile.in diff --git a/src/spicelib/devices/vccs/vccsbindCSC.c b/src/spicelib/devices/vccs/vccsbindCSC.c new file mode 100644 index 000000000..44b3b60d1 --- /dev/null +++ b/src/spicelib/devices/vccs/vccsbindCSC.c @@ -0,0 +1,98 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "vccsdefs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +VCCSbindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + VCCSmodel *model = (VCCSmodel *)inModel ; + VCCSinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the VCCS models */ + for ( ; model != NULL ; model = VCCSnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = VCCSinstances(model); here != NULL ; here = VCCSnextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(VCCSposContPosPtr, VCCSposContPosBinding, VCCSposNode, VCCScontPosNode); + CREATE_KLU_BINDING_TABLE(VCCSposContNegPtr, VCCSposContNegBinding, VCCSposNode, VCCScontNegNode); + CREATE_KLU_BINDING_TABLE(VCCSnegContPosPtr, VCCSnegContPosBinding, VCCSnegNode, VCCScontPosNode); + CREATE_KLU_BINDING_TABLE(VCCSnegContNegPtr, VCCSnegContNegBinding, VCCSnegNode, VCCScontNegNode); + } + } + + return (OK) ; +} + +int +VCCSbindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + VCCSmodel *model = (VCCSmodel *)inModel ; + VCCSinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the VCCS models */ + for ( ; model != NULL ; model = VCCSnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = VCCSinstances(model); here != NULL ; here = VCCSnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VCCSposContPosPtr, VCCSposContPosBinding, VCCSposNode, VCCScontPosNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VCCSposContNegPtr, VCCSposContNegBinding, VCCSposNode, VCCScontNegNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VCCSnegContPosPtr, VCCSnegContPosBinding, VCCSnegNode, VCCScontPosNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VCCSnegContNegPtr, VCCSnegContNegBinding, VCCSnegNode, VCCScontNegNode); + } + } + + return (OK) ; +} + +int +VCCSbindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + VCCSmodel *model = (VCCSmodel *)inModel ; + VCCSinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the VCCS models */ + for ( ; model != NULL ; model = VCCSnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = VCCSinstances(model); here != NULL ; here = VCCSnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(VCCSposContPosPtr, VCCSposContPosBinding, VCCSposNode, VCCScontPosNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VCCSposContNegPtr, VCCSposContNegBinding, VCCSposNode, VCCScontNegNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VCCSnegContPosPtr, VCCSnegContPosBinding, VCCSnegNode, VCCScontPosNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VCCSnegContNegPtr, VCCSnegContNegBinding, VCCSnegNode, VCCScontNegNode); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/vccs/vccsdefs.h b/src/spicelib/devices/vccs/vccsdefs.h index 3b9d9cde5..a97ef7c59 100644 --- a/src/spicelib/devices/vccs/vccsdefs.h +++ b/src/spicelib/devices/vccs/vccsdefs.h @@ -49,6 +49,13 @@ typedef struct sVCCSinstance { int VCCSsenParmNo; /* parameter # for sensitivity use; set equal to 0 if not a design parameter*/ +#ifdef KLU + BindElement *VCCSposContPosBinding ; + BindElement *VCCSposContNegBinding ; + BindElement *VCCSnegContPosBinding ; + BindElement *VCCSnegContNegBinding ; +#endif + } VCCSinstance ; #define VCCSvOld VCCSstates diff --git a/src/spicelib/devices/vccs/vccsext.h b/src/spicelib/devices/vccs/vccsext.h index 8b6f2f2c6..489afcfdd 100644 --- a/src/spicelib/devices/vccs/vccsext.h +++ b/src/spicelib/devices/vccs/vccsext.h @@ -15,3 +15,9 @@ extern int VCCSsLoad(GENmodel*,CKTcircuit*); extern int VCCSsSetup(SENstruct*,GENmodel*); extern void VCCSsPrint(GENmodel*,CKTcircuit*); extern int VCCSsetup(SMPmatrix*,GENmodel*,CKTcircuit*,int*); + +#ifdef KLU +extern int VCCSbindCSC (GENmodel*, CKTcircuit*) ; +extern int VCCSbindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int VCCSbindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/vccs/vccsinit.c b/src/spicelib/devices/vccs/vccsinit.c index 1e1ba8002..d5e86fa02 100644 --- a/src/spicelib/devices/vccs/vccsinit.c +++ b/src/spicelib/devices/vccs/vccsinit.c @@ -66,6 +66,11 @@ SPICEdev VCCSinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = VCCSbindCSC, + .DEVbindCSCComplex = VCCSbindCSCComplex, + .DEVbindCSCComplexToReal = VCCSbindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/vcvs/Makefile.am b/src/spicelib/devices/vcvs/Makefile.am index 8ad37e37b..9f9c548ad 100644 --- a/src/spicelib/devices/vcvs/Makefile.am +++ b/src/spicelib/devices/vcvs/Makefile.am @@ -24,7 +24,11 @@ libvcvs_la_SOURCES = \ vcvssset.c +if KLU_WANTED +libvcvs_la_SOURCES += vcvsbindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) + MAINTAINERCLEANFILES = Makefile.in diff --git a/src/spicelib/devices/vcvs/vcvsbindCSC.c b/src/spicelib/devices/vcvs/vcvsbindCSC.c new file mode 100644 index 000000000..769ebab02 --- /dev/null +++ b/src/spicelib/devices/vcvs/vcvsbindCSC.c @@ -0,0 +1,104 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "vcvsdefs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +VCVSbindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + VCVSmodel *model = (VCVSmodel *)inModel ; + VCVSinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the VCVS models */ + for ( ; model != NULL ; model = VCVSnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = VCVSinstances(model); here != NULL ; here = VCVSnextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(VCVSposIbrPtr, VCVSposIbrBinding, VCVSposNode, VCVSbranch); + CREATE_KLU_BINDING_TABLE(VCVSnegIbrPtr, VCVSnegIbrBinding, VCVSnegNode, VCVSbranch); + CREATE_KLU_BINDING_TABLE(VCVSibrNegPtr, VCVSibrNegBinding, VCVSbranch, VCVSnegNode); + CREATE_KLU_BINDING_TABLE(VCVSibrPosPtr, VCVSibrPosBinding, VCVSbranch, VCVSposNode); + CREATE_KLU_BINDING_TABLE(VCVSibrContPosPtr, VCVSibrContPosBinding, VCVSbranch, VCVScontPosNode); + CREATE_KLU_BINDING_TABLE(VCVSibrContNegPtr, VCVSibrContNegBinding, VCVSbranch, VCVScontNegNode); + } + } + + return (OK) ; +} + +int +VCVSbindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + VCVSmodel *model = (VCVSmodel *)inModel ; + VCVSinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the VCVS models */ + for ( ; model != NULL ; model = VCVSnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = VCVSinstances(model); here != NULL ; here = VCVSnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VCVSposIbrPtr, VCVSposIbrBinding, VCVSposNode, VCVSbranch); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VCVSnegIbrPtr, VCVSnegIbrBinding, VCVSnegNode, VCVSbranch); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VCVSibrNegPtr, VCVSibrNegBinding, VCVSbranch, VCVSnegNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VCVSibrPosPtr, VCVSibrPosBinding, VCVSbranch, VCVSposNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VCVSibrContPosPtr, VCVSibrContPosBinding, VCVSbranch, VCVScontPosNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VCVSibrContNegPtr, VCVSibrContNegBinding, VCVSbranch, VCVScontNegNode); + } + } + + return (OK) ; +} + +int +VCVSbindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + VCVSmodel *model = (VCVSmodel *)inModel ; + VCVSinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the VCVS models */ + for ( ; model != NULL ; model = VCVSnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = VCVSinstances(model); here != NULL ; here = VCVSnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(VCVSposIbrPtr, VCVSposIbrBinding, VCVSposNode, VCVSbranch); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VCVSnegIbrPtr, VCVSnegIbrBinding, VCVSnegNode, VCVSbranch); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VCVSibrNegPtr, VCVSibrNegBinding, VCVSbranch, VCVSnegNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VCVSibrPosPtr, VCVSibrPosBinding, VCVSbranch, VCVSposNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VCVSibrContPosPtr, VCVSibrContPosBinding, VCVSbranch, VCVScontPosNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VCVSibrContNegPtr, VCVSibrContNegBinding, VCVSbranch, VCVScontNegNode); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/vcvs/vcvsdefs.h b/src/spicelib/devices/vcvs/vcvsdefs.h index a2c36874e..a89fc79ca 100644 --- a/src/spicelib/devices/vcvs/vcvsdefs.h +++ b/src/spicelib/devices/vcvs/vcvsdefs.h @@ -53,6 +53,15 @@ typedef struct sVCVSinstance { int VCVSsenParmNo; /* parameter # for sensitivity use; set equal to 0 if not a design parameter*/ +#ifdef KLU + BindElement *VCVSposIbrBinding ; + BindElement *VCVSnegIbrBinding ; + BindElement *VCVSibrNegBinding ; + BindElement *VCVSibrPosBinding ; + BindElement *VCVSibrContPosBinding ; + BindElement *VCVSibrContNegBinding ; +#endif + } VCVSinstance ; #define VCVSvOld VCVSstates diff --git a/src/spicelib/devices/vcvs/vcvsext.h b/src/spicelib/devices/vcvs/vcvsext.h index a5ca450ad..7dcbf52f6 100644 --- a/src/spicelib/devices/vcvs/vcvsext.h +++ b/src/spicelib/devices/vcvs/vcvsext.h @@ -18,3 +18,8 @@ extern void VCVSsPrint(GENmodel*,CKTcircuit*); extern int VCVSsetup(SMPmatrix*,GENmodel*,CKTcircuit*,int*); extern int VCVSunsetup(GENmodel*,CKTcircuit*); +#ifdef KLU +extern int VCVSbindCSC (GENmodel*, CKTcircuit*) ; +extern int VCVSbindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int VCVSbindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/vcvs/vcvsinit.c b/src/spicelib/devices/vcvs/vcvsinit.c index 7b5147d88..b0583d015 100644 --- a/src/spicelib/devices/vcvs/vcvsinit.c +++ b/src/spicelib/devices/vcvs/vcvsinit.c @@ -66,6 +66,11 @@ SPICEdev VCVSinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = VCVSbindCSC, + .DEVbindCSCComplex = VCVSbindCSCComplex, + .DEVbindCSCComplexToReal = VCVSbindCSCComplexToReal, +#endif }; diff --git a/src/spicelib/devices/vsrc/Makefile.am b/src/spicelib/devices/vsrc/Makefile.am index 28d5fb38b..9800efa14 100644 --- a/src/spicelib/devices/vsrc/Makefile.am +++ b/src/spicelib/devices/vsrc/Makefile.am @@ -24,6 +24,9 @@ libvsrc_la_SOURCES = \ vsrctemp.c +if KLU_WANTED +libvsrc_la_SOURCES += vsrcbindCSC.c +endif AM_CPPFLAGS = @AM_CPPFLAGS@ -I$(top_srcdir)/src/include AM_CFLAGS = $(STATIC) diff --git a/src/spicelib/devices/vsrc/vsrcbindCSC.c b/src/spicelib/devices/vsrc/vsrcbindCSC.c new file mode 100644 index 000000000..8c1781395 --- /dev/null +++ b/src/spicelib/devices/vsrc/vsrcbindCSC.c @@ -0,0 +1,98 @@ +/********** +Author: 2013 Francesco Lannutti +**********/ + +#include "ngspice/ngspice.h" +#include "ngspice/cktdefs.h" +#include "vsrcdefs.h" +#include "ngspice/sperror.h" +#include "ngspice/klu-binding.h" + +#include + +static +int +BindCompare (const void *a, const void *b) +{ + BindElement *A, *B ; + A = (BindElement *)a ; + B = (BindElement *)b ; + + return ((int)(A->Sparse - B->Sparse)) ; +} + +int +VSRCbindCSC (GENmodel *inModel, CKTcircuit *ckt) +{ + VSRCmodel *model = (VSRCmodel *)inModel ; + VSRCinstance *here ; + double *i ; + BindElement *matched, *BindStruct ; + size_t nz ; + + BindStruct = ckt->CKTmatrix->CKTbindStruct ; + nz = (size_t)ckt->CKTmatrix->CKTklunz ; + + /* loop through all the VSRC models */ + for ( ; model != NULL ; model = VSRCnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = VSRCinstances(model); here != NULL ; here = VSRCnextInstance(here)) + { + CREATE_KLU_BINDING_TABLE(VSRCposIbrPtr, VSRCposIbrBinding, VSRCposNode, VSRCbranch); + CREATE_KLU_BINDING_TABLE(VSRCnegIbrPtr, VSRCnegIbrBinding, VSRCnegNode, VSRCbranch); + CREATE_KLU_BINDING_TABLE(VSRCibrNegPtr, VSRCibrNegBinding, VSRCbranch, VSRCnegNode); + CREATE_KLU_BINDING_TABLE(VSRCibrPosPtr, VSRCibrPosBinding, VSRCbranch, VSRCposNode); + } + } + + return (OK) ; +} + +int +VSRCbindCSCComplex (GENmodel *inModel, CKTcircuit *ckt) +{ + VSRCmodel *model = (VSRCmodel *)inModel ; + VSRCinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the VSRC models */ + for ( ; model != NULL ; model = VSRCnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = VSRCinstances(model); here != NULL ; here = VSRCnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VSRCposIbrPtr, VSRCposIbrBinding, VSRCposNode, VSRCbranch); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VSRCnegIbrPtr, VSRCnegIbrBinding, VSRCnegNode, VSRCbranch); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VSRCibrNegPtr, VSRCibrNegBinding, VSRCbranch, VSRCnegNode); + CONVERT_KLU_BINDING_TABLE_TO_COMPLEX(VSRCibrPosPtr, VSRCibrPosBinding, VSRCbranch, VSRCposNode); + } + } + + return (OK) ; +} + +int +VSRCbindCSCComplexToReal (GENmodel *inModel, CKTcircuit *ckt) +{ + VSRCmodel *model = (VSRCmodel *)inModel ; + VSRCinstance *here ; + + NG_IGNORE (ckt) ; + + /* loop through all the VSRC models */ + for ( ; model != NULL ; model = VSRCnextModel(model)) + { + /* loop through all the instances of the model */ + for (here = VSRCinstances(model); here != NULL ; here = VSRCnextInstance(here)) + { + CONVERT_KLU_BINDING_TABLE_TO_REAL(VSRCposIbrPtr, VSRCposIbrBinding, VSRCposNode, VSRCbranch); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VSRCnegIbrPtr, VSRCnegIbrBinding, VSRCnegNode, VSRCbranch); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VSRCibrNegPtr, VSRCibrNegBinding, VSRCbranch, VSRCnegNode); + CONVERT_KLU_BINDING_TABLE_TO_REAL(VSRCibrPosPtr, VSRCibrPosBinding, VSRCbranch, VSRCposNode); + } + } + + return (OK) ; +} diff --git a/src/spicelib/devices/vsrc/vsrcdefs.h b/src/spicelib/devices/vsrc/vsrcdefs.h index 0c5cfeddb..e3cb8d551 100644 --- a/src/spicelib/devices/vsrc/vsrcdefs.h +++ b/src/spicelib/devices/vsrc/vsrcdefs.h @@ -77,6 +77,14 @@ typedef struct sVSRCinstance { unsigned VSRCdF1given :1 ; /* flag to indicate source is an f1 distortion input */ unsigned VSRCdF2given :1 ; /* flag to indicate source is an f2 distortion input */ unsigned VSRCrGiven :1 ; /* flag to indicate repeating pwl */ + +#ifdef KLU + BindElement *VSRCposIbrBinding ; + BindElement *VSRCnegIbrBinding ; + BindElement *VSRCibrNegBinding ; + BindElement *VSRCibrPosBinding ; +#endif + } VSRCinstance ; diff --git a/src/spicelib/devices/vsrc/vsrcext.h b/src/spicelib/devices/vsrc/vsrcext.h index 4e2ee8534..f5f74e89e 100644 --- a/src/spicelib/devices/vsrc/vsrcext.h +++ b/src/spicelib/devices/vsrc/vsrcext.h @@ -18,3 +18,9 @@ extern int VSRCsetup(SMPmatrix*,GENmodel*,CKTcircuit*,int*); extern int VSRCunsetup(GENmodel*,CKTcircuit*); extern int VSRCpzSetup(SMPmatrix*,GENmodel*,CKTcircuit*,int*); extern int VSRCtemp(GENmodel*,CKTcircuit*); + +#ifdef KLU +extern int VSRCbindCSC (GENmodel*, CKTcircuit*) ; +extern int VSRCbindCSCComplex (GENmodel*, CKTcircuit*) ; +extern int VSRCbindCSCComplexToReal (GENmodel*, CKTcircuit*) ; +#endif diff --git a/src/spicelib/devices/vsrc/vsrcinit.c b/src/spicelib/devices/vsrc/vsrcinit.c index db0417a0d..97af7a504 100644 --- a/src/spicelib/devices/vsrc/vsrcinit.c +++ b/src/spicelib/devices/vsrc/vsrcinit.c @@ -66,6 +66,11 @@ SPICEdev VSRCinfo = { .DEVdump = NULL, .DEVacct = NULL, #endif +#ifdef KLU + .DEVbindCSC = VSRCbindCSC, + .DEVbindCSCComplex = VSRCbindCSCComplex, + .DEVbindCSCComplexToReal = VSRCbindCSCComplexToReal, +#endif };