source: trunk/Mars/mfileio/MFitsArray.cc@ 19662

Last change on this file since 19662 was 19288, checked in by tbretz, 6 years ago
This fixes some compiler warning about alignment during casts.
File size: 7.6 KB
Line 
1#include "MAGIC.h"
2#include "MLogManip.h"
3
4#include "MFitsArray.h"
5
6#include <TDataMember.h>
7#include <TClonesArray.h>
8#include <TClass.h>
9#include <TList.h>
10
11using namespace std;
12
13// ----------------------------------------------------------------------------
14//
15// Opens the FITS table of this TClonesArray. This should be done after all
16// columns are initialized. baseFileName is the name of the group, this
17// children table belongs to. dataName is the name of the TClonesArray
18// variable in the MParContainer - class.
19//
20Bool_t MArrayHelperBase::OpenFitsTable(const char * baseFileName,
21 const char * dataName,
22 const char * option, MLog * log )
23{
24 // get the baseFileName without extension
25 char fileNameNoExt[strlen(baseFileName) + 1];
26 strcpy(fileNameNoExt, baseFileName);
27 // remove the extension
28 char * pos = strrchr(fileNameNoExt, '.');
29 if (pos) *pos = 0;
30
31 // add the dataName to the file name define the table name:
32 // result will be something like:
33 // baseFileName_dataName.fits[dataName]
34 TString dol = fileNameNoExt;
35 TString fileName;
36 dol += "_";
37 dol += dataName;
38 dol += ".fits";
39 fileName = dol;
40// dol += "[";
41// dol += dataName;
42// dol += "]";
43
44// try {
45
46 if (strcmp(option, "RECREATE") == 0)
47 // remove the file
48 unlink(fileName.Data());
49
50 // create the file with the FITS table and all its columns
51 //FIXME I must implement a constructor and set fFitsTable to NULL
52 //Otherwise I cannot safely destroy the object (in the destructor, also to be implemented)
53 fFitsTable = new ofits();
54 fFitsTable->open(dol.Data());
55
56// }
57// catch (exception & e)
58// {
59// *log << err << e.what() << endl;
60// return kFALSE;
61 // }
62 return kTRUE;
63}
64
65///////////////////////////////////////////////////////////////////////////////
66///////////////////////////////////////////////////////////////////////////////
67
68// ----------------------------------------------------------------------------
69//
70// Determines the size of the buffer to store all data of the clonesArray -
71// Class, which should be written to a FITS table. The buffer is allocated.
72//
73// status is set to kFALSE if some data cannot be stored in a FITS table,
74// for example more than 1 dimensional arrays.
75MClonesArrayHelper::MClonesArrayHelper(const TClonesArray * clonesArray, MLog * log,
76 Bool_t & status)
77 : fClonesArray(clonesArray)
78{
79 status = kTRUE;
80
81 // get size of buffer
82 fDataBufferSize = 0;
83 fStartOfData = 0x7fffffff;
84
85 TList * dataMembers = fClonesArray->GetClass()->GetListOfDataMembers();
86 TIter next(dataMembers);
87 TDataMember * dataMember;
88
89 while ((dataMember = (TDataMember*)next()) != NULL)
90 {
91 if (!dataMember->IsPersistent())
92 continue;
93
94#if ROOT_VERSION_CODE < ROOT_VERSION(6,00,00)
95 if (dataMember->Property() & ( G__BIT_ISENUM | G__BIT_ISSTATIC))
96 continue;
97#else
98 if (dataMember->Property() & ( EProperty::kIsEnum | EProperty::kIsStatic))
99 continue;
100#endif
101 if (strcmp(dataMember->GetTrueTypeName(), "TClass*") == 0)
102 continue;
103
104 // is it an array of more than 1 dimension?
105 if (dataMember->GetArrayDim() > 1)
106 {
107 *log << err << "Two and more dimensional arrays of member variables"
108 " are not supported." << endl;
109 *log << "See variable " << dataMember->GetName() <<
110 " in container " << fClonesArray->GetClass()->GetName() << endl;
111 status = kFALSE;
112 return;
113 }
114
115
116 // get the position, where the current variable ends.
117 Int_t endPos;
118 if (dataMember->GetArrayDim() == 1)
119 endPos = dataMember->GetOffset() + (dataMember->GetUnitSize() *
120 dataMember->GetMaxIndex(0) );
121 else
122 endPos = dataMember->GetOffset() + dataMember->GetUnitSize();
123
124 if (endPos > fDataBufferSize)
125 fDataBufferSize = endPos;
126
127 if (dataMember->GetOffset() < fStartOfData)
128 fStartOfData = dataMember->GetOffset();
129 }
130
131 fDataBuffer = new Byte_t[fDataBufferSize];
132
133}
134
135// ----------------------------------------------------------------------------
136//
137// the fClonesArray, the size of the data buffer and the fits Table are
138// copied. A new buffer is allocated. Note: the fArraySize is not copied.
139// Anyhow only its pointer is needed, which will change during this copy
140//
141MClonesArrayHelper::MClonesArrayHelper(const MClonesArrayHelper & clHelper)
142 : fClonesArray(clHelper.fClonesArray)
143{
144 fFitsTable = clHelper.fFitsTable;
145 fDataBufferSize = clHelper.fDataBufferSize;
146 fStartOfData = clHelper.fStartOfData;
147 fDataBuffer = new Byte_t[fDataBufferSize];
148}
149
150
151
152// ----------------------------------------------------------------------------
153//
154// Writes all currently stored classes in the fClonesArray, i. e. writes 0 to
155// may rows to the FITS table.
156// fArraySize is updated with the number of new row, written to the FITS
157// table. Therefore the parent FITS table must be updated after calling this
158// method.
159//
160void MClonesArrayHelper::Write()
161{
162 // get number of classes in fClonesArray.
163 fArraySize = fClonesArray->GetLast() + 1;
164
165 for (UInt_t idx = 0; idx < fArraySize; idx++)
166 {
167 // copy the data of one class to fDataBuffer
168 memcpy(fDataBuffer, (*fClonesArray)[idx], fDataBufferSize);
169
170 // now the data can be written from the fDataBuffer to the FITS table
171 fFitsTable->WriteRow(fDataBuffer, fDataBufferSize);
172 }
173}
174
175// ----------------------------------------------------------------------------
176//
177// resize the clone array (fClonesArray) and reads fArraySize data sets from
178// the FITS file into the fClonesArray.
179// The number of data sets must be determined before calling this function,
180// i.e. the parent FITS table must be read before calling this method.
181Int_t MClonesArrayHelper::Read()
182{
183 /* fClonesArray->ExpandCreate(fArraySize);
184
185 for (int idx = 0; idx < fArraySize; idx++)
186 {
187 // read the data in the buffer
188 if (!fFitsTable.Read())
189 {
190 gLog << "Expecting more entries in " << fFitsTable.GetFileName() << endl;
191 return kERROR;
192 }
193 // copy the data of one class from fDataBuffer into the class
194 memcpy( (Byte_t*)((*fClonesArray)[idx]) + fStartOfData,
195 fDataBuffer + fStartOfData, fDataBufferSize - fStartOfData);
196 }
197*/
198 return kTRUE;
199}
Note: See TracBrowser for help on using the repository browser.