1 //**************************************************************************************************
2 // CmdGnuCapGEN.cpp *
3 // ------------------ *
4 // Started : 2008-03-11 *
5 // Last Update : 2014-12-23 *
6 // Copyright : (C) 2008 by MSWaters *
7 //**************************************************************************************************
8
9 //**************************************************************************************************
10 // *
11 // This program is free software; you can redistribute it and/or modify it under the *
12 // terms of the GNU General Public License as published by the Free Software Foundation; *
13 // either version 3 of the License, or (at your option) any later version. *
14 // *
15 //**************************************************************************************************
16
17 #include "CmdGnuCapGEN.hpp"
18
19 //**************************************************************************************************
20 // Constructor.
21
CmdGnuCapGEN(void)22 CmdGnuCapGEN::CmdGnuCapGEN( void )
23 {
24 bSetDefaults( );
25 }
26
27 //**************************************************************************************************
28 // Destructor.
29
~CmdGnuCapGEN()30 CmdGnuCapGEN::~CmdGnuCapGEN( )
31 {
32 }
33
34 //**************************************************************************************************
35 // Check that the object attributes are valid.
36 //
37 // Return Values :
38 // true - Success
39 // false - Failure
40
bValidate(void)41 bool CmdGnuCapGEN::bValidate( void )
42 {
43 double df1, df2, df3, df4;
44
45 CmdBase::bValidate( );
46
47 // Overall source characteristics
48 if( ! CnvtType::bStrToFlt( m_osAmplitude, &df1 ) )
49 SetErrMsg( wxT("overall amplitude value is invalid") );
50 // if( df1 <= 0.0 ) ??? 05/10/2009
51 // SetErrMsg( wxT("overall amplitude value must be greater than zero") );
52 if( ! CnvtType::bStrToFlt( m_osOffset, &df1 ) )
53 SetErrMsg( wxT("overall offset value is invalid") );
54
55 // Sinusoidal source characteristics
56 if( ! CnvtType::bStrToFlt( m_osSinFreq, &df1 ) )
57 SetErrMsg( wxT("sinusoid frequency value is invalid") );
58 if( ! CnvtType::bStrToFlt( m_osSinPhase, &df1 ) )
59 SetErrMsg( wxT("sinusoid phase value is invalid") );
60
61 // Check the pulse time values
62 if( ! CnvtType::bStrToFlt( m_osPulRise, &df1 ) )
63 SetErrMsg( wxT("pulse rise time value is invalid") );
64 if( ! CnvtType::bStrToFlt( m_osPulWidth, &df2 ) )
65 SetErrMsg( wxT("pulse width value is invalid") );
66 if( ! CnvtType::bStrToFlt( m_osPulFall, &df3 ) )
67 SetErrMsg( wxT("pulse fall time value is invalid") );
68 if( ! CnvtType::bStrToFlt( m_osPulPeriod, &df4 ) )
69 SetErrMsg( wxT("pulse period value is invalid") );
70 if( df4 < df1 )
71 SetErrMsg( wxT("pulse rise time is greater than the pulse period") );
72 else if( df4 < df2 )
73 SetErrMsg( wxT("pulse width is greater than the pulse period") );
74 else if( df4 < df3 )
75 SetErrMsg( wxT("pulse fall time is greater than the pulse period") );
76 else if( df4 < df1+df2+df3 )
77 SetErrMsg( wxT("pulse period is less then the pulse width") );
78
79 // Check the pulse level values
80 if( ! CnvtType::bStrToFlt( m_osPulInitial, &df1 ) )
81 SetErrMsg( wxT("initial pulse value is invalid") );
82 if( ! CnvtType::bStrToFlt( m_osPulMin, &df2 ) )
83 SetErrMsg( wxT("minimum pulse value is invalid") );
84 if( ! CnvtType::bStrToFlt( m_osPulMax, &df3 ) )
85 SetErrMsg( wxT("maximum pulse value is invalid") );
86 if( df1 < df2 )
87 SetErrMsg( wxT("initial pulse value is less than the minimum pulse value") );
88 else if( df1 > df3 )
89 SetErrMsg( wxT("initial pulse value is greater than the maximum pulse value") );
90 else if( df2 > df3 )
91 SetErrMsg( wxT("minimum pulse value is less than the maximum pulse value") );
92
93 // Check overall pulse source logic
94 if( df4!=0.0 && (df2==0.0 && df3==0.0) )
95 SetErrMsg( wxT("pulse timing has been defined but no pulse levels") );
96 if( df4==0.0 && (df2!=0.0 || df3!=0.0) )
97 SetErrMsg( wxT("pulse levels have been defined but no pulse timing") );
98
99 return( true );
100 }
101
102 //**************************************************************************************************
103 // Set the object attributes to they're default values.
104 //
105 // Return Values :
106 // true - Success
107 // false - Failure
108
bSetDefaults(void)109 bool CmdGnuCapGEN::bSetDefaults( void )
110 {
111 CmdBase::bSetDefaults( );
112
113 m_eSimEng = eSIMR_GNUCAP;
114 m_eCmdType = eCMD_GEN;
115
116 m_osAmplitude = GCP_AMPLITUDE;
117 m_osOffset = GCP_OFFSET;
118
119 m_osSinFreq = GCP_SINFREQ;
120 m_osSinPhase = GCP_SINPHASE;
121
122 m_osPulInitial = GCP_PULINITIAL;
123 m_osPulMin = GCP_PULMIN;
124 m_osPulMax = GCP_PULMAX;
125 m_osPulDelay = GCP_PULDELAY;
126 m_osPulRise = GCP_PULRISE;
127 m_osPulWidth = GCP_PULWIDTH;
128 m_osPulFall = GCP_PULFALL;
129 m_osPulPeriod = GCP_PULPERIOD;
130
131 return( true );
132 }
133
134 //**************************************************************************************************
135 // Parse the command string.
136 //
137 // Eg.s : .GENERATOR AMP=2.00K OFFSET=1.00 FREQ=1.00K PHASE=50.00 INIT=5.00m
138 // MIN=2.00m MAX=10.00m DELAY=4.00m RISE=2.00m WIDTH=8.00m
139 // FALL=1.00m PERIOD=20.00m
140 //
141 // Return Values :
142 // true - Success
143 // false - Failure
144
bParse(void)145 bool CmdGnuCapGEN::bParse( void )
146 {
147 wxStringTokenizer ostk1;
148 wxString os1, os2;
149 size_t szt1;
150 int i1;
151
152 // Clear the object attributes
153 os1 = (wxString &) *this;
154 bSetDefaults( );
155 assign( os1 );
156
157 // Tokenize the command string
158 ostk1.SetString( *this );
159 i1 = ostk1.CountTokens( );
160 if( i1<2 || i1>13 ) return( bValidate( ) );
161
162 // Check command type
163 os1 = ostk1.GetNextToken( ).Left( 4 ).Upper( );
164 if( os1 != wxT(".GEN") ) return( bValidate( ) );
165
166 // Extract each parameter value
167 while( ostk1.HasMoreTokens( ) )
168 {
169 // Extract the field name and the associated value
170 os1 = ostk1.GetNextToken( );
171 os2 = wxT("");
172 if( ( szt1=os1.find( wxT("=") ) ) != wxString::npos )
173 {
174 os2 = os1.Right( os1.Length( )-szt1-1 );
175 os1 = os1.Left( szt1 );
176 }
177
178 // Set the object attribute values
179 if( os1 == wxT("AMP") ) m_osAmplitude = os2;
180 else if( os1 == wxT("OFFSET") ) m_osOffset = os2;
181 else if( os1 == wxT("FREQ") ) m_osSinFreq = os2;
182 else if( os1 == wxT("PHASE") ) m_osSinPhase = os2;
183 else if( os1 == wxT("INIT") ) m_osPulInitial = os2;
184 else if( os1 == wxT("MIN") ) m_osPulMin = os2;
185 else if( os1 == wxT("MAX") ) m_osPulMax = os2;
186 else if( os1 == wxT("DELAY") ) m_osPulDelay = os2;
187 else if( os1 == wxT("RISE") ) m_osPulRise = os2;
188 else if( os1 == wxT("WIDTH") ) m_osPulWidth = os2;
189 else if( os1 == wxT("FALL") ) m_osPulFall = os2;
190 else if( os1 == wxT("PERIOD") ) m_osPulPeriod = os2;
191 else return( bValidate( ) );
192 }
193
194 return( bValidate( ) );
195 }
196
197 //**************************************************************************************************
198 // Format the command string.
199 //
200 // Return Values :
201 // true - Success
202 // false - Failure
203
bFormat(void)204 bool CmdGnuCapGEN::bFormat( void )
205 {
206 wxString os1;
207 float f1;
208 bool b1;
209
210 os1 = wxT(".GENERATOR");
211
212 if( ! m_osAmplitude .IsEmpty( ) ) os1 << wxT(" AMP=") << m_osAmplitude;
213 if( ! m_osOffset .IsEmpty( ) ) os1 << wxT(" OFFSET=") << m_osOffset;
214
215 f1 = 0.0;
216 b1 = CnvtType::bStrToFlt( m_osSinFreq, &f1 );
217 if( b1==true && f1!=0.0 )
218 {
219 os1 << wxT(" FREQ=") << m_osSinFreq;
220 os1 << wxT(" PHASE=") << m_osSinPhase;
221 }
222
223 f1 = 0.0;
224 b1 = CnvtType::bStrToFlt( m_osPulMax, &f1 );
225 if( b1==true && f1!=0.0 )
226 {
227 os1 << wxT(" INIT=") << m_osPulInitial;
228 os1 << wxT(" MIN=") << m_osPulMin;
229 os1 << wxT(" MAX=") << m_osPulMax;
230 os1 << wxT(" DELAY=") << m_osPulDelay;
231 os1 << wxT(" RISE=") << m_osPulRise;
232 os1 << wxT(" WIDTH=") << m_osPulWidth;
233 os1 << wxT(" FALL=") << m_osPulFall;
234 os1 << wxT(" PERIOD=") << m_osPulPeriod;
235 }
236
237 assign( os1 );
238
239 return( bValidate( ) );
240 }
241
242 //**************************************************************************************************
243 // Copy the contents of a CpntNgsIndSrc object.
244 //
245 // Argument List :
246 // roIndSrc - A reference to a CpntNgsIndSrc object
247 //
248 // Return Values :
249 // A reference to this object
250
operator =(const CpntNgsIndSrc & roIndSrc)251 CmdGnuCapGEN & CmdGnuCapGEN::operator = ( const CpntNgsIndSrc & roIndSrc )
252 {
253 double df1, df2;
254
255 if( ! roIndSrc.m_osSinAmp.IsEmpty( ) ) m_osAmplitude = roIndSrc.m_osSinAmp;
256 else m_osAmplitude = wxT("1.0");
257 m_osOffset = roIndSrc.m_osSinOffset;
258
259 m_osSinFreq = roIndSrc.m_osSinFreq;
260 if( CnvtType::bStrToFlt( roIndSrc.m_osSinFreq, &df1 ) &&
261 CnvtType::bStrToFlt( roIndSrc.m_osSinDelay, &df2 ) )
262 CnvtType::bFltToStr( 360.0 * df2 * df1, m_osSinPhase );
263 else
264 m_osSinPhase = wxT("0.0");
265
266 m_osPulInitial = roIndSrc.m_osPulInitial;
267 m_osPulMax = roIndSrc.m_osPulMax;
268 m_osPulDelay = roIndSrc.m_osPulDelay;
269 m_osPulRise = roIndSrc.m_osPulRise;
270 m_osPulWidth = roIndSrc.m_osPulWidth;
271 m_osPulFall = roIndSrc.m_osPulFall;
272 m_osPulPeriod = roIndSrc.m_osPulPeriod;
273
274 bFormat( );
275
276 return( *this );
277 }
278
279 //**************************************************************************************************
280 // Print the object attributes.
281 //
282 // Argument List :
283 // rosPrefix - A prefix to every line displayed (usually just spaces)
284
Print(const wxString & rosPrefix)285 void CmdGnuCapGEN::Print( const wxString & rosPrefix )
286 {
287 CmdBase::Print( rosPrefix + wxT("CmdBase::") );
288
289 std::cout << rosPrefix.mb_str( ) << "m_osAmplitude : " << m_osAmplitude .mb_str( ) << '\n';
290 std::cout << rosPrefix.mb_str( ) << "m_osOffset : " << m_osOffset .mb_str( ) << '\n';
291
292 std::cout << rosPrefix.mb_str( ) << "m_osSinFreq : " << m_osSinFreq .mb_str( ) << '\n';
293 std::cout << rosPrefix.mb_str( ) << "m_osSinPhase : " << m_osSinPhase .mb_str( ) << '\n';
294
295 std::cout << rosPrefix.mb_str( ) << "m_osPulInitial : " << m_osPulInitial.mb_str( ) << '\n';
296 std::cout << rosPrefix.mb_str( ) << "m_osPulMin : " << m_osPulMin .mb_str( ) << '\n';
297 std::cout << rosPrefix.mb_str( ) << "m_osPulMax : " << m_osPulMax .mb_str( ) << '\n';
298 std::cout << rosPrefix.mb_str( ) << "m_osPulDelay : " << m_osPulDelay .mb_str( ) << '\n';
299 std::cout << rosPrefix.mb_str( ) << "m_osPulRise : " << m_osPulRise .mb_str( ) << '\n';
300 std::cout << rosPrefix.mb_str( ) << "m_osPulWidth : " << m_osPulWidth .mb_str( ) << '\n';
301 std::cout << rosPrefix.mb_str( ) << "m_osPulFall : " << m_osPulFall .mb_str( ) << '\n';
302 std::cout << rosPrefix.mb_str( ) << "m_osPulPeriod : " << m_osPulPeriod .mb_str( ) << '\n';
303 }
304
305 //**************************************************************************************************
306 // Test Utility *
307 //**************************************************************************************************
308
309 #ifdef TEST_CMDGNUCAPGEN
310
311 using namespace std;
312
313 // Function prototypes
314
315 void Usage( char * psAppName );
316
317 //**************************************************************************************************
318
main(int argc,char * argv[])319 int main( int argc, char * argv[ ] )
320 {
321 wxString osCmd;
322 wxString os1;
323
324 // Validate the argument count passed to the application
325 if( argc > 2 ) { Usage( argv[ 0 ] ); exit( EXIT_FAILURE ); }
326
327 // Process the command line arguments
328 os1 = wxConvLibc.cMB2WC( argv[ 1 ] );
329 if( argc > 1 )
330 {
331 if( os1 == wxT("-h") ) { Usage( argv[ 0 ] ); exit( EXIT_SUCCESS ); }
332 else { Usage( argv[ 0 ] ); exit( EXIT_FAILURE ); }
333 }
334
335 // Display the utility banner
336 cout << "\n Class CmdGnuCapGEN Test Utility"
337 << "\n Version 1.04 (12/08/2011)\n";
338
339 // Create a GNU-CAP Transient command object
340 CmdGnuCapGEN tCmd_GEN;
341
342 // Use the following command example to check the formatter and the parser :
343 osCmd << wxT(".GENERATOR AMP=2.00K OFFSET=1.00 FREQ=1.00K PHASE=50.00 ")
344 << wxT("INIT=5.00m MIN=2.00m MAX=10.00m DELAY=4.00m RISE=2.00m ")
345 << wxT("WIDTH=8.00m FALL=1.00m PERIOD=20.00m");
346
347 // Set things up for a formatter test
348 tCmd_GEN.m_osAmplitude = wxT("2.00K");
349 tCmd_GEN.m_osOffset = wxT("1.00");
350 tCmd_GEN.m_osSinFreq = wxT("1.00K");
351 tCmd_GEN.m_osSinPhase = wxT("50.00");
352 tCmd_GEN.m_osPulInitial = wxT("5.00m");
353 tCmd_GEN.m_osPulMin = wxT("2.00m");
354 tCmd_GEN.m_osPulMax = wxT("10.00m");
355 tCmd_GEN.m_osPulDelay = wxT("4.00m");
356 tCmd_GEN.m_osPulRise = wxT("2.00m");
357 tCmd_GEN.m_osPulWidth = wxT("8.00m");
358 tCmd_GEN.m_osPulFall = wxT("1.00m");
359 tCmd_GEN.m_osPulPeriod = wxT("20.00m");
360 cout << "\nRun Formatter : " << ( tCmd_GEN.bFormat( ) ? "OK" : "FAULT" );
361 cout << "\nTest Cmd Format : " << ( tCmd_GEN == osCmd ? "OK" : "FAULT" );
362 cout << "\nExample Command : " << osCmd .mb_str( );
363 cout << "\ntCmd_GEN Contents : " << tCmd_GEN.mb_str( ) << '\n';
364
365 // Set things up for a parser test
366 tCmd_GEN.bSetString( osCmd );
367 cout << "\nRun Parser : " << ( tCmd_GEN.bParse( ) ? "OK" : "FAULT" );
368 tCmd_GEN.bFormat( );
369 cout << "\nTest Cmd Format : " << ( tCmd_GEN == osCmd ? "OK" : "FAULT" );
370 cout << "\nExample Command : " << osCmd .mb_str( );
371 cout << "\ntCmd_GEN Contents : " << tCmd_GEN.mb_str( ) << '\n';
372
373 cout << '\n';
374
375 exit( EXIT_SUCCESS );
376 }
377
378 //**************************************************************************************************
379
Usage(char * psAppName)380 void Usage( char * psAppName )
381 {
382 cout << "\nUsage : " << psAppName << " [-OPTIONS]"
383 << "\nOptions :"
384 << "\n -h : Print usage (this message)\n";
385 }
386
387 #endif // TEST_CMDGNUCAPGEN
388
389 //**************************************************************************************************
390