1 /****************************************************************************/
3 /* Chaine de CAO & VLSI AVERTEC */
5 /* Produit : STM Version 1.00 */
6 /* Fichier : stm_noise.c */
8 /* (c) copyright 2000 AVERTEC */
9 /* Tous droits reserves */
11 /* Auteur(s) : Grégoire Avot */
13 /****************************************************************************/
15 /****************************************************************************/
17 /****************************************************************************/
21 /****************************************************************************/
23 /****************************************************************************/
25 stm_simu_pi_load_parameter stm_simu_param_standard
= {
26 /* DEFAULT_TIME_STEP */ 10.0 , // 10 FS
27 /* MIN_TIME_STEP */ 1.0 , // 1 FS
28 /* MAX_TIME_STEP */ 100.0 , // 100 Fs
29 /* MAX_DELTA_CURRENT */ 0.000100 , // 100uA
30 /* MIN_DELTA_CURRENT */ 0.000001 , // 1uA
31 /* MAX_DELTA_VOLTAGE */ 0.001000 , // 1000uV
32 /* MIN_DELTA_VOLTAGE */ 0.000010 , // 10uV
33 /* MAX_ITER */ 100000 ,
34 /* VARIABLE_STEP */ 1 ,
36 /* STAT_CHANGE_STEP */ 0 ,
37 /* STAT_MIN_TIME_STEP */ 0.0 ,
38 /* STAT_MAX_TIME_STEP */ 0.0 ,
39 /* STAT_MIN_DELTA_VOLTAGE */ 0.0 ,
40 /* STAT_MAX_DELTA_VOLTAGE */ 0.0 ,
41 /* STAT_MIN_DELTA_CURRENT */ 0.0 ,
42 /* STAT_MAX_DELTA_CURRENT */ 0.0
45 /******************************************************************************\
47 \******************************************************************************/
49 /******************************************************************************\
51 Convention générateur :
52 transition UD : le courant décharge la sortie, il est négatif.
53 transition DU : le courant charge la sortie, il est positif
55 \******************************************************************************/
57 char stm_simu_mcc_ids( param_mcc_ids
*param
, float vgs
, float vds
, float *ids
)
61 float vdd
= param
->VDD
;
62 float rnt
= param
->RNT
;
63 float rns
= param
->RNS
;
65 char neg
= param
->NEG
;
66 float imax
= param
->IMAX
;
79 if( param
->k
== 0.0 ) {
81 k
= imax
* rnt
/ (vdd
-vt
);
83 x
= ( imax
* rnt
- vdd
*rnt
/rns
)/( 1.0 - rnt
/rns
);
96 isat
= a
*(vgs
-vt
)*(vgs
-vt
) / ( 1.0 + b
*(vgs
-vt
) );
99 ures
= kres
*( vgs
-vt
);
101 rsat
= (vdd
-ures
) / (isat
-ires
);
104 *ids
= isat
- (vdd
-vds
)/rsat
;
114 /******************************************************************************\
116 \******************************************************************************/
118 char stm_simu_tanh( stm_simu_tanh_param
*param
, float t
, float *v
)
120 *v
= stm_get_v( t
, param
->VT
, param
->VI
, param
->VF
, param
->F
);
124 /******************************************************************************\
130 Capacité Femto-seconde
135 fn_is Pointeur sur fonction de calcul du courant dans la branche.
136 fn_ve Pointeur sur fonction de calcul de la tension d'entrée.
137 dat_is Données utilisées par fn_is.
138 dat_ve Données utilisées par fn_ve.
139 r, c1, c2 Charge de la branche.
140 vi Tension initiale de la sortie.
141 vth Tension de sortie à laquelle la simulation s'arrète.
142 ts, fs Pointeurs vers le temps et le front simulé lorsque la sortie
143 vaut vth. NULL autorisé.
144 param Configuration du simulateur. NULL autorisé.
149 Le front calculé correspond à la pente du signal, en V/fs. Il ne correspond
150 PAS au front défini par Amjad. Le passage de l'un à l'autre se fait avec la
151 relation 3-12-b page III/15 de la thèse.
153 \******************************************************************************/
155 char stm_simu_pi_load_ts( char (*fn_is
)( void *dat_is
,
160 char (*fn_ve
)( void *dat_ve
, float t
, float *v
),
170 stm_simu_pi_load_parameter
*param
,
174 double vx1
, vx2
, vx3
, vx4
, vx5
;
191 /* Various initialisation */
193 if( plotcurvename
) {
194 ptf
= mbkfopen( plotcurvename
, "dat", WRITE_TEXT
);
195 fprintf( ptf
, "#time vin vout igate\n" );
198 if( !param
) param
= &stm_simu_param_standard
;
200 param
->STAT_ITER
= 0.0 ;
201 param
->STAT_CHANGE_STEP
= 0.0;
202 param
->STAT_MIN_TIME_STEP
= 1.0e9
;
203 param
->STAT_MAX_TIME_STEP
= -1.0e9
;
204 param
->STAT_MIN_DELTA_VOLTAGE
= 1.0e9
;
205 param
->STAT_MAX_DELTA_VOLTAGE
= -1.0e9
;
206 param
->STAT_MIN_DELTA_CURRENT
= 1.0e9
;
207 param
->STAT_MAX_DELTA_CURRENT
= -1.0e9
;
211 dt
= param
->DEFAULT_TIME_STEP
;
229 if( needmodifyconst
)
231 param
->STAT_CHANGE_STEP
++;
233 vx1
= 1.0/( c1
/ dt
+ c2
/ a
);
235 vx3
= ( c2
- b
* c2
/ a
) / dt
;
241 /* Le corp du simulateur */
243 if( !fn_ve( dat_ve
, ti
-t0
, &ve
) ) {
249 if( !fn_is( dat_is
, ve
, v1i
, &ii
) ) {
253 v1i
= vx1
* ( ii
+ vx2
* v1j
+ vx3
* v2j
) ;
258 v2i
= vx4
* v1i
+ vx5
* v2j
;
261 if( param
->VARIABLE_STEP
) {
262 /* Vérification du step */
271 if( ( dv
> param
->MAX_DELTA_VOLTAGE
||
272 di
> param
->MAX_DELTA_CURRENT
) && dt
> param
->MIN_TIME_STEP
)
279 while( needmodifyconst
);
284 if( param
->VARIABLE_STEP
) {
285 /* Vérification du step */
286 if( ( di
< param
->MIN_DELTA_CURRENT
&&
287 dv
< param
->MIN_DELTA_VOLTAGE
) && dt
< param
->MAX_TIME_STEP
)
295 if( dv
< param
->STAT_MIN_DELTA_VOLTAGE
) param
->STAT_MIN_DELTA_VOLTAGE
= dv
;
296 if( dv
> param
->STAT_MAX_DELTA_VOLTAGE
) param
->STAT_MAX_DELTA_VOLTAGE
= dv
;
297 if( dt
< param
->STAT_MIN_TIME_STEP
) param
->STAT_MIN_TIME_STEP
= dt
;
298 if( dt
> param
->STAT_MAX_TIME_STEP
) param
->STAT_MAX_TIME_STEP
= dt
;
299 if( di
< param
->STAT_MIN_DELTA_CURRENT
) param
->STAT_MIN_DELTA_CURRENT
= di
;
300 if( di
> param
->STAT_MAX_DELTA_CURRENT
) param
->STAT_MAX_DELTA_CURRENT
= di
;
307 fprintf( ptf
, "%g %g %g %g\n", ti
, ve
, v1i
, ii
);
310 if( param
->STAT_ITER
> param
->MAX_ITER
)
312 if( ( v1i
> vth
&& v1j
< vth
) || ( v1i
< vth
&& v1j
> vth
) )
317 if( !ret
|| param
->STAT_ITER
>= param
->MAX_ITER
) {
323 if(ts
) *ts
= tj
+(vth
-v1j
)/(v1i
-v1j
)*(ti
-tj
);
324 if(fs
) *fs
= fabs(v1i
-v1j
)/dt
;