]> git.uio.no Git - u/mrichter/AliRoot.git/blame - SHUTTLE/AliDCSMessage.cxx
Updated comments (Raffaele)
[u/mrichter/AliRoot.git] / SHUTTLE / AliDCSMessage.cxx
CommitLineData
73abe331 1/**************************************************************************
2 * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
3 * *
4 * Author: The ALICE Off-line Project. *
5 * Contributors are mentioned in the code where appropriate. *
6 * *
7 * Permission to use, copy, modify and distribute this software and its *
8 * documentation strictly for non-commercial purposes is hereby granted *
9 * without fee, provided that the above copyright notice appears in all *
10 * copies and that both the copyright notice and this permission notice *
11 * appear in the supporting documentation. The authors make no claims *
12 * about the suitability of this software for any purpose. It is *
13 * provided "as is" without express or implied warranty. *
14 **************************************************************************/
15
16/*
17$Log$
2bb7b766 18Revision 1.6 2006/08/15 10:50:00 jgrosseo
19effc++ corrections (alberto)
20
4f0ab988 21Revision 1.5 2006/07/20 09:54:40 jgrosseo
22introducing status management: The processing per subdetector is divided into several steps,
23after each step the status is stored on disk. If the system crashes in any of the steps the Shuttle
24can keep track of the number of failures and skips further processing after a certain threshold is
25exceeded. These thresholds can be configured in LDAP.
26
5164a766 27Revision 1.4 2006/07/04 14:59:57 jgrosseo
28revision of AliDCSValue: Removed wrapper classes, reduced storage size per value by factor 2
29
45a493ce 30Revision 1.3 2006/06/12 09:11:16 jgrosseo
31coding conventions (Alberto)
32
58bc3020 33Revision 1.2 2006/03/07 07:52:34 hristov
34New version (B.Yordanov)
35
d477ad88 36Revision 1.3 2005/11/17 17:47:34 byordano
37TList changed to TObjArray
38
39Revision 1.2 2005/11/17 14:43:23 byordano
40import to local CVS
41
42Revision 1.1.1.1 2005/10/28 07:33:58 hristov
43Initial import as subdirectory in AliRoot
44
73abe331 45Revision 1.1.1.1 2005/09/12 22:11:40 byordano
46SHUTTLE package
47
48Revision 1.2 2005/08/30 10:53:23 byordano
49some more descriptions added
50
51*/
52
53
54//
55// This class is a wrapper of AliDCSMessage.
56// These are the messages which form AliDCSProtocol.
57// Every message has header and body. The body size is written in the header.
58// There are five message types:
59// 1) Request - used by the client to form a single request to DCS server
60// 2) Count - returned by the server to inidicate the total number of
61// values which would be sent to the client.
62// 3) ResultSet - returned by the server and contains part of values set
63// which forms the server resposen.
64// 4) Error - returned by the server in case of error
65// 5) MultiRequest - used by the client to form multi request.
66// This is a request which serves many aliases/dp at the same time
67// For all aliases/dp the same time interval is used.
68// Short description of the schema:
69// The client sends a request (Request or MultiRequest) and the server
70// returns:
71// 1) Count - the total number of values that the client should
72// expect.
73// 2) ResultSet* - every ResultSet message contains a part
74// of valueSet (some values) which the client should expect
75// The client can wait for ResultMessage until it gets
76// all values (total number) which was returned by the
77// Count message at the beginning of the ResutlSet sereie.
78// In case of error:
79// 1) Error - contains the error code and error description
80//
81
82#include "AliDCSMessage.h"
83
84#include "AliLog.h"
85
86#include <Bytes.h>
87#include <TObjString.h>
88
89#include <ctype.h>
90#include <assert.h>
91
92ClassImp(AliDCSMessage)
93
58bc3020 94//______________________________________________________________________
73abe331 95AliDCSMessage::AliDCSMessage():
4f0ab988 96 fMessage(NULL), fMessageSize(0), fType(kInvalid),
97 fStartTime(0), fEndTime(0),
98 fRequestString(""), fCount(0),
2bb7b766 99 fValueType(AliDCSValue::kInvalid),
4f0ab988 100 fErrorCode(kNoneError), fErrorString(""),
101 fRequestStrings()
73abe331 102{
58bc3020 103// default constructor
2bb7b766 104 fValues = new TObjArray();
105 fValues->SetOwner(0);
73abe331 106
107}
108
58bc3020 109//______________________________________________________________________
73abe331 110AliDCSMessage::AliDCSMessage(const char* message, UInt_t size):
4f0ab988 111 fMessageSize(size), fType(kInvalid),
112 fStartTime(0), fEndTime(0),
113 fRequestString(""), fCount(0),
2bb7b766 114 fValueType(AliDCSValue::kInvalid),
4f0ab988 115 fErrorCode(kNoneError), fErrorString(""),
116 fRequestStrings()
73abe331 117{
58bc3020 118// default constructor
119
73abe331 120 fMessage = new char[size];
121
122 memcpy(fMessage, message, size);
2bb7b766 123 fValues = new TObjArray();
124 fValues->SetOwner(0);
73abe331 125}
126
58bc3020 127//______________________________________________________________________
128AliDCSMessage::AliDCSMessage(const AliDCSMessage& /*other*/):
4f0ab988 129 TObject(), fMessage(NULL), fMessageSize(0), fType(kInvalid),
130 fStartTime(0), fEndTime(0),
131 fRequestString(""), fCount(0),
2bb7b766 132 fValueType(AliDCSValue::kInvalid),
4f0ab988 133 fErrorCode(kNoneError), fErrorString(""),
134 fRequestStrings()
58bc3020 135{
136// copy constructor (not implemented)
137
138}
139
140//______________________________________________________________________
141AliDCSMessage &AliDCSMessage::operator=(const AliDCSMessage& /*other*/)
142{
143// assignment operator (not implemented)
144
145return *this;
146}
147
148//______________________________________________________________________
149AliDCSMessage::~AliDCSMessage()
150{
151// destructor
152
73abe331 153 DestroyMessage();
154 DestroyBuffer();
2bb7b766 155 if(fValues) delete fValues; fValues=0;
73abe331 156}
157
58bc3020 158//______________________________________________________________________
2bb7b766 159void AliDCSMessage::CreateRequestMessage(RequestType type,
73abe331 160 UInt_t startTime, UInt_t endTime, const char* request)
161{
58bc3020 162// Create request message
163
73abe331 164 DestroyMessage();
165
166 fType = AliDCSMessage::kRequest;
167 fRequestType = type;
168 fStartTime = startTime;
169 fEndTime = endTime;
170 fRequestString = request;
171}
172
58bc3020 173//______________________________________________________________________
73abe331 174void AliDCSMessage::CreateMultiRequestMessage(RequestType type,
175 UInt_t startTime, UInt_t endTime)
176{
58bc3020 177// Create multi request message
178
73abe331 179 DestroyMessage();
180
181 fType = AliDCSMessage::kMultiRequest;
182 fRequestType = type;
183 fStartTime = startTime;
184 fEndTime = endTime;
185}
186
58bc3020 187//______________________________________________________________________
188void AliDCSMessage::CreateCountMessage(UInt_t count)
189{
190// Create count request message
191
73abe331 192 DestroyMessage();
193
194 fType = AliDCSMessage::kCount;
195 fCount = count;
196}
197
58bc3020 198//______________________________________________________________________
45a493ce 199void AliDCSMessage::CreateResultSetMessage(AliDCSValue::Type type)
58bc3020 200{
45a493ce 201 // Create result set message
58bc3020 202
73abe331 203 DestroyMessage();
204
205 fType = AliDCSMessage::kResultSet;
45a493ce 206 fValueType = type;
73abe331 207}
208
58bc3020 209//______________________________________________________________________
73abe331 210void AliDCSMessage::CreateErrorMessage(ErrorCode errorCode,
211 const char* errorString)
212{
58bc3020 213// Create error message
214
73abe331 215 DestroyMessage();
216
217 fType = AliDCSMessage::kError;
218 fErrorCode = errorCode;
219 fErrorString = errorString;
220}
221
222/*
223void AliDCSMessage::CreateNextMessage() {
224 DestroyMessage();
225
226 fType = AliDCSMessage::kNext;
227} */
228
58bc3020 229//______________________________________________________________________
230void AliDCSMessage::DestroyMessage()
231{
232// Destroy message
233
73abe331 234 fType = kInvalid;
235 ClearValues();
236 ClearRequestStrings();
237}
238
58bc3020 239//______________________________________________________________________
240void AliDCSMessage::SetBool(char* buf, Bool_t val)
241{
242// Set bool value to buf
243
73abe331 244 tobuf(buf, val);
245}
246
58bc3020 247//______________________________________________________________________
248void AliDCSMessage::SetByte(char* buf, Char_t val)
249{
250// Set byte value to buf
251
73abe331 252 tobuf(buf, val);
253}
254
58bc3020 255//______________________________________________________________________
2bb7b766 256void AliDCSMessage::SetUByte(char* buf, UChar_t val)
58bc3020 257{
258// Set ubyte value to buf
259
73abe331 260 tobuf(buf, val);
261}
262
58bc3020 263//______________________________________________________________________
264void AliDCSMessage::SetInt(char* buf, Int_t val)
265{
266// Set int value to buf
267
73abe331 268 tobuf(buf, val);
269}
270
58bc3020 271//______________________________________________________________________
272void AliDCSMessage::SetUInt(char* buf, UInt_t val)
273{
274// Set uint value to buf
275
73abe331 276 tobuf(buf, val);
277}
278
58bc3020 279//______________________________________________________________________
280void AliDCSMessage::SetFloat(char* buf, Float_t val)
281{
282// Set float value to buf
283
73abe331 284 tobuf(buf, val);
285}
286
58bc3020 287//______________________________________________________________________
288Bool_t AliDCSMessage::GetBool(const char* buf)
289{
290// get bool value from buf
291
73abe331 292 Bool_t val;
293 char* aBuffer = (char*) buf;
294
295 frombuf(aBuffer, &val);
296
297 return val;
298}
299
58bc3020 300//______________________________________________________________________
301Char_t AliDCSMessage::GetByte(const char* buf)
302{
303// get byte value from buf
304
73abe331 305 Char_t val;
306 char* aBuffer = (char*) buf;
307
308 frombuf(aBuffer, &val);
309
310 return val;
311}
312
58bc3020 313//______________________________________________________________________
314UChar_t AliDCSMessage::GetUByte(const char* buf)
315{
316// get ubyte value from buf
317
73abe331 318 UChar_t val;
319 char* aBuffer = (char*) buf;
320
321 frombuf(aBuffer, &val);
322
323 return val;
324}
325
58bc3020 326//______________________________________________________________________
327Int_t AliDCSMessage::GetInt(const char* buf)
328{
329// get int value from buf
330
73abe331 331 Int_t val;
332 char* aBuffer = (char*) buf;
333
334 frombuf(aBuffer, &val);
335
336 return val;
337}
338
58bc3020 339//______________________________________________________________________
340UInt_t AliDCSMessage::GetUInt(const char* buf)
341{
342// get uint value from buf
343
73abe331 344 UInt_t val;
345 char* aBuffer = (char*) buf;
346
347 frombuf(aBuffer, &val);
348
349 return val;
350}
351
58bc3020 352//______________________________________________________________________
353Float_t AliDCSMessage::GetFloat(const char* buf)
354{
355// get float value from buf
356
73abe331 357 Float_t val;
358 char* aBuffer = (char*) buf;
359
360 frombuf(aBuffer, &val);
361
362 return val;
363}
364
58bc3020 365//______________________________________________________________________
366TString AliDCSMessage::GetString(const char* buf, Int_t maxLen)
367{
368// get string from buf
73abe331 369
370 for (Int_t k = 0; k < maxLen; k ++) {
371 if (buf[k] == 0) {
372 return TString(buf);
373 }
374 }
375
376 return TString(buf, maxLen);
377}
378
58bc3020 379//______________________________________________________________________
380void AliDCSMessage::StoreHeader()
381{
382// store header message
73abe331 383
384 SetUByte(fMessage + ID_OFFSET, 'A');
385 SetUByte(fMessage + ID_OFFSET + 1, 'D');
386
387 SetUByte(fMessage + VERSION_OFFSET, 1);
388
389 SetUByte(fMessage + TYPE_OFFSET, fType);
390
391 SetUInt(fMessage + BODY_SIZE_OFFSET, fMessageSize - HEADER_SIZE);
392}
393
58bc3020 394//______________________________________________________________________
395void AliDCSMessage::StoreRequestMessage()
396{
397// store request message
73abe331 398
399 fMessageSize = REQUEST_STRING_OFFSET +
400 fRequestString.Length() + 1;
401
402 fMessage = new char[fMessageSize];
403
404 StoreHeader();
405
406 SetUByte(fMessage + REQUEST_TYPE_OFFSET, fRequestType);
407 SetUInt(fMessage + START_TIME_OFFSET, fStartTime);
408 SetUInt(fMessage + END_TIME_OFFSET, fEndTime);
409 strcpy(fMessage + REQUEST_STRING_OFFSET, fRequestString.Data());
410}
411
58bc3020 412//______________________________________________________________________
413void AliDCSMessage::StoreCountMessage()
414{
415// store count message
73abe331 416
417 fMessageSize = COUNT_OFFSET + sizeof(UInt_t);
418
419 fMessage = new char[fMessageSize];
420
421 StoreHeader();
422
423 SetUInt(fMessage + COUNT_OFFSET, fCount);
424}
425
58bc3020 426//______________________________________________________________________
45a493ce 427void AliDCSMessage::StoreResultSetMessage()
58bc3020 428{
429// store result set message
73abe331 430
2bb7b766 431 TIter iter(fValues);
45a493ce 432 AliDCSValue* aValue;
433
434 UInt_t valueDataSize = 0;
435 while ((aValue = (AliDCSValue*) iter.Next())) {
45a493ce 436 valueDataSize += aValue->GetSize();
437 }
438
439 fMessageSize = VALUES_OFFSET + valueDataSize;
440
441 fMessage = new char[fMessageSize];
442
443 StoreHeader();
444
445 SetUByte(fMessage + SVT_OFFSET, fValueType);
446 SetUInt(fMessage + VALUE_COUNT_OFFSET, GetValueCount());
447
448 UInt_t cursor = VALUES_OFFSET;
449
450 iter.Reset();
451
452 if (fValueType == AliDCSValue::kBool) {
453 while ((aValue = (AliDCSValue*) iter.Next())) {
454 SetBool(fMessage + cursor, aValue->GetBool());
455 cursor += 1;
456 SetUInt(fMessage + cursor, aValue->GetTimeStamp());
457 cursor += sizeof(UInt_t);
458 }
459 } else if (fValueType == AliDCSValue::kChar) {
460 while ((aValue = (AliDCSValue*) iter.Next())) {
461 SetByte(fMessage + cursor, aValue->GetChar());
462 cursor += sizeof(Char_t);
463 SetUInt(fMessage + cursor, aValue->GetTimeStamp());
464 cursor += sizeof(UInt_t);
465 }
466 } else if (fValueType == AliDCSValue::kInt) {
467 while ((aValue = (AliDCSValue*) iter.Next())) {
468 SetInt(fMessage + cursor, aValue->GetInt());
469 cursor += sizeof(Int_t);
470 SetUInt(fMessage + cursor, aValue->GetTimeStamp());
471 cursor += sizeof(UInt_t);
472 }
473 } else if (fValueType == AliDCSValue::kUInt) {
474 while ((aValue = (AliDCSValue*) iter.Next())) {
475 SetUInt(fMessage + cursor, aValue->GetUInt());
476 cursor += sizeof(UInt_t);
477 SetUInt(fMessage + cursor, aValue->GetTimeStamp());
478 cursor += sizeof(UInt_t);
479 }
480 } else if (fValueType == AliDCSValue::kFloat) {
481 while ((aValue = (AliDCSValue*) iter.Next())) {
482 SetFloat(fMessage + cursor, aValue->GetFloat());
483 cursor += sizeof(Float_t);
484 SetUInt(fMessage + cursor, aValue->GetTimeStamp());
485 cursor += sizeof(UInt_t);
486 }
45a493ce 487 } else {
488 AliError("Invalid or unknown ValueType!");
489 return;
490 }
73abe331 491
492}
493
58bc3020 494//______________________________________________________________________
495void AliDCSMessage::StoreErrorMessage()
496{
497// store error message
73abe331 498
499 fMessageSize = ERROR_STRING_OFFSET + fErrorString.Length() + 1;
500
501 fMessage = new char[fMessageSize];
502
503 StoreHeader();
504
505 SetUByte(fMessage + ERROR_CODE_OFFSET, fErrorCode);
506 strcpy(fMessage + ERROR_STRING_OFFSET, fErrorString.Data());
507}
508
58bc3020 509//______________________________________________________________________
510void AliDCSMessage::StoreMultiRequestMessage()
511{
512// store multi request message
73abe331 513
514 UInt_t requestDataSize = 0;
515
516 TIter iter(&fRequestStrings);
517 TObjString* anObjString;
518
519 while ((anObjString = (TObjString*) iter.Next())) {
520 assert(anObjString->String().Length() <= 255);
521 requestDataSize += anObjString->String().Length() + 1;
522 }
523
524 fMessageSize = REQUEST_STRINGS_OFFSET + requestDataSize;
525
526 fMessage = new char[fMessageSize];
527
528 StoreHeader();
529
530 SetUByte(fMessage + REQUEST_TYPE_OFFSET, fRequestType);
531 SetUInt(fMessage + START_TIME_OFFSET, fStartTime);
532 SetUInt(fMessage + END_TIME_OFFSET, fEndTime);
533
534 iter.Reset();
535
536 UInt_t cursor = REQUEST_STRINGS_OFFSET;
537
538 while ((anObjString = (TObjString*) iter.Next())) {
539 UChar_t strLength = anObjString->String().Length();
540 SetUByte(fMessage + cursor, strLength);
541 cursor += 1;
542 strncpy(fMessage + cursor, anObjString->String().Data(),
543 strLength);
544 cursor += strLength;
545 }
546}
547
58bc3020 548//______________________________________________________________________
73abe331 549/*
550void AliDCSMessage::StoreNextMessage() {
551
552 fMessageSize = HEADER_SIZE;
553
554 fMessage = new char[fMessageSize];
555
556 StoreHeader();
557} */
558
58bc3020 559//______________________________________________________________________
560Bool_t AliDCSMessage::ValidateHeader(const char* buf)
561{
562// validate message header
73abe331 563
564 if (!(buf[ID_OFFSET] == 'A' && buf[ID_OFFSET + 1] == 'D')) {
565 AliError("Bad message ID!");
566 return kFALSE;
567 }
568
569 if (buf[VERSION_OFFSET] != 1) {
570 AliError("Bad message version!");
571 return kFALSE;
572 }
573
574 Type type = (Type) GetUByte(buf + TYPE_OFFSET);
575 switch (type) {
576 case kRequest:
577 case kCount:
578 case kResultSet:
579 case kError:
580 case kMultiRequest:
581 break;
582 default:
583 AliError("Unknown message type!");
584 return kFALSE;
585 }
586
587 UInt_t bodySize = GetInt(buf + BODY_SIZE_OFFSET);
588 if (bodySize > MAX_BODY_SIZE) {
589 AliError("Too big message body size!");
590 return kFALSE;
591 }
592
593 return kTRUE;
594}
595
58bc3020 596//______________________________________________________________________
597void AliDCSMessage::LoadRequestMessage()
598{
599// load request message
73abe331 600
601 if (fMessageSize < REQUEST_STRING_OFFSET) {
602 AliError("Body size is too small for request message!");
603 return;
604 }
605
606 fRequestType = (RequestType) GetUByte(fMessage + REQUEST_TYPE_OFFSET);
607
608 fStartTime = GetUInt(fMessage + START_TIME_OFFSET);
609 fEndTime = GetUInt(fMessage + END_TIME_OFFSET);
610 fRequestString = GetString(fMessage + REQUEST_STRING_OFFSET,
611 fMessageSize - REQUEST_STRING_OFFSET);
612
613 switch (fRequestType) {
614 case kAlias:
615 case kDPName:
616 fType = kRequest;
617 break;
618 default:
619 AliError("Invalid request type!");
620 }
621}
622
58bc3020 623//______________________________________________________________________
624void AliDCSMessage::LoadCountMessage()
625{
626// load count message
73abe331 627
628 if (fMessageSize < HEADER_SIZE + sizeof(UInt_t)) {
629 AliError("Body size is too small for count message!");
630 return;
631 }
632
633 fCount = GetUInt(fMessage + COUNT_OFFSET);
634
635 fType = kCount;
636}
637
58bc3020 638//______________________________________________________________________
45a493ce 639void AliDCSMessage::LoadResultSetMessage()
58bc3020 640{
45a493ce 641 // load result message
642
643 if (fMessageSize < VALUES_OFFSET) {
644 AliError("Body size is too small for result set message!");
645 return;
646 }
647
648 fValueType = (AliDCSValue::Type) GetUByte(fMessage + SVT_OFFSET);
649 UInt_t count = GetUInt(fMessage + VALUE_COUNT_OFFSET);
650
651 UInt_t cursor = VALUES_OFFSET;
652
653 if (fValueType == AliDCSValue::kBool) {
654 if (VALUES_OFFSET + count + count * sizeof(UInt_t) >
655 fMessageSize) {
656 AliError("Too many bool values for this buffer size!");
657 return;
658 }
659
660 for (UInt_t k = 0; k < count; k ++) {
661 Bool_t aBool = GetBool(fMessage + cursor);
662 cursor += 1;
663 UInt_t timeStamp = GetUInt(fMessage + cursor);
664 cursor += sizeof(UInt_t);
2bb7b766 665 fValues->Add(new AliDCSValue(aBool, timeStamp));
45a493ce 666 }
667 } else if (fValueType == AliDCSValue::kChar) {
668 if (VALUES_OFFSET + count + count * sizeof(UInt_t) >
669 fMessageSize) {
670 AliError("Too many byte values for this buffer size!");
671 return;
672 }
673
674 for (UInt_t k = 0; k < count; k ++) {
675 Char_t aByte = GetByte(fMessage + cursor);
676 cursor += sizeof(Char_t);
677 UInt_t timeStamp = GetUInt(fMessage + cursor);
678 cursor += sizeof(UInt_t);
2bb7b766 679 fValues->Add(new AliDCSValue(aByte, timeStamp));
45a493ce 680 }
681 } else if (fValueType == AliDCSValue::kInt) {
682 if (VALUES_OFFSET + count * sizeof(Int_t) +
683 count * sizeof(UInt_t) > fMessageSize) {
684 AliError("Too many int values for this buffer size!");
685 return;
686 }
687
688 for (UInt_t k = 0; k < count; k ++) {
689 Int_t aInt = GetInt(fMessage + cursor);
690 cursor += sizeof(Int_t);
691 UInt_t timeStamp = GetUInt(fMessage + cursor);
692 cursor += sizeof(UInt_t);
2bb7b766 693 fValues->Add(new AliDCSValue(aInt, timeStamp));
45a493ce 694 }
695
696 } else if (fValueType == AliDCSValue::kUInt) {
697 if (VALUES_OFFSET + count * sizeof(UInt_t) +
698 count * sizeof(UInt_t) > fMessageSize) {
699 AliError("Too many uint values for this buffer size!");
700 return;
701 }
702
703 for (UInt_t k = 0; k < count; k ++) {
704 UInt_t aUInt = GetUInt(fMessage + cursor);
705 cursor += sizeof(UInt_t);
706 UInt_t timeStamp = GetUInt(fMessage + cursor);
707 cursor += sizeof(UInt_t);
2bb7b766 708 fValues->Add(new AliDCSValue(aUInt, timeStamp));
45a493ce 709 }
710 } else if (fValueType == AliDCSValue::kFloat) {
711 if (VALUES_OFFSET + count * sizeof(Float_t) +
712 count * sizeof(UInt_t) > fMessageSize) {
713 AliError("Too many float values for this buffer size!");
714 return;
715 }
716
717 for (UInt_t k = 0; k < count; k ++) {
718 Float_t aFloat = GetFloat(fMessage + cursor);
719 cursor += sizeof(Float_t);
720 UInt_t timeStamp = GetUInt(fMessage + cursor);
721 cursor += sizeof(UInt_t);
2bb7b766 722 fValues->Add(new AliDCSValue(aFloat, timeStamp));
45a493ce 723 }
724
725 } else {
726 AliError("Unknown or invalid value type!");
727 }
728
729 fType = kResultSet;
73abe331 730}
731
58bc3020 732//______________________________________________________________________
2bb7b766 733void AliDCSMessage::LoadErrorMessage()
58bc3020 734{
735// load error message
73abe331 736
737 if (fMessageSize < ERROR_STRING_OFFSET) {
738 AliError("Body size is too small for error message!");
739 return;
740 }
741
742 fErrorCode = (ErrorCode) GetUByte(fMessage + ERROR_CODE_OFFSET);
743 fErrorString = GetString(fMessage + ERROR_STRING_OFFSET,
744 fMessageSize - ERROR_STRING_OFFSET);
745
746 switch (fErrorCode) {
747 case kUnknownAliasDPName:
748 case kInvalidTimeRange:
749 case kInvalidBufferSize:
750 case kInvalidRequest:
751 case kUnsupportedType:
752 case kUnknownError:
753 fType = kError;
754 break;
755 default:
756 AliError("Invalid error code!");
757 }
758}
759
58bc3020 760//______________________________________________________________________
761void AliDCSMessage::LoadMultiRequestMessage()
762{
763// load multi request message
73abe331 764
765 if (fMessageSize - HEADER_SIZE < REQUEST_STRINGS_OFFSET) {
766 AliError("Body size is too small for multi request message!");
767 return;
768 }
769
770 fRequestType = (RequestType) GetUByte(fMessage + REQUEST_TYPE_OFFSET);
771
772 fStartTime = GetUInt(fMessage + START_TIME_OFFSET);
773 fEndTime = GetUInt(fMessage + END_TIME_OFFSET);
774
775 switch (fRequestType) {
776 case kAlias:
777 case kDPName:
778 fType = kRequest;
779 break;
780 default:
781 AliError("Invalid request type!");
782 return;
783 }
784
785 UInt_t cursor = REQUEST_STRINGS_OFFSET;
786
787 while ((cursor < fMessageSize)) {
788 UChar_t strSize = GetUByte(fMessage + cursor);
789 cursor += 1;
790
791 if (cursor + strSize > fMessageSize) {
792 AliError("Invalid multi request message!");
793 return;
794 }
795
796 TObjString* anObjString = new TObjString(
797 GetString(fMessage + cursor, strSize));
d477ad88 798 fRequestStrings.AddLast(anObjString);
73abe331 799
800 cursor += strSize;
801 }
802
803 fType = kMultiRequest;
804}
805
58bc3020 806//______________________________________________________________________
73abe331 807/*
808void AliDCSMessage::LoadNextMessage() {
809
810 fType = kNext;
811} */
812
58bc3020 813//______________________________________________________________________
814void AliDCSMessage::StoreToBuffer()
815{
816 // Creates an underlying message buffer which can be sent to the socket.
73abe331 817
818 DestroyBuffer();
819
820 switch (fType) {
821 case kRequest:
822 StoreRequestMessage();
823 break;
824 case kCount:
825 StoreCountMessage();
826 break;
827 case kResultSet:
828 StoreResultSetMessage();
829 break;
830 case kError:
831 StoreErrorMessage();
832 break;
833 case kMultiRequest:
834 StoreMultiRequestMessage();
835 break;
836/* case kNext:
837 StoreNextMessage();
838 break; */
839 default:
840 AliError("Can't store to buffer invalid message!");
841 }
842}
843
58bc3020 844//______________________________________________________________________
2bb7b766 845void AliDCSMessage::LoadFromBuffer()
58bc3020 846{
73abe331 847 // Reads the underlying message buffer and if it's valid message
848 // creates the corresponding message.
849 // If not set the message type kInvalid.
850 // This buffer is read from the socket.
73abe331 851
852 DestroyMessage();
853
854 if (!fMessage) {
855 AliError("Message buffer is empty! Can't load it.");
856 return;
857 }
858
859 if (fMessageSize < HEADER_SIZE) {
860 AliError("Invalid message buffer. Too small for the header!");
861 return;
862 }
863
864 if (!ValidateHeader(fMessage)) {
865 AliError("Invalid message header!");
866 return;
867 }
868
869 UInt_t bodySize = GetUInt(fMessage + BODY_SIZE_OFFSET);
870 if (bodySize > fMessageSize - HEADER_SIZE) {
871 AliError("Message size is to small for the message body!");
872 return;
873 }
874
875 fMessageSize = HEADER_SIZE + bodySize;
876
877 Type aType = (Type) GetUByte(fMessage + TYPE_OFFSET);
2bb7b766 878
73abe331 879 switch (aType) {
880 case kRequest:
881 LoadRequestMessage();
882 break;
883 case kCount:
884 LoadCountMessage();
885 break;
886 case kResultSet:
887 LoadResultSetMessage();
888 break;
889 case kError:
890 LoadErrorMessage();
891 break;
892 case kMultiRequest:
893 LoadMultiRequestMessage();
894 break;
895/* case kNext:
896 LoadNextMessage();
897 break; */
898 default:
899 AliError("Invalid message type!");
900 }
901}
902
58bc3020 903//______________________________________________________________________
904AliDCSMessage::RequestType AliDCSMessage::GetRequestType() const
905{
73abe331 906 // Request and MultiRequest.
907 // Returns the request type: alias or dp (Data Point)
73abe331 908
909 if (!(fType == kRequest || fType == kMultiRequest)) {
910 AliError("Invalid AliDCSMessage type!");
911 return kNoneType;
912 }
913
914 return fRequestType;
915}
916
58bc3020 917//______________________________________________________________________
918UInt_t AliDCSMessage::GetStartTime() const
919{
73abe331 920 // Request and MultiRequest.
921 // Returns the request start time. (begining of the time interval).
73abe331 922
923 if (!(fType == kRequest || fType == kMultiRequest)) {
924 AliError("Invalid AliDCSMessage type!");
925 return 0;
926 }
927
928 return fStartTime;
929}
930
58bc3020 931//______________________________________________________________________
932UInt_t AliDCSMessage::GetEndTime() const
933{
73abe331 934 // Request and MultiRequest.
935 // Returns the request start time. (end of the time interval).
73abe331 936
937
938 if (!(fType == kRequest || fType == kMultiRequest)) {
939 AliError("Invalid AliDCSMessage type!");
940 return 0;
941 }
942
943 return fEndTime;
944}
945
58bc3020 946//______________________________________________________________________
947TString AliDCSMessage::GetRequestString() const
948{
73abe331 949 // Request.
950 // Returns the request string. (alias or dp)
73abe331 951
952 if (fType != kRequest) {
953 AliError("Invalid AliDCSMessage type!");
954 return TString("");
955 }
956
957 return fRequestString;
958}
959
58bc3020 960//______________________________________________________________________
2bb7b766 961Bool_t AliDCSMessage::AddRequestString(const char* request)
58bc3020 962{
73abe331 963 // MultRequest.
964 // Add a request to the request set.
965 // Returns kFALSE in case of invalid request (too long request string).
966 // Otherwise returns kTRUE.
58bc3020 967
73abe331 968
969 if (fType != kMultiRequest) {
970 AliError("Invalid AliDCSMessage type!");
971 return kFALSE;
972 }
973
974 if (strlen(request) > 255) {
975 AliError("Alias/dpName is too long! Max size 255.");
976 return kFALSE;
977 }
978
d477ad88 979 fRequestStrings.AddLast(new TObjString(request));
73abe331 980 return kTRUE;
981}
982
58bc3020 983//______________________________________________________________________
2bb7b766 984void AliDCSMessage::ClearRequestStrings()
58bc3020 985{
73abe331 986 // MultRequest.
987 // Clears the request set.
58bc3020 988
73abe331 989 fRequestStrings.Delete();
990}
991
58bc3020 992//______________________________________________________________________
2bb7b766 993void AliDCSMessage::GetRequestStrings(TObjArray& result) const
58bc3020 994{
73abe331 995 // MultRequest.
996 // Returns all request strings in this message.
997 // result: container where the requests are returned. Collection of
998 // TObjString.
73abe331 999
1000
1001 if (fType != kMultiRequest) {
1002 AliError("Invalid AliDCSMessage type!");
1003 return;
1004 }
1005
1006 TIter iter(&fRequestStrings);
1007 TObjString* anObjString;
1008
1009 while ((anObjString = (TObjString*) iter.Next())) {
d477ad88 1010 result.AddLast(new TObjString(*anObjString));
73abe331 1011 }
1012}
1013
58bc3020 1014//______________________________________________________________________
1015UInt_t AliDCSMessage::GetCount() const
1016{
73abe331 1017 // Count.
1018 // Returns the total number of values.
73abe331 1019
1020
1021 if (fType != kCount) {
1022 AliError("Invalid AliDCSMessage type!");
1023 return 0;
1024 }
1025
1026 return fCount;
1027}
1028
58bc3020 1029//______________________________________________________________________
45a493ce 1030AliDCSValue::Type AliDCSMessage::GetValueType() const
58bc3020 1031{
45a493ce 1032 // ResultSet.
1033 // Returns simple value type (see AliDCSValue) for the values
1034 // in this ResultSet.
73abe331 1035
45a493ce 1036 if (fType != kResultSet) {
1037 AliError("Invalid AliDCSMessage type!");
1038 return AliDCSValue::kInvalid;
1039 }
73abe331 1040
45a493ce 1041 return fValueType;
73abe331 1042}
1043
58bc3020 1044//______________________________________________________________________
2bb7b766 1045UInt_t AliDCSMessage::GetValueCount() const
58bc3020 1046{
45a493ce 1047 // ResultSet.
1048 // Returns the count of values in this ResultSet.
73abe331 1049
1050
45a493ce 1051 if (fType != kResultSet) {
1052 AliError("Invalid AliDCSMessage type!");
1053 return 0;
1054 }
73abe331 1055
2bb7b766 1056 return fValues->GetEntriesFast();
73abe331 1057}
1058
58bc3020 1059//______________________________________________________________________
2bb7b766 1060UInt_t AliDCSMessage::GetValues(TObjArray* result) const
58bc3020 1061{
45a493ce 1062 // ResultSet.
1063 // Returns the number of values got from the message.
1064 // result: used to return the values. Collection of AliDCSValue.
2bb7b766 1065 // result must be owner of the AliDCSValues because fVaule is not!
1066 // creator of the result array and used GetValues to fill it must delete object by himself!
73abe331 1067
2bb7b766 1068 // TODO do not copy -> corrected?
73abe331 1069
1070 if (fType != kResultSet) {
1071 AliError("Invalid AliDCSMessage type!");
1072 return 0;
1073 }
1074
2bb7b766 1075 TIter iter(fValues);
73abe331 1076 AliDCSValue* aValue;
1077
1078 while ((aValue = (AliDCSValue*) iter.Next())) {
2bb7b766 1079 result->AddLast(aValue);
73abe331 1080 }
1081
2bb7b766 1082 return fValues->GetEntriesFast();
73abe331 1083}
1084
2bb7b766 1085
58bc3020 1086//______________________________________________________________________
2bb7b766 1087Bool_t AliDCSMessage::AddValue(AliDCSValue& value)
58bc3020 1088{
45a493ce 1089 // Adds value to the ResultSet value list.
1090 // Returns kFALSE in case of error.
1091 // Otherwise returns kTRUE;
73abe331 1092
45a493ce 1093 if (fType != kResultSet) {
1094 AliError("Invalid AliDCSMessage type!");
1095 return kFALSE;
1096 }
73abe331 1097
45a493ce 1098 if (value.GetType() != fValueType) {
1099 AliError(Form("Can't add value with type %d to this message!", value.GetType()));
1100 return kFALSE;
1101 }
73abe331 1102
2bb7b766 1103 fValues->Add(&value);
45a493ce 1104
1105 return kTRUE;
73abe331 1106}
1107
2bb7b766 1108
58bc3020 1109//______________________________________________________________________
2bb7b766 1110void AliDCSMessage::ClearValues()
58bc3020 1111{
1112// clear values array
1113
2bb7b766 1114 if(fValues) fValues->Clear();
73abe331 1115}
1116
58bc3020 1117//______________________________________________________________________
1118AliDCSMessage::ErrorCode AliDCSMessage::GetErrorCode() const
1119{
73abe331 1120 //
1121 // Error.
1122 // Returns the error code which has this error message.
1123 //
1124
1125 if (fType != kError) {
1126 AliError("Invalid AliDCSMessage type!");
1127 return kNoneError;
1128 }
1129
1130 return fErrorCode;
1131}
1132
58bc3020 1133//______________________________________________________________________
1134TString AliDCSMessage::GetErrorString() const
1135{
73abe331 1136 //
1137 // Error.
1138 // Returns the error string (error description) which has this
1139 // error message.
1140 //
1141
1142 if (GetType() != kError) {
1143 AliError("Invalid AliDCSMessage type!");
1144 return TString("");
1145 }
1146
1147 return fErrorString;
1148}
1149
1150
58bc3020 1151//______________________________________________________________________
1152void AliDCSMessage::Print(Option_t* /*option*/) const
1153{
1154// print message
73abe331 1155
1156 if (AliLog::GetGlobalDebugLevel() < 2) {
1157 return;
1158 }
1159
1160 TString printString;
1161 printString += "\n <<AliDCSMessage>>\n";
1162
1163 printString += " Size: ";
1164 printString += fMessageSize;
1165 printString += '\n';
1166
1167 printString += " Type: ";
1168 switch (GetType()) {
1169 case kRequest: {
1170 printString += "Request\n";
1171
1172 printString += " RequestType: ";
1173 if (GetRequestType() == kDPName) {
1174 printString += "DPName";
1175 } else {
1176 printString += "Alias";
1177 }
1178 printString += '\n';
1179
1180 printString += " RequestString: ";
1181 printString += GetRequestString();
1182 printString += '\n';
1183 printString += " StartTime: ";
1184 printString += GetStartTime();
1185 printString += '\n';
1186 printString += " EndTime: ";
1187 printString += GetEndTime();
1188 printString += '\n';
1189 break;
1190 }
1191
1192 case kCount: {
1193 printString += "Count\n";
1194 printString += " Count: ";
1195 printString += GetCount();
1196 printString += '\n';
1197 break;
1198 }
1199
1200 case kResultSet: {
1201 printString += "ResultSet\n";
1202 printString += " SimpleValueType: ";
45a493ce 1203 printString += fValueType;
73abe331 1204 printString += '\n';
1205 printString += " ValueCount: ";
1206 printString += GetValueCount();
1207 printString += '\n';
1208 break;
1209 }
1210
1211 case kError: {
1212 printString += "Error\n";
1213 printString += " ErrorCode: ";
1214 switch (GetErrorCode()) {
1215 case AliDCSMessage::kNoneError:
1216 printString += "NoneError";
1217 break;
1218 case AliDCSMessage::kUnknownAliasDPName:
1219 printString += "UnknownAliasDPName";
1220 break;
1221 case AliDCSMessage::kInvalidTimeRange:
1222 printString += "InvalidTimeRange";
1223 break;
1224 case AliDCSMessage::kInvalidBufferSize:
1225 printString += "InvalidBufferSize";
1226 break;
1227 case AliDCSMessage::kInvalidRequest:
1228 printString += "InvalidRequest";
1229 break;
1230 case AliDCSMessage::kUnsupportedType:
1231 printString += "UnsupportedType";
1232 break;
1233 case AliDCSMessage::kUnknownError:
1234 printString += "UnknownError";
1235 break;
1236 default:
1237 printString += "Invalid";
1238 }
1239
1240 printString += '\n';
1241 printString += " ErrorString: ";
1242 printString += GetErrorString();
1243 printString += '\n';
1244 break;
1245 }
1246
1247 case kMultiRequest: {
1248 printString += "MultiRequest\n";
1249
1250 printString += " RequestType: ";
1251 if (GetRequestType() == kDPName) {
1252 printString += "DPName";
1253 } else {
1254 printString += "Alias";
1255 }
1256 printString += '\n';
1257
1258 printString += " RequestStrings: ";
1259 TIter iter(&fRequestStrings);
1260 TObjString* anObjString;
1261 while ((anObjString = (TObjString*) iter.Next())) {
1262 printString += anObjString->String();
1263 printString += ' ';
1264 }
1265 printString += '\n';
1266
1267 printString += " StartTime: ";
1268 printString += GetStartTime();
1269 printString += '\n';
1270 printString += " EndTime: ";
1271 printString += GetEndTime();
1272 printString += '\n';
1273 break;
1274 }
1275
1276/* case kNext: {
1277 printString += "Next\n";
1278 break;
1279 } */
1280
1281 default:
1282 printString += "Invalid\n";
1283 }
1284
1285 if (AliLog::GetGlobalDebugLevel() >= 3 && fMessage) {
1286 PrintBuffer(fMessage, fMessageSize, printString);
1287 }
1288
1289 AliDebug(2, printString);
1290}
1291
58bc3020 1292//______________________________________________________________________
1293Bool_t AliDCSMessage::SetRawHeader(const char* header)
1294{
73abe331 1295 //
1296 // Checks if the header buffer represents a valid header message.
1297 // If so it creates a message buffer with the appropriate body size
1298 // and returns true.
1299 // If not returns false.
1300 // header: header buffer
1301 //
1302
1303 if (!ValidateHeader(header)) {
1304 AliError("Invalid message header!");
1305 return kFALSE;
1306 }
1307
1308 DestroyBuffer();
1309
1310 UInt_t bodySize = GetUInt(header + BODY_SIZE_OFFSET);
1311 fMessageSize = HEADER_SIZE + bodySize;
1312
1313 fMessage = new char[fMessageSize];
1314
1315 memcpy(fMessage, header, HEADER_SIZE);
1316
1317 return kTRUE;
1318}
1319
1320
58bc3020 1321//______________________________________________________________________
1322void AliDCSMessage::DestroyBuffer()
1323{
73abe331 1324 //
1325 // Destroy the underlying message buffer.
1326 //
1327
1328 if (fMessage) {
1329 delete[] fMessage;
1330 fMessage = NULL;
1331 }
1332
1333 fMessageSize = 0;
1334}
1335
58bc3020 1336//______________________________________________________________________
73abe331 1337void AliDCSMessage::PrintBuffer(const char* buffer, UInt_t size,
1338 TString& output)
1339{
58bc3020 1340// print buffer
73abe331 1341
1342 UInt_t index = 0;
1343
1344 while (index < size) {
1345 if (!(index % 16)) {
1346 output += Form("\n %.4x:", index);
1347 }
1348
1349 if (!(index % 8)) {
1350 output += ' ';
1351 }
1352
1353 output += Form(" %.2x", (UChar_t) buffer[index]);
1354
1355 if (!((index + 1) % 16) || index + 1 == size) {
1356 if (index + 1 == size) {
1357 output.Append(' ',3 * (15 - index % 16));
1358 if (index % 16 < 8) {
1359 output.Append(' ');
1360 }
1361 }
1362
1363 output.Append(' ', 2);
1364 for (Int_t k = index % 16; k >= 0; k --) {
1365 Char_t aChar = buffer[index - k];
1366 output += isgraph(aChar) ? aChar: '.';
1367 }
1368 }
1369
1370 index ++;
1371 }
1372
1373 output += '\n';
1374}