Qucs-core  0.0.18
 All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
triac.cpp
Go to the documentation of this file.
1 /*
2  * triac.cpp - triac class implementation
3  *
4  * Copyright (C) 2008 Stefan Jahn <stefan@lkcc.org>
5  * Copyright (C) 2008 Michael Margraf <Michael.Margraf@alumni.TU-Berlin.DE>
6  *
7  * This is free software; you can redistribute it and/or modify
8  * it under the terms of the GNU General Public License as published by
9  * the Free Software Foundation; either version 2, or (at your option)
10  * any later version.
11  *
12  * This software is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15  * GNU General Public License for more details.
16  *
17  * You should have received a copy of the GNU General Public License
18  * along with this package; see the file COPYING. If not, write to
19  * the Free Software Foundation, Inc., 51 Franklin Street - Fifth Floor,
20  * Boston, MA 02110-1301, USA.
21  *
22  * $Id$
23  *
24  */
25 
26 #if HAVE_CONFIG_H
27 # include <config.h>
28 #endif
29 
30 #include "component.h"
31 #include "device.h"
32 #include "devstates.h"
33 #include "triac.h"
34 
35 #define NODE_A1 0 /* anode 1 */
36 #define NODE_A2 1 /* anode 2 (cathode) */
37 #define NODE_GA 2 /* gate */
38 #define NODE_IN 3 /* internal node */
39 
40 using namespace qucs;
41 using namespace qucs::device;
42 
43 // Constructor for the triac.
44 triac::triac () : circuit (4) {
45  type = CIR_TRIAC;
46 }
47 
48 // Callback for initializing the DC analysis.
49 void triac::initDC (void) {
50  Ud_last = 0.0;
51  // allocate MNA matrices
52  allocMatrixMNA ();
53  // create internal node
54  setInternalNode (NODE_IN, "int");
55 }
56 
57 // Callback for DC analysis.
58 void triac::calcDC (void) {
59  calcTheModel (false);
60 }
61 
62 void triac::calcTheModel (bool last) {
63  // get device properties
64  nr_double_t Ubo = getPropertyDouble ("Vbo");
65  nr_double_t Ibo = getPropertyDouble ("Igt");
66  nr_double_t Is = getPropertyDouble ("Is");
67  nr_double_t N = getPropertyDouble ("N");
68  nr_double_t Gg = 1.0 / getPropertyDouble ("Rg");
69  nr_double_t T = getPropertyDouble ("Temp");
70  gi = 1.0 / getPropertyDouble ("Ri");
71 
72  nr_double_t Ut, Ud_bo, Ieq, Vd;
73 
74  Ut = N * kelvin (T) * kBoverQ;
75  Ud_bo = std::log (Ibo / Is + 1.0);
76 
77  Vd = Ud = real (getV (NODE_IN) - getV (NODE_A2));
78  Id = sign (Ud) * Is;
79  Ud = fabs (Ud) / Ut;
80 
81  bool isOn;
82  if (last)
83  isOn = (Ud_last / Ut) > Ud_bo;
84  else
85  isOn = Ud > Ud_bo;
86 
87  if (Ud >= 80.0) {
88  Id *= std::exp (80.0) * (1.0 + Ud - 80.0) - 1.0;
89  Ud = 80.0;
90  }
91  else
92  Id *= std::exp (Ud) - 1.0;
93 
94  gd = Is / Ut * std::exp (Ud);
95  Ieq = Id - Vd * gd;
96 
97  // fill in I-Vector
98  setI (NODE_A2, +Ieq);
99  setI (NODE_IN, -Ieq);
100  setI (NODE_A1, +0.0);
101  setI (NODE_GA, +0.0);
102 
103  if (!isOn) {
104  Ut = Ubo / std::log (Ibo / Is);
105  Vd = Ud = real (getV (NODE_A1) - getV (NODE_IN));
106  Id = sign (Ud) * Is;
107  Ud = fabs (Ud) / Ut;
108 
109  if (Ud >= 80.0) {
110  Id *= std::exp (80.0) * (1.0 + Ud - 80.0) - 1.0;
111  Ud = 80.0;
112  }
113  else
114  Id *= std::exp (Ud) - 1.0;
115 
116  gi = Is / Ut * std::exp (Ud);
117  Ieq = Id - Vd * gi;
118  addI (NODE_A1, -Ieq);
119  addI (NODE_IN, +Ieq);
120  }
121 
122  // fill in G-Matrix
123  setY (NODE_A2, NODE_A2, +gd); setY (NODE_IN, NODE_IN, +gd);
124  setY (NODE_A2, NODE_IN, -gd); setY (NODE_IN, NODE_A2, -gd);
127  setY (NODE_GA, NODE_GA, +Gg); addY (NODE_IN, NODE_IN, +Gg);
128  setY (NODE_GA, NODE_IN, -Gg); setY (NODE_IN, NODE_GA, -Gg);
129 }
130 
131 // Saves operating points (voltages).
133  nr_double_t Vd = real (getV (NODE_IN) - getV (NODE_A2));
134  nr_double_t Vi = real (getV (NODE_A1) - getV (NODE_IN));
135  setOperatingPoint ("Vd", Vd);
136  setOperatingPoint ("Vi", Vi);
137 }
138 
139 // Loads operating points (voltages).
141  Ud = getOperatingPoint ("Vd");
142  Ui = getOperatingPoint ("Vi");
143 }
144 
145 // Calculates and saves operating points.
147  nr_double_t Cj0 = getPropertyDouble ("Cj0");
148  // calculate capacitances and charges
149  nr_double_t Ci;
150  Ci = Cj0;
151  Qi = Cj0 * Ui;
152  // save operating points
153  setOperatingPoint ("gi", gi);
154  setOperatingPoint ("gd", gd);
155  setOperatingPoint ("Id", Id);
156  setOperatingPoint ("Ci", Ci);
157 }
158 
159 // Callback for initializing the AC analysis.
160 void triac::initAC (void) {
161  initDC ();
162 }
163 
164 // Build admittance matrix for AC and SP analysis.
165 matrix triac::calcMatrixY (nr_double_t frequency) {
166  nr_double_t gd = getOperatingPoint ("gd");
167  nr_double_t gi = getOperatingPoint ("gi");
168  nr_double_t gg = 1.0 / getPropertyDouble ("Rg");
169  nr_double_t Ci = getOperatingPoint ("Ci");
170  nr_complex_t yi = nr_complex_t (gi, Ci * 2.0 * M_PI * frequency);
171  matrix y (4);
172  y.set (NODE_A2, NODE_A2, +gd);
173  y.set (NODE_IN, NODE_IN, +gd +yi +gg);
174  y.set (NODE_A2, NODE_IN, -gd);
175  y.set (NODE_IN, NODE_A2, -gd);
176  y.set (NODE_A1, NODE_A1, +yi);
177  y.set (NODE_A1, NODE_IN, -yi);
178  y.set (NODE_IN, NODE_A1, -yi);
179  y.set (NODE_GA, NODE_GA, +gg);
180  y.set (NODE_GA, NODE_IN, -gg);
181  y.set (NODE_IN, NODE_GA, -gg);
182  return y;
183 }
184 
185 // Callback for the AC analysis.
186 void triac::calcAC (nr_double_t frequency) {
187  setMatrixY (calcMatrixY (frequency));
188 }
189 
190 // Callback for S-parameter analysis.
191 void triac::calcSP (nr_double_t frequency) {
192  setMatrixS (ytos (calcMatrixY (frequency)));
193 }
194 
195 #define qState 0 // charge state
196 #define cState 1 // current state
197 
198 // Callback for initializing the TR analysis.
199 void triac::initTR (void) {
200  setStates (2);
201  initDC ();
202  time_prev = -1.0;
203 }
204 
205 // Callback for the TR analysis.
206 void triac::calcTR (nr_double_t time) {
207  if (time_prev < time) {
208  time_prev = time;
209  Ud_last = fabs (real (getV (NODE_IN) - getV (NODE_A2)));
210  }
211  calcTheModel (true);
212 
216 
217  nr_double_t Ci = getOperatingPoint ("Ci");
219 }
220 
221 // properties
222 PROP_REQ [] = {
223  { "Igt", PROP_REAL, { 50e-6, PROP_NO_STR }, PROP_POS_RANGEX },
224  { "Vbo", PROP_REAL, { 30, PROP_NO_STR }, PROP_POS_RANGEX },
225  PROP_NO_PROP };
226 PROP_OPT [] = {
227  { "Cj0", PROP_REAL, { 10e-12, PROP_NO_STR }, PROP_POS_RANGE },
228  { "Is", PROP_REAL, { 1e-10, PROP_NO_STR }, PROP_POS_RANGE },
229  { "N", PROP_REAL, { 2.0, PROP_NO_STR }, PROP_RNGII (0.1, 100) },
230  { "Ri", PROP_REAL, { 10.0, PROP_NO_STR }, PROP_POS_RANGEX },
231  { "Rg", PROP_REAL, { 5.0, PROP_NO_STR }, PROP_POS_RANGEX },
232  { "Temp", PROP_REAL, { 26.85, PROP_NO_STR }, PROP_MIN_VAL (K) },
233  PROP_NO_PROP };
234 struct define_t triac::cirdef =
std::complex< nr_double_t > nr_complex_t
Definition: complex.h:31
void loadOperatingPoints(void)
Definition: triac.cpp:140
nr_double_t getOperatingPoint(const char *)
Definition: circuit.cpp:525
#define PROP_POS_RANGE
Definition: netdefs.h:129
matrix ytos(matrix y, qucs::vector z0)
Admittance matrix to scattering parameters.
Definition: matrix.cpp:1133
#define NODE_IN
Definition: triac.cpp:38
matrix real(matrix a)
Real part matrix.
Definition: matrix.cpp:568
#define PROP_RNGII(f, t)
Definition: netdefs.h:138
#define N(n)
Definition: equation.cpp:58
void initDC(void)
Definition: triac.cpp:49
#define kelvin(x)
Definition: constants.h:108
#define NODE_A2
Definition: triac.cpp:36
PROP_OPT[]
Definition: triac.cpp:226
#define PROP_DEF
Definition: netdefs.h:189
void calcDC(void)
Definition: triac.cpp:58
void calcSP(nr_double_t)
Definition: triac.cpp:191
PROP_REQ[]
Definition: triac.cpp:222
void saveOperatingPoints(void)
Definition: triac.cpp:132
nr_double_t getPropertyDouble(const char *)
Definition: object.cpp:176
#define PROP_REAL
Definition: netdefs.h:174
void setStates(int n)
Definition: states.h:52
nr_double_t Qi
Definition: triac.h:46
#define PROP_NO_PROP
Definition: netdefs.h:122
void calcOperatingPoints(void)
Definition: triac.cpp:146
#define K
Absolute 0 in centigrade.
Definition: constants.h:59
#define PROP_NO_STR
Definition: netdefs.h:125
void initAC(void)
Definition: triac.cpp:160
void calcTheModel(bool)
Definition: triac.cpp:62
nr_complex_t sign(const nr_complex_t z)
complex sign function
Definition: complex.cpp:435
void addY(int, int, nr_complex_t)
Definition: circuit.cpp:458
void calcAC(nr_double_t)
Definition: triac.cpp:186
nr_double_t Id
Definition: triac.h:46
void transientCapacitance(int, int, int, nr_double_t, nr_double_t, nr_double_t)
Definition: circuit.cpp:759
#define qState
Definition: triac.cpp:195
#define kBoverQ
Boltzmann constant over Elementary charge ( )
Definition: constants.h:68
#define PROP_COMPONENT
Definition: netdefs.h:116
nr_double_t Ud_last
Definition: triac.h:48
#define NODE_A1
Definition: triac.cpp:35
void addI(int, nr_complex_t)
Definition: circuit.cpp:403
void setMatrixY(matrix)
Definition: circuit.cpp:685
nr_double_t Ui
Definition: triac.h:46
#define M_PI
Archimedes' constant ( )
Definition: consts.h:47
nr_double_t gi
Definition: triac.h:46
void setI(int, nr_complex_t)
Definition: circuit.cpp:397
nr_double_t gd
Definition: triac.h:46
void calcTR(nr_double_t)
Definition: triac.cpp:206
void setMatrixS(matrix)
Definition: circuit.cpp:643
type
Definition: parse_vcd.y:164
void setY(int, int, nr_complex_t)
Definition: circuit.cpp:452
#define PROP_MIN_VAL(k)
Definition: netdefs.h:133
nr_double_t time_prev
Definition: triac.h:48
void setInternalNode(int, const char *)
Definition: circuit.cpp:635
void allocMatrixMNA(void)
Definition: circuit.cpp:267
#define PROP_POS_RANGEX
Definition: netdefs.h:131
y
Definition: parse_mdl.y:499
nr_double_t getV(int, nr_double_t)
Definition: circuit.cpp:941
qucs::matrix calcMatrixY(nr_double_t)
Definition: triac.cpp:165
nr_complex_t exp(const nr_complex_t z)
Compute complex exponential.
Definition: complex.cpp:205
nr_double_t Ud
Definition: triac.h:46
void setOperatingPoint(const char *, nr_double_t)
Definition: circuit.cpp:533
void initTR(void)
Definition: triac.cpp:199
Definition: triac.cpp:234
#define NODE_GA
Definition: triac.cpp:37
nr_complex_t log(const nr_complex_t z)
Compute principal value of natural logarithm of z.
Definition: complex.cpp:215
#define PROP_NONLINEAR
Definition: netdefs.h:119
#define PROP_NO_SUBSTRATE
Definition: netdefs.h:118