]> git.uio.no Git - u/mrichter/AliRoot.git/blame - HLT/BASE/AliHLTConfiguration.cxx
documentation
[u/mrichter/AliRoot.git] / HLT / BASE / AliHLTConfiguration.cxx
CommitLineData
3495cce2 1// $Id$
2
3/**************************************************************************
9be2600f 4 * This file is property of and copyright by the ALICE HLT Project *
5 * ALICE Experiment at CERN, All rights reserved. *
3495cce2 6 * *
9be2600f 7 * Primary Authors: Matthias Richter <Matthias.Richter@ift.uib.no> *
8 * for The ALICE HLT Project. *
3495cce2 9 * *
10 * Permission to use, copy, modify and distribute this software and its *
11 * documentation strictly for non-commercial purposes is hereby granted *
12 * without fee, provided that the above copyright notice appears in all *
13 * copies and that both the copyright notice and this permission notice *
14 * appear in the supporting documentation. The authors make no claims *
15 * about the suitability of this software for any purpose. It is *
16 * provided "as is" without express or implied warranty. *
17 **************************************************************************/
18
b22e91eb 19/** @file AliHLTConfiguration.cxx
20 @author Matthias Richter
21 @date
22 @brief Implementation of HLT configuration handler.
23*/
3495cce2 24
0c0c9d99 25#if __GNUC__>= 3
3495cce2 26using namespace std;
27#endif
28
a5854ddd 29#include <cerrno>
3495cce2 30#include "AliHLTConfiguration.h"
c38ba6f9 31#include "AliHLTConfigurationHandler.h"
32#include "AliHLTTask.h"
3495cce2 33#include "AliHLTComponent.h"
34#include "AliHLTComponentHandler.h"
35#include <iostream>
a5854ddd 36#include <string>
70ed7d01 37#include "TList.h"
3495cce2 38
b22e91eb 39/** ROOT macro for the implementation of ROOT specific class methods */
3495cce2 40ClassImp(AliHLTConfiguration)
41
42AliHLTConfiguration::AliHLTConfiguration()
85869391 43 :
52c1c164 44 fID(""),
45 fComponent(""),
46 fStringSources(""),
85869391 47 fNofSources(-1),
53feaef5 48 fListSources(),
49 fListSrcElement(),
52c1c164 50 fArguments(""),
85869391 51 fArgc(-1),
53feaef5 52 fArgv(NULL)
3495cce2 53{
70ed7d01 54 // see header file for function documentation
3495cce2 55 fListSrcElement=fListSources.begin();
56}
57
58AliHLTConfiguration::AliHLTConfiguration(const char* id, const char* component, const char* sources, const char* arguments)
85869391 59 :
60 fID(id),
61 fComponent(component),
62 fStringSources(sources),
63 fNofSources(-1),
53feaef5 64 fListSources(),
65 fListSrcElement(),
85869391 66 fArguments(arguments),
67 fArgc(-1),
53feaef5 68 fArgv(NULL)
3495cce2 69{
70ed7d01 70 // see header file for function documentation
85869391 71 fListSrcElement=fListSources.begin();
3495cce2 72 if (id && component) {
70ed7d01 73 if (fgConfigurationHandler) {
74 fgConfigurationHandler->RegisterConfiguration(this);
85465857 75 } else {
76 HLTError("no configuration handler set, abort registration");
77 }
3495cce2 78 }
79}
80
fc455fba 81AliHLTConfiguration::AliHLTConfiguration(const AliHLTConfiguration& src)
85869391 82 :
53feaef5 83 TObject(),
84 AliHLTLogging(),
fc455fba 85 fID(src.fID),
86 fComponent(src.fComponent),
87 fStringSources(src.fStringSources),
85869391 88 fNofSources(-1),
53feaef5 89 fListSources(),
90 fListSrcElement(),
fc455fba 91 fArguments(src.fArguments),
85869391 92 fArgc(-1),
53feaef5 93 fArgv(NULL)
85869391 94{
70ed7d01 95 // see header file for function documentation
85869391 96 fListSrcElement=fListSources.begin();
85869391 97}
98
fc455fba 99AliHLTConfiguration& AliHLTConfiguration::operator=(const AliHLTConfiguration& src)
85869391 100{
70ed7d01 101 // see header file for function documentation
fc455fba 102 fID=src.fID;
103 fComponent=src.fComponent;
104 fStringSources=src.fStringSources;
105 fNofSources=-1;
106 fArguments=src.fArguments;
107 fArgc=-1;
108 fArgv=NULL;
85869391 109 return *this;
110}
111
3495cce2 112AliHLTConfiguration::~AliHLTConfiguration()
113{
70ed7d01 114 // see header file for function documentation
115 if (fgConfigurationHandler) {
52c1c164 116 if (fgConfigurationHandler->FindConfiguration(fID.Data())!=NULL) {
70ed7d01 117 fgConfigurationHandler->RemoveConfiguration(this);
85465857 118 }
3495cce2 119 }
120 if (fArgv != NULL) {
121 if (fArgc>0) {
122 for (int i=0; i<fArgc; i++) {
123 delete[] fArgv[i];
124 }
125 }
126 delete[] fArgv;
127 fArgv=NULL;
128 }
a742f6f8 129
130 vector<AliHLTConfiguration*>::iterator element=fListSources.begin();
131 while (element!=fListSources.end()) {
132 fListSources.erase(element);
133 element=fListSources.begin();
134 }
3495cce2 135}
136
b22e91eb 137/* the global configuration handler which is used to automatically register the configuration
138 */
70ed7d01 139AliHLTConfigurationHandler* AliHLTConfiguration::fgConfigurationHandler=NULL;
b22e91eb 140
85465857 141int AliHLTConfiguration::GlobalInit(AliHLTConfigurationHandler* pHandler)
142{
70ed7d01 143 // see header file for function documentation
85465857 144 int iResult=0;
70ed7d01 145 if (fgConfigurationHandler!=NULL) {
fc455fba 146 fgConfigurationHandler->Logging(kHLTLogWarning, "AliHLTConfiguration::GlobalInit", HLT_DEFAULT_LOG_KEYWORD, "configuration handler already initialized, overriding object %p with %p", fgConfigurationHandler, pHandler);
85465857 147 }
70ed7d01 148 fgConfigurationHandler=pHandler;
85465857 149 return iResult;
150}
151
fc455fba 152int AliHLTConfiguration::GlobalDeinit(AliHLTConfigurationHandler* pHandler)
85465857 153{
70ed7d01 154 // see header file for function documentation
85465857 155 int iResult=0;
fc455fba 156 if (pHandler!=NULL && fgConfigurationHandler!=pHandler) {
157 fgConfigurationHandler->Logging(kHLTLogWarning, "AliHLTConfiguration::GlobalDeinit", HLT_DEFAULT_LOG_KEYWORD, "handler %p is not set, skip ...", pHandler);
158 return -EBADF;
159 }
70ed7d01 160 fgConfigurationHandler=NULL;
85465857 161 return iResult;
162}
163
70ed7d01 164const char* AliHLTConfiguration::GetName() const
165{
166 // see header file for function documentation
52c1c164 167 if (!fID.IsNull())
168 return fID.Data();
3495cce2 169 return TObject::GetName();
170}
171
172AliHLTConfiguration* AliHLTConfiguration::GetSource(const char* id)
173{
70ed7d01 174 // see header file for function documentation
3495cce2 175 AliHLTConfiguration* pSrc=NULL;
176 if (id) {
177 // first check the current element
178 if (fListSrcElement!=fListSources.end() && strcmp(id, (*fListSrcElement)->GetName())==0) {
179 pSrc=*fListSrcElement;
180 } else {
181 // check the list
182
183 pSrc=GetFirstSource();
184 while (pSrc) {
185 if (strcmp(id, pSrc->GetName())==0)
186 break;
187 pSrc=GetNextSource();
188 }
189 }
190 }
191 return pSrc;
192}
193
194AliHLTConfiguration* AliHLTConfiguration::GetFirstSource()
195{
70ed7d01 196 // see header file for function documentation
3495cce2 197 AliHLTConfiguration* pSrc=NULL;
198 if (fNofSources>=0 || ExtractSources()) {
199 fListSrcElement=fListSources.begin();
200 if (fListSrcElement!=fListSources.end()) pSrc=*fListSrcElement;
201 }
202 return pSrc;
203}
204
205AliHLTConfiguration* AliHLTConfiguration::GetNextSource()
206{
70ed7d01 207 // see header file for function documentation
3495cce2 208 AliHLTConfiguration* pSrc=NULL;
209 if (fNofSources>0) {
210 if (fListSrcElement!=fListSources.end() && (++fListSrcElement)!=fListSources.end())
211 pSrc=*fListSrcElement;
212 }
213 return pSrc;
214}
215
216int AliHLTConfiguration::SourcesResolved(int bAuto)
217{
70ed7d01 218 // see header file for function documentation
3495cce2 219 int iResult=0;
220 if (fNofSources>=0 || bAuto && (iResult=ExtractSources())>=0) {
85465857 221 //HLTDebug("fNofSources=%d", fNofSources);
222 //HLTDebug("list size = %d", fListSources.size());
3495cce2 223 iResult=fNofSources==(int)fListSources.size();
224 }
225 return iResult;
226}
227
228int AliHLTConfiguration::InvalidateSource(AliHLTConfiguration* pConf)
229{
70ed7d01 230 // see header file for function documentation
3495cce2 231 int iResult=0;
232 if (pConf) {
233 vector<AliHLTConfiguration*>::iterator element=fListSources.begin();
234 while (element!=fListSources.end()) {
235 if (*element==pConf) {
236 fListSources.erase(element);
237 fListSrcElement=fListSources.end();
238 // there is no need to re-evaluate until there was a new configuration registered
239 // -> postpone the invalidation, its done in AliHLTConfigurationHandler::RegisterConfiguration
240 //InvalidateSources();
241 break;
242 }
243 element++;
244 }
245 } else {
246 iResult=-EINVAL;
247 }
248 return iResult;
249}
250
251void AliHLTConfiguration::PrintStatus()
252{
70ed7d01 253 // see header file for function documentation
85465857 254 HLTLogKeyword("configuration status");
255 HLTMessage("status of configuration \"%s\" (%p)", GetName(), this);
52c1c164 256 if (!fComponent.IsNull()) HLTMessage(" - component: \"%s\"", fComponent.Data());
85465857 257 else HLTMessage(" - component string invalid");
52c1c164 258 if (!fStringSources.IsNull()) HLTMessage(" - sources: \"%s\"", fStringSources.Data());
85465857 259 else HLTMessage(" - no sources");
3495cce2 260 if (SourcesResolved(1)<=0)
85465857 261 HLTMessage(" there are unresolved sources");
3495cce2 262 AliHLTConfiguration* pSrc=GetFirstSource();
263 while (pSrc) {
85465857 264 HLTMessage(" source \"%s\" (%p) resolved", pSrc->GetName(), pSrc);
3495cce2 265 pSrc=GetNextSource();
266 }
267}
268
0c0c9d99 269int AliHLTConfiguration::GetArguments(const char*** pArgv)
3495cce2 270{
70ed7d01 271 // see header file for function documentation
3495cce2 272 int iResult=0;
0c0c9d99 273 if (pArgv) {
9ce4bf4a 274 if (fArgc==-1) {
275 if ((iResult=ExtractArguments())<0) {
276 HLTError("error extracting arguments for configuration %s", GetName());
277 fArgc=-EINVAL;
278 }
279 } else if (fArgc<0) {
280 HLTError("previous argument extraction failed");
281 }
282 //HLTDebug("%s fArgc %d", GetName(), fArgc);
0c0c9d99 283 iResult=fArgc;
3495cce2 284 *pArgv=(const char**)fArgv;
285 } else {
9ce4bf4a 286 HLTError("invalid parameter");
3495cce2 287 iResult=-EINVAL;
288 }
289 return iResult;
290}
291
292
293int AliHLTConfiguration::ExtractSources()
294{
70ed7d01 295 // see header file for function documentation
3495cce2 296 int iResult=0;
297 fNofSources=0;
52c1c164 298 if (!fStringSources.IsNull()) {
3495cce2 299 vector<char*> tgtList;
300 fListSources.clear();
52c1c164 301 if ((iResult=InterpreteString(fStringSources.Data(), tgtList))>=0) {
3495cce2 302 fNofSources=tgtList.size();
303 vector<char*>::iterator element=tgtList.begin();
85465857 304 while ((element=tgtList.begin())!=tgtList.end()) {
70ed7d01 305 if (fgConfigurationHandler) {
306 AliHLTConfiguration* pConf=fgConfigurationHandler->FindConfiguration(*element);
85465857 307 if (pConf) {
a742f6f8 308 //HLTDebug("configuration %s (%p): source \"%s\" (%p) inserted", GetName(), this, pConf->GetName(), pConf);
85465857 309 fListSources.push_back(pConf);
310 } else {
311 HLTError("can not find source \"%s\"", (*element));
312 iResult=-ENOENT;
313 }
314 } else if (iResult>=0) {
315 iResult=-EFAULT;
316 HLTFatal("global configuration handler not initialized, can not resolve sources");
3495cce2 317 }
318 delete[] (*element);
319 tgtList.erase(element);
320 }
321 fListSrcElement=fListSources.begin();
322 }
323 }
324 return iResult;
325}
326
327int AliHLTConfiguration::ExtractArguments()
328{
70ed7d01 329 // see header file for function documentation
3495cce2 330 int iResult=0;
52c1c164 331 if (!fArguments.IsNull()) {
3495cce2 332 vector<char*> tgtList;
333 if ((iResult=InterpreteString(fArguments, tgtList))>=0) {
334 fArgc=tgtList.size();
9ce4bf4a 335 //HLTDebug("configuration %s: extracted %d arguments from \"%s\"", GetName(), fArgc, fArguments);
3495cce2 336 if (fArgc>0) {
337 fArgv = new char*[fArgc];
338 if (fArgv) {
339 vector<char*>::iterator element=tgtList.begin();
340 int i=0;
341 while (element!=tgtList.end()) {
85465857 342 //HLTDebug("assign arguments %d (%s)", i, *element);
3495cce2 343 fArgv[i++]=(*element);
344 element++;
345 }
346 } else {
347 iResult=-ENOMEM;
348 }
349 }
350 }
9ce4bf4a 351 } else {
352 // there are zero arguments
353 fArgc=0;
3495cce2 354 }
355 return iResult;
356}
357
358int AliHLTConfiguration::InterpreteString(const char* arg, vector<char*>& argList)
359{
70ed7d01 360 // see header file for function documentation
3495cce2 361 int iResult=0;
362 if (arg) {
85465857 363 //HLTDebug("interprete \"%s\"", arg);
3495cce2 364 int i=0;
365 int prec=-1;
5f5b708b 366 int bQuote=0;
3495cce2 367 do {
5f5b708b 368 //HLTDebug("%d %x", i, arg[i]);
369 if (arg[i]=='\'' && bQuote==0) {
370 bQuote=1;
371 } else if (arg[i]==0 ||
372 (arg[i]==' ' && bQuote==0) ||
373 (arg[i]=='\'' && bQuote==1)) {
374 bQuote=0;
3495cce2 375 if (prec>=0) {
376 char* pEntry= new char[i-prec+1];
377 if (pEntry) {
378 strncpy(pEntry, &arg[prec], i-prec);
379 pEntry[i-prec]=0; // terminate string
85465857 380 //HLTDebug("create string \"%s\", insert at %d", pEntry, argList.size());
3495cce2 381 argList.push_back(pEntry);
382 } else
383 iResult=-ENOMEM;
384 prec=-1;
385 }
386 } else if (prec==-1) prec=i;
387 } while (arg[i++]!=0 && iResult>=0);
388 } else {
389 iResult=-EINVAL;
390 }
391 return iResult;
392}
393
394int AliHLTConfiguration::FollowDependency(const char* id, TList* pTgtList)
395{
70ed7d01 396 // see header file for function documentation
3495cce2 397 int iResult=0;
398 if (id) {
399 AliHLTConfiguration* pDep=NULL;
400 if ((pDep=GetSource(id))!=NULL) {
401 if (pTgtList) pTgtList->Add(pDep);
402 iResult++;
403 } else {
404 pDep=GetFirstSource();
405 while (pDep && iResult==0) {
406 if ((iResult=pDep->FollowDependency(id, pTgtList))>0) {
407 if (pTgtList) pTgtList->AddFirst(pDep);
408 iResult++;
409 }
410 pDep=GetNextSource();
411 }
412 }
413 } else {
414 iResult=-EINVAL;
415 }
416 return iResult;
417}
418
419///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
420
b22e91eb 421/** ROOT macro for the implementation of ROOT specific class methods */
3495cce2 422ClassImp(AliHLTTask)
423
424AliHLTTask::AliHLTTask()
85869391 425 :
426 fpConfiguration(NULL),
427 fpComponent(NULL),
85869391 428 fpDataBuffer(NULL),
429 fListTargets(),
53feaef5 430 fListDependencies(),
431 fpBlockDataArray(NULL),
432 fBlockDataArraySize(0)
3495cce2 433{
70ed7d01 434 // see header file for function documentation
3495cce2 435}
436
53feaef5 437AliHLTTask::AliHLTTask(AliHLTConfiguration* pConf)
85869391 438 :
53feaef5 439 fpConfiguration(pConf),
85869391 440 fpComponent(NULL),
85869391 441 fpDataBuffer(NULL),
442 fListTargets(),
53feaef5 443 fListDependencies(),
444 fpBlockDataArray(NULL),
445 fBlockDataArraySize(0)
3495cce2 446{
70ed7d01 447 // see header file for function documentation
3495cce2 448}
449
85869391 450AliHLTTask::AliHLTTask(const AliHLTTask&)
451 :
53feaef5 452 TObject(),
453 AliHLTLogging(),
85869391 454 fpConfiguration(NULL),
455 fpComponent(NULL),
85869391 456 fpDataBuffer(NULL),
457 fListTargets(),
53feaef5 458 fListDependencies(),
459 fpBlockDataArray(NULL),
460 fBlockDataArraySize(0)
85869391 461{
462 HLTFatal("copy constructor untested");
463}
464
465AliHLTTask& AliHLTTask::operator=(const AliHLTTask&)
466{
70ed7d01 467 // see header file for function documentation
85869391 468 HLTFatal("assignment operator untested");
469 return *this;
470}
471
3495cce2 472AliHLTTask::~AliHLTTask()
473{
a742f6f8 474 TObjLink* lnk=fListDependencies.FirstLink();
475
476 while (lnk!=NULL) {
477 AliHLTTask* pTask=(AliHLTTask*)lnk->GetObject();
478 pTask->UnsetTarget(this);
479 lnk=lnk->Next();
480 }
481 lnk=fListTargets.FirstLink();
482
483 while (lnk!=NULL) {
484 AliHLTTask* pTask=(AliHLTTask*)lnk->GetObject();
485 pTask->UnsetDependency(this);
486 lnk=lnk->Next();
487 }
488
3495cce2 489 if (fpComponent) delete fpComponent;
490 fpComponent=NULL;
491 if (fpBlockDataArray) delete[] fpBlockDataArray;
492 fpBlockDataArray=NULL;
493}
494
53feaef5 495int AliHLTTask::Init(AliHLTConfiguration* pConf, AliHLTComponentHandler* pCH)
3495cce2 496{
70ed7d01 497 // see header file for function documentation
3495cce2 498 int iResult=0;
9ce4bf4a 499 if (fpConfiguration!=NULL && pConf!=NULL && fpConfiguration!=pConf) {
2d7ff710 500 HLTWarning("overriding existing reference to configuration object %p (%s) by %p",
53feaef5 501 fpConfiguration, GetName(), pConf);
502 }
503 if (pConf!=NULL) fpConfiguration=pConf;
504 if (fpConfiguration) {
3495cce2 505 if (pCH) {
506 int argc=0;
507 const char** argv=NULL;
53feaef5 508 if ((iResult=fpConfiguration->GetArguments(&argv))>=0) {
0c0c9d99 509 argc=iResult; // just to make it clear
2d7ff710 510 // TODO: we have to think about the optional environment parameter,
511 // currently just set to NULL.
53feaef5 512 iResult=pCH->CreateComponent(fpConfiguration->GetComponentID(), NULL, argc, argv, fpComponent);
9ce4bf4a 513 if (fpComponent || iResult<=0) {
a742f6f8 514 //HLTDebug("component %s (%p) created", fpComponent->GetComponentID(), fpComponent);
3495cce2 515 } else {
9ce4bf4a 516 HLTError("can not find component \"%s\" (%d)", fpConfiguration->GetComponentID(), iResult);
3495cce2 517 }
9ce4bf4a 518 } else {
519 HLTError("can not get argument list for configuration %s (%s)", fpConfiguration->GetName(), fpConfiguration->GetComponentID());
520 iResult=-EINVAL;
3495cce2 521 }
53feaef5 522 } else {
523 HLTError("component handler instance needed for task initialization");
524 iResult=-EINVAL;
3495cce2 525 }
526 } else {
53feaef5 527 HLTError("configuration object instance needed for task initialization");
3495cce2 528 iResult=-EINVAL;
529 }
530 return iResult;
531}
532
53feaef5 533int AliHLTTask::Deinit()
534{
70ed7d01 535 // see header file for function documentation
2d7ff710 536 int iResult=0;
537 AliHLTComponent* pComponent=GetComponent();
538 fpComponent=NULL;
539 if (pComponent) {
a742f6f8 540 //HLTDebug("delete component %s (%p)", pComponent->GetComponentID(), pComponent);
2d7ff710 541 pComponent->Deinit();
542 delete pComponent;
543 } else {
544 HLTWarning("task %s (%p) doesn't seem to be in initialized", GetName(), this);
545 }
546 return iResult;
53feaef5 547}
548
3495cce2 549const char *AliHLTTask::GetName() const
550{
70ed7d01 551 // see header file for function documentation
3495cce2 552 if (fpConfiguration)
553 return fpConfiguration->GetName();
554 return TObject::GetName();
555}
556
0c0c9d99 557AliHLTConfiguration* AliHLTTask::GetConf() const
3495cce2 558{
70ed7d01 559 // see header file for function documentation
3495cce2 560 return fpConfiguration;
561}
562
0c0c9d99 563AliHLTComponent* AliHLTTask::GetComponent() const
3495cce2 564{
70ed7d01 565 // see header file for function documentation
3495cce2 566 return fpComponent;
567}
568
569AliHLTTask* AliHLTTask::FindDependency(const char* id)
570{
70ed7d01 571 // see header file for function documentation
3495cce2 572 AliHLTTask* pTask=NULL;
573 if (id) {
574 pTask=(AliHLTTask*)fListDependencies.FindObject(id);
575 }
576 return pTask;
577}
578
579int AliHLTTask::FollowDependency(const char* id, TList* pTgtList)
580{
70ed7d01 581 // see header file for function documentation
3495cce2 582 int iResult=0;
583 if (id) {
584 AliHLTTask* pDep=NULL;
585 if ((pDep=(AliHLTTask*)fListDependencies.FindObject(id))!=NULL) {
586 if (pTgtList) pTgtList->Add(pDep);
587 iResult++;
588 } else {
589 TObjLink* lnk=fListDependencies.FirstLink();
590 while (lnk && iResult==0) {
591 pDep=(AliHLTTask*)lnk->GetObject();
592 if (pDep) {
593 if ((iResult=pDep->FollowDependency(id, pTgtList))>0) {
594 if (pTgtList) pTgtList->AddFirst(pDep);
595 iResult++;
596 }
597 } else {
598 iResult=-EFAULT;
599 }
600 lnk=lnk->Next();
601 }
602 }
603 } else {
604 iResult=-EINVAL;
605 }
606 return iResult;
607}
608
609void AliHLTTask::PrintDependencyTree(const char* id, int bFromConfiguration)
610{
70ed7d01 611 // see header file for function documentation
85465857 612 HLTLogKeyword("task dependencies");
3495cce2 613 int iResult=0;
614 TList tgtList;
615 if (bFromConfiguration) {
616 if (fpConfiguration)
617 iResult=fpConfiguration->FollowDependency(id, &tgtList);
618 else
619 iResult=-EFAULT;
620 } else
621 iResult=FollowDependency(id, &tgtList);
622 if (iResult>0) {
85465857 623 HLTMessage(" task \"%s\": dependency level %d ", GetName(), iResult);
3495cce2 624 TObjLink* lnk=tgtList.FirstLink();
625 int i=iResult;
626 char* pSpace = new char[iResult+1];
627 if (pSpace) {
628 memset(pSpace, 32, iResult);
629 pSpace[i]=0;
630 while (lnk) {
631 TObject* obj=lnk->GetObject();
85465857 632 HLTMessage(" %s^-- %s ", &pSpace[i--], obj->GetName());
3495cce2 633 lnk=lnk->Next();
634 }
635 delete [] pSpace;
636 } else {
637 iResult=-ENOMEM;
638 }
639 }
640}
641
3495cce2 642int AliHLTTask::SetDependency(AliHLTTask* pDep)
643{
70ed7d01 644 // see header file for function documentation
3495cce2 645 int iResult=0;
646 if (pDep) {
647 if (FindDependency(pDep->GetName())==NULL) {
648 fListDependencies.Add(pDep);
649 } else {
650 iResult=-EEXIST;
651 }
652 } else {
653 iResult=-EINVAL;
654 }
655 return iResult;
656}
657
a742f6f8 658int AliHLTTask::UnsetDependency(AliHLTTask* pDep)
659{
660 fListDependencies.Remove(pDep);
661 if (fpConfiguration) {
662 fpConfiguration->InvalidateSources();
663 }
664 return 0;
665}
666
3495cce2 667int AliHLTTask::CheckDependencies()
668{
70ed7d01 669 // see header file for function documentation
3495cce2 670 int iResult=0;
671 AliHLTConfiguration* pSrc=fpConfiguration->GetFirstSource();
672 while (pSrc) {
673 if (FindDependency(pSrc->GetName())==NULL) {
85465857 674 //HLTDebug("dependency \"%s\" unresolved", pSrc->GetName());
3495cce2 675 iResult++;
676 }
677 pSrc=fpConfiguration->GetNextSource();
678 }
679 return iResult;
680}
681
682
683int AliHLTTask::Depends(AliHLTTask* pTask)
684{
70ed7d01 685 // see header file for function documentation
3495cce2 686 int iResult=0;
687 if (pTask) {
688 if (fpConfiguration) {
689 iResult=fpConfiguration->GetSource(pTask->GetName())!=NULL;
690 if (iResult>0) {
85465857 691 //HLTDebug("task \"%s\" depends on \"%s\"", GetName(), pTask->GetName());
3495cce2 692 } else {
85465857 693 //HLTDebug("task \"%s\" independend of \"%s\"", GetName(), pTask->GetName());
3495cce2 694 }
695 } else {
696 iResult=-EFAULT;
697 }
698 } else {
699 iResult=-EINVAL;
700 }
701 return iResult;
702}
703
704AliHLTTask* AliHLTTask::FindTarget(const char* id)
705{
70ed7d01 706 // see header file for function documentation
3495cce2 707 AliHLTTask* pTask=NULL;
708 if (id) {
709 pTask=(AliHLTTask*)fListTargets.FindObject(id);
710 }
711 return pTask;
712}
713
714int AliHLTTask::SetTarget(AliHLTTask* pTgt)
715{
70ed7d01 716 // see header file for function documentation
3495cce2 717 int iResult=0;
718 if (pTgt) {
719 if (FindTarget(pTgt->GetName())==NULL) {
720 fListTargets.Add(pTgt);
721 } else {
722 iResult=-EEXIST;
723 }
724 } else {
725 iResult=-EINVAL;
726 }
727 return iResult;
728}
729
a742f6f8 730int AliHLTTask::UnsetTarget(AliHLTTask* pTarget)
731{
732 fListTargets.Remove(pTarget);
733 return 0;
734}
735
0c0c9d99 736int AliHLTTask::StartRun()
737{
70ed7d01 738 // see header file for function documentation
0c0c9d99 739 int iResult=0;
740 int iNofInputDataBlocks=0;
741 AliHLTComponent* pComponent=GetComponent();
742 if (pComponent) {
743 // determine the number of input data blocks provided from the source tasks
744 TObjLink* lnk=fListDependencies.FirstLink();
745 while (lnk && iResult>=0) {
746 AliHLTTask* pSrcTask=(AliHLTTask*)lnk->GetObject();
747 if (pSrcTask) {
748 if ((iResult=pSrcTask->GetNofMatchingDataTypes(this))>0) {
749 iNofInputDataBlocks+=iResult;
750 } else if (iResult==0) {
751 HLTWarning("source task %s (%p) does not provide any matching data type for task %s (%p)", pSrcTask->GetName(), pSrcTask, GetName(), this);
752 } else {
753 HLTError("task %s (%p): error getting matching data types for source task %s (%p)", GetName(), this, pSrcTask->GetName(), pSrcTask);
754 iResult=-EFAULT;
755 }
756 }
757 lnk=lnk->Next();
758 }
759 if (iResult>=0) {
760 if (fpBlockDataArray) {
761 HLTWarning("block data array for task %s (%p) was not cleaned", GetName(), this);
762 delete [] fpBlockDataArray;
763 fpBlockDataArray=NULL;
764 fBlockDataArraySize=0;
765 }
766
767 // component init
2d7ff710 768 // the initialization of the component is done by the ComponentHandler after creation
769 // of the component.
0c0c9d99 770 //iResult=Init( AliHLTComponentEnvironment* environ, void* environ_param, int argc, const char** argv );
771
2d7ff710 772 // allocate internal task variables for bookkeeping aso.
9ce4bf4a 773 // we allocate the BlockData array with at least one member
774 if (iNofInputDataBlocks==0) iNofInputDataBlocks=1;
8ede8717 775 fpBlockDataArray=new AliHLTComponentBlockData[iNofInputDataBlocks];
0c0c9d99 776 if (fpBlockDataArray) {
777 fBlockDataArraySize=iNofInputDataBlocks;
778 } else {
779 HLTError("memory allocation failed");
780 iResult=-ENOMEM;
781 }
9ce4bf4a 782
783 // allocate the data buffer, which controls the output buffer and subscriptions
784 if (iResult>=0) {
785 fpDataBuffer=new AliHLTDataBuffer;
786 if (fpDataBuffer!=NULL) {
787 HLTDebug("created data buffer %p for task %s (%p)", fpDataBuffer, GetName(), this);
788 TObjLink* lnk=fListTargets.FirstLink();
789 while (lnk && iResult>=0) {
790 AliHLTTask* pTgtTask=(AliHLTTask*)lnk->GetObject();
791 if (pTgtTask) {
792 if ((iResult=fpDataBuffer->SetConsumer(pTgtTask->GetComponent()))>=0) {
793 }
794 } else {
795 break;
796 iResult=-EFAULT;
797 }
798 lnk=lnk->Next();
799 }
800 } else {
801 HLTFatal("can not create data buffer object, memory allocation failed");
802 iResult=-ENOMEM;
803 }
804 }
0c0c9d99 805 }
806 } else {
807 HLTError("task %s (%p) does not have a component", GetName(), this);
808 iResult=-EFAULT;
809 }
810 return iResult;
811}
3495cce2 812
0c0c9d99 813int AliHLTTask::EndRun()
814{
70ed7d01 815 // see header file for function documentation
0c0c9d99 816 int iResult=0;
2d7ff710 817 if (fpBlockDataArray) {
818 fBlockDataArraySize=0;
819 delete [] fpBlockDataArray;
820 fpBlockDataArray=0;
821 } else {
822 HLTWarning("task %s (%p) doesn't seem to be in running mode", GetName(), this);
823 }
9ce4bf4a 824 if (fpDataBuffer) {
825 AliHLTDataBuffer* pBuffer=fpDataBuffer;
826 fpDataBuffer=NULL;
827 delete pBuffer;
828 }
0c0c9d99 829 return iResult;
830}
3495cce2 831
9ce4bf4a 832int AliHLTTask::ProcessTask(Int_t eventNo)
0c0c9d99 833{
70ed7d01 834 // see header file for function documentation
0c0c9d99 835 int iResult=0;
2d7ff710 836 AliHLTComponent* pComponent=GetComponent();
9ce4bf4a 837 if (pComponent && fpDataBuffer) {
838 HLTDebug("Processing task %s (%p) fpDataBuffer %p", GetName(), this, fpDataBuffer);
839 fpDataBuffer->Reset();
0c0c9d99 840 int iSourceDataBlock=0;
841 int iInputDataVolume=0;
842
843 int iNofInputDataBlocks=0;
844 /* TODO: the assumption of only one output data type per component is the current constraint
845 * later it should be checked how many output blocks of the source component match the input
846 * data types of the consumer component (GetNofMatchingDataBlocks). If one assumes that a
847 * certain output block is always been produced, the initialization could be done in the
848 * StartRun. Otherwise the fpBlockDataArray has to be adapted each time.
849 */
850 iNofInputDataBlocks=fListDependencies.GetSize(); // one block per source
851 // is not been used since the allocation was done in StartRun, but check the size
852 if (iNofInputDataBlocks>fBlockDataArraySize) {
853 HLTError("block data array too small");
854 }
855
856 AliHLTTask* pSrcTask=NULL;
857 TList subscribedTaskList;
858 TObjLink* lnk=fListDependencies.FirstLink();
859
860 // subscribe to all source tasks
861 while (lnk && iResult>=0) {
862 pSrcTask=(AliHLTTask*)lnk->GetObject();
863 if (pSrcTask) {
9ce4bf4a 864 int iMatchingDB=pSrcTask->GetNofMatchingDataBlocks(this);
865 if (iMatchingDB<=fBlockDataArraySize-iSourceDataBlock) {
866 if (fpBlockDataArray) {
0c0c9d99 867 if ((iResult=pSrcTask->Subscribe(this, &fpBlockDataArray[iSourceDataBlock],fBlockDataArraySize-iSourceDataBlock))>0) {
868 for (int i=0; i<iResult; i++) {
869 iInputDataVolume+=fpBlockDataArray[i+iSourceDataBlock].fSize;
870 // put the source task as many times into the list as it provides data blocks
871 // makes the bookkeeping for the data release easier
872 subscribedTaskList.Add(pSrcTask);
873 }
874 iSourceDataBlock+=iResult;
9ce4bf4a 875 HLTDebug("Task %s (%p) successfully subscribed to %d data block(s) of task %s (%p)", GetName(), this, iResult, pSrcTask->GetName(), pSrcTask);
0c0c9d99 876 iResult=0;
877 } else {
878 HLTError("Task %s (%p): subscription to task %s (%p) failed with error %d", GetName(), this, pSrcTask->GetName(), pSrcTask, iResult);
879 iResult=-EFAULT;
880 }
9ce4bf4a 881 } else {
882 HLTFatal("Task %s (%p): BlockData array not allocated", GetName(), this);
883 iResult=-EFAULT;
884 }
0c0c9d99 885 } else {
886 HLTFatal("Task %s (%p): too little space in data block array for subscription to task %s (%p)", GetName(), this, pSrcTask->GetName(), pSrcTask);
9ce4bf4a 887 HLTDebug("#data types=%d, array size=%d, current index=%d", iMatchingDB, fBlockDataArraySize, iSourceDataBlock);
0c0c9d99 888 iResult=-EFAULT;
889 }
890 } else {
891 HLTFatal("fatal internal error in ROOT list handling");
892 iResult=-EFAULT;
893 }
894 lnk=lnk->Next();
895 }
896
897 // process the event
898 if (iResult>=0) {
899 long unsigned int iConstBase=0;
900 double fInputMultiplier=0;
9ce4bf4a 901 if (pComponent->GetComponentType()!=AliHLTComponent::kSink)
902 pComponent->GetOutputDataSize(iConstBase, fInputMultiplier);
0c0c9d99 903 int iOutputDataSize=int(fInputMultiplier*iInputDataVolume) + iConstBase;
9ce4bf4a 904 //HLTDebug("task %s: reqired output size %d", GetName(), iOutputDataSize);
905 AliHLTUInt8_t* pTgtBuffer=NULL;
906 if (iOutputDataSize>0) pTgtBuffer=fpDataBuffer->GetTargetBuffer(iOutputDataSize);
907 //HLTDebug("provided raw buffer %p", pTgtBuffer);
8ede8717 908 AliHLTComponentEventData evtData;
9ce4bf4a 909 AliHLTComponent::FillEventData(evtData);
910 evtData.fEventID=(AliHLTEventID_t)eventNo;
911 evtData.fBlockCnt=iSourceDataBlock;
8ede8717 912 AliHLTComponentTriggerData trigData;
0c0c9d99 913 AliHLTUInt32_t size=iOutputDataSize;
914 AliHLTUInt32_t outputBlockCnt=0;
8ede8717 915 AliHLTComponentBlockData* outputBlocks=NULL;
916 AliHLTComponentEventDoneData* edd;
0c0c9d99 917 if (pTgtBuffer!=NULL || iOutputDataSize==0) {
2d7ff710 918 iResult=pComponent->ProcessEvent(evtData, fpBlockDataArray, trigData, pTgtBuffer, size, outputBlockCnt, outputBlocks, edd);
9ce4bf4a 919 HLTDebug("task %s: component %s ProcessEvent finnished (%d): size=%d blocks=%d", GetName(), pComponent->GetComponentID(), iResult, size, outputBlockCnt);
920 if (iResult>=0 && pTgtBuffer) {
2d7ff710 921 iResult=fpDataBuffer->SetSegments(pTgtBuffer, outputBlocks, outputBlockCnt);
a742f6f8 922 delete [] outputBlocks; outputBlocks=NULL; outputBlockCnt=0;
2d7ff710 923 }
0c0c9d99 924 } else {
9ce4bf4a 925 HLTError("task %s: no target buffer available", GetName());
926 iResult=-EFAULT;
0c0c9d99 927 }
928 }
929
930 // now release all buffers which we have subscribed to
931 iSourceDataBlock=0;
932 lnk=subscribedTaskList.FirstLink();
933 while (lnk) {
934 pSrcTask=(AliHLTTask*)lnk->GetObject();
935 if (pSrcTask) {
936 int iTempRes=0;
937 if ((iTempRes=pSrcTask->Release(&fpBlockDataArray[iSourceDataBlock], this))>=0) {
938 HLTDebug("Task %s (%p) successfully released task %s (%p)", GetName(), this, pSrcTask->GetName(), pSrcTask);
939 } else {
940 HLTError("Task %s (%p): realease of task %s (%p) failed with error %d", GetName(), this, pSrcTask->GetName(), pSrcTask, iTempRes);
941 }
942 } else {
9ce4bf4a 943 HLTFatal("task %s (%p): internal error in ROOT list handling", GetName(), this);
2d7ff710 944 if (iResult>=0) iResult=-EFAULT;
0c0c9d99 945 }
946 subscribedTaskList.Remove(lnk);
947 lnk=subscribedTaskList.FirstLink();
948 iSourceDataBlock++;
949 }
950 if (subscribedTaskList.GetSize()>0) {
951 HLTError("task %s (%p): could not release all data buffers", GetName(), this);
952 }
953 } else {
9ce4bf4a 954 HLTError("task %s (%p): internal failure (not initialized component %p, data buffer %p)", GetName(), this, fpComponent, fpDataBuffer);
0c0c9d99 955 iResult=-EFAULT;
956 }
957 return iResult;
958}
959
2d7ff710 960int AliHLTTask::GetNofMatchingDataBlocks(const AliHLTTask* pConsumerTask) const
0c0c9d99 961{
70ed7d01 962 // see header file for function documentation
0c0c9d99 963 int iResult=0;
964 if (pConsumerTask) {
965 if (fpDataBuffer) {
966 iResult=fpDataBuffer->FindMatchingDataBlocks(pConsumerTask->GetComponent(), NULL);
967 } else {
968 HLTFatal("internal data buffer missing");
969 iResult=-EFAULT;
970 }
971 } else {
972 iResult=-EINVAL;
973 }
974 return iResult;
975}
976
2d7ff710 977int AliHLTTask::GetNofMatchingDataTypes(const AliHLTTask* pConsumerTask) const
0c0c9d99 978{
70ed7d01 979 // see header file for function documentation
0c0c9d99 980 int iResult=0;
981 if (pConsumerTask) {
982 AliHLTComponent* pComponent=GetComponent();
983 if (!pComponent) {
a655eae3 984 // init ?
985 HLTError("component not initialized");
986 iResult=-EFAULT;
0c0c9d99 987 }
988 if (pComponent) {
989 iResult=pComponent->FindMatchingDataTypes(pConsumerTask->GetComponent(), NULL);
990 } else {
991 HLTFatal("task initialization failed");
992 iResult=-EFAULT;
993 }
994 } else {
995 iResult=-EINVAL;
996 }
997 return iResult;
998}
999
8ede8717 1000int AliHLTTask::Subscribe(const AliHLTTask* pConsumerTask, AliHLTComponentBlockData* pBlockDesc, int iArraySize)
0c0c9d99 1001{
70ed7d01 1002 // see header file for function documentation
0c0c9d99 1003 int iResult=0;
1004 if (pConsumerTask) {
1005 if (fpDataBuffer) {
1006 iResult=fpDataBuffer->Subscribe(pConsumerTask->GetComponent(), pBlockDesc, iArraySize);
1007 } else {
1008 HLTFatal("internal data buffer missing");
1009 iResult=-EFAULT;
1010 }
1011 } else {
1012 iResult=-EINVAL;
1013 }
1014 return iResult;
1015}
1016
8ede8717 1017int AliHLTTask::Release(AliHLTComponentBlockData* pBlockDesc, const AliHLTTask* pConsumerTask)
0c0c9d99 1018{
70ed7d01 1019 // see header file for function documentation
0c0c9d99 1020 int iResult=0;
1021 if (pConsumerTask && pBlockDesc) {
1022 if (fpDataBuffer) {
1023 iResult=fpDataBuffer->Release(pBlockDesc, pConsumerTask->GetComponent());
1024 } else {
1025 HLTFatal("internal data buffer missing");
1026 iResult=-EFAULT;
1027 }
1028 } else {
1029 iResult=-EINVAL;
1030 }
1031 return iResult;
1032}
3495cce2 1033
3495cce2 1034void AliHLTTask::PrintStatus()
1035{
70ed7d01 1036 // see header file for function documentation
85465857 1037 HLTLogKeyword("task properties");
2d7ff710 1038 AliHLTComponent* pComponent=GetComponent();
1039 if (pComponent) {
1040 HLTMessage(" component: %s (%p)", pComponent->GetComponentID(), pComponent);
3495cce2 1041 } else {
85465857 1042 HLTMessage(" no component set!");
3495cce2 1043 }
1044 if (fpConfiguration) {
1045 AliHLTConfiguration* pSrc=fpConfiguration->GetFirstSource();
1046 while (pSrc) {
1047 const char* pQualifier="unresolved";
1048 if (FindDependency(pSrc->GetName()))
1049 pQualifier="resolved";
85465857 1050 HLTMessage(" source: %s (%s)", pSrc->GetName(), pQualifier);
3495cce2 1051 pSrc=fpConfiguration->GetNextSource();
1052 }
1053 TObjLink* lnk = fListTargets.FirstLink();
1054 while (lnk) {
1055 TObject *obj = lnk->GetObject();
85465857 1056 HLTMessage(" target: %s", obj->GetName());
3495cce2 1057 lnk = lnk->Next();
1058 }
1059 } else {
85465857 1060 HLTMessage(" task \"%s\" not initialized", GetName());
3495cce2 1061 }
1062}
1063
1064///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
1065
b22e91eb 1066/** ROOT macro for the implementation of ROOT specific class methods */
3495cce2 1067ClassImp(AliHLTConfigurationHandler)
1068
1069AliHLTConfigurationHandler::AliHLTConfigurationHandler()
88ea49c8 1070 :
1071 fgListConfigurations()
3495cce2 1072{
70ed7d01 1073 // see header file for function documentation
88ea49c8 1074 SetLocalLoggingLevel(kHLTLogInfo);
3495cce2 1075}
1076
1077AliHLTConfigurationHandler::~AliHLTConfigurationHandler()
1078{
70ed7d01 1079 // see header file for function documentation
a742f6f8 1080 TObjLink* lnk=NULL;
1081 while (lnk=fgListConfigurations.FirstLink()) {
1082 AliHLTConfiguration* pConf=(AliHLTConfiguration*)lnk->GetObject();
1083 HLTDebug("delete configuration \"%s\"", pConf->GetName());
1084 fgListConfigurations.Remove(lnk);
1085 delete pConf;
3495cce2 1086 }
1087}
1088
1089int AliHLTConfigurationHandler::RegisterConfiguration(AliHLTConfiguration* pConf)
1090{
70ed7d01 1091 // see header file for function documentation
3495cce2 1092 int iResult=0;
1093 if (pConf) {
1094 if (FindConfiguration(pConf->GetName()) == NULL) {
fc455fba 1095 AliHLTConfiguration* pClone=new AliHLTConfiguration(*pConf);
1096 fgListConfigurations.Add(pClone);
a742f6f8 1097 HLTDebug("configuration \"%s\" (%p) registered from %p", pClone->GetName(), pClone, pConf);
3495cce2 1098
1099 // mark all configurations with unresolved dependencies for re-evaluation
70ed7d01 1100 TObjLink* lnk=fgListConfigurations.FirstLink();
3495cce2 1101 while (lnk) {
1102 AliHLTConfiguration* pSrc=(AliHLTConfiguration*)lnk->GetObject();
fc455fba 1103 if (pSrc && pSrc!=pClone && pSrc->SourcesResolved()!=1) {
3495cce2 1104 pSrc->InvalidateSources();
1105 }
1106 lnk=lnk->Next();
1107 }
1108 } else {
1109 iResult=-EEXIST;
85465857 1110 HLTWarning("configuration \"%s\" already registered", pConf->GetName());
3495cce2 1111 }
1112 } else {
1113 iResult=-EINVAL;
1114 }
1115 return iResult;
1116}
1117
1118int AliHLTConfigurationHandler::CreateConfiguration(const char* id, const char* component, const char* sources, const char* arguments)
1119{
70ed7d01 1120 // see header file for function documentation
3495cce2 1121 int iResult=0;
1122 AliHLTConfiguration* pConf= new AliHLTConfiguration(id, component, sources, arguments);
1123 if (pConf) {
1124 // the configuration will be registered automatically, if this failes the configuration
1125 // is missing -> delete it
1126 if (FindConfiguration(id)==NULL) {
1127 delete pConf;
1128 pConf=NULL;
1129 iResult=-EEXIST;
3495cce2 1130 }
1131 } else {
85465857 1132 HLTError("system error: object allocation failed");
3495cce2 1133 iResult=-ENOMEM;
1134 }
1135 return iResult;
1136}
1137
1138void AliHLTConfigurationHandler::PrintConfigurations()
1139{
70ed7d01 1140 // see header file for function documentation
85465857 1141 HLTLogKeyword("configuration listing");
1142 HLTMessage("registered configurations:");
70ed7d01 1143 TObjLink *lnk = fgListConfigurations.FirstLink();
3495cce2 1144 while (lnk) {
1145 TObject *obj = lnk->GetObject();
85465857 1146 HLTMessage(" %s", obj->GetName());
3495cce2 1147 lnk = lnk->Next();
1148 }
1149}
1150
1151int AliHLTConfigurationHandler::RemoveConfiguration(const char* id)
1152{
70ed7d01 1153 // see header file for function documentation
3495cce2 1154 int iResult=0;
1155 if (id) {
1156 AliHLTConfiguration* pConf=NULL;
1157 if ((pConf=FindConfiguration(id))!=NULL) {
1158 iResult=RemoveConfiguration(pConf);
fc455fba 1159 delete pConf;
1160 pConf=NULL;
3495cce2 1161 } else {
85465857 1162 HLTWarning("can not find configuration \"%s\"", id);
3495cce2 1163 iResult=-ENOENT;
1164 }
1165 } else {
1166 iResult=-EINVAL;
1167 }
1168 return iResult;
1169}
1170
1171int AliHLTConfigurationHandler::RemoveConfiguration(AliHLTConfiguration* pConf)
1172{
70ed7d01 1173 // see header file for function documentation
3495cce2 1174 int iResult=0;
1175 if (pConf) {
1176 // remove the configuration from the list
9ce4bf4a 1177 HLTDebug("remove configuration \"%s\"", pConf->GetName());
70ed7d01 1178 fgListConfigurations.Remove(pConf);
3495cce2 1179 // remove cross links in the remaining configurations
70ed7d01 1180 TObjLink* lnk=fgListConfigurations.FirstLink();
3495cce2 1181 while (lnk && iResult>=0) {
1182 AliHLTConfiguration* pRem=(AliHLTConfiguration*)lnk->GetObject();
1183 if (pRem) {
1184 pRem->InvalidateSource(pConf);
1185 } else {
1186 iResult=-EFAULT;
1187 }
1188 lnk=lnk->Next();
1189 }
1190 }
1191 return iResult;
1192}
1193
1194AliHLTConfiguration* AliHLTConfigurationHandler::FindConfiguration(const char* id)
1195{
70ed7d01 1196 // see header file for function documentation
3495cce2 1197 AliHLTConfiguration* pConf=NULL;
1198 if (id) {
70ed7d01 1199 pConf=(AliHLTConfiguration*)fgListConfigurations.FindObject(id);
3495cce2 1200 }
1201 return pConf;
1202}
1203