Introducing mobility reduction over Vgs. Model parameter: theta
This commit is contained in:
parent
96a5ea0353
commit
8b424dd3d3
|
|
@ -64,6 +64,7 @@ IFparm VDMOSmPTable[] = { /* model parameters */
|
||||||
IOP("kp", VDMOS_MOD_KP, IF_REAL, "Transconductance parameter"),
|
IOP("kp", VDMOS_MOD_KP, IF_REAL, "Transconductance parameter"),
|
||||||
IOP("phi", VDMOS_MOD_PHI, IF_REAL, "Surface potential"),
|
IOP("phi", VDMOS_MOD_PHI, IF_REAL, "Surface potential"),
|
||||||
IOP("lambda",VDMOS_MOD_LAMBDA,IF_REAL, "Channel length modulation"),
|
IOP("lambda",VDMOS_MOD_LAMBDA,IF_REAL, "Channel length modulation"),
|
||||||
|
IOP("theta", VDMOS_MOD_THETA, IF_REAL, "Vgs dependence on mobility"),
|
||||||
IOP("rd", VDMOS_MOD_RD, IF_REAL, "Drain ohmic resistance"),
|
IOP("rd", VDMOS_MOD_RD, IF_REAL, "Drain ohmic resistance"),
|
||||||
IOP("rs", VDMOS_MOD_RS, IF_REAL, "Source ohmic resistance"),
|
IOP("rs", VDMOS_MOD_RS, IF_REAL, "Source ohmic resistance"),
|
||||||
IOP("rg", VDMOS_MOD_RG, IF_REAL, "Gate ohmic resistance"),
|
IOP("rg", VDMOS_MOD_RG, IF_REAL, "Gate ohmic resistance"),
|
||||||
|
|
|
||||||
|
|
@ -265,8 +265,10 @@ typedef struct sVDMOSmodel { /* model structure for a resistor */
|
||||||
double VDMOSvt0; /* input - use tVto */
|
double VDMOSvt0; /* input - use tVto */
|
||||||
double VDMOSphi; /* input - use tPhi */
|
double VDMOSphi; /* input - use tPhi */
|
||||||
double VDMOSlambda;
|
double VDMOSlambda;
|
||||||
|
double VDMOStheta;
|
||||||
double VDMOSfNcoef;
|
double VDMOSfNcoef;
|
||||||
double VDMOSfNexp;
|
double VDMOSfNexp;
|
||||||
|
|
||||||
double VDMOScgdmin;
|
double VDMOScgdmin;
|
||||||
double VDMOScgdmax;
|
double VDMOScgdmax;
|
||||||
double VDMOSa;
|
double VDMOSa;
|
||||||
|
|
@ -313,6 +315,7 @@ typedef struct sVDMOSmodel { /* model structure for a resistor */
|
||||||
unsigned VDIOdepletionCapCoeffGiven :1;
|
unsigned VDIOdepletionCapCoeffGiven :1;
|
||||||
unsigned VDMOSphiGiven :1;
|
unsigned VDMOSphiGiven :1;
|
||||||
unsigned VDMOSlambdaGiven :1;
|
unsigned VDMOSlambdaGiven :1;
|
||||||
|
unsigned VDMOSthetaGiven :1;
|
||||||
unsigned VDMOStnomGiven :1;
|
unsigned VDMOStnomGiven :1;
|
||||||
unsigned VDMOSfNcoefGiven :1;
|
unsigned VDMOSfNcoefGiven :1;
|
||||||
unsigned VDMOSfNexpGiven :1;
|
unsigned VDMOSfNexpGiven :1;
|
||||||
|
|
@ -367,6 +370,7 @@ enum {
|
||||||
VDMOS_MOD_KP,
|
VDMOS_MOD_KP,
|
||||||
VDMOS_MOD_PHI,
|
VDMOS_MOD_PHI,
|
||||||
VDMOS_MOD_LAMBDA,
|
VDMOS_MOD_LAMBDA,
|
||||||
|
VDMOS_MOD_THETA,
|
||||||
VDMOS_MOD_RD,
|
VDMOS_MOD_RD,
|
||||||
VDMOS_MOD_RS,
|
VDMOS_MOD_RS,
|
||||||
VDMOS_MOD_RG,
|
VDMOS_MOD_RG,
|
||||||
|
|
|
||||||
|
|
@ -282,53 +282,58 @@ VDMOSload(GENmodel *inModel, CKTcircuit *ckt)
|
||||||
*/
|
*/
|
||||||
double betap;
|
double betap;
|
||||||
double vgst;
|
double vgst;
|
||||||
|
double onfg, fgate, Betam, dfgdvg;
|
||||||
|
|
||||||
von = (model->VDMOSvt0*model->VDMOStype);
|
von = (model->VDMOSvt0*model->VDMOStype);
|
||||||
vgst = (here->VDMOSmode == 1 ? vgs : vgd) - von;
|
vgst = (here->VDMOSmode == 1 ? vgs : vgd) - von;
|
||||||
vdsat = MAX(vgst, 0);
|
vdsat = MAX(vgst, 0);
|
||||||
|
onfg = 1.0+model->VDMOStheta*vgst;
|
||||||
|
fgate = 1.0/onfg;
|
||||||
|
Betam = Beta * fgate;
|
||||||
|
dfgdvg = -model->VDMOStheta*fgate*fgate;
|
||||||
/* drain current including subthreshold current
|
/* drain current including subthreshold current
|
||||||
* numerical differentiation for gd and gm with a delta of 2 mV */
|
* numerical differentiation for gd and gm with a delta of 2 mV */
|
||||||
if (model->VDMOSksubthresGiven && (here->VDMOSmode == 1)) {
|
if (model->VDMOSksubthresGiven && (here->VDMOSmode == 1)) {
|
||||||
double delta = 0.001;
|
double delta = 0.001;
|
||||||
cdrain = cweakinv(model->VDMOSksubthres, model->VDMOSsubshift, vgst, vds, model->VDMOSlambda,
|
cdrain = cweakinv(model->VDMOSksubthres, model->VDMOSsubshift, vgst, vds, model->VDMOSlambda,
|
||||||
Beta, vt, model->VDMOSmtr);
|
Betam, vt, model->VDMOSmtr);
|
||||||
/* gd */
|
/* gd */
|
||||||
double vds1 = vds + delta;
|
double vds1 = vds + delta;
|
||||||
double cdrp = cweakinv(model->VDMOSksubthres, model->VDMOSsubshift, vgst, vds1, model->VDMOSlambda,
|
double cdrp = cweakinv(model->VDMOSksubthres, model->VDMOSsubshift, vgst, vds1, model->VDMOSlambda,
|
||||||
Beta, vt, model->VDMOSmtr);
|
Betam, vt, model->VDMOSmtr);
|
||||||
vds1 = vds - delta;
|
vds1 = vds - delta;
|
||||||
double cdrm = cweakinv(model->VDMOSksubthres, model->VDMOSsubshift, vgst, vds1, model->VDMOSlambda,
|
double cdrm = cweakinv(model->VDMOSksubthres, model->VDMOSsubshift, vgst, vds1, model->VDMOSlambda,
|
||||||
Beta, vt, model->VDMOSmtr);
|
Betam, vt, model->VDMOSmtr);
|
||||||
here->VDMOSgds = (cdrp - cdrm) / (2. * delta);
|
here->VDMOSgds = (cdrp - cdrm) / (2. * delta);
|
||||||
/* gm */
|
/* gm */
|
||||||
double vgst1 = vgst + delta;
|
double vgst1 = vgst + delta;
|
||||||
cdrp = cweakinv(model->VDMOSksubthres, model->VDMOSsubshift, vgst1, vds, model->VDMOSlambda,
|
cdrp = cweakinv(model->VDMOSksubthres, model->VDMOSsubshift, vgst1, vds, model->VDMOSlambda,
|
||||||
Beta, vt, model->VDMOSmtr);
|
Betam, vt, model->VDMOSmtr);
|
||||||
vgst1 = vgst - delta;
|
vgst1 = vgst - delta;
|
||||||
cdrm = cweakinv(model->VDMOSksubthres, model->VDMOSsubshift, vgst1, vds, model->VDMOSlambda,
|
cdrm = cweakinv(model->VDMOSksubthres, model->VDMOSsubshift, vgst1, vds, model->VDMOSlambda,
|
||||||
Beta, vt, model->VDMOSmtr);
|
Betam, vt, model->VDMOSmtr);
|
||||||
here->VDMOSgm = (cdrp - cdrm) / (2. * delta);
|
here->VDMOSgm = (cdrp - cdrm) / (2. * delta) * fgate + dfgdvg * cdrain;
|
||||||
}
|
}
|
||||||
else if (model->VDMOSsubslGiven && (here->VDMOSmode == 1)) {
|
else if (model->VDMOSsubslGiven && (here->VDMOSmode == 1)) {
|
||||||
double delta = 0.001;
|
double delta = 0.001;
|
||||||
cdrain = cweakinv2(model->VDMOSsubsl, model->VDMOSsubshift, vgst, vds, model->VDMOSlambda,
|
cdrain = cweakinv2(model->VDMOSsubsl, model->VDMOSsubshift, vgst, vds, model->VDMOSlambda,
|
||||||
Beta, vt, model->VDMOSmtr);
|
Betam, vt, model->VDMOSmtr);
|
||||||
/* gd */
|
/* gd */
|
||||||
double vds1 = vds + delta;
|
double vds1 = vds + delta;
|
||||||
double cdrp = cweakinv2(model->VDMOSsubsl, model->VDMOSsubshift, vgst, vds1, model->VDMOSlambda,
|
double cdrp = cweakinv2(model->VDMOSsubsl, model->VDMOSsubshift, vgst, vds1, model->VDMOSlambda,
|
||||||
Beta, vt, model->VDMOSmtr);
|
Betam, vt, model->VDMOSmtr);
|
||||||
vds1 = vds - delta;
|
vds1 = vds - delta;
|
||||||
double cdrm = cweakinv2(model->VDMOSsubsl, model->VDMOSsubshift, vgst, vds1, model->VDMOSlambda,
|
double cdrm = cweakinv2(model->VDMOSsubsl, model->VDMOSsubshift, vgst, vds1, model->VDMOSlambda,
|
||||||
Beta, vt, model->VDMOSmtr);
|
Betam, vt, model->VDMOSmtr);
|
||||||
here->VDMOSgds = (cdrp - cdrm) / (2. * delta);
|
here->VDMOSgds = (cdrp - cdrm) / (2. * delta);
|
||||||
/* gm */
|
/* gm */
|
||||||
double vgst1 = vgst + delta;
|
double vgst1 = vgst + delta;
|
||||||
cdrp = cweakinv2(model->VDMOSsubsl, model->VDMOSsubshift, vgst1, vds, model->VDMOSlambda,
|
cdrp = cweakinv2(model->VDMOSsubsl, model->VDMOSsubshift, vgst1, vds, model->VDMOSlambda,
|
||||||
Beta, vt, model->VDMOSmtr);
|
Betam, vt, model->VDMOSmtr);
|
||||||
vgst1 = vgst - delta;
|
vgst1 = vgst - delta;
|
||||||
cdrm = cweakinv2(model->VDMOSsubsl, model->VDMOSsubshift, vgst1, vds, model->VDMOSlambda,
|
cdrm = cweakinv2(model->VDMOSsubsl, model->VDMOSsubshift, vgst1, vds, model->VDMOSlambda,
|
||||||
Beta, vt, model->VDMOSmtr);
|
Betam, vt, model->VDMOSmtr);
|
||||||
here->VDMOSgm = (cdrp - cdrm) / (2. * delta);
|
here->VDMOSgm = (cdrp - cdrm) / (2. * delta) * fgate + dfgdvg * cdrain;
|
||||||
} else {
|
} else {
|
||||||
if (vgst <= 0) {
|
if (vgst <= 0) {
|
||||||
/*
|
/*
|
||||||
|
|
@ -343,20 +348,20 @@ VDMOSload(GENmodel *inModel, CKTcircuit *ckt)
|
||||||
*/
|
*/
|
||||||
/* scale vds with mtr */
|
/* scale vds with mtr */
|
||||||
double mtr = model->VDMOSmtr;
|
double mtr = model->VDMOSmtr;
|
||||||
betap = Beta*(1 + model->VDMOSlambda*(vds*here->VDMOSmode));
|
betap = Betam*(1 + model->VDMOSlambda*(vds*here->VDMOSmode));
|
||||||
if (vgst <= (vds * here->VDMOSmode) * mtr) {
|
if (vgst <= (vds * here->VDMOSmode) * mtr) {
|
||||||
cdrain = betap*vgst*vgst*.5;
|
cdrain = betap*vgst*vgst*.5;
|
||||||
here->VDMOSgm = betap*vgst;
|
here->VDMOSgm = betap*vgst * fgate + dfgdvg * cdrain;
|
||||||
here->VDMOSgds = model->VDMOSlambda*Beta*vgst*vgst*.5;
|
here->VDMOSgds = model->VDMOSlambda*Betam*vgst*vgst*.5;
|
||||||
} else {
|
} else {
|
||||||
/*
|
/*
|
||||||
* linear region
|
* linear region
|
||||||
*/
|
*/
|
||||||
cdrain = betap * (vds * here->VDMOSmode) * mtr *
|
cdrain = betap * (vds * here->VDMOSmode) * mtr *
|
||||||
(vgst - .5 * (vds*here->VDMOSmode) * mtr);
|
(vgst - .5 * (vds*here->VDMOSmode) * mtr);
|
||||||
here->VDMOSgm = betap * (vds * here->VDMOSmode) * mtr;
|
here->VDMOSgm = betap * (vds * here->VDMOSmode) * mtr * fgate + dfgdvg * cdrain;
|
||||||
here->VDMOSgds = betap * (vgst - (vds * here->VDMOSmode) * mtr) +
|
here->VDMOSgds = betap * (vgst - (vds * here->VDMOSmode) * mtr) +
|
||||||
model->VDMOSlambda * Beta *
|
model->VDMOSlambda * Betam *
|
||||||
(vds * here->VDMOSmode) * mtr *
|
(vds * here->VDMOSmode) * mtr *
|
||||||
(vgst - .5 * (vds * here->VDMOSmode) * mtr);
|
(vgst - .5 * (vds * here->VDMOSmode) * mtr);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -36,6 +36,9 @@ VDMOSmAsk(CKTcircuit *ckt, GENmodel *inst, int which, IFvalue *value)
|
||||||
case VDMOS_MOD_LAMBDA:
|
case VDMOS_MOD_LAMBDA:
|
||||||
value->rValue = model->VDMOSlambda;
|
value->rValue = model->VDMOSlambda;
|
||||||
return(OK);
|
return(OK);
|
||||||
|
case VDMOS_MOD_THETA:
|
||||||
|
value->rValue = model->VDMOStheta;
|
||||||
|
return(OK);
|
||||||
case VDMOS_MOD_RD:
|
case VDMOS_MOD_RD:
|
||||||
value->rValue = model->VDMOSdrainResistance;
|
value->rValue = model->VDMOSdrainResistance;
|
||||||
return(OK);
|
return(OK);
|
||||||
|
|
|
||||||
|
|
@ -35,6 +35,10 @@ VDMOSmParam(int param, IFvalue *value, GENmodel *inModel)
|
||||||
model->VDMOSlambda = value->rValue;
|
model->VDMOSlambda = value->rValue;
|
||||||
model->VDMOSlambdaGiven = TRUE;
|
model->VDMOSlambdaGiven = TRUE;
|
||||||
break;
|
break;
|
||||||
|
case VDMOS_MOD_THETA:
|
||||||
|
model->VDMOStheta = value->rValue;
|
||||||
|
model->VDMOSthetaGiven = TRUE;
|
||||||
|
break;
|
||||||
case VDMOS_MOD_RD:
|
case VDMOS_MOD_RD:
|
||||||
model->VDMOSdrainResistance = value->rValue;
|
model->VDMOSdrainResistance = value->rValue;
|
||||||
model->VDMOSdrainResistanceGiven = TRUE;
|
model->VDMOSdrainResistanceGiven = TRUE;
|
||||||
|
|
|
||||||
|
|
@ -54,6 +54,9 @@ VDMOSsetup(SMPmatrix *matrix, GENmodel *inModel, CKTcircuit *ckt,
|
||||||
if (!model->VDMOSlambdaGiven) {
|
if (!model->VDMOSlambdaGiven) {
|
||||||
model->VDMOSlambda = 0;
|
model->VDMOSlambda = 0;
|
||||||
}
|
}
|
||||||
|
if (!model->VDMOSthetaGiven) {
|
||||||
|
model->VDMOStheta = 0;
|
||||||
|
}
|
||||||
if (!model->VDMOSfNcoefGiven) {
|
if (!model->VDMOSfNcoefGiven) {
|
||||||
model->VDMOSfNcoef = 0;
|
model->VDMOSfNcoef = 0;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue