1 /***************************************************************************
2 JSPICE3 adaptation of Spice3e2 - Copyright (c) Stephen R. Whiteley 1992
3 Copyright 1990 Regents of the University of California.  All rights reserved.
4 Authors: 1985 Gordon M. Jacobs
5          1992 Stephen R. Whiteley
6 ****************************************************************************/
7 
8 #include "spice.h"
9 #include <stdio.h>
10 #include "swdefs.h"
11 #include "sperror.h"
12 #include "util.h"
13 
14 
15 int
SWload(inModel,ckt)16 SWload(inModel,ckt)
17 
18 GENmodel *inModel;
19 CKTcircuit *ckt;
20 /* actually load the current values into the
21  * sparse matrix previously provided
22  */
23 {
24     SWmodel *model = (SWmodel *) inModel;
25     SWinstance *here;
26     double g_now;
27     double ctrl;
28     double previous_state;
29     double current_state;
30 
31     /* loop through all the switch models */
32     for ( ; model != NULL; model = model->SWnextModel) {
33 
34         /* loop through all the instances of the model */
35         for (here = model->SWinstances; here != NULL;
36                 here = here->SWnextInstance) {
37 
38             /* decide the state of the switch */
39 
40             if (ckt->CKTmode & (MODEINITFIX|MODEINITJCT)) {
41 
42                 if (here->SWzero_stateGiven)
43                     /* switch specified "on" */
44                     current_state = 1.0;
45                 else
46                     current_state = 0.0;
47                 *(ckt->CKTstate0 + here->SWstate) = current_state;;
48 
49             }
50             else if (ckt->CKTmode & (MODEINITSMSIG)) {
51 
52                 previous_state = *(ckt->CKTstate0 + here->SWstate);
53                 current_state = previous_state;
54 
55             }
56             else if (ckt->CKTmode & (MODEINITFLOAT)) {
57 
58                 /* use state0 since INITTRAN or INITPRED already called */
59                 previous_state = *(ckt->CKTstate0 + here->SWstate);
60                 current_state = previous_state;
61 
62                 if (here->SWcontName) {
63                     ctrl = *(ckt->CKTrhsOld + here->SWcontBranch);
64                     if (ctrl > (model->SWiThreshold+model->SWiHysteresis))
65                         current_state = 1.0;
66                     else if
67                         (ctrl < (model->SWiThreshold-model->SWiHysteresis))
68                         current_state = 0.0;
69                 }
70                 else {
71                     ctrl = *(ckt->CKTrhsOld + here->SWposCntrlNode)
72                             - *(ckt->CKTrhsOld + here->SWnegCntrlNode);
73                     if (ctrl > (model->SWvThreshold+model->SWvHysteresis))
74                         current_state = 1.0;
75                     else if
76                         (ctrl < (model->SWvThreshold-model->SWvHysteresis))
77                         current_state = 0.0;
78                 }
79                 *(ckt->CKTstate0 + here->SWstate) = current_state;
80 
81                 if (current_state != previous_state) {
82                     ckt->CKTnoncon++;   /* ensure one more iteration */
83                     ckt->CKTtroubleElt = (GENinstance *) here;
84                 }
85             }
86             else if (ckt->CKTmode & (MODEINITTRAN|MODEINITPRED) ) {
87 
88                 previous_state = *(ckt->CKTstate1 + here->SWstate);
89                 current_state = previous_state;
90 
91                 if (here->SWcontName) {
92                     ctrl = *(ckt->CKTrhsOld + here->SWcontBranch);
93                     if (ctrl > (model->SWiThreshold+model->SWiHysteresis))
94                         current_state = 1.0;
95                     else if
96                         (ctrl < (model->SWiThreshold-model->SWiHysteresis))
97                         current_state = 0.0;
98                 }
99                 else {
100                     ctrl = *(ckt->CKTrhsOld + here->SWposCntrlNode)
101                             - *(ckt->CKTrhsOld + here->SWnegCntrlNode);
102                     if (ctrl > (model->SWvThreshold+model->SWvHysteresis))
103                         current_state = 1.0;
104                     else if
105                         (ctrl < (model->SWvThreshold-model->SWvHysteresis))
106                         current_state = 0.0;
107                 }
108                 *(ckt->CKTstate0 + here->SWstate) = current_state;
109             }
110 
111             g_now = current_state?(model->SWonConduct):(model->SWoffConduct);
112             here->SWcond = g_now;
113 
114             *(here->SWposPosptr) += g_now;
115             *(here->SWposNegptr) -= g_now;
116             *(here->SWnegPosptr) -= g_now;
117             *(here->SWnegNegptr) += g_now;
118         }
119     }
120     return (OK);
121 }
122