release
[tango-nonfree.git] / lib / cpp / client / devapi_datahist.cpp
blob32f1b8f90362cff74e5e67465fd1483f97dd11cb
1 static const char *RcsId = "$Id: devapi_datahist.cpp 27410 2015-01-27 05:46:17Z taurel $\n$Name$";
3 //
4 // devapi_datahist.cpp - C++ source code file for TANGO devapi class
5 // DeviceDataHistory and DeviceAttributeHistory
6 //
7 // programmer(s) - Emmanuel Taurel (taurel@esrf.fr)
8 //
9 // original - June 2002
11 // Copyright (C) : 2002,2003,2004,2005,2006,2007,2008,2009,2010,2011,2012,2013,2014,2015
12 // European Synchrotron Radiation Facility
13 // BP 220, Grenoble 38043
14 // FRANCE
16 // This file is part of Tango.
18 // Tango is free software: you can redistribute it and/or modify
19 // it under the terms of the GNU Lesser General Public License as published by
20 // the Free Software Foundation, either version 3 of the License, or
21 // (at your option) any later version.
23 // Tango is distributed in the hope that it will be useful,
24 // but WITHOUT ANY WARRANTY; without even the implied warranty of
25 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
26 // GNU Lesser General Public License for more details.
28 // You should have received a copy of the GNU Lesser General Public License
29 // along with Tango. If not, see <http://www.gnu.org/licenses/>.
32 // version - $Revision: 27410 $
35 #if HAVE_CONFIG_H
36 #include <ac_config.h>
37 #endif
39 #include <tango.h>
40 #include <iomanip>
42 using namespace CORBA;
44 namespace Tango
47 //-----------------------------------------------------------------------------
49 // DeviceDataHistory::DeviceDataHistory() - constructors to create DeviceDataHistory
51 //-----------------------------------------------------------------------------
53 DeviceDataHistory::DeviceDataHistory():DeviceData(),ext_hist(Tango_nullptr)
55 fail = false;
56 err = new DevErrorList();
57 seq_ptr = NULL;
58 ref_ctr_ptr = NULL;
61 DeviceDataHistory::DeviceDataHistory(int n, int *ref,DevCmdHistoryList *ptr):ext_hist(Tango_nullptr)
63 ref_ctr_ptr = ref;
64 seq_ptr = ptr;
66 (*ref_ctr_ptr)++;
68 any = &((*ptr)[n].value);
69 fail = (*ptr)[n].cmd_failed;
70 time = (*ptr)[n].time;
71 err = &((*ptr)[n].errors);
74 DeviceDataHistory::DeviceDataHistory(const DeviceDataHistory & source):DeviceData(source),ext_hist(Tango_nullptr)
76 fail = source.fail;
77 time = source.time;
78 err = const_cast<DeviceDataHistory &>(source).err._retn();
80 seq_ptr = source.seq_ptr;
81 ref_ctr_ptr = source.ref_ctr_ptr;
82 if (ref_ctr_ptr != NULL)
83 (*ref_ctr_ptr)++;
85 #ifdef HAS_UNIQUE_PTR
86 if (source.ext_hist.get() != NULL)
88 ext_hist.reset(new DeviceDataHistoryExt);
89 *(ext_hist.get()) = *(source.ext_hist.get());
91 #else
92 if (source.ext_hist == NULL)
93 ext_hist = NULL;
94 else
96 ext_hist = new DeviceDataHistoryExt();
97 *ext_hist = *(source.ext_hist);
99 #endif
102 #ifdef HAS_RVALUE
103 DeviceDataHistory::DeviceDataHistory(DeviceDataHistory && source):DeviceData(move(source)),ext_hist(Tango_nullptr)
105 fail = source.fail;
106 time = source.time;
107 err = source.err._retn();
109 seq_ptr = source.seq_ptr;
110 ref_ctr_ptr = source.ref_ctr_ptr;
112 if (source.ext_hist.get() != NULL)
113 ext_hist = move(source.ext_hist);
114 else
115 ext_hist.reset();
117 #endif
119 //-----------------------------------------------------------------------------
121 // DeviceDataHistory::~DeviceDataHistory() - Destructor
123 //-----------------------------------------------------------------------------
125 DeviceDataHistory::~DeviceDataHistory()
127 if (seq_ptr != NULL)
129 any._retn();
130 err._retn();
132 (*ref_ctr_ptr)--;
133 if (*ref_ctr_ptr == 0)
135 delete seq_ptr;
136 delete ref_ctr_ptr;
140 #ifndef HAS_UNIQUE_PTR
141 delete ext_hist;
142 #endif
146 //-----------------------------------------------------------------------------
148 // DeviceDataHistory::operator=() - assignement operator
150 //-----------------------------------------------------------------------------
152 DeviceDataHistory & DeviceDataHistory::operator=(const DeviceDataHistory &rval)
155 if (this != &rval)
159 // Assignement of DeviceData class members first
162 this->DeviceData::operator=(rval);
165 // Then, assignement of DeviceDataHistory members
168 fail = rval.fail;
169 time = rval.time;
170 #ifdef HAS_RVALUE
171 err = rval.err;
172 #else
173 err = const_cast<DeviceDataHistory &>(rval).err._retn();
174 #endif
176 if (ref_ctr_ptr != NULL)
178 (*ref_ctr_ptr)--;
179 if (*ref_ctr_ptr == 0)
181 delete seq_ptr;
182 delete ref_ctr_ptr;
186 seq_ptr = rval.seq_ptr;
187 ref_ctr_ptr = rval.ref_ctr_ptr;
188 (*ref_ctr_ptr)++;
190 #ifdef HAS_UNIQUE_PTR
191 if (rval.ext_hist.get() != NULL)
193 ext_hist.reset(new DeviceDataHistoryExt);
194 *(ext_hist.get()) = *(rval.ext_hist.get());
196 else
197 ext_hist.reset();
198 #else
199 delete ext_hist;
200 if (rval.ext_hist != NULL)
202 ext_hist = new DeviceDataHistoryExt();
203 *ext_hist = *(rval.ext_hist);
205 else
206 ext_hist = NULL;
207 #endif
210 return *this;
213 //-----------------------------------------------------------------------------
215 // DeviceDataHistory::operator=() - move assignement operator
217 //-----------------------------------------------------------------------------
219 #ifdef HAS_RVALUE
220 DeviceDataHistory & DeviceDataHistory::operator=(DeviceDataHistory &&rval)
224 // Assignement of DeviceData class members first
227 this->DeviceData::operator=(move(rval));
230 // Then, assignement of DeviceDataHistory members
233 fail = rval.fail;
234 time = rval.time;
235 err = rval.err._retn();
238 // Decrement old ctr
240 if (ref_ctr_ptr != NULL)
242 (*ref_ctr_ptr)--;
243 if (*ref_ctr_ptr == 0)
245 delete seq_ptr;
246 delete ref_ctr_ptr;
251 // Copy ctr (but don't increment it) and ptr
254 seq_ptr = rval.seq_ptr;
255 ref_ctr_ptr = rval.ref_ctr_ptr;
258 // Extension class
261 if (rval.ext_hist.get() != NULL)
262 ext_hist = move(rval.ext_hist);
263 else
264 ext_hist.reset();
266 return *this;
268 #endif
270 //+-------------------------------------------------------------------------
272 // operator overloading : <<
274 // description : Friend function to ease printing instance of the
275 // DeviceDataHistory class
277 //--------------------------------------------------------------------------
279 ostream &operator<<(ostream &o_str,DeviceDataHistory &dh)
283 // First, print date
286 time_t tmp_val = dh.time.tv_sec;
287 char tmp_date[128];
288 #ifdef _TG_WINDOWS_
289 ctime_s(tmp_date,128,&tmp_val);
290 #else
291 ctime_r(&tmp_val,tmp_date);
292 #endif
293 tmp_date[strlen(tmp_date) - 1] = '\0';
294 o_str << tmp_date;
295 o_str << " (" << dh.time.tv_sec << "," << setw(6) << setfill('0') << dh.time.tv_usec << " sec) : ";
298 // Print data or error stack
301 if (dh.fail == true)
303 unsigned int nb_err = dh.err.in().length();
304 for (unsigned long i = 0;i < nb_err;i++)
306 o_str << "Tango error stack" << endl;
307 o_str << "Severity = ";
308 switch ((dh.err.in())[i].severity)
310 case Tango::WARN :
311 o_str << "WARNING ";
312 break;
314 case Tango::ERR :
315 o_str << "ERROR ";
316 break;
318 case Tango::PANIC :
319 o_str << "PANIC ";
320 break;
322 default :
323 o_str << "Unknown severity code";
324 break;
326 o_str << endl;
327 o_str << "Error reason = " << (dh.err.in())[i].reason.in() << endl;
328 o_str << "Desc : " << (dh.err.in())[i].desc.in() << endl;
329 o_str << "Origin : " << (dh.err.in())[i].origin.in();
330 if (i != nb_err - 1)
331 o_str << endl;
334 else
336 o_str << static_cast<DeviceData &>(dh);
339 return o_str;
342 //-----------------------------------------------------------------------------
344 // DeviceAttributeHistory::DeviceAttributeHistory() - constructors to create DeviceAttributeHistory
346 //-----------------------------------------------------------------------------
348 DeviceAttributeHistory::DeviceAttributeHistory():DeviceAttribute(),ext_hist(Tango_nullptr)
350 fail = false;
351 err_list = new DevErrorList();
354 DeviceAttributeHistory::DeviceAttributeHistory(int n,DevAttrHistoryList_var &seq):ext_hist(Tango_nullptr)
356 fail = seq[n].attr_failed;
358 err_list = new DevErrorList(seq[n].errors);
359 time = seq[n].value.time;
360 quality = seq[n].value.quality;
361 dim_x = seq[n].value.dim_x;
362 dim_y = seq[n].value.dim_y;
363 name = seq[n].value.name;
365 const DevVarLongArray *tmp_seq_lo;
366 CORBA::Long *tmp_lo;
367 const DevVarLong64Array *tmp_seq_lolo;
368 CORBA::LongLong *tmp_lolo;
369 const DevVarShortArray *tmp_seq_sh;
370 CORBA::Short *tmp_sh;
371 const DevVarDoubleArray *tmp_seq_db;
372 CORBA::Double *tmp_db;
373 const DevVarStringArray *tmp_seq_str;
374 char **tmp_str;
375 const DevVarFloatArray *tmp_seq_fl;
376 CORBA::Float *tmp_fl;
377 const DevVarBooleanArray *tmp_seq_boo;
378 CORBA::Boolean *tmp_boo;
379 const DevVarUShortArray *tmp_seq_ush;
380 CORBA::UShort *tmp_ush;
381 const DevVarCharArray *tmp_seq_uch;
382 CORBA::Octet *tmp_uch;
383 const DevVarULongArray *tmp_seq_ulo;
384 CORBA::ULong *tmp_ulo;
385 const DevVarULong64Array *tmp_seq_ulolo;
386 CORBA::ULongLong *tmp_ulolo;
387 const DevVarStateArray *tmp_seq_state;
388 Tango::DevState *tmp_state;
390 CORBA::ULong max,len;
392 if ((fail == false) && (quality != Tango::ATTR_INVALID))
394 CORBA::TypeCode_var ty = seq[n].value.value.type();
395 CORBA::TypeCode_var ty_alias = ty->content_type();
396 CORBA::TypeCode_var ty_seq = ty_alias->content_type();
397 switch (ty_seq->kind())
399 case tk_long:
400 seq[n].value.value >>= tmp_seq_lo;
401 max = tmp_seq_lo->maximum();
402 len = tmp_seq_lo->length();
403 tmp_lo = (const_cast<DevVarLongArray *>(tmp_seq_lo))->get_buffer((CORBA::Boolean)true);
404 LongSeq = new DevVarLongArray(max,len,tmp_lo,true);
405 break;
407 case tk_longlong:
408 seq[n].value.value >>= tmp_seq_lolo;
409 max = tmp_seq_lolo->maximum();
410 len = tmp_seq_lolo->length();
411 tmp_lolo = (const_cast<DevVarLong64Array *>(tmp_seq_lolo))->get_buffer((CORBA::Boolean)true);
412 Long64Seq = new DevVarLong64Array(max,len,tmp_lolo,true);
413 break;
415 case tk_short:
416 seq[n].value.value >>= tmp_seq_sh;
417 max = tmp_seq_sh->maximum();
418 len = tmp_seq_sh->length();
419 tmp_sh = (const_cast<DevVarShortArray *>(tmp_seq_sh))->get_buffer((CORBA::Boolean)true);
420 ShortSeq = new DevVarShortArray(max,len,tmp_sh,true);
421 break;
423 case tk_double:
424 seq[n].value.value >>= tmp_seq_db;
425 max = tmp_seq_db->maximum();
426 len = tmp_seq_db->length();
427 tmp_db = (const_cast<DevVarDoubleArray *>(tmp_seq_db))->get_buffer((CORBA::Boolean)true);
428 DoubleSeq = new DevVarDoubleArray(max,len,tmp_db,true);
429 break;
431 case tk_string:
432 seq[n].value.value >>= tmp_seq_str;
433 max = tmp_seq_str->maximum();
434 len = tmp_seq_str->length();
435 tmp_str = (const_cast<DevVarStringArray *>(tmp_seq_str))->get_buffer((CORBA::Boolean)true);
436 StringSeq = new DevVarStringArray(max,len,tmp_str,true);
437 break;
439 case tk_float:
440 seq[n].value.value >>= tmp_seq_fl;
441 max = tmp_seq_fl->maximum();
442 len = tmp_seq_fl->length();
443 tmp_fl = (const_cast<DevVarFloatArray *>(tmp_seq_fl))->get_buffer((CORBA::Boolean)true);
444 FloatSeq = new DevVarFloatArray(max,len,tmp_fl,true);
445 break;
447 case tk_boolean:
448 seq[n].value.value >>= tmp_seq_boo;
449 max = tmp_seq_boo->maximum();
450 len = tmp_seq_boo->length();
451 tmp_boo = (const_cast<DevVarBooleanArray *>(tmp_seq_boo))->get_buffer((CORBA::Boolean)true);
452 BooleanSeq = new DevVarBooleanArray(max,len,tmp_boo,true);
453 break;
455 case tk_ushort:
456 seq[n].value.value >>= tmp_seq_ush;
457 max = tmp_seq_ush->maximum();
458 len = tmp_seq_ush->length();
459 tmp_ush = (const_cast<DevVarUShortArray *>(tmp_seq_ush))->get_buffer((CORBA::Boolean)true);
460 UShortSeq = new DevVarUShortArray(max,len,tmp_ush,true);
461 break;
463 case tk_octet:
464 seq[n].value.value >>= tmp_seq_uch;
465 max = tmp_seq_uch->maximum();
466 len = tmp_seq_uch->length();
467 tmp_uch = (const_cast<DevVarCharArray *>(tmp_seq_uch))->get_buffer((CORBA::Boolean)true);
468 UCharSeq = new DevVarCharArray(max,len,tmp_uch,true);
469 break;
471 case tk_ulong:
472 seq[n].value.value >>= tmp_seq_ulo;
473 max = tmp_seq_ulo->maximum();
474 len = tmp_seq_ulo->length();
475 tmp_ulo = (const_cast<DevVarULongArray *>(tmp_seq_ulo))->get_buffer((CORBA::Boolean)true);
476 ULongSeq = new DevVarULongArray(max,len,tmp_ulo,true);
477 break;
479 case tk_ulonglong:
480 seq[n].value.value >>= tmp_seq_ulolo;
481 max = tmp_seq_ulolo->maximum();
482 len = tmp_seq_ulolo->length();
483 tmp_ulolo = (const_cast<DevVarULong64Array *>(tmp_seq_ulolo))->get_buffer((CORBA::Boolean)true);
484 ULong64Seq = new DevVarULong64Array(max,len,tmp_ulolo,true);
485 break;
487 case tk_enum:
488 seq[n].value.value >>= tmp_seq_state;
489 max = tmp_seq_state->maximum();
490 len = tmp_seq_state->length();
491 tmp_state = (const_cast<DevVarStateArray *>(tmp_seq_state))->get_buffer((CORBA::Boolean)true);
492 StateSeq = new DevVarStateArray(max,len,tmp_state,true);
493 break;
495 default:
496 break;
503 DeviceAttributeHistory::DeviceAttributeHistory(int n,DevAttrHistoryList_3_var &seq):ext_hist(Tango_nullptr)
505 fail = seq[n].attr_failed;
507 err_list = new DevErrorList(seq[n].value.err_list);
508 time = seq[n].value.time;
509 quality = seq[n].value.quality;
510 dim_x = seq[n].value.r_dim.dim_x;
511 dim_y = seq[n].value.r_dim.dim_y;
512 w_dim_x = seq[n].value.w_dim.dim_x;
513 w_dim_y = seq[n].value.w_dim.dim_y;
514 name = seq[n].value.name;
516 const DevVarLongArray *tmp_seq_lo;
517 CORBA::Long *tmp_lo;
518 const DevVarLong64Array *tmp_seq_lolo;
519 CORBA::LongLong *tmp_lolo;
520 const DevVarShortArray *tmp_seq_sh;
521 CORBA::Short *tmp_sh;
522 const DevVarDoubleArray *tmp_seq_db;
523 CORBA::Double *tmp_db;
524 const DevVarStringArray *tmp_seq_str;
525 char **tmp_str;
526 const DevVarFloatArray *tmp_seq_fl;
527 CORBA::Float *tmp_fl;
528 const DevVarBooleanArray *tmp_seq_boo;
529 CORBA::Boolean *tmp_boo;
530 const DevVarUShortArray *tmp_seq_ush;
531 CORBA::UShort *tmp_ush;
532 const DevVarCharArray *tmp_seq_uch;
533 CORBA::Octet *tmp_uch;
534 const DevVarULongArray *tmp_seq_ulo;
535 CORBA::ULong *tmp_ulo;
536 const DevVarULong64Array *tmp_seq_ulolo;
537 CORBA::ULongLong *tmp_ulolo;
538 const DevVarStateArray *tmp_seq_state;
539 Tango::DevState *tmp_state;
541 CORBA::ULong max,len;
543 if ((fail == false) && (quality != Tango::ATTR_INVALID))
545 CORBA::TypeCode_var ty = seq[n].value.value.type();
546 CORBA::TypeCode_var ty_alias = ty->content_type();
547 CORBA::TypeCode_var ty_seq = ty_alias->content_type();
548 switch (ty_seq->kind())
550 case tk_long:
551 seq[n].value.value >>= tmp_seq_lo;
552 max = tmp_seq_lo->maximum();
553 len = tmp_seq_lo->length();
554 tmp_lo = (const_cast<DevVarLongArray *>(tmp_seq_lo))->get_buffer((CORBA::Boolean)true);
555 LongSeq = new DevVarLongArray(max,len,tmp_lo,true);
556 break;
558 case tk_longlong:
559 seq[n].value.value >>= tmp_seq_lolo;
560 max = tmp_seq_lolo->maximum();
561 len = tmp_seq_lolo->length();
562 tmp_lolo = (const_cast<DevVarLong64Array *>(tmp_seq_lolo))->get_buffer((CORBA::Boolean)true);
563 Long64Seq = new DevVarLong64Array(max,len,tmp_lolo,true);
564 break;
566 case tk_short:
567 seq[n].value.value >>= tmp_seq_sh;
568 max = tmp_seq_sh->maximum();
569 len = tmp_seq_sh->length();
570 tmp_sh = (const_cast<DevVarShortArray *>(tmp_seq_sh))->get_buffer((CORBA::Boolean)true);
571 ShortSeq = new DevVarShortArray(max,len,tmp_sh,true);
572 break;
574 case tk_double:
575 seq[n].value.value >>= tmp_seq_db;
576 max = tmp_seq_db->maximum();
577 len = tmp_seq_db->length();
578 tmp_db = (const_cast<DevVarDoubleArray *>(tmp_seq_db))->get_buffer((CORBA::Boolean)true);
579 DoubleSeq = new DevVarDoubleArray(max,len,tmp_db,true);
580 break;
582 case tk_string:
583 seq[n].value.value >>= tmp_seq_str;
584 max = tmp_seq_str->maximum();
585 len = tmp_seq_str->length();
586 tmp_str = (const_cast<DevVarStringArray *>(tmp_seq_str))->get_buffer((CORBA::Boolean)true);
587 StringSeq = new DevVarStringArray(max,len,tmp_str,true);
588 break;
590 case tk_float:
591 seq[n].value.value >>= tmp_seq_fl;
592 max = tmp_seq_fl->maximum();
593 len = tmp_seq_fl->length();
594 tmp_fl = (const_cast<DevVarFloatArray *>(tmp_seq_fl))->get_buffer((CORBA::Boolean)true);
595 FloatSeq = new DevVarFloatArray(max,len,tmp_fl,true);
596 break;
598 case tk_boolean:
599 seq[n].value.value >>= tmp_seq_boo;
600 max = tmp_seq_boo->maximum();
601 len = tmp_seq_boo->length();
602 tmp_boo = (const_cast<DevVarBooleanArray *>(tmp_seq_boo))->get_buffer((CORBA::Boolean)true);
603 BooleanSeq = new DevVarBooleanArray(max,len,tmp_boo,true);
604 break;
606 case tk_ushort:
607 seq[n].value.value >>= tmp_seq_ush;
608 max = tmp_seq_ush->maximum();
609 len = tmp_seq_ush->length();
610 tmp_ush = (const_cast<DevVarUShortArray *>(tmp_seq_ush))->get_buffer((CORBA::Boolean)true);
611 UShortSeq = new DevVarUShortArray(max,len,tmp_ush,true);
612 break;
614 case tk_octet:
615 seq[n].value.value >>= tmp_seq_uch;
616 max = tmp_seq_uch->maximum();
617 len = tmp_seq_uch->length();
618 tmp_uch = (const_cast<DevVarCharArray *>(tmp_seq_uch))->get_buffer((CORBA::Boolean)true);
619 UCharSeq = new DevVarCharArray(max,len,tmp_uch,true);
620 break;
622 case tk_ulong:
623 seq[n].value.value >>= tmp_seq_ulo;
624 max = tmp_seq_ulo->maximum();
625 len = tmp_seq_ulo->length();
626 tmp_ulo = (const_cast<DevVarULongArray *>(tmp_seq_ulo))->get_buffer((CORBA::Boolean)true);
627 ULongSeq = new DevVarULongArray(max,len,tmp_ulo,true);
628 break;
630 case tk_ulonglong:
631 seq[n].value.value >>= tmp_seq_ulolo;
632 max = tmp_seq_ulolo->maximum();
633 len = tmp_seq_ulolo->length();
634 tmp_ulolo = (const_cast<DevVarULong64Array *>(tmp_seq_ulolo))->get_buffer((CORBA::Boolean)true);
635 ULong64Seq = new DevVarULong64Array(max,len,tmp_ulolo,true);
636 break;
638 case tk_enum:
639 seq[n].value.value >>= tmp_seq_state;
640 max = tmp_seq_state->maximum();
641 len = tmp_seq_state->length();
642 tmp_state = (const_cast<DevVarStateArray *>(tmp_seq_state))->get_buffer((CORBA::Boolean)true);
643 StateSeq = new DevVarStateArray(max,len,tmp_state,true);
644 break;
646 default:
647 break;
655 DeviceAttributeHistory::DeviceAttributeHistory(const DeviceAttributeHistory & source):DeviceAttribute(source),ext_hist(Tango_nullptr)
657 fail = source.fail;
659 #ifdef HAS_UNIQUE_PTR
660 if (source.ext_hist.get() != NULL)
662 ext_hist.reset(new DeviceAttributeHistoryExt);
663 *(ext_hist.get()) = *(source.ext_hist.get());
665 #else
666 if (source.ext_hist == NULL)
667 ext_hist = NULL;
668 else
670 ext_hist = new DeviceAttributeHistoryExt();
671 *ext_hist = *(source.ext_hist);
673 #endif
676 #ifdef HAS_RVALUE
677 DeviceAttributeHistory::DeviceAttributeHistory(DeviceAttributeHistory &&source):DeviceAttribute(move(source)),ext_hist(Tango_nullptr)
679 fail = source.fail;
681 if (source.ext_hist.get() != NULL)
682 ext_hist = move(source.ext_hist);
685 #endif
687 //-----------------------------------------------------------------------------
689 // DeviceAttributeHistory::~DeviceAttributeHistory() - Destructor
691 //-----------------------------------------------------------------------------
693 DeviceAttributeHistory::~DeviceAttributeHistory()
695 #ifndef HAS_UNIQUE_PTR
696 delete ext_hist;
697 #endif
701 //-----------------------------------------------------------------------------
703 // DeviceAttributeHistory::operator=() - assignement operator
705 //-----------------------------------------------------------------------------
707 DeviceAttributeHistory & DeviceAttributeHistory::operator=(const DeviceAttributeHistory &rval)
710 if (this != &rval)
713 // First, assignement of DeviceAttribute class members
716 this->DeviceAttribute::operator=(rval);
719 // Then, assignement of DeviceAttributeHistory members
722 fail = rval.fail;
724 #ifdef HAS_UNIQUE_PTR
725 if (rval.ext_hist.get() != NULL)
727 ext_hist.reset(new DeviceAttributeHistoryExt);
728 *(ext_hist.get()) = *(rval.ext_hist.get());
730 else
731 ext_hist.reset();
732 #else
733 delete ext_hist;
734 if (rval.ext_hist != NULL)
736 ext_hist = new DeviceAttributeHistoryExt();
737 *ext_hist = *(rval.ext_hist);
739 else
740 ext_hist = NULL;
741 #endif
744 return *this;
747 #ifdef HAS_RVALUE
748 DeviceAttributeHistory & DeviceAttributeHistory::operator=(DeviceAttributeHistory &&rval)
752 // First, assignement of DeviceAttribute class members
755 this->DeviceAttribute::operator=(move(rval));
758 // Then, assignement of DeviceAttributeHistory members
761 fail = rval.fail;
763 if (rval.ext_hist.get() != NULL)
764 ext_hist = move(rval.ext_hist);
765 else
766 ext_hist.reset();
768 return *this;
770 #endif
772 //+-------------------------------------------------------------------------
774 // operator overloading : <<
776 // description : Friend function to ease printing instance of the
777 // DeviceAttributeHistory class
779 //--------------------------------------------------------------------------
781 ostream &operator<<(ostream &o_str,DeviceAttributeHistory &dah)
784 // Print date
787 if (dah.time.tv_sec != 0)
789 char tmp_date[128];
790 time_t tmp_val = dah.time.tv_sec;
791 #ifdef _TG_WINDOWS_
792 ctime_s(tmp_date,128,&tmp_val);
793 #else
794 ctime_r(&tmp_val,tmp_date);
795 #endif
796 tmp_date[strlen(tmp_date) - 1] = '\0';
797 o_str << tmp_date;
798 o_str << " (" << dah.time.tv_sec << "," << setw(6) << setfill('0') << dah.time.tv_usec << " sec) : ";
802 // print attribute name
805 o_str << dah.name;
808 // print dim_x and dim_y
811 o_str << " (dim_x = " << dah.dim_x << ", dim_y = " << dah.dim_y << ", ";
814 // print write dim_x and dim_y
817 o_str << "w_dim_x = " << dah.w_dim_x << ", w_dim_y = " << dah.w_dim_y << ", ";
820 // Print quality
823 o_str << "Data quality factor = ";
824 switch (dah.quality)
826 case Tango::ATTR_VALID:
827 o_str << "VALID)" << endl;
828 break;
830 case Tango::ATTR_INVALID:
831 o_str << "INVALID)";
832 break;
834 case Tango::ATTR_ALARM:
835 o_str << "ALARM)" << endl;
836 break;
838 case Tango::ATTR_CHANGING:
839 o_str << "CHANGING)" << endl;
840 break;
842 case Tango::ATTR_WARNING:
843 o_str << "WARNING) " << endl;
844 break;
848 // Print data (if valid) or error stack
851 if (dah.fail == true)
853 unsigned int nb_err = dah.err_list.in().length();
854 for (unsigned long i = 0;i < nb_err;i++)
856 o_str << "Tango error stack" << endl;
857 o_str << "Severity = ";
858 switch (dah.err_list[i].severity)
860 case Tango::WARN :
861 o_str << "WARNING ";
862 break;
864 case Tango::ERR :
865 o_str << "ERROR ";
866 break;
868 case Tango::PANIC :
869 o_str << "PANIC ";
870 break;
872 default :
873 o_str << "Unknown severity code";
874 break;
876 o_str << endl;
877 o_str << "Error reason = " << dah.err_list[i].reason.in() << endl;
878 o_str << "Desc : " << dah.err_list[i].desc.in() << endl;
879 o_str << "Origin : " << dah.err_list[i].origin.in();
880 if (i != nb_err - 1)
881 o_str << endl;
884 else
886 if (dah.quality != Tango::ATTR_INVALID)
888 if (dah.is_empty() == true)
889 o_str << "No data in DeviceData object";
890 else
892 if (dah.LongSeq.operator->() != NULL)
893 o_str << *(dah.LongSeq.operator->());
894 else if (dah.ShortSeq.operator->() != NULL)
895 o_str << *(dah.ShortSeq.operator->());
896 else if (dah.DoubleSeq.operator->() != NULL)
897 o_str << *(dah.DoubleSeq.operator->());
898 else if (dah.FloatSeq.operator->() != NULL)
899 o_str << *(dah.FloatSeq.operator->());
900 else if (dah.BooleanSeq.operator->() != NULL)
901 o_str << *(dah.BooleanSeq.operator->());
902 else if (dah.UShortSeq.operator->() != NULL)
903 o_str << *(dah.UShortSeq.operator->());
904 else if (dah.UCharSeq.operator->() != NULL)
905 o_str << *(dah.UCharSeq.operator->());
906 else if (dah.Long64Seq.operator->() != NULL)
907 o_str << *(dah.Long64Seq.operator->());
908 else if (dah.ULongSeq.operator->() != NULL)
909 o_str << *(dah.ULongSeq.operator->());
910 else if (dah.ULong64Seq.operator->() != NULL)
911 o_str << *(dah.ULong64Seq.operator->());
912 else if (dah.StateSeq.operator->() != NULL)
913 o_str << *(dah.StateSeq.operator->());
914 else if (dah.EncodedSeq.operator->() != NULL)
915 o_str << *(dah.EncodedSeq.operator->());
916 else
917 o_str << *(dah.StringSeq.operator->());
922 return o_str;
925 } // End of Tango namepsace