⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 mesaload.c

📁 ngspice又一个电子CAD仿真软件代码.功能更全
💻 C
📖 第 1 页 / 共 3 页
字号:
/**********Copyright 1993: T. Ytterdal, K. Lee, M. Shur and T. A. Fjeldly. All rights reserved.Author: Trond Ytterdal**********/#include "ngspice.h"#include "devdefs.h"#include "cktdefs.h"#include "mesadefs.h"#include "const.h"#include "trandefs.h"#include "sperror.h"#include "suffix.h"/*#define true 1#define false 0*/#define EPSILONGAAS (12.244*8.85418e-12)#define W (here->MESAwidth)#define L (here->MESAlength)static void mesa1(MESAmodel*, MESAinstance*, double, double, double,                  double*, double*, double*, double*,double*);static void mesa2(MESAmodel*, MESAinstance*, double, double, double,                  double*, double*, double*, double*,double*);                  static void mesa3(MESAmodel*, MESAinstance*, double, double, double,                  double*, double*, double*, double*,double*);void Pause(void);intMESAload(GENmodel *inModel, CKTcircuit *ckt){    MESAmodel *model = (MESAmodel*)inModel;    MESAinstance *here;    double capgd;    double capgs;    double cd;    double cdhat = 0.0;    double cdrain;    double cdreq;    double ceq;    double ceqgd;    double ceqgs;    double cg;    double cgd;    double cgs;    double cghat = 0.0;    double arg;    double earg;    double delvds;    double delvgd;    double delvgs;    double delvgspp=0;    double delvgdpp=0;    double evgd;    double evgs;    double gds;                                double geq;    double ggd;    double ggs;    double gm;    double ggspp=0;    double cgspp=0;    double ggdpp=0;    double cgdpp=0;    double vcrits;    double vcritd;    double vds=0;    double vgd=0;    double vgs=0;    double vgspp=0;    double vgdpp=0;        double vgs1=0;    double vgd1=0;    double xfact;    double temp;    double vted;    double vtes;    double vtd;    double vts;    double von;    double ccorr;    int inverse=FALSE;    int icheck;    int ichk1;    int error;    double m;    /*  loop through all the models */    for( ; model != NULL; model = model->MESAnextModel ) {        /* loop through all the instances of the model */        for (here = model->MESAinstances; here != NULL ;                here=here->MESAnextInstance) {            if (here->MESAowner != ARCHme) continue;            /*             *  dc model parameters              */            vcrits = here->MESAvcrits;            vcritd = here->MESAvcritd;            vtd  = CONSTKoverQ * here->MESAtd;            vts  = CONSTKoverQ * here->MESAts;            vted = model->MESAn*vtd;            vtes = model->MESAn*vts;            /*             *    initialization             */            icheck = 1;            if( ckt->CKTmode & MODEINITSMSIG) {                vgs = *(ckt->CKTstate0 + here->MESAvgs);                vgd = *(ckt->CKTstate0 + here->MESAvgd);                vgspp = *(ckt->CKTstate0 + here->MESAvgspp);                vgdpp = *(ckt->CKTstate0 + here->MESAvgdpp);            } else if (ckt->CKTmode & MODEINITTRAN) {                vgs = *(ckt->CKTstate1 + here->MESAvgs);                vgd = *(ckt->CKTstate1 + here->MESAvgd);                vgspp = *(ckt->CKTstate1 + here->MESAvgspp);                vgdpp = *(ckt->CKTstate1 + here->MESAvgdpp);            } else if ( (ckt->CKTmode & MODEINITJCT) &&                    (ckt->CKTmode & MODETRANOP) &&                    (ckt->CKTmode & MODEUIC) ) {                vds = here->MESAicVDS;                vgs = here->MESAicVGS;                vgd = vgs-vds;                vgspp = vgs;                vgdpp = vgd;            } else if ( (ckt->CKTmode & MODEINITJCT) &&                    (here->MESAoff == 0)  ) {                vgs = -1;                vgd = -1;                vgspp = 0;                vgdpp = 0;            } else if( (ckt->CKTmode & MODEINITJCT) ||                    ((ckt->CKTmode & MODEINITFIX) && (here->MESAoff))) {                vgs = 0;                vgd = 0;                vgspp = 0;                vgdpp = 0;            } else {#ifndef PREDICTOR                if(ckt->CKTmode & MODEINITPRED) {                    xfact = ckt->CKTdelta/ckt->CKTdeltaOld[2];                    *(ckt->CKTstate0 + here->MESAvgs) =                             *(ckt->CKTstate1 + here->MESAvgs);                    vgs = (1+xfact) * *(ckt->CKTstate1 + here->MESAvgs) -                           xfact * *(ckt->CKTstate2 + here->MESAvgs);                    *(ckt->CKTstate0 + here->MESAvgspp) =                            *(ckt->CKTstate1 + here->MESAvgspp);                    vgspp = (1+xfact) * *(ckt->CKTstate1 + here->MESAvgspp) -                           xfact * *(ckt->CKTstate2 + here->MESAvgspp);                    *(ckt->CKTstate0 + here->MESAvgd) =                             *(ckt->CKTstate1 + here->MESAvgd);                    vgd = (1+xfact)* *(ckt->CKTstate1 + here->MESAvgd) -                           xfact * *(ckt->CKTstate2 + here->MESAvgd);                    *(ckt->CKTstate0 + here->MESAvgdpp) =                            *(ckt->CKTstate1 + here->MESAvgdpp);                    vgdpp = (1+xfact) * *(ckt->CKTstate1 + here->MESAvgdpp) -                           xfact * *(ckt->CKTstate2 + here->MESAvgdpp);                    *(ckt->CKTstate0 + here->MESAcg) =                             *(ckt->CKTstate1 + here->MESAcg);                    *(ckt->CKTstate0 + here->MESAcd) =                             *(ckt->CKTstate1 + here->MESAcd);                    *(ckt->CKTstate0 + here->MESAcgd) =                            *(ckt->CKTstate1 + here->MESAcgd);                    *(ckt->CKTstate0 + here->MESAcgs) =                            *(ckt->CKTstate1 + here->MESAcgs);                                                *(ckt->CKTstate0 + here->MESAgm) =                            *(ckt->CKTstate1 + here->MESAgm);                    *(ckt->CKTstate0 + here->MESAgds) =                            *(ckt->CKTstate1 + here->MESAgds);                    *(ckt->CKTstate0 + here->MESAggs) =                            *(ckt->CKTstate1 + here->MESAggs);                    *(ckt->CKTstate0 + here->MESAggd) =                            *(ckt->CKTstate1 + here->MESAggd);                    *(ckt->CKTstate0 + here->MESAggspp) =                            *(ckt->CKTstate1 + here->MESAggspp);                    *(ckt->CKTstate0 + here->MESAcgspp) =                            *(ckt->CKTstate1 + here->MESAcgspp);                    *(ckt->CKTstate0 + here->MESAggdpp) =                            *(ckt->CKTstate1 + here->MESAggdpp);                    *(ckt->CKTstate0 + here->MESAcgdpp) =                            *(ckt->CKTstate1 + here->MESAcgdpp);                } else {#endif /* PREDICTOR */                    /*                     *  compute new nonlinear branch voltages                      */                    vgs = (*(ckt->CKTrhsOld+ here->MESAgatePrimeNode)-                        *(ckt->CKTrhsOld+here->MESAsourcePrimeNode));                    vgd = (*(ckt->CKTrhsOld+here->MESAgatePrimeNode)-                        *(ckt->CKTrhsOld+here->MESAdrainPrimeNode));                    vgspp = (*(ckt->CKTrhsOld+here->MESAgatePrimeNode)-                        *(ckt->CKTrhsOld+here->MESAsourcePrmPrmNode));                    vgdpp = (*(ckt->CKTrhsOld+here->MESAgatePrimeNode)-                        *(ckt->CKTrhsOld+here->MESAdrainPrmPrmNode));                        #ifndef PREDICTOR                }#endif /* PREDICTOR */                delvgs=vgs - *(ckt->CKTstate0 + here->MESAvgs);                delvgd=vgd - *(ckt->CKTstate0 + here->MESAvgd);                delvds=delvgs - delvgd;                delvgspp = vgspp - *(ckt->CKTstate0 + here->MESAvgspp);                delvgdpp = vgdpp - *(ckt->CKTstate0 + here->MESAvgdpp);                cghat= *(ckt->CKTstate0 + here->MESAcg) +                         *(ckt->CKTstate0 + here->MESAggd)*delvgd +                        *(ckt->CKTstate0 + here->MESAggs)*delvgs +                        *(ckt->CKTstate0 + here->MESAggspp)*delvgspp+                        *(ckt->CKTstate0 + here->MESAggdpp)*delvgdpp;                cdhat= *(ckt->CKTstate0 + here->MESAcd) +                        *(ckt->CKTstate0 + here->MESAgm)*delvgs +                        *(ckt->CKTstate0 + here->MESAgds)*delvds -                        *(ckt->CKTstate0 + here->MESAggd)*delvgd;                /*                 *   bypass if solution has not changed                  */                if((ckt->CKTbypass) &&                    (!(ckt->CKTmode & MODEINITPRED)) &&                    (fabs(delvgs) < ckt->CKTreltol*MAX(fabs(vgs),                        fabs(*(ckt->CKTstate0 + here->MESAvgs)))+                        ckt->CKTvoltTol) )                if((fabs(delvgd) < ckt->CKTreltol*MAX(fabs(vgd),                        fabs(*(ckt->CKTstate0 + here->MESAvgd)))+                        ckt->CKTvoltTol))                if((fabs(delvgspp) < ckt->CKTreltol*MAX(fabs(vgspp),                        fabs(*(ckt->CKTstate0 + here->MESAvgspp)))+                        ckt->CKTvoltTol))                if((fabs(delvgdpp) < ckt->CKTreltol*MAX(fabs(vgdpp),                        fabs(*(ckt->CKTstate0 + here->MESAvgdpp)))+                        ckt->CKTvoltTol))                if((fabs(cghat-*(ckt->CKTstate0 + here->MESAcg))                         < ckt->CKTreltol*MAX(fabs(cghat),                        fabs(*(ckt->CKTstate0 + here->MESAcg)))+                        ckt->CKTabstol))                if((fabs(cdhat-*(ckt->CKTstate0 + here->MESAcd))                        < ckt->CKTreltol*MAX(fabs(cdhat),                        fabs(*(ckt->CKTstate0 + here->MESAcd)))+                        ckt->CKTabstol)) {                    /* we can do a bypass */                    vgs= *(ckt->CKTstate0 + here->MESAvgs);                    vgd= *(ckt->CKTstate0 + here->MESAvgd);                    vds= vgs-vgd;                    vgspp = *(ckt->CKTstate0 + here->MESAvgspp);                    vgdpp = *(ckt->CKTstate0 + here->MESAvgdpp);                    cg= *(ckt->CKTstate0 + here->MESAcg);                    cd= *(ckt->CKTstate0 + here->MESAcd);                    cgs= *(ckt->CKTstate0 + here->MESAcgs);                    cgd= *(ckt->CKTstate0 + here->MESAcgd);                    gm= *(ckt->CKTstate0 + here->MESAgm);                    gds= *(ckt->CKTstate0 + here->MESAgds);                    ggs= *(ckt->CKTstate0 + here->MESAggs);                    ggd= *(ckt->CKTstate0 + here->MESAggd);                    ggspp = *(ckt->CKTstate0 + here->MESAggspp);                    cgspp = *(ckt->CKTstate0 + here->MESAcgspp);                    ggdpp = *(ckt->CKTstate0 + here->MESAggdpp);                    cgdpp = *(ckt->CKTstate0 + here->MESAcgdpp);                    goto load;                }                /*                 *  limit nonlinear branch voltages                  */                ichk1=1;                vgs = DEVpnjlim(vgs,*(ckt->CKTstate0 + here->MESAvgs),vtes,                        vcrits, &icheck);                vgd = DEVpnjlim(vgd,*(ckt->CKTstate0 + here->MESAvgd),vted,                        vcritd,&ichk1);                if (ichk1 == 1) {                    icheck=1;                }                vgs = DEVfetlim(vgs,*(ckt->CKTstate0 + here->MESAvgs),                        here->MESAtVto);                vgd = DEVfetlim(vgd,*(ckt->CKTstate0 + here->MESAvgd),                        here->MESAtVto);                if(here->MESAsourcePrmPrmNode == here->MESAsourcePrimeNode)                  vgspp = vgs;                if(here->MESAdrainPrmPrmNode == here->MESAdrainPrimeNode)                  vgdpp = vgd;            }            /*             *   determine dc current and derivatives              */            vds = vgs-vgd;                                  arg = -vgs*model->MESAdel/vts;            earg = exp(arg);            evgs = exp(vgs/vtes);            ggs  = here->MESAcsatfs*evgs/vtes+here->MESAggrwl*earg*(1-arg)+ckt->CKTgmin;            cgs  = here->MESAcsatfs*(evgs-1)+here->MESAggrwl*vgs*earg+                   ckt->CKTgmin*vgs;            cg   = cgs;                         arg = -vgd*model->MESAdel/vtd;            earg = exp(arg);            evgd = exp(vgd/vted);            ggd  = here->MESAcsatfd*evgd/vted+here->MESAggrwl*earg*(1-arg)+ckt->CKTgmin;            cgd  = here->MESAcsatfd*(evgd-1)+here->MESAggrwl*vgd*earg+                   ckt->CKTgmin*vgd;            cg = cg+cgd;                        if(vds < 0) {              vds = -vds;              inverse = TRUE;            }            von = here->MESAtVto+model->MESAks*(*(ckt->CKTrhsOld+here->MESAsourcePrimeNode)-model->MESAvsg);            if(model->MESAlevel == 2)              mesa1(model,here,inverse?vgd:vgs,vds,von,&cdrain,&gm,&gds,&capgs,&capgd);            else if(model->MESAlevel == 3)              mesa2(model,here,inverse?vgd:vgs,vds,von,&cdrain,&gm,&gds,&capgs,&capgd);            else if(model->MESAlevel == 4)              mesa3(model,here,inverse?vgd:vgs,vds,von,&cdrain,&gm,&gds,&capgs,&capgd);            if(inverse) {              cdrain = -cdrain;              vds = -vds;              temp = capgs;              capgs = capgd;              capgd = temp;            }            /*             *   compute equivalent drain current source              */            cd = cdrain - cgd;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -