Logo ROOT   6.16/01
Reference Guide
TKeyXML.cxx
Go to the documentation of this file.
1// @(#)root/xml:$Id$
2// Author: Sergey Linev, Rene Brun 10.05.2004
3
4/*************************************************************************
5 * Copyright (C) 1995-2004, Rene Brun and Fons Rademakers. *
6 * All rights reserved. *
7 * *
8 * For the licensing terms see $ROOTSYS/LICENSE. *
9 * For the list of contributors see $ROOTSYS/README/CREDITS. *
10 *************************************************************************/
11
12//________________________________________________________________________
13//
14// TKeyXML is represents one block of data in TXMLFile
15// Normally this block corresponds to data of single object like histogram,
16// TObjArray and so on.
17//________________________________________________________________________
18
19#include "TKeyXML.h"
20
21#include "TBufferXML.h"
22#include "TXMLFile.h"
23#include "TClass.h"
24#include "TROOT.h"
25#include "TBrowser.h"
26
28
29////////////////////////////////////////////////////////////////////////////////
30/// default constructor
31
32TKeyXML::TKeyXML() : TKey(), fKeyNode(nullptr), fKeyId(0), fSubdir(kFALSE)
33{
34}
35
36////////////////////////////////////////////////////////////////////////////////
37/// Creates TKeyXML and convert object data to xml structures
38
39TKeyXML::TKeyXML(TDirectory *mother, Long64_t keyid, const TObject *obj, const char *name, const char *title)
40 : TKey(mother), fKeyNode(nullptr), fKeyId(keyid), fSubdir(kFALSE)
41{
42 if (name) {
44 } else if (obj) {
45 SetName(obj->GetName());
46 fClassName = obj->ClassName();
47 } else
48 SetName("Noname");
49
50 if (title)
51 SetTitle(title);
52
53 fCycle = GetMotherDir()->AppendKey(this);
54
55 TXMLEngine *xml = XMLEngine();
56 if (xml)
57 fKeyNode = xml->NewChild(nullptr, nullptr, xmlio::Xmlkey);
58
59 fDatime.Set();
60
61 StoreObject(obj, nullptr, kTRUE);
62}
63
64////////////////////////////////////////////////////////////////////////////////
65/// Creates TKeyXML and convert object data to xml structures
66
67TKeyXML::TKeyXML(TDirectory *mother, Long64_t keyid, const void *obj, const TClass *cl, const char *name,
68 const char *title)
69 : TKey(mother), fKeyNode(nullptr), fKeyId(keyid), fSubdir(kFALSE)
70{
71 if (name && *name)
73 else
74 SetName(cl ? cl->GetName() : "Noname");
75
76 if (title)
77 SetTitle(title);
78
79 fCycle = GetMotherDir()->AppendKey(this);
80
81 TXMLEngine *xml = XMLEngine();
82 if (xml)
83 fKeyNode = xml->NewChild(nullptr, nullptr, xmlio::Xmlkey);
84
85 fDatime.Set();
86
87 StoreObject(obj, cl, kFALSE);
88}
89
90////////////////////////////////////////////////////////////////////////////////
91/// Creates TKeyXML and takes ownership over xml node, from which object can be restored
92
94 : TKey(mother), fKeyNode(keynode), fKeyId(keyid), fSubdir(kFALSE)
95{
96 TXMLEngine *xml = XMLEngine();
97
98 SetName(xml->GetAttr(keynode, xmlio::Name));
99
100 if (xml->HasAttr(keynode, xmlio::Title))
101 SetTitle(xml->GetAttr(keynode, xmlio::Title));
102
103 fCycle = xml->GetIntAttr(keynode, xmlio::Cycle);
104
105 if (xml->HasAttr(keynode, xmlio::CreateTm)) {
106 TDatime tm(xml->GetAttr(keynode, xmlio::CreateTm));
107 fDatime = tm;
108 }
109
110 XMLNodePointer_t objnode = xml->GetChild(keynode);
111 xml->SkipEmpty(objnode);
112
113 fClassName = xml->GetAttr(objnode, xmlio::ObjClass);
114}
115
116////////////////////////////////////////////////////////////////////////////////
117/// TKeyXML destructor
118
120{
121 if (fKeyNode) {
122 TXMLEngine *xml = XMLEngine();
123 if (xml) {
124 xml->FreeNode(fKeyNode);
125 } else {
126 TXMLEngine xml_;
127 xml_.FreeNode(fKeyNode);
128 }
129 }
130}
131
132////////////////////////////////////////////////////////////////////////////////
133/// Delete key from current directory
134/// Note: TKeyXML object is not deleted. You still have to call "delete key"
135
136void TKeyXML::Delete(Option_t * /*option*/)
137{
138 TXMLEngine *xml = XMLEngine();
139 if (fKeyNode && xml) {
140 xml->FreeNode(fKeyNode);
141 fKeyNode = nullptr;
142 }
143
145}
146
147////////////////////////////////////////////////////////////////////////////////
148/// Stores keys attributes in key node
149
151{
152 TXMLEngine *xml = XMLEngine();
153 TXMLFile *f = (TXMLFile *)GetFile();
154 if (!f || !xml || !fKeyNode)
155 return;
156
157 xml->NewAttr(fKeyNode, nullptr, xmlio::Name, GetName());
158
160
161 if (f->GetIOVersion() > 1) {
162 if (strlen(GetTitle()) > 0)
163 xml->NewAttr(fKeyNode, nullptr, xmlio::Title, GetTitle());
165 }
166}
167
168////////////////////////////////////////////////////////////////////////////////
169/// convert object to xml structure and keep this structure in key
170
171void TKeyXML::StoreObject(const void *obj, const TClass *cl, Bool_t check_tobj)
172{
173 TXMLFile *f = (TXMLFile *)GetFile();
174 TXMLEngine *xml = XMLEngine();
175 if (!f || !xml || !fKeyNode)
176 return;
177
178 if (obj && check_tobj) {
179 TClass *actual = TObject::Class()->GetActualClass((TObject *)obj);
180 if (!actual) {
181 actual = TObject::Class();
182 } else if (actual != TObject::Class())
183 obj = (void *)((Long_t)obj - actual->GetBaseClassOffset(TObject::Class()));
184 cl = actual;
185 }
186
188
190 buffer.InitMap();
191 if (f->GetIOVersion() == 1)
193
194 XMLNodePointer_t node = buffer.XmlWriteAny(obj, cl);
195
196 if (node)
197 xml->AddChildFirst(fKeyNode, node);
198
199 buffer.XmlWriteBlock(fKeyNode);
200
201 if (cl)
202 fClassName = cl->GetName();
203}
204
205////////////////////////////////////////////////////////////////////////////////
206/// update key attributes in key node
207
209{
210 TXMLEngine *xml = XMLEngine();
211 if (!xml || !fKeyNode)
212 return;
213
214 xml->FreeAllAttr(fKeyNode);
215
217}
218
219////////////////////////////////////////////////////////////////////////////////
220/// updates object, stored in the node
221/// Used for TDirectory data update
222
224{
225 TXMLFile *f = (TXMLFile *)GetFile();
226 TXMLEngine *xml = XMLEngine();
227 if (!f || !xml || !obj || !fKeyNode)
228 return;
229
230 XMLNodePointer_t objnode = xml->GetChild(fKeyNode);
231 xml->SkipEmpty(objnode);
232
233 if (!objnode)
234 return;
235
236 xml->UnlinkNode(objnode);
237 xml->FreeNode(objnode);
238
239 xml->FreeAllAttr(fKeyNode);
240
241 StoreObject(obj, nullptr, kTRUE);
242}
243
244////////////////////////////////////////////////////////////////////////////////
245/// To read an object from the file.
246/// The object associated to this key is read from the file into memory.
247/// Before invoking this function, obj has been created via the
248/// default constructor.
249
251{
252 if (!tobj)
253 return 0;
254
255 void *res = XmlReadAny(tobj, nullptr);
256
257 return !res ? 0 : 1;
258}
259
260////////////////////////////////////////////////////////////////////////////////
261/// read object derived from TObject class, from key
262/// if it is not TObject or in case of error, return nullptr
263
265{
266 TObject *tobj = (TObject *)XmlReadAny(nullptr, TObject::Class());
267
268 if (tobj) {
269 if (gROOT->GetForceStyle())
270 tobj->UseCurrentStyle();
271 if (tobj->IsA() == TDirectoryFile::Class()) {
272 TDirectoryFile *dir = (TDirectoryFile *)tobj;
273 dir->SetName(GetName());
274 dir->SetTitle(GetTitle());
275 dir->SetSeekDir(GetKeyId());
276 // set mother before reading keys
277 dir->SetMother(fMotherDir);
278 dir->ReadKeys();
279 fMotherDir->Append(dir);
280 fSubdir = kTRUE;
281 }
282 }
283
284 return tobj;
285}
286
287////////////////////////////////////////////////////////////////////////////////
288/// read object derived from TObject class, from key
289/// if it is not TObject or in case of error, return nullptr
290
291TObject *TKeyXML::ReadObjWithBuffer(char * /*bufferRead*/)
292{
293 TObject *tobj = (TObject *)XmlReadAny(nullptr, TObject::Class());
294
295 if (tobj) {
296 if (gROOT->GetForceStyle())
297 tobj->UseCurrentStyle();
298 if (tobj->IsA() == TDirectoryFile::Class()) {
299 TDirectoryFile *dir = (TDirectoryFile *)tobj;
300 dir->SetName(GetName());
301 dir->SetTitle(GetTitle());
302 dir->SetSeekDir(GetKeyId());
303 // set mother before reading keys
304 dir->SetMother(fMotherDir);
305 dir->ReadKeys();
306 fMotherDir->Append(dir);
307 fSubdir = kTRUE;
308 }
309 }
310
311 return tobj;
312}
313
314////////////////////////////////////////////////////////////////////////////////
315/// read object of any type
316
317void *TKeyXML::ReadObjectAny(const TClass *expectedClass)
318{
319 void *res = XmlReadAny(nullptr, expectedClass);
320
321 if (res && (expectedClass == TDirectoryFile::Class())) {
322 TDirectoryFile *dir = (TDirectoryFile *)res;
323 dir->SetName(GetName());
324 dir->SetTitle(GetTitle());
325 dir->SetSeekDir(GetKeyId());
326 // set mother before reading keys
327 dir->SetMother(fMotherDir);
328 dir->ReadKeys();
329 fMotherDir->Append(dir);
330 fSubdir = kTRUE;
331 }
332
333 return res;
334}
335
336////////////////////////////////////////////////////////////////////////////////
337/// read object from key and cast to expected class
338
339void *TKeyXML::XmlReadAny(void *obj, const TClass *expectedClass)
340{
341 if (!fKeyNode)
342 return obj;
343
344 TXMLFile *f = (TXMLFile *)GetFile();
345 TXMLEngine *xml = XMLEngine();
346 if (!f || !xml)
347 return obj;
348
349 TBufferXML buffer(TBuffer::kRead, f);
350 buffer.InitMap();
351 if (f->GetIOVersion() == 1)
353
354 XMLNodePointer_t blocknode = xml->GetChild(fKeyNode);
355 xml->SkipEmpty(blocknode);
356 while (blocknode) {
357 if (strcmp(xml->GetNodeName(blocknode), xmlio::XmlBlock) == 0)
358 break;
359 xml->ShiftToNext(blocknode);
360 }
361 buffer.XmlReadBlock(blocknode);
362
363 XMLNodePointer_t objnode = xml->GetChild(fKeyNode);
364 xml->SkipEmpty(objnode);
365
366 TClass *cl = nullptr;
367 void *res = buffer.XmlReadAny(objnode, obj, &cl);
368
369 if (!cl || !res)
370 return obj;
371
372 Int_t delta = 0;
373
374 if (expectedClass) {
375 delta = cl->GetBaseClassOffset(expectedClass);
376 if (delta < 0) {
377 if (!obj)
378 cl->Destructor(res);
379 return nullptr;
380 }
381 if (cl->GetState() > TClass::kEmulated && expectedClass->GetState() <= TClass::kEmulated) {
382 // we cannot mix a compiled class with an emulated class in the inheritance
383 Warning("XmlReadAny", "Trying to read an emulated class (%s) to store in a compiled pointer (%s)",
384 cl->GetName(), expectedClass->GetName());
385 }
386 }
387
388 return ((char *)res) + delta;
389}
390
391////////////////////////////////////////////////////////////////////////////////
392/// return pointer on TXMLEngine object, used for xml conversion
393
395{
396 TXMLFile *f = (TXMLFile *)GetFile();
397 return f ? f->XML() : nullptr;
398}
void Class()
Definition: Class.C:29
#define f(i)
Definition: RSha256.hxx:104
int Int_t
Definition: RtypesCore.h:41
const Bool_t kFALSE
Definition: RtypesCore.h:88
long Long_t
Definition: RtypesCore.h:50
bool Bool_t
Definition: RtypesCore.h:59
long long Long64_t
Definition: RtypesCore.h:69
const Bool_t kTRUE
Definition: RtypesCore.h:87
const char Option_t
Definition: RtypesCore.h:62
#define ClassImp(name)
Definition: Rtypes.h:363
#define gROOT
Definition: TROOT.h:410
void * XMLNodePointer_t
Definition: TXMLEngine.h:17
virtual void InitMap()
Create the fMap container and initialize them with the null object.
Definition: TBufferIO.cxx:129
Class for serializing/deserializing object to/from xml.
Definition: TBufferXML.h:36
XMLNodePointer_t XmlWriteAny(const void *obj, const TClass *cl)
Convert object of any class to xml structures Return pointer on top xml element.
Definition: TBufferXML.cxx:242
void XmlReadBlock(XMLNodePointer_t node)
Read binary block of data from xml.
Definition: TBufferXML.cxx:470
void * XmlReadAny(XMLNodePointer_t node, void *obj, TClass **cl)
Recreate object from xml structure.
Definition: TBufferXML.cxx:259
void XmlWriteBlock(XMLNodePointer_t node)
Write binary data block from buffer to xml.
Definition: TBufferXML.cxx:409
@ kCannotHandleMemberWiseStreaming
Definition: TBuffer.h:73
@ kWrite
Definition: TBuffer.h:70
@ kRead
Definition: TBuffer.h:70
The ROOT global object gROOT contains a list of all defined classes.
Definition: TClass.h:75
EState GetState() const
Definition: TClass.h:458
void Destructor(void *obj, Bool_t dtorOnly=kFALSE)
Explicitly call destructor for object.
Definition: TClass.cxx:5181
Int_t GetBaseClassOffset(const TClass *toBase, void *address=0, bool isDerivedObject=true)
Definition: TClass.cxx:2708
@ kEmulated
Definition: TClass.h:119
This class stores the date and time with a precision of one second in an unsigned 32 bit word (950130...
Definition: TDatime.h:37
const char * AsSQLString() const
Return the date & time in SQL compatible string format, like: 1997-01-15 20:16:28.
Definition: TDatime.cxx:151
void Set()
Set Date/Time to current time as reported by the system.
Definition: TDatime.cxx:288
A ROOT file is structured in Directories (like a file system).
virtual Int_t ReadKeys(Bool_t forceRead=kTRUE)
Read the linked list of keys.
void SetSeekDir(Long64_t v)
Describe directory structure in memory.
Definition: TDirectory.h:34
virtual Int_t AppendKey(TKey *)
Definition: TDirectory.h:119
virtual void Append(TObject *obj, Bool_t replace=kFALSE)
Append object to this directory.
Definition: TDirectory.cxx:190
virtual void SetName(const char *newname)
Set the name for directory If the directory name is changed after the directory was written once,...
virtual void SetMother(TObject *mother)
Definition: TDirectory.h:184
virtual TList * GetListOfKeys() const
Definition: TDirectory.h:150
void UpdateObject(TObject *obj)
updates object, stored in the node Used for TDirectory data update
Definition: TKeyXML.cxx:223
virtual TObject * ReadObjWithBuffer(char *bufferRead)
read object derived from TObject class, from key if it is not TObject or in case of error,...
Definition: TKeyXML.cxx:291
Long64_t GetKeyId() const
Definition: TKeyXML.h:61
virtual void Delete(Option_t *option="")
Delete key from current directory Note: TKeyXML object is not deleted.
Definition: TKeyXML.cxx:136
virtual Int_t Read(TObject *tobj)
To read an object from the file.
Definition: TKeyXML.cxx:250
XMLNodePointer_t fKeyNode
Definition: TKeyXML.h:75
TXMLEngine * XMLEngine()
return pointer on TXMLEngine object, used for xml conversion
Definition: TKeyXML.cxx:394
virtual void * ReadObjectAny(const TClass *expectedClass)
read object of any type
Definition: TKeyXML.cxx:317
void * XmlReadAny(void *obj, const TClass *expectedClass)
read object from key and cast to expected class
Definition: TKeyXML.cxx:339
virtual ~TKeyXML()
TKeyXML destructor.
Definition: TKeyXML.cxx:119
virtual TObject * ReadObj()
read object derived from TObject class, from key if it is not TObject or in case of error,...
Definition: TKeyXML.cxx:264
void StoreObject(const void *obj, const TClass *cl, Bool_t check_tobj=kFALSE)
convert object to xml structure and keep this structure in key
Definition: TKeyXML.cxx:171
void UpdateAttributes()
update key attributes in key node
Definition: TKeyXML.cxx:208
TKeyXML()
default constructor
Definition: TKeyXML.cxx:32
void StoreKeyAttributes()
Stores keys attributes in key node.
Definition: TKeyXML.cxx:150
Bool_t fSubdir
unique identifier of key for search methods
Definition: TKeyXML.h:77
Book space in a file, create I/O buffers, to fill them, (un)compress them.
Definition: TKey.h:24
TFile * GetFile() const
Returns file to which key belong.
Definition: TKey.cxx:572
TDatime fDatime
Date/Time of insertion in file.
Definition: TKey.h:37
virtual const char * GetTitle() const
Returns title (title can contain 32x32 xpm thumbnail/icon).
Definition: TKey.cxx:1501
Short_t fCycle
Cycle number.
Definition: TKey.h:39
TDirectory * GetMotherDir() const
Definition: TKey.h:81
TDirectory * fMotherDir
!pointer to mother directory
Definition: TKey.h:47
TString fClassName
Object Class name.
Definition: TKey.h:42
virtual TObject * Remove(TObject *obj)
Remove object from the list.
Definition: TList.cxx:818
virtual void SetTitle(const char *title="")
Set the title of the TNamed.
Definition: TNamed.cxx:164
virtual void SetName(const char *name)
Set the name of the TNamed.
Definition: TNamed.cxx:140
virtual const char * GetName() const
Returns name of object.
Definition: TNamed.h:47
Mother of all ROOT objects.
Definition: TObject.h:37
virtual const char * GetName() const
Returns name of object.
Definition: TObject.cxx:357
virtual const char * ClassName() const
Returns name of class to which the object belongs.
Definition: TObject.cxx:128
virtual void UseCurrentStyle()
Set current style settings in this object This function is called when either TCanvas::UseCurrentStyl...
Definition: TObject.cxx:715
virtual void Warning(const char *method, const char *msgfmt,...) const
Issue warning message.
Definition: TObject.cxx:866
void SetBit(UInt_t f, Bool_t set)
Set or unset the user status bits as specified in f.
Definition: TObject.cxx:694
XMLNodePointer_t GetChild(XMLNodePointer_t xmlnode, Bool_t realnode=kTRUE)
returns first child of xmlnode
XMLAttrPointer_t NewAttr(XMLNodePointer_t xmlnode, XMLNsPointer_t, const char *name, const char *value)
creates new attribute for xmlnode, namespaces are not supported for attributes
Definition: TXMLEngine.cxx:578
XMLNodePointer_t NewChild(XMLNodePointer_t parent, XMLNsPointer_t ns, const char *name, const char *content=0)
create new child element for parent node
Definition: TXMLEngine.cxx:707
void UnlinkNode(XMLNodePointer_t node)
unlink (detach) xmlnode from parent
Definition: TXMLEngine.cxx:997
XMLAttrPointer_t NewIntAttr(XMLNodePointer_t xmlnode, const char *name, Int_t value)
create node attribute with integer value
Definition: TXMLEngine.cxx:604
Bool_t HasAttr(XMLNodePointer_t xmlnode, const char *name)
checks if node has attribute of specified name
Definition: TXMLEngine.cxx:531
const char * GetNodeName(XMLNodePointer_t xmlnode)
returns name of xmlnode
const char * GetAttr(XMLNodePointer_t xmlnode, const char *name)
returns value of attribute for xmlnode
Definition: TXMLEngine.cxx:547
Int_t GetIntAttr(XMLNodePointer_t node, const char *name)
returns value of attribute as integer
Definition: TXMLEngine.cxx:563
void FreeAllAttr(XMLNodePointer_t xmlnode)
Free all attributes of the node.
Definition: TXMLEngine.cxx:639
void FreeNode(XMLNodePointer_t xmlnode)
release all memory, allocated from this node and destroys node itself
void SkipEmpty(XMLNodePointer_t &xmlnode)
Skip all current empty nodes and locate on first "true" node.
void ShiftToNext(XMLNodePointer_t &xmlnode, Bool_t realnode=kTRUE)
shifts specified node to next if realnode==kTRUE, any special nodes in between will be skipped
void AddChildFirst(XMLNodePointer_t parent, XMLNodePointer_t child)
add node as first child
Definition: TXMLEngine.cxx:816
const char * Name
Definition: TXMLSetup.cxx:66
const char * Title
Definition: TXMLSetup.cxx:67
const char * XmlBlock
Definition: TXMLSetup.cxx:59
const char * Cycle
Definition: TXMLSetup.cxx:58
const char * CreateTm
Definition: TXMLSetup.cxx:68
const char * ObjClass
Definition: TXMLSetup.cxx:62
const char * Xmlkey
Definition: TXMLSetup.cxx:57