Jspice3
b1eval.c
Go to the documentation of this file.
1 /***************************************************************************
2 JSPICE3 adaptation of Spice3f2 - Copyright (c) Stephen R. Whiteley 1992
3 Copyright 1990 Regents of the University of California. All rights reserved.
4 Authors: 1985 Hong J. Park, Thomas L. Quarles
5  1993 Stephen R. Whiteley
6 ****************************************************************************/
7 
8 #include "spice.h"
9 #include <stdio.h>
10 #include <math.h>
11 #include "bsim1def.h"
12 #include "const.h"
13 #include "util.h"
14 
15 
16 /* This routine evaluates the drain current, its derivatives and the
17  * charges associated with the gate,bulk and drain terminal
18  * using the BSIM1 (Berkeley Short-Channel IGFET Model) Equations.
19  */
20 void
21 B1evaluate(vds,vbs,vgs,here,model,gmPointer,gdsPointer,gmbsPointer,
22  qgPointer,qbPointer,qdPointer,cggbPointer,cgdbPointer,cgsbPointer,
23  cbgbPointer,cbdbPointer,cbsbPointer,cdgbPointer,cddbPointer,
24  cdsbPointer,cdrainPointer,vonPointer,vdsatPointer,ckt)
25 
26  register CKTcircuit *ckt;
27  register B1model *model;
28  register B1instance *here;
29  double vds;
30  double vbs;
31  double vgs;
32  double *gmPointer;
33  double *gdsPointer;
34  double *gmbsPointer;
35  double *qgPointer;
36  double *qbPointer;
37  double *qdPointer;
38  double *cggbPointer;
39  double *cgdbPointer;
40  double *cgsbPointer;
41  double *cbgbPointer;
42  double *cbdbPointer;
43  double *cbsbPointer;
44  double *cdgbPointer;
45  double *cddbPointer;
46  double *cdsbPointer;
47  double *cdrainPointer;
48  double *vonPointer;
49  double *vdsatPointer;
50 
51  {
52  double gm;
53  double gds;
54  double gmbs;
55  double qg;
56  double qb;
57  double qd;
58  double cggb;
59  double cgdb;
60  double cgsb;
61  double cbgb;
62  double cbdb;
63  double cbsb;
64  double cdgb;
65  double cddb;
66  double cdsb;
67  double Vfb;
68  double Phi;
69  double K1;
70  double K2;
71  double Vdd;
72  double Ugs;
73  double Uds;
74  double dUgsdVbs;
75  double Leff;
76  double dUdsdVbs;
77  double dUdsdVds;
78  double Eta;
79  double dEtadVds;
80  double dEtadVbs;
81  double Vpb;
82  double SqrtVpb;
83  double Von;
84  double Vth;
85  double dVthdVbs;
86  double dVthdVds;
87  double Vgs_Vth;
88  double DrainCurrent;
89  double G;
90  double A;
91  double Arg;
92  double dGdVbs;
93  double dAdVbs;
94  double Beta;
95  double Beta_Vds_0;
96  double BetaVdd;
97  double dBetaVdd_dVds;
98  double Beta0;
99  double dBeta0dVds;
100  double dBeta0dVbs;
101  double VddSquare;
102  double C1;
103  double C2;
104  double dBetaVdd_dVbs;
105  double dBeta_Vds_0_dVbs;
106  double dC1dVbs;
107  double dC2dVbs;
108  double dBetadVgs;
109  double dBetadVds;
110  double dBetadVbs;
111  double VdsSat;
112  double Argl1;
113  double Argl2;
114  double Vc;
115  double Term1;
116  double K;
117  double Args1;
118  double dVcdVgs;
119  double dVcdVds;
120  double dVcdVbs;
121  double dKdVc;
122  double dKdVgs;
123  double dKdVds;
124  double dKdVbs;
125  double Args2;
126  double Args3;
127  double Warg1;
128  double Vcut;
129  double N;
130  double N0;
131  double NB;
132  double ND;
133  double Warg2;
134  double Wds;
135  double Wgs;
136  double Ilimit;
137  double Iexp;
138  double Temp1;
139  double Vth0;
140  double Arg1;
141  double Arg2;
142  double Arg3;
143  double Arg5;
144  double Ent;
145  double Vcom;
146  double Vgb;
147  double Vgb_Vfb;
148  double VdsPinchoff;
149  double EntSquare;
150  double Vgs_VthSquare;
151  double Argl3;
152  double Argl4;
153  double Argl5;
154  double Argl6;
155  double Argl7;
156  double Argl8;
157  double Argl9;
158  double dEntdVds;
159  double dEntdVbs;
160  double cgbb;
161  double cdbb;
162  double cbbb;
163  double WLCox;
164  double Vtsquare;
165  double Temp3;
166  int ChargeComputationNeeded;
167  double co4v15;
168 
169  if (ckt->CKTmode & (MODEAC | MODETRAN)) {
170  ChargeComputationNeeded = 1;
171  } else if (ckt->CKTmode & MODEINITSMSIG) {
172  ChargeComputationNeeded = 1;
173  } else if ((ckt->CKTmode & MODETRANOP) && (ckt->CKTmode & MODEUIC)) {
174  ChargeComputationNeeded = 1;
175  } else {
176  ChargeComputationNeeded = 0;
177  }
178 
179  Vfb = here->B1vfb;
180  Phi = here->B1phi;
181  K1 = here->B1K1;
182  K2 = here->B1K2;
183  Vdd = model->B1vdd;
184  if((Ugs = here->B1ugs + here->B1ugsB * vbs) <= 0 ) {
185  Ugs = 0;
186  dUgsdVbs = 0.0;
187  } else {
188  dUgsdVbs = here->B1ugsB;
189  }
190  if((Uds = here->B1uds + here->B1udsB * vbs +
191  here->B1udsD*(vds-Vdd)) <= 0 ) {
192  Uds = 0.0;
193  dUdsdVbs = dUdsdVds = 0.0;
194  } else {
195  Leff = here->B1l * 1.e6 - model->B1deltaL; /* Leff in um */
196  Uds = Uds / Leff;
197  dUdsdVbs = here->B1udsB / Leff;
198  dUdsdVds = here->B1udsD / Leff;
199  }
200  Eta = here->B1eta + here->B1etaB * vbs + here->B1etaD *
201  (vds - Vdd);
202  if( Eta <= 0 ) {
203  Eta = 0;
204  dEtadVds = dEtadVbs = 0.0 ;
205  } else if ( Eta > 1 ) {
206  Eta = 1;
207  dEtadVds = dEtadVbs = 0;
208  } else {
209  dEtadVds = here->B1etaD;
210  dEtadVbs = here->B1etaB;
211  }
212  if( vbs < 0 ) {
213  Vpb = Phi - vbs;
214  } else {
215  Vpb = Phi;
216  }
217  SqrtVpb = sqrt( Vpb );
218  Von = Vfb + Phi + K1 * SqrtVpb - K2 * Vpb - Eta * vds;
219  Vth = Von;
220  dVthdVds = - Eta - dEtadVds * vds;
221  dVthdVbs = K2 - 0.5 * K1 / SqrtVpb - dEtadVbs * vds;
222  Vgs_Vth = vgs - Vth;
223 
224  G = 1. - 1./(1.744+0.8364 * Vpb);
225  A = 1. + 0.5*G*K1/SqrtVpb;
226  A = MAX( A, 1.0); /* Modified */
227  Arg = MAX(( 1 + Ugs * Vgs_Vth), 1.0);
228  dGdVbs = -0.8364 * (1-G) * (1-G);
229  dAdVbs = 0.25 * K1 / SqrtVpb *(2*dGdVbs + G/Vpb);
230 
231  if( Vgs_Vth < 0 ) {
232  /* cutoff */
233  DrainCurrent = 0;
234  gm = 0;
235  gds = 0;
236  gmbs = 0;
237  goto SubthresholdComputation;
238  }
239 
240  /* Quadratic Interpolation for Beta0 (Beta at vgs = 0, vds=Vds) */
241 
242  Beta_Vds_0 = (here->B1betaZero + here->B1betaZeroB * vbs);
243  BetaVdd = (here->B1betaVdd + here->B1betaVddB * vbs);
244  dBetaVdd_dVds = MAX( here->B1betaVddD, 0.0); /* Modified */
245  if( vds > Vdd ) {
246  Beta0 = BetaVdd + dBetaVdd_dVds * (vds - Vdd);
247  dBeta0dVds = dBetaVdd_dVds;
248  dBeta0dVbs = here->B1betaVddB;
249  } else {
250  VddSquare = Vdd * Vdd;
251  C1 = ( -BetaVdd + Beta_Vds_0 + dBetaVdd_dVds * Vdd) / VddSquare;
252  C2 = 2 * (BetaVdd - Beta_Vds_0) / Vdd - dBetaVdd_dVds;
253  dBeta_Vds_0_dVbs = here->B1betaZeroB;
254  dBetaVdd_dVbs = here->B1betaVddB;
255  dC1dVbs = (dBeta_Vds_0_dVbs - dBetaVdd_dVbs) / VddSquare;
256  dC2dVbs = dC1dVbs * (-2) * Vdd;
257  Beta0 = (C1 * vds + C2) * vds + Beta_Vds_0;
258  dBeta0dVds = 2*C1*vds + C2;
259  dBeta0dVbs = dC1dVbs * vds * vds + dC2dVbs * vds + dBeta_Vds_0_dVbs;
260  }
261 
262  /*Beta = Beta0 / ( 1 + Ugs * Vgs_Vth );*/
263 
264  Beta = Beta0 / Arg ;
265  dBetadVgs = - Beta * Ugs / Arg;
266  dBetadVds = dBeta0dVds / Arg - dBetadVgs * dVthdVds ;
267  dBetadVbs = dBeta0dVbs / Arg + Beta * Ugs * dVthdVbs / Arg -
268  Beta * Vgs_Vth * dUgsdVbs / Arg;
269 
270  /*VdsSat = MAX( Vgs_Vth / ( A + Uds * Vgs_Vth ), 0.0);*/
271 
272  if((Vc = Uds * Vgs_Vth / A) < 0.0 ) Vc=0.0;
273  Term1 = sqrt( 1 + 2 * Vc );
274  K = 0.5 * ( 1 + Vc + Term1 );
275  VdsSat = MAX( Vgs_Vth / ( A * sqrt(K) ) , 0.0 );
276 
277  if( vds < VdsSat ) {
278  /* Triode Region */
279  /*Argl1 = 1 + Uds * vds;*/
280  Argl1 = MAX( (1 + Uds * vds), 1.);
281  Argl2 = Vgs_Vth - 0.5 * A * vds;
282  DrainCurrent = Beta * Argl2 * vds / Argl1;
283  gm = (dBetadVgs * Argl2 * vds + Beta * vds) / Argl1;
284  gds = (dBetadVds * Argl2 * vds + Beta *
285  (Vgs_Vth - vds * dVthdVds - A * vds) -
286  DrainCurrent * (vds * dUdsdVds + Uds )) / Argl1;
287  gmbs = (dBetadVbs * Argl2 * vds + Beta * vds *
288  (- dVthdVbs - 0.5 * vds * dAdVbs ) -
289  DrainCurrent * vds * dUdsdVbs ) / Argl1;
290  } else {
291  /* Pinchoff (Saturation) Region */
292  Args1 = 1. + 1. / Term1;
293  dVcdVgs = Uds / A;
294  dVcdVds = Vgs_Vth * dUdsdVds / A - dVcdVgs * dVthdVds;
295  dVcdVbs = ( Vgs_Vth * dUdsdVbs - Uds *
296  (dVthdVbs + Vgs_Vth * dAdVbs / A ))/ A;
297  dKdVc = 0.5* Args1;
298  dKdVgs = dKdVc * dVcdVgs;
299  dKdVds = dKdVc * dVcdVds;
300  dKdVbs = dKdVc * dVcdVbs;
301  Args2 = Vgs_Vth / A / K;
302  Args3 = Args2 * Vgs_Vth;
303  DrainCurrent = 0.5 * Beta * Args3;
304  gm = 0.5 * Args3 * dBetadVgs + Beta * Args2 -
305  DrainCurrent * dKdVgs / K;
306  gds = 0.5 * Args3 * dBetadVds - Beta * Args2 * dVthdVds -
307  DrainCurrent * dKdVds / K;
308  gmbs = 0.5 * dBetadVbs * Args3 - Beta * Args2 *dVthdVbs -
309  DrainCurrent * (dAdVbs / A + dKdVbs / K );
310  }
311 
312 SubthresholdComputation:
313 
314  N0 = here->B1subthSlope;
315  Vcut = - 40. * N0 * CONSTvt0 ;
316 
317 /* The following 'if' statement has been modified so that subthreshold *
318  * current computation is always executed unless N0 >= 200. This should *
319  * get rid of the Ids kink seen on Ids-Vgs plots at low Vds. *
320  * Peter M. Lee *
321  * 6/8/90 *
322  * Old 'if' statement: *
323  * if( (N0 >= 200) || (Vgs_Vth < Vcut ) || (Vgs_Vth > (-0.5*Vcut))) */
324 
325  if (N0 >= 200) {
326  goto ChargeComputation;
327  }
328 
329  NB = here->B1subthSlopeB;
330  ND = here->B1subthSlopeD;
331  N = N0 + NB * vbs + ND * vds; /* subthreshold slope */
332  if( N < 0.5 ) N = 0.5;
333  Warg1 = exp( - vds / CONSTvt0 );
334  Wds = 1 - Warg1;
335  Wgs = exp( Vgs_Vth / ( N * CONSTvt0 ));
336  Vtsquare = CONSTvt0 * CONSTvt0 ;
337  Warg2 = 6.04965 * Vtsquare * here->B1betaZero;
338  Ilimit = 4.5 * Vtsquare * here->B1betaZero;
339  Iexp = Warg2 * Wgs * Wds;
340  DrainCurrent = DrainCurrent + Ilimit * Iexp / ( Ilimit + Iexp );
341  Temp1 = Ilimit / ( Ilimit + Iexp );
342  Temp1 = Temp1 * Temp1;
343  Temp3 = Ilimit / ( Ilimit + Wgs * Warg2 );
344  Temp3=Temp3 * Temp3 * Warg2 * Wgs;
345 /* if ( Temp3 > Ilimit ) Temp3=Ilimit;*/
346  gm = gm + Temp1 * Iexp / ( N * CONSTvt0 );
347  /* gds term has been modified to prevent blow up at Vds=0 */
348  gds = gds + Temp3 * ( -Wds / N / CONSTvt0 * (dVthdVds +
349  Vgs_Vth * ND / N ) + Warg1 / CONSTvt0 );
350  gmbs = gmbs - Temp1 * Iexp * (dVthdVbs + Vgs_Vth * NB / N ) /
351  ( N * CONSTvt0 );
352 
353 ChargeComputation:
354 
355  /* Some Limiting of DC Parameters */
356  if(DrainCurrent < 0.0) DrainCurrent = 0.0;
357  if(gm < 0.0) gm = 0.0;
358  if(gds < 0.0) gds = 0.0;
359  if(gmbs < 0.0) gmbs = 0.0;
360 
361  WLCox = model->B1Cox *
362  (here->B1l - model->B1deltaL * 1.e-6) *
363  (here->B1w - model->B1deltaW * 1.e-6) * 1.e4; /* F */
364 
365  if( ! ChargeComputationNeeded ) {
366  qg = 0;
367  qd = 0;
368  qb = 0;
369  cggb = 0;
370  cgsb = 0;
371  cgdb = 0;
372  cdgb = 0;
373  cdsb = 0;
374  cddb = 0;
375  cbgb = 0;
376  cbsb = 0;
377  cbdb = 0;
378  goto finished;
379  }
380  G = 1. - 1./(1.744+0.8364 * Vpb);
381  A = 1. + 0.5*G*K1/SqrtVpb;
382  A = MAX( A, 1.0); /* Modified */
383  /*Arg = 1 + Ugs * Vgs_Vth;*/
384  dGdVbs = -0.8364 * (1-G) * (1-G);
385  dAdVbs = 0.25 * K1 / SqrtVpb *(2*dGdVbs + G/Vpb);
386  Phi = MAX( 0.1, Phi);
387 
388  if( model->B1channelChargePartitionFlag >= 1 ) {
389 
390 /*0/100 partitioning for drain/source chArges at the saturation region*/
391  Vth0 = Vfb + Phi + K1 * SqrtVpb;
392  Vgs_Vth = vgs - Vth0;
393  Arg1 = A * vds;
394  Arg2 = Vgs_Vth - 0.5 * Arg1;
395  Arg3 = vds - Arg1;
396  Arg5 = Arg1 * Arg1;
397  dVthdVbs = - 0.5 * K1 / SqrtVpb;
398  dAdVbs = 0.5 * K1 * (0.5 * G / Vpb - 0.8364 * (1 -G) * (1 - G) ) /
399  SqrtVpb ;
400  Ent = MAX(Arg2,1.0e-8);
401  dEntdVds = - 0.5 * A;
402  dEntdVbs = - dVthdVbs - 0.5 * vds * dAdVbs;
403  Vcom = Vgs_Vth * Vgs_Vth / 6.0 - 1.25e-1 * Arg1 *
404  Vgs_Vth + 2.5e-2 * Arg5;
405  VdsPinchoff = MAX( Vgs_Vth / A, 0.0);
406  Vgb = vgs - vbs ;
407  Vgb_Vfb = Vgb - Vfb;
408 
409  if( Vgb_Vfb < 0){
410  /* Accumulation Region */
411  qg = WLCox * Vgb_Vfb;
412  qb = - qg;
413  qd = 0. ;
414  cggb = WLCox;
415  cgdb = 0.;
416  cgsb = 0.;
417  cbgb = -WLCox;
418  cbdb = 0.;
419  cbsb = 0.;
420  cdgb = 0.;
421  cddb = 0.;
422  cdsb = 0.;
423  goto finished;
424  } else if ( vgs < Vth0 ){
425  /* Subthreshold Region */
426  qg = 0.5 * WLCox * K1 * K1 * (-1 +
427  sqrt(1 + 4 * Vgb_Vfb / (K1 * K1)));
428  qb = -qg;
429  qd = 0.;
430  cggb = WLCox / sqrt(1 + 4 * Vgb_Vfb / (K1 * K1));
431  cgdb = cgsb = 0.;
432  cbgb = -cggb;
433  cbdb = cbsb = cdgb = cddb = cdsb = 0.0;
434  goto finished;
435  } else if( vds < VdsPinchoff ){ /* triode region */
436  /*Vgs_Vth2 = Vgs_Vth*Vgs_Vth;*/
437  EntSquare = Ent * Ent;
438  Argl1 = 1.2e1 * EntSquare;
439  Argl2 = 1.0 - A;
440  Argl3 = Arg1 * vds;
441  /*Argl4 = Vcom/Ent/EntSquare;*/
442  if (Ent > 1.0e-8) {
443  Argl5 = Arg1 / Ent;
444  /*Argl6 = Vcom/EntSquare;*/
445  } else {
446  Argl5 = 2.0;
447  Argl6 = 4.0 / 1.5e1;
448  }
449  Argl7 = Argl5 / 1.2e1;
450  Argl8 = 6.0 * Ent;
451  Argl9 = 0.125 * Argl5 * Argl5;
452  qg = WLCox * (vgs - Vfb - Phi - 0.5 * vds + vds * Argl7);
453  qb = WLCox * ( - Vth0 + Vfb + Phi + 0.5 * Arg3 - Arg3 * Argl7);
454  qd = - WLCox * (0.5 * Vgs_Vth - 0.75 * Arg1 +
455  0.125 * Arg1 * Argl5);
456  cggb = WLCox * (1.0 - Argl3 / Argl1);
457  cgdb = WLCox * ( - 0.5 + Arg1 / Argl8 - Argl3 * dEntdVds /
458  Argl1);
459  cgbb = WLCox * (vds * vds * dAdVbs * Ent - Argl3 * dEntdVbs) /
460  Argl1;
461  cgsb = - (cggb + cgdb + cgbb);
462  cbgb = WLCox * Argl3 * Argl2 / Argl1;
463  cbdb = WLCox * Argl2 * (0.5 - Arg1 / Argl8 + Argl3 * dEntdVds /
464  Argl1);
465  cbbb = - WLCox * (dVthdVbs + 0.5 * vds * dAdVbs + vds *
466  vds * ((1.0 - 2.0 * A) * dAdVbs * Ent - Argl2 *
467  A * dEntdVbs) / Argl1);
468  cbsb = - (cbgb + cbdb + cbbb);
469  cdgb = - WLCox * (0.5 - Argl9);
470  cddb = WLCox * (0.75 * A - 0.25 * A * Arg1 / Ent +
471  Argl9 * dEntdVds);
472  cdbb = WLCox * (0.5 * dVthdVbs + vds * dAdVbs *
473  (0.75 - 0.25 * Argl5 ) + Argl9 * dEntdVbs);
474  cdsb = - (cdgb + cddb + cdbb);
475  goto finished;
476  } else if( vds >= VdsPinchoff ) { /* saturation region */
477  Args1 = 1.0 / (3.0 * A);
478  qg = WLCox * (vgs - Vfb - Phi - Vgs_Vth * Args1);
479  qb = WLCox * (Vfb + Phi - Vth0 + (1.0 - A) * Vgs_Vth * Args1);
480  qd = 0.0;
481  cggb = WLCox * (1.0 - Args1);
482  cgdb = 0.0;
483  cgbb = WLCox * Args1 * (dVthdVbs + Vgs_Vth * dAdVbs / A);
484  cgsb = - (cggb + cgdb + cgbb);
485  cbgb = WLCox * (Args1 - 1.0 / 3.0);
486  cbdb = 0.0;
487  cbbb = - WLCox * ((2.0 / 3.0 + Args1) * dVthdVbs +
488  Vgs_Vth * Args1 * dAdVbs / A); /* Modified */
489  cbsb = - (cbgb + cbdb + cbbb);
490  cdgb = 0.0;
491  cddb = 0.0;
492  cdsb = 0.0;
493  goto finished;
494  }
495 
496  goto finished;
497 
498  } else {
499  /* ChannelChargePartionFlag < = 0 */
500 
501 /*40/60 partitioning for drain/source chArges at the saturation region*/
502  co4v15 = 4./15.;
503  Vth0 = Vfb+Phi+K1*SqrtVpb;
504  Vgs_Vth = vgs-Vth0;
505  Arg1 = A*vds;
506  Arg2 = Vgs_Vth-0.5*Arg1;
507  Arg3 = vds-Arg1;
508  Arg5 = Arg1*Arg1;
509  dVthdVbs = -0.5*K1/SqrtVpb;
510  dAdVbs = 0.5*K1*(0.5*G/Vpb-0.8364*(1-G)*(1-G))/SqrtVpb;
511  Ent = MAX(Arg2,1.0e-8);
512  dEntdVds = -0.5*A;
513  dEntdVbs = -dVthdVbs-0.5*vds*dAdVbs;
514  Vcom = Vgs_Vth*Vgs_Vth/6.0-1.25e-1*Arg1*Vgs_Vth+2.5e-2*Arg5;
515  VdsPinchoff = MAX( Vgs_Vth/A, 0.0);
516  Vgb = vgs - vbs ;
517  Vgb_Vfb = Vgb - Vfb;
518 
519  if( Vgb_Vfb < 0) { /* Accumulation Region */
520  qg = WLCox * Vgb_Vfb;
521  qb = - qg;
522  qd = 0. ;
523  cggb = WLCox;
524  cgdb = 0.;
525  cgsb = 0.;
526  cbgb = -WLCox;
527  cbdb = 0.;
528  cbsb = 0.;
529  cdgb = 0.;
530  cddb = 0.;
531  cdsb = 0.;
532  goto finished;
533  } else if ( vgs < Vth0 ) { /* Subthreshold Region */
534  qg = 0.5 * WLCox * K1 * K1 * (-1+sqrt(1+4*Vgb_Vfb/(K1*K1)));
535  qb = -qg;
536  qd = 0.;
537  cggb = WLCox/sqrt(1+4*Vgb_Vfb/(K1*K1));
538  cgdb = cgsb = 0.;
539  cbgb = -cggb;
540  cbdb = cbsb = cdgb = cddb = cdsb = 0.0;
541  goto finished;
542  } else if ( vds < VdsPinchoff ) { /* triode region */
543 
544  Vgs_VthSquare = Vgs_Vth*Vgs_Vth;
545  EntSquare = Ent*Ent;
546  Argl1 = 1.2e1*EntSquare;
547  Argl2 = 1.0-A;
548  Argl3 = Arg1*vds;
549  Argl4 = Vcom/Ent/EntSquare;
550  if (Ent > 1.0e-8) {
551  Argl5 = Arg1/Ent;
552  Argl6 = Vcom/EntSquare;
553  } else {
554  Argl5 = 2.0;
555  Argl6 = 4.0/1.5e1;
556  }
557  Argl7 = Argl5/1.2e1;
558  Argl8 = 6.0*Ent;
559  qg = WLCox*(vgs-Vfb-Phi-0.5*vds+vds*Argl7);
560  qb = WLCox*(-Vth0+Vfb+Phi+0.5*Arg3-Arg3*Argl7);
561  qd = -WLCox*(0.5*(Vgs_Vth-Arg1)+Arg1*Argl6);
562  cggb = WLCox*(1.0-Argl3/Argl1);
563  cgdb = WLCox*(-0.5+Arg1/Argl8-Argl3*dEntdVds/Argl1);
564  cgbb = WLCox*(vds*vds*dAdVbs*Ent-Argl3*dEntdVbs)/Argl1;
565  cgsb = -(cggb+cgdb+cgbb);
566  cbgb = WLCox*Argl3*Argl2/Argl1;
567  cbdb = WLCox*Argl2*(0.5-Arg1/Argl8+Argl3*dEntdVds/Argl1);
568  cbbb = -WLCox*(dVthdVbs+0.5*vds*dAdVbs+vds*vds*((1.0-2.0*A)
569  *dAdVbs*Ent-Argl2*A*dEntdVbs)/Argl1);
570  cbsb = -(cbgb+cbdb+cbbb);
571  cdgb = -WLCox*(0.5+Arg1*(4.0*Vgs_Vth-1.5*Arg1)/Argl1-
572  2.0*Arg1*Argl4);
573  cddb = WLCox*(0.5*A+2.0*Arg1*dEntdVds*Argl4-A*(2.0*Vgs_VthSquare
574  -3.0*Arg1*Vgs_Vth+0.9*Arg5)/Argl1);
575  cdbb = WLCox*(0.5*dVthdVbs+0.5*vds*dAdVbs+2.0*Arg1*dEntdVbs
576  *Argl4-vds*(2.0*Vgs_VthSquare*dAdVbs-4.0*A*Vgs_Vth*dVthdVbs-3.0
577  *Arg1*Vgs_Vth*dAdVbs+1.5*A*Arg1*dVthdVbs+0.9*Arg5*dAdVbs)
578  /Argl1);
579  cdsb = -(cdgb+cddb+cdbb);
580  goto finished;
581  } else if( vds >= VdsPinchoff ) { /* saturation region */
582 
583  Args1 = 1.0/(3.0*A);
584  qg = WLCox*(vgs-Vfb-Phi-Vgs_Vth*Args1);
585  qb = WLCox*(Vfb+Phi-Vth0+(1.0-A)*Vgs_Vth*Args1);
586  qd = -co4v15*WLCox*Vgs_Vth;
587  cggb = WLCox*(1.0-Args1);
588  cgdb = 0.0;
589  cgbb = WLCox*Args1*(dVthdVbs+Vgs_Vth*dAdVbs/A);
590  cgsb = -(cggb+cgdb+cgbb);
591  cbgb = WLCox*(Args1-1.0/3.0);
592  cbdb = 0.0;
593  cbbb = -WLCox*((2.0/3.0+Args1)*dVthdVbs+Vgs_Vth*Args1*dAdVbs/A);
594  cbsb = -(cbgb+cbdb+cbbb);
595  cdgb = -co4v15*WLCox;
596  cddb = 0.0;
597  cdbb = co4v15*WLCox*dVthdVbs;
598  cdsb = -(cdgb+cddb+cdbb);
599  goto finished;
600  }
601  }
602 
603 finished: /* returning Values to Calling Routine */
604 
605  *gmPointer = MAX(gm,0.0);
606  *gdsPointer = MAX( gds, 0.0);
607  *gmbsPointer = MAX(gmbs,0.0);
608  *qgPointer = qg;
609  *qbPointer = qb;
610  *qdPointer = qd;
611  *cggbPointer = cggb;
612  *cgdbPointer = cgdb;
613  *cgsbPointer = cgsb;
614  *cbgbPointer = cbgb;
615  *cbdbPointer = cbdb;
616  *cbsbPointer = cbsb;
617  *cdgbPointer = cdgb;
618  *cddbPointer = cddb;
619  *cdsbPointer = cdsb;
620  *cdrainPointer = MAX(DrainCurrent,0.0);
621  *vonPointer = Von;
622  *vdsatPointer = VdsSat;
623 
624 }
625 
#define MODEAC
Definition: cktdefs.h:146
#define MODETRAN
Definition: cktdefs.h:145
#define MAX(a, b)
Definition: spdefs.h:135
static double e
Definition: vectors.c:17
void B1evaluate(double vds, double vbs, double vgs, B1instance *here, B1model *model, double *gmPointer, double *gdsPointer, double *gmbsPointer, double *qgPointer, double *qbPointer, double *qdPointer, double *cggbPointer, double *cgdbPointer, double *cgsbPointer, double *cbgbPointer, double *cbdbPointer, double *cbsbPointer, double *cdgbPointer, double *cddbPointer, double *cdsbPointer, double *cdrainPointer, double *vonPointer, double *vdsatPointer, CKTcircuit *ckt)
Definition: b1eval.c:21
#define G
Definition: parse.c:441
#define MODEINITSMSIG
Definition: cktdefs.h:159
#define MODETRANOP
Definition: cktdefs.h:151
static char model[32]
Definition: subckt.c:76
double CONSTvt0
Definition: main.c:914
#define MODEUIC
Definition: cktdefs.h:166