source: trunk/FACT++/src/fscctrl.cc@ 12105

Last change on this file since 12105 was 12089, checked in by tbretz, 13 years ago
Updated scaling of some voltages; added commands and states to help output
File size: 24.9 KB
Line 
1#include <functional>
2
3#include "Dim.h"
4#include "Event.h"
5#include "Shell.h"
6#include "StateMachineDim.h"
7#include "Connection.h"
8#include "Configuration.h"
9#include "Console.h"
10#include "Converter.h"
11
12#include "tools.h"
13
14namespace ba = boost::asio;
15namespace bs = boost::system;
16namespace dummy = ba::placeholders;
17
18using namespace std;
19
20// ------------------------------------------------------------------------
21
22class ConnectionFSC : public Connection
23{
24 boost::asio::streambuf fBuffer;
25
26 bool fIsVerbose;
27 bool fDump;
28
29 ofstream fDumpStream;
30
31protected:
32
33 virtual void UpdateTemp(float, const vector<float> &)
34 {
35 }
36
37 virtual void UpdateHum(float, const vector<float>&)
38 {
39 }
40
41 virtual void UpdateVolt(float, const vector<float>&)
42 {
43 }
44
45 virtual void UpdateCur(float, const vector<float>&)
46 {
47 }
48
49 /*
50 virtual void UpdateError()
51 {
52 if (!fIsVerbose)
53 return;
54
55 Out() << endl << kRed << "Error received:" << endl;
56 Out() << fError;
57 if (fIsHexOutput)
58 Out() << Converter::GetHex<uint16_t>(fError, 16) << endl;
59 }
60*/
61
62 void Dump(const string &str)
63 {
64 if (!fDumpStream.is_open())
65 {
66 fDumpStream.open("socket_dump-fsc.txt", ios::app);
67 if (!fDumpStream)
68 {
69 //ostringstream str;
70 //str << "Open file " << name << ": " << strerror(errno) << " (errno=" << errno << ")";
71 //Error(str);
72
73 return;
74 }
75 }
76
77 fDumpStream << str << endl;
78 }
79
80private:
81 //
82 // From: http://de.wikipedia.org/wiki/Pt100
83 //
84 double GetTempPT1000(double R) const
85 {
86 const double R0 = 1000; // 1kOhm
87
88 const double a = 3.85e-3;
89
90 return (R/R0 - 1)/a;
91 }
92
93
94 void HandleReceivedData(const bs::error_code& err, size_t bytes_received, int /*type*/)
95 {
96 // Do not schedule a new read if the connection failed.
97 if (bytes_received==0 || err)
98 {
99 if (err==ba::error::eof)
100 Warn("Connection closed by remote host (FTM).");
101
102 // 107: Transport endpoint is not connected (bs::error_code(107, bs::system_category))
103 // 125: Operation canceled
104 if (err && err!=ba::error::eof && // Connection closed by remote host
105 err!=ba::error::basic_errors::not_connected && // Connection closed by remote host
106 err!=ba::error::basic_errors::operation_aborted) // Connection closed by us
107 {
108 ostringstream str;
109 str << "Reading from " << URL() << ": " << err.message() << " (" << err << ")";// << endl;
110 Error(str);
111 }
112 PostClose(err!=ba::error::basic_errors::operation_aborted);
113 return;
114 }
115
116 if (fIsVerbose)
117 Out() << kBold << "Received (" << bytes_received << " bytes):" << endl;
118
119 /*
120 "status: 00000538 \n"
121 "time_s: 764.755 \n"
122 "VOLTAGES \n"
123 " \n"
124 "enable:11111111 11111111 11111111 11111111 11111111 11111111 11111111 11111111 11111111 11111111 00001111 \n"
125 " done:11111111 11111111 11111111 11111111 11111111 11111111 11111111 11111111 11111111 11111111 00001111 \n"
126 "values:0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 00 0 0 0 0 0 0 0 0 \n"
127 "RESISTANCES \n"
128 " \n"
129 "enable:11111111 11111111 11111111 11111111 11111111 11111111 11111111 11111111 \n"
130 " done:11111111 11111111 11111111 11111111 11111111 11111111 11111111 11111111 \n"
131 "values: \n"
132 "1000.16 3199.99 3199.99 3199.99 3199.99 3199.99 3199.99 3199.99 \n"
133 "3199.99 3199.99 3199.99 3199.99 3199.99 3199.99 3199.99 3199.99 \n"
134 "1197.07 3199.99 3199.99 3199.99 3199.99 3199.99 3199.99 3199.99 \n"
135 " 558.59 677.92 817.26 989.39 1200.35 1503.06 1799.90 2204.18 \n"
136 "3199.99 3199.99 3199.99 3199.99 3199.99 3199.99 3199.99 3199.99 \n"
137 "3199.99 3199.99 3199.99 3199.99 3199.99 3199.99 3199.99 3199.99 \n"
138 "3199.99 3199.99 3199.99 3199.99 3199.99 3199.99 3199.99 3199.99 \n"
139 "3199.99 3199.99 3199.99 3199.99 3199.99 3199.99 3199.99 3199.99 \n"
140 "end.\n";
141 */
142/*
143 const unsigned int TIME_OFF = 3;
144 const unsigned int VOLT_OFF = 30;
145 const unsigned int CURR_OFF = 70;
146 const unsigned int HUMI_OFF = 110;
147 const unsigned int TEMP_OFF = 134;
148 */
149
150 if (fDump)
151 {
152 ostringstream msg;
153 msg << "--- " << Time().GetAsStr() << " --- received " << bytes_received << " bytes.";
154 Dump(msg.str());
155 }
156
157
158 istream is(&fBuffer);
159
160 int state = 0;
161 bool values = false;
162
163 vector<int> volt;
164 vector<float> resist;
165 int status=-1;
166 float time=0;
167
168 string buffer;
169 while (getline(is, buffer, '\n'))
170 {
171 if (fIsVerbose)
172 Out() << buffer << endl;
173 if (fDump)
174 Dump(buffer);
175
176 buffer = Tools::Trim(buffer);
177
178 if (buffer.empty())
179 continue;
180
181 if (buffer.substr(0, 4)=="end.")
182 break;
183
184 if (buffer.substr(0, 8)=="status: ")
185 {
186 status = stoi(buffer.substr(8));
187 continue;
188 }
189
190 if (buffer.substr(0, 8)=="time_s: ")
191 {
192 time = stof(buffer.substr(8));
193 continue;
194 }
195
196 if (buffer.substr(0, 8)=="VOLTAGES")
197 {
198 state = 1;
199 continue;
200 }
201
202 if (buffer.substr(0, 11)=="RESISTANCES")
203 {
204 state = 2;
205 continue;
206 }
207
208 if (state==1 && buffer.substr(0, 7)=="values:")
209 {
210 istringstream in(buffer.substr(7));
211 while (1)
212 {
213 int v;
214 in >> v;
215 if (!in)
216 break;
217
218 volt.push_back(v);
219 }
220 continue;
221 }
222
223 if (state==2 && buffer.substr(0, 7)=="values:")
224 {
225 values = true;
226 continue;
227 }
228
229 if (state==2 && !values)
230 continue;
231
232 istringstream in(buffer);
233 while (1)
234 {
235 float f;
236 in >> f;
237 if (!in)
238 break;
239
240 resist.push_back(f);
241 }
242 }
243
244 if (volt.size()!=84 || resist.size()!=64)
245 {
246 ostringstream out;
247
248 out << "Corrupted data received (" << volt.size() << " voltages and ";
249 out << resist.size() << " resistances received; 84 and 64 expected)";
250 Warn(out);
251 StartRead();
252 return;
253 }
254
255 int mapv[] =
256 {
257 0, 24, 16, 8,
258 1, 25, 17, 9,
259 2, 26, 18, 10,
260 //
261 3, 27, 19, 11,
262 4, 28, 20, 12,
263 5, 29, 21, 13,
264 //
265 32, 36, 33, 34, 37, 38,
266 //
267 -1
268 };
269
270
271 int mapc[] =
272 {
273 40, 64, 56, 48,
274 41, 65, 57, 49,
275 42, 66, 58, 50,
276 //
277 43, 67, 59, 51,
278 44, 68, 60, 52,
279 45, 69, 61, 53,
280 //
281 72, 76, 73, 74, 77, 78,
282 //
283 -1
284 };
285
286
287 int maprh[] =
288 {
289 80, 81, 82, 83, -1
290 };
291
292 int offrh[] =
293 {
294 821, 822, 816, 822,
295 };
296
297 int mapt[] =
298 {
299 // sensor compartment temperatures
300 0, 1, 2, 3, 4, 5, 6, 56, 57, 58, 59, 60,
301 61, 62, 32, 33, 34, 35, 36, 63, 37, 38, 39, 24,
302 25, 26, 27, 28, 29, 30, 31,
303 // crate temperatures (0-3, back, front)
304 12, 13, 52, 53, 44, 45, 20, 21,
305 //crate power supply temperatures (0-3)
306 8, 9, 48, 49, 40, 41, 16, 17,
307 // aux power supplies (FTM-side top/bot, FSC-side top/bot)
308 10, 50, 18, 42,
309 // backpanel (FTM-side top/bot, FSC-side top/bot)
310 11, 51, 19, 43,
311 // switch boxes (top front/back, bottom front/back)
312 15, 14, 47, 46,
313 //
314 -1
315 };
316
317 vector<float> voltages;
318 vector<float> currents;
319 vector<float> humidities;
320 vector<float> temperatures;
321
322 for (int *pv=mapv; *pv>=0; pv++)
323 voltages.push_back(volt[*pv]*0.001);
324
325 for (int *pc=mapc; *pc>=0; pc++)
326 currents.push_back(volt[*pc]*0.005);
327
328 for (int idx=0; idx<4; idx++)
329 {
330 voltages[idx +8] *= -1;
331 voltages[idx+20] *= -1;
332 currents[idx +8] *= -1;
333 currents[idx+20] *= -1;
334 }
335 voltages[12] *= 2;
336 voltages[13] *= 2;
337 voltages[14] *= 2;
338 voltages[15] *= 2;
339
340 voltages[24] *= 2;
341 voltages[25] *= 2;
342
343 voltages[27] *= -1;
344 voltages[29] *= -1;
345
346 currents[27] *= -1;
347 currents[29] *= -1;
348
349 int idx=0;
350 for (int *ph=maprh; *ph>=0; ph++, idx++)
351 humidities.push_back((volt[*ph]-offrh[idx])*0.0313);
352
353 for (int *pt=mapt; *pt>=0; pt++)
354 temperatures.push_back(resist[*pt]>800&&resist[*pt]<2000 ? GetTempPT1000(resist[*pt]) : 0);
355
356 // 0 = 3-(3+0)%4
357 // 3 = 3-(3+1)%4
358 // 2 = 3-(3+2)%4
359 // 1 = 3-(3+3)%4
360
361 /*
362 index unit offset scale crate for board:
363 0 mV 0 1 0 FAD 3.3V
364 24 mV 0 1 1 FAD 3.3V
365 16 mV 0 1 2 FAD 3.3V
366 8 mV 0 1 3 FAD 3.3V
367
368 1 mV 0 1 0 FAD 3.3V
369 25 mV 0 1 1 FAD 3.3V
370 17 mV 0 1 2 FAD 3.3V
371 9 mV 0 1 3 FAD 3.3V
372
373 2 mV 0 -1 0 FAD -2.0V
374 26 mV 0 -1 1 FAD -2.0V
375 18 mV 0 -1 2 FAD -2.0V
376 10 mV 0 -1 3 FAD -2.0V
377
378 --
379
380 3 mV 0 1 0 FPA 5.0V
381 27 mV 0 1 1 FPA 5.0V
382 19 mV 0 1 2 FPA 5.0V
383 11 mV 0 1 3 FPA 5.0V
384
385 4 mV 0 1 0 FPA 3.3V
386 28 mV 0 1 1 FPA 3.3V
387 20 mV 0 1 2 FPA 3.3V
388 12 mV 0 1 3 FPA 3.3V
389
390 5 mV 0 -1 0 FPA -3.3V
391 29 mV 0 -1 1 FPA -3.3V
392 21 mV 0 -1 2 FPA -3.3V
393 13 mV 0 -1 3 FPA -3.3V
394
395 --
396
397 32 mV 0 1 bottom ETH 5V
398 36 mV 0 1 top ETH 5V
399
400 33 mV 0 1 bottom FTM 3.3V
401 34 mV 0 -1 bottom FTM -3.3V
402
403 37 mV 0 1 top FFC 3.3V
404 38 mV 0 -1 top FLP -3.3V
405
406 -----
407
408 40 mA 0 5 0 FAD
409 64 mA 0 5 1 FAD
410 56 mA 0 5 2 FAD
411 48 mA 0 5 3 FAD
412
413 41 mA 0 5 0 FAD
414 65 mA 0 5 1 FAD
415 57 mA 0 5 2 FAD
416 49 mA 0 5 3 FAD
417
418 42 mA 0 -5 0 FAD
419 66 mA 0 -5 1 FAD
420 58 mA 0 -5 2 FAD
421 50 mA 0 -5 3 FAD
422
423 --
424
425 43 mA 0 5 0 FPA
426 67 mA 0 5 1 FPA
427 59 mA 0 5 2 FPA
428 51 mA 0 5 3 FPA
429
430 44 mA 0 5 0 FPA
431 68 mA 0 5 1 FPA
432 60 mA 0 5 2 FPA
433 52 mA 0 5 3 FPA
434
435 45 mA 0 -5 0 FPA
436 69 mA 0 -5 1 FPA
437 61 mA 0 -5 2 FPA
438 53 mA 0 -5 3 FPA
439
440 ---
441
442 72 mA 0 5 bottom ETH
443 76 mA 0 5 top ETH
444
445 73 mA 0 5 bottom FTM
446 74 mA 0 -5 bottom FTM
447
448 77 mA 0 5 top FFC
449 78 mA 0 -5 top FLP
450
451 ----
452
453 80 % RH -821 0.0313 FSP000
454 81 % RH -822 0.0313 FSP221
455 82 % RH -816 0.0313 Sector0
456 83 % RH -822 0.0313 Sector2
457 */
458
459 // TEMPERATURES
460 // 31 x Sensor plate
461 // 8 x Crate
462 // 12 x PS
463 // 4 x Backpanel
464 // 4 x Switchbox
465
466
467
468 /*
469 0 ohms FSP 000
470 1 ohms FSP 010
471 2 ohms FSP 023
472 3 ohms FSP 043
473 4 ohms FSP 072
474 5 ohms FSP 080
475 6 ohms FSP 092
476 56 ohms FSP 103
477 57 ohms FSP 111
478 58 ohms FSP 121
479 59 ohms FSP 152
480 60 ohms FSP 163
481 61 ohms FSP 171
482 62 ohms FSP 192
483 32 ohms FSP 200
484 33 ohms FSP 210
485 34 ohms FSP 223
486 35 ohms FSP 233
487 36 ohms FSP 243
488 63 ohms FSP 252
489 37 ohms FSP 280
490 38 ohms FSP 283
491 39 ohms FSP 293
492 24 ohms FSP 311
493 25 ohms FSP 321
494 26 ohms FSP 343
495 27 ohms FSP 352
496 28 ohms FSP 363
497 29 ohms FSP 371
498 30 ohms FSP 381
499 31 ohms FSP 392
500 8 ohms Crate0 ?
501 9 ohms Crate0 ?
502 48 ohms Crate1 ?
503 49 ohms Crate1 ?
504 40 ohms Crate2 ?
505 41 ohms Crate2 ?
506 16 ohms Crate3 ?
507 17 ohms Crate3 ?
508 10 ohms PS Crate 0
509 11 ohms PS Crate 0
510 50 ohms PS Crate 1
511 51 ohms PS Crate 1
512 42 ohms PS Crate 2
513 43 ohms PS Crate 2
514 18 ohms PS Crate 3
515 19 ohms PS Crate 3
516 12 ohms PS Aux0
517 52 ohms PS Aux0
518 20 ohms PS Aux1
519 44 ohms PS Aux1
520 13 ohms Backpanel ?
521 21 ohms Backpanel ?
522 45 ohms Backpanel ?
523 53 ohms Backpanel ?
524 14 ohms Switchbox0 ?
525 15 ohms Switchbox0 ?
526 46 ohms Switchbox1 ?
527 47 ohms Switchbox1 ?
528 7 ohms nc nc
529 22 ohms nc nc
530 23 ohms nc nc
531 54 ohms nc nc
532 55 ohms nc nc
533 */
534
535 for (size_t i=0; i<resist.size(); i++)
536 if (resist[i]>800 && resist[i]<2000)
537 cout << setw(2) << i << " - " << setw(4) << (int)resist[i] << ": " << setprecision(1) << fixed << GetTempPT1000(resist[i]) << endl;
538 else
539 cout << setw(2) << i << " - " << setw(4) << (int)resist[i] << ": " << "----" << endl;
540
541 UpdateTemp(time, temperatures);
542 UpdateVolt(time, voltages);
543 UpdateCur( time, currents);
544 UpdateHum( time, humidities);
545
546 StartRead();
547 }
548
549 void StartRead()
550 {
551 ba::async_read_until(*this, fBuffer, "end.\n",
552 boost::bind(&ConnectionFSC::HandleReceivedData, this,
553 dummy::error, dummy::bytes_transferred, 0));
554
555 // FIXME: Add timeout here
556 }
557
558 // This is called when a connection was established
559 void ConnectionEstablished()
560 {
561 PostMessage("m", 1);
562
563 fBuffer.prepare(10000);
564 StartRead();
565 }
566
567/*
568 void HandleReadTimeout(const bs::error_code &error)
569 {
570 if (error==ba::error::basic_errors::operation_aborted)
571 return;
572
573 if (error)
574 {
575 ostringstream str;
576 str << "Read timeout of " << URL() << ": " << error.message() << " (" << error << ")";// << endl;
577 Error(str);
578
579 PostClose();
580 return;
581
582 }
583
584 if (!is_open())
585 {
586 // For example: Here we could schedule a new accept if we
587 // would not want to allow two connections at the same time.
588 return;
589 }
590
591 // Check whether the deadline has passed. We compare the deadline
592 // against the current time since a new asynchronous operation
593 // may have moved the deadline before this actor had a chance
594 // to run.
595 if (fInTimeout.expires_at() > ba::deadline_timer::traits_type::now())
596 return;
597
598 Error("Timeout reading data from "+URL());
599
600 PostClose();
601 }
602*/
603
604public:
605 ConnectionFSC(ba::io_service& ioservice, MessageImp &imp) : Connection(ioservice, imp()),
606 fIsVerbose(true), fDump(false)
607 {
608 SetLogStream(&imp);
609 }
610
611 void SetVerbose(bool b)
612 {
613 fIsVerbose = b;
614 }
615
616 void SetDumpStream(bool b)
617 {
618 fDump = b;
619 }
620};
621
622// ------------------------------------------------------------------------
623
624#include "DimDescriptionService.h"
625
626class ConnectionDimFSC : public ConnectionFSC
627{
628private:
629
630 DimDescribedService fDimTemp;
631 DimDescribedService fDimHum;
632 DimDescribedService fDimVolt;
633 DimDescribedService fDimCurrent;
634
635 void Update(DimDescribedService &svc, vector<float> data, float time) const
636 {
637 data.insert(data.begin(), time);
638 svc.Update(data);
639 }
640
641 void UpdateTemp(float time, const vector<float> &temp)
642 {
643 Update(fDimTemp, temp, time);
644 }
645
646 void UpdateHum(float time, const vector<float> &hum)
647 {
648 Update(fDimHum, hum, time);
649 }
650
651 void UpdateVolt(float time, const vector<float> &volt)
652 {
653 Update(fDimVolt, volt, time);
654 }
655
656 void UpdateCur(float time, const vector<float> &curr)
657 {
658 Update(fDimCurrent, curr, time);
659 }
660
661public:
662 ConnectionDimFSC(ba::io_service& ioservice, MessageImp &imp) :
663 ConnectionFSC(ioservice, imp),
664 fDimTemp ("FSC_CONTROL/TEMPERATURE", "F:1;F:31;F:8;F:12;F:4;F:4", ""),
665 fDimHum ("FSC_CONTROL/HUMIDITY", "F:1;F:1;F:1;F:1;F:1", ""),
666 fDimVolt ("FSC_CONTROL/VOLTAGE", "F:1;F:4;F:4;F:4;F:4;F:4;F:4;F:2;F:2;F:1;F:1", ""),
667 fDimCurrent("FSC_CONTROL/CURRENT", "F:1;F:4;F:4;F:4;F:4;F:4;F:4;F:2;F:2;F:1;F:1", "")
668 {
669 }
670
671 // A B [C] [D] E [F] G H [I] J K [L] M N O P Q R [S] T U V W [X] Y Z
672};
673
674// ------------------------------------------------------------------------
675
676template <class T, class S>
677class StateMachineFSC : public T, public ba::io_service, public ba::io_service::work
678{
679 int Wrap(boost::function<void()> f)
680 {
681 f();
682 return T::GetCurrentState();
683 }
684
685 function<int(const EventImp &)> Wrapper(function<void()> func)
686 {
687 return bind(&StateMachineFSC::Wrap, this, func);
688 }
689
690private:
691 S fFSC;
692
693 enum states_t
694 {
695 kStateDisconnected = 1,
696 kStateConnected = 2,
697 };
698
699 int Disconnect()
700 {
701 // Close all connections
702 fFSC.PostClose(false);
703
704 /*
705 // Now wait until all connection have been closed and
706 // all pending handlers have been processed
707 poll();
708 */
709
710 return T::GetCurrentState();
711 }
712
713 int Reconnect(const EventImp &evt)
714 {
715 // Close all connections to supress the warning in SetEndpoint
716 fFSC.PostClose(false);
717
718 // Now wait until all connection have been closed and
719 // all pending handlers have been processed
720 poll();
721
722 if (evt.GetBool())
723 fFSC.SetEndpoint(evt.GetString());
724
725 // Now we can reopen the connection
726 fFSC.PostClose(true);
727
728 return T::GetCurrentState();
729 }
730
731 int Execute()
732 {
733 // Dispatch (execute) at most one handler from the queue. In contrary
734 // to run_one(), it doesn't wait until a handler is available
735 // which can be dispatched, so poll_one() might return with 0
736 // handlers dispatched. The handlers are always dispatched/executed
737 // synchronously, i.e. within the call to poll_one()
738 poll_one();
739
740 return fFSC.IsConnected() ? kStateConnected : kStateDisconnected;
741 }
742
743 bool CheckEventSize(size_t has, const char *name, size_t size)
744 {
745 if (has==size)
746 return true;
747
748 ostringstream msg;
749 msg << name << " - Received event has " << has << " bytes, but expected " << size << ".";
750 T::Fatal(msg);
751 return false;
752 }
753
754 int SetVerbosity(const EventImp &evt)
755 {
756 if (!CheckEventSize(evt.GetSize(), "SetVerbosity", 1))
757 return T::kSM_FatalError;
758
759 fFSC.SetVerbose(evt.GetBool());
760
761 return T::GetCurrentState();
762 }
763
764 int SetDumpStream(const EventImp &evt)
765 {
766 if (!CheckEventSize(evt.GetSize(), "SetDumpStream", 1))
767 return T::kSM_FatalError;
768
769 fFSC.SetDumpStream(evt.GetBool());
770
771 return T::GetCurrentState();
772 }
773
774public:
775 StateMachineFSC(ostream &out=cout) :
776 T(out, "FSC_CONTROL"), ba::io_service::work(static_cast<ba::io_service&>(*this)),
777 fFSC(*this, *this)
778 {
779 // ba::io_service::work is a kind of keep_alive for the loop.
780 // It prevents the io_service to go to stopped state, which
781 // would prevent any consecutive calls to run()
782 // or poll() to do nothing. reset() could also revoke to the
783 // previous state but this might introduce some overhead of
784 // deletion and creation of threads and more.
785
786 // State names
787 AddStateName(kStateDisconnected, "Disconnected",
788 "FSC board not connected via ethernet.");
789
790 AddStateName(kStateConnected, "Connected",
791 "Ethernet connection to FSC established.");
792
793 // Verbosity commands
794 T::AddEvent("SET_VERBOSE", "B:1")
795 (bind(&StateMachineFSC::SetVerbosity, this, placeholders::_1))
796 ("set verbosity state"
797 "|verbosity[bool]:disable or enable verbosity for received data (yes/no), except dynamic data");
798
799 T::AddEvent("DUMP_STREAM", "B:1")
800 (bind(&StateMachineFSC::SetDumpStream, this, placeholders::_1))
801 (""
802 "");
803
804 // Conenction commands
805 AddEvent("DISCONNECT", kStateConnected)
806 (bind(&StateMachineFSC::Disconnect, this))
807 ("disconnect from ethernet");
808
809 AddEvent("RECONNECT", "O", kStateDisconnected, kStateConnected)
810 (bind(&StateMachineFSC::Reconnect, this, placeholders::_1))
811 ("(Re)connect ethernet connection to FTM, a new address can be given"
812 "|[host][string]:new ethernet address in the form <host:port>");
813
814 fFSC.StartConnect();
815 }
816
817 void SetEndpoint(const string &url)
818 {
819 fFSC.SetEndpoint(url);
820 }
821
822 int EvalOptions(Configuration &conf)
823 {
824 SetEndpoint(conf.Get<string>("addr"));
825
826 fFSC.SetVerbose(!conf.Get<bool>("quiet"));
827
828 return -1;
829 }
830};
831
832// ------------------------------------------------------------------------
833
834#include "Main.h"
835
836template<class T, class S, class R>
837int RunShell(Configuration &conf)
838{
839 return Main::execute<T, StateMachineFSC<S, R>>(conf);
840}
841
842void SetupConfiguration(Configuration &conf)
843{
844 po::options_description control("FTM control options");
845 control.add_options()
846 ("no-dim", po_bool(), "Disable dim services")
847 ("addr,a", var<string>("localhost:5000"), "Network address of FTM")
848 ("quiet,q", po_bool(), "Disable printing contents of all received messages (except dynamic data) in clear text.")
849 ;
850
851 conf.AddOptions(control);
852}
853
854/*
855 Extract usage clause(s) [if any] for SYNOPSIS.
856 Translators: "Usage" and "or" here are patterns (regular expressions) which
857 are used to match the usage synopsis in program output. An example from cp
858 (GNU coreutils) which contains both strings:
859 Usage: cp [OPTION]... [-T] SOURCE DEST
860 or: cp [OPTION]... SOURCE... DIRECTORY
861 or: cp [OPTION]... -t DIRECTORY SOURCE...
862 */
863void PrintUsage()
864{
865 cout <<
866 "The ftmctrl controls the FSC (FACT Slow Control) board.\n"
867 "\n"
868 "The default is that the program is started without user intercation. "
869 "All actions are supposed to arrive as DimCommands. Using the -c "
870 "option, a local shell can be initialized. With h or help a short "
871 "help message about the usuage can be brought to the screen.\n"
872 "\n"
873 "Usage: fscctrl [-c type] [OPTIONS]\n"
874 " or: fscctrl [OPTIONS]\n";
875 cout << endl;
876}
877
878void PrintHelp()
879{
880 Main::PrintHelp<StateMachineFSC<StateMachine, ConnectionFSC>>();
881
882 /* Additional help text which is printed after the configuration
883 options goes here */
884
885 /*
886 cout << "bla bla bla" << endl << endl;
887 cout << endl;
888 cout << "Environment:" << endl;
889 cout << "environment" << endl;
890 cout << endl;
891 cout << "Examples:" << endl;
892 cout << "test exam" << endl;
893 cout << endl;
894 cout << "Files:" << endl;
895 cout << "files" << endl;
896 cout << endl;
897 */
898}
899
900int main(int argc, const char* argv[])
901{
902 Configuration conf(argv[0]);
903 conf.SetPrintUsage(PrintUsage);
904 Main::SetupConfiguration(conf);
905 SetupConfiguration(conf);
906
907 if (!conf.DoParse(argc, argv, PrintHelp))
908 return -1;
909
910 //try
911 {
912 // No console access at all
913 if (!conf.Has("console"))
914 {
915 if (conf.Get<bool>("no-dim"))
916 return RunShell<LocalStream, StateMachine, ConnectionFSC>(conf);
917 else
918 return RunShell<LocalStream, StateMachineDim, ConnectionDimFSC>(conf);
919 }
920 // Cosole access w/ and w/o Dim
921 if (conf.Get<bool>("no-dim"))
922 {
923 if (conf.Get<int>("console")==0)
924 return RunShell<LocalShell, StateMachine, ConnectionFSC>(conf);
925 else
926 return RunShell<LocalConsole, StateMachine, ConnectionFSC>(conf);
927 }
928 else
929 {
930 if (conf.Get<int>("console")==0)
931 return RunShell<LocalShell, StateMachineDim, ConnectionDimFSC>(conf);
932 else
933 return RunShell<LocalConsole, StateMachineDim, ConnectionDimFSC>(conf);
934 }
935 }
936 /*catch (std::exception& e)
937 {
938 cerr << "Exception: " << e.what() << endl;
939 return -1;
940 }*/
941
942 return 0;
943}
Note: See TracBrowser for help on using the repository browser.