]> git.uio.no Git - u/mrichter/AliRoot.git/blob - HLT/BASE/AliHLTHOMERLibManager.cxx
correcting a typo in initialization
[u/mrichter/AliRoot.git] / HLT / BASE / AliHLTHOMERLibManager.cxx
1 // $Id$
2
3 /**************************************************************************
4  * This file is property of and copyright by the ALICE HLT Project        * 
5  * ALICE Experiment at CERN, All rights reserved.                         *
6  *                                                                        *
7  * Primary Authors: Matthias Richter <Matthias.Richter@ift.uib.no>        *
8  *                  for The ALICE HLT Project.                            *
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
19 /** @file   AliHLTHOMERLibManager.cxx
20     @author Matthias Richter
21     @date   
22     @brief  dynamic HLT HOMER reader/writer generation and destruction.   */
23
24 // see header file for class documentation
25 // or
26 // refer to README to build package
27 // or
28 // visit http://web.ift.uib.no/~kjeks/doc/alice-hlt
29
30 #include <cerrno>
31 #include <cassert>
32 #include "AliHLTHOMERLibManager.h"
33 #include "AliHLTHOMERReader.h"
34 #include "AliHLTHOMERWriter.h"
35 #include "AliHLTLogging.h"
36 #include "TString.h"
37 #include "TSystem.h"
38
39 /** ROOT macro for the implementation of ROOT specific class methods */
40 ClassImp(AliHLTHOMERLibManager)
41
42 // This list must be NULL terminated, since we use it as a marker to identify
43 // the end of the list.
44 const char* AliHLTHOMERLibManager::fgkLibraries[] = {"libAliHLTHOMER.so", "libHOMER.so", NULL};
45 // The size of the list of reference counts must be one less than fgkLibraries.
46 int AliHLTHOMERLibManager::fgkLibRefCount[] = {0, 0};
47
48 AliHLTHOMERLibManager::AliHLTHOMERLibManager()
49   :
50   fLibraryStatus(0),
51   fFctCreateReaderFromTCPPort(NULL),
52   fFctCreateReaderFromTCPPorts(NULL),
53   fFctCreateReaderFromBuffer(NULL),
54   fFctDeleteReader(NULL),
55   fFctCreateWriter(NULL),
56   fFctDeleteWriter(NULL),
57   fLoadedLib(NULL)
58 {
59   // see header file for class documentation
60   // or
61   // refer to README to build package
62   // or
63   // visit http://web.ift.uib.no/~kjeks/doc/alice-hlt
64 }
65
66 AliHLTHOMERLibManager::~AliHLTHOMERLibManager()
67 {
68   // see header file for class documentation
69   UnloadHOMERLibrary();
70 }
71
72 AliHLTHOMERReader* AliHLTHOMERLibManager::OpenReader(const char* hostname, unsigned short port )
73 {
74   // see header file for class documentation
75   if (fLibraryStatus<0) return NULL;
76
77   if (fLibraryStatus==0) {
78     fLibraryStatus=LoadHOMERLibrary();
79   }
80   
81   AliHLTHOMERReader* pReader=NULL;
82   if (fFctCreateReaderFromTCPPort!=NULL && (pReader=(((AliHLTHOMERReaderCreateFromTCPPort_t)fFctCreateReaderFromTCPPort)(hostname, port)))==NULL) {
83     cout <<"can not create instance of HOMER reader from ports" << endl;
84   }
85   
86   return pReader;
87 }
88
89 AliHLTHOMERReader* AliHLTHOMERLibManager::OpenReader(unsigned int tcpCnt, const char** hostnames, unsigned short* ports)
90 {
91   // see header file for class documentation
92   if (fLibraryStatus<0) return NULL;
93
94   if (fLibraryStatus==0) {
95     fLibraryStatus=LoadHOMERLibrary();
96   }
97   
98   AliHLTHOMERReader* pReader=NULL;
99   if (fFctCreateReaderFromTCPPorts!=NULL && (pReader=(((AliHLTHOMERReaderCreateFromTCPPorts_t)fFctCreateReaderFromTCPPorts)(tcpCnt, hostnames, ports)))==NULL) {
100     //HLTError("can not create instance of HOMER reader (function %p)", fFctCreateReaderFromTCPPorts);
101     cout << "can not create instance of HOMER reader from port"<<endl;
102   }
103   
104   return pReader;
105 }
106
107 AliHLTHOMERReader* AliHLTHOMERLibManager::OpenReaderBuffer(const AliHLTUInt8_t* pBuffer, int size)
108 {
109   // see header file for class documentation
110   if (fLibraryStatus<0) return NULL;
111
112   if (fLibraryStatus==0) {
113     fLibraryStatus=LoadHOMERLibrary();
114   }
115   
116   AliHLTHOMERReader* pReader=NULL;
117   if (fFctCreateReaderFromBuffer!=NULL && (pReader=(((AliHLTHOMERReaderCreateFromBuffer_t)fFctCreateReaderFromBuffer)(pBuffer, size)))==NULL) {
118     //HLTError("can not create instance of HOMER reader (function %p)", fFctCreateReaderFromBuffer);
119   }
120   
121   return pReader;
122 }
123
124 int AliHLTHOMERLibManager::DeleteReader(AliHLTHOMERReader* pReader)
125 {
126   // see header file for class documentation
127   if (fLibraryStatus<0) return fLibraryStatus;
128
129   if (fLibraryStatus==0) {
130     fLibraryStatus=LoadHOMERLibrary();
131   }
132   
133   if (fFctDeleteReader!=NULL) {
134     ((AliHLTHOMERReaderDelete_t)fFctDeleteReader)(pReader);
135   }
136   
137   return 0;
138 }
139
140 AliHLTHOMERWriter* AliHLTHOMERLibManager::OpenWriter()
141 {
142   // see header file for class documentation
143   if (fLibraryStatus<0) return NULL;
144
145   if (fLibraryStatus==0) {
146     fLibraryStatus=LoadHOMERLibrary();
147   }
148   
149   AliHLTHOMERWriter* pWriter=NULL;
150   if (fFctCreateWriter!=NULL && (pWriter=(((AliHLTHOMERWriterCreate_t)fFctCreateWriter)()))==NULL) {
151 //     HLTError("can not create instance of HOMER writer (function %p)", fFctCreateWriter);
152   }
153   
154   return pWriter;
155 }
156
157 int AliHLTHOMERLibManager::DeleteWriter(AliHLTHOMERWriter* pWriter)
158 {
159   // see header file for class documentation
160   if (fLibraryStatus<0) return fLibraryStatus;
161
162   if (fLibraryStatus==0) {
163     fLibraryStatus=LoadHOMERLibrary();
164   }
165   
166   if (fFctDeleteWriter!=NULL) {
167     ((AliHLTHOMERWriterDelete_t)fFctDeleteWriter)(pWriter);
168   }
169   
170   return 0;
171 }
172
173 int AliHLTHOMERLibManager::LoadHOMERLibrary()
174 {
175   // see header file for class documentation
176   int iResult=-EBADF;
177   const char** library=&fgkLibraries[0];
178   int* refcount = &fgkLibRefCount[0];
179   do {
180     TString libs = gSystem->GetLibraries();
181     if (libs.Contains(*library)) {
182       iResult=1;
183       break;
184     }
185     if ((gSystem->Load(*library)) >= 0) {
186       ++(*refcount);
187       fLoadedLib = *library;
188       iResult=1;
189       break;
190     }
191     ++library;
192     ++refcount;
193   } while ((*library)!=NULL);
194
195   if (iResult>0 && *library!=NULL) {
196     // print compile info
197     typedef void (*CompileInfo)( char*& date, char*& time);
198
199     fFctCreateReaderFromTCPPort=(void (*)())gSystem->DynFindSymbol(*library, ALIHLTHOMERREADER_CREATE_FROM_TCPPORT);
200     fFctCreateReaderFromTCPPorts=(void (*)())gSystem->DynFindSymbol(*library, ALIHLTHOMERREADER_CREATE_FROM_TCPPORTS);
201     fFctCreateReaderFromBuffer=(void (*)())gSystem->DynFindSymbol(*library, ALIHLTHOMERREADER_CREATE_FROM_BUFFER);
202     fFctDeleteReader=(void (*)())gSystem->DynFindSymbol(*library, ALIHLTHOMERREADER_DELETE);
203     fFctCreateWriter=(void (*)())gSystem->DynFindSymbol(*library, ALIHLTHOMERWRITER_CREATE);
204     fFctDeleteWriter=(void (*)())gSystem->DynFindSymbol(*library, ALIHLTHOMERWRITER_DELETE);
205     if (fFctCreateReaderFromTCPPort==NULL ||
206         fFctCreateReaderFromTCPPorts==NULL ||
207         fFctCreateReaderFromBuffer==NULL || 
208         fFctDeleteReader==NULL ||
209         fFctCreateWriter==NULL ||
210         fFctDeleteWriter==NULL) {
211       iResult=-ENOSYS;
212     } else {
213     }
214   }
215   if (iResult<0 || *library==NULL) {
216     fFctCreateReaderFromTCPPort=NULL;
217     fFctCreateReaderFromTCPPorts=NULL;
218     fFctCreateReaderFromBuffer=NULL;
219     fFctDeleteReader=NULL;
220     fFctCreateWriter=NULL;
221     fFctDeleteWriter=NULL;
222   }
223
224   return iResult;
225 }
226
227 int AliHLTHOMERLibManager::UnloadHOMERLibrary()
228 {
229   // see header file for class documentation
230   int iResult=0;
231   
232   if (fLoadedLib != NULL)
233   {
234     // Find the corresponding reference count.
235     const char** library=&fgkLibraries[0];
236     int* refcount = &fgkLibRefCount[0];
237     while (*library != NULL)
238     {
239       if (strcmp(*library, fLoadedLib) == 0) break;
240       ++library;
241       ++refcount;
242     }
243     
244     // Decrease the reference count and remove the library if it is zero.
245     if (*refcount >= 0) --(*refcount);
246     if (*refcount == 0)
247     {
248       // Check that the library we are trying to unload is actually the last library
249       // in the gSystem->GetLibraries() list. If not then we must abort the removal.
250       // This is because of a ROOT bug/feature/limitation. If we try unload the library
251       // then ROOT will also wipe all libraries in the gSystem->GetLibraries() list
252       // following the library we want to unload.
253       TString libstring = gSystem->GetLibraries();
254       TString token, lastlib;
255       Ssiz_t from = 0;
256       Int_t numOfLibs = 0, posOfLib = -1;
257       while (libstring.Tokenize(token, from, " "))
258       {
259         ++numOfLibs;
260         lastlib = token;
261         if (token.Contains(fLoadedLib)) posOfLib = numOfLibs;
262       }
263       if (numOfLibs == posOfLib)
264       {
265         gSystem->Unload(fLoadedLib);
266
267         // Check that the library is gone, since Unload() does not return a status code.
268         libstring = gSystem->GetLibraries();
269         if (libstring.Contains(fLoadedLib)) iResult = -EBADF;
270       }
271       else
272       {
273         AliHLTLogging log;
274         log.LoggingVarargs(kHLTLogWarning, Class_Name(), FUNCTIONNAME(), __FILE__, __LINE__,
275           Form("ROOT limitation! Cannot properly cleanup and unload the shared"
276             " library '%s' since another library '%s' was loaded afterwards. Trying to"
277             " unload this library will remove the others and lead to serious memory faults.",
278             fLoadedLib, lastlib.Data()
279         ));
280       }
281     }
282   }
283
284   // Clear the function pointers.
285   fFctCreateReaderFromTCPPort = NULL;
286   fFctCreateReaderFromTCPPorts = NULL;
287   fFctCreateReaderFromBuffer = NULL;
288   fFctDeleteReader = NULL;
289   fFctCreateWriter = NULL;
290   fFctDeleteWriter = NULL;
291
292   return iResult;
293 }