CMS 3D CMS Logo

 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Pages
DDLParser.cc
Go to the documentation of this file.
1 /***************************************************************************
2  DDLParser.cc - description
3  -------------------
4  begin : Mon Oct 22 2001
5  email : case@ucdhep.ucdavis.edu
6 ***************************************************************************/
7 
8 /***************************************************************************
9  * *
10  * DDDParser sub-component of DDD *
11  * *
12  ***************************************************************************/
13 
16 
18 
19 #include <xercesc/framework/MemBufInputSource.hpp>
22 
23 #include <iostream>
24 
25 using namespace std;
26 
27 using namespace XERCES_CPP_NAMESPACE;
28 
31  : cpv_( cpv ),
32  nFiles_( 0 )
33 {
35  SAX2Parser_ = XMLReaderFactory::createXMLReader();
36 
37  SAX2Parser_->setFeature(XMLUni::fgSAX2CoreValidation, false); // optional
38  SAX2Parser_->setFeature(XMLUni::fgSAX2CoreNameSpaces, false); // optional
39  // Specify other parser features, e.g.
40  // SAX2Parser_->setFeature(XMLUni::fgXercesSchemaFullChecking, false);
41 
45  SAX2Parser_->setErrorHandler(errHandler_);
46  SAX2Parser_->setContentHandler(fileHandler_);
47 
48  DCOUT_V('P', "DDLParser::DDLParser(): new (and only) DDLParser");
49 }
50 
53 {
54  // clean up and leave
55  delete expHandler_;
56  delete fileHandler_;
57  delete errHandler_;
59  DCOUT_V('P', "DDLParser::~DDLParser(): destruct DDLParser");
60 }
61 
66 SAX2XMLReader*
68 {
69  return SAX2Parser_;
70 }
71 
74 {
75  return fileHandler_;
76 }
77 
78 size_t
80 {
81  FileNameHolder::const_iterator it = fileNames_.begin();
82  size_t i = 1;
83  bool foundFile = false;
84  while( it != fileNames_.end() && !foundFile )
85  {
86  if( it->second.first == filename )
87  {
88  foundFile = true;
89  }
90  else ++i;
91  ++it;
92  }
93  if( foundFile )
94  return i;
95  return 0;
96 }
97 
98 bool
100 {
101  size_t found = isFound(filename);
102  if (found)
103  return parsed_[found];
104  return false;
105 }
106 
107 // Must receive a filename and path relative to the src directory of a CMSSW release
108 // e.g. DetectorDescription/test/myfile.xml
109 bool
110 DDLParser::parseOneFile( const std::string& fullname ) //, const std::string& url)
111 {
112  // std::string filename = expHandler_->extractFileName(fullname);
114  // std::cout << "parseOneFile - fullname = " << fullname << std::endl;
115  // std::cout << "parseOneFile - filename = " << filename << std::endl;
116  edm::FileInPath fp(fullname);
117  std::string absoluteFileName = fp.fullPath();
118  size_t foundFile = isFound(filename);
119  if (!foundFile)
120  {
121  pair <std::string, std::string> pss;
122  pss.first = filename;
123  pss.second = absoluteFileName; //url+filename;
124  int fIndex = nFiles_;
126  ++nFiles_;
127  parsed_[fIndex]=false;
128 
129  currFileName_ = fileNames_[fIndex].second;
130 
131  // in cleaning up try-catch blocks 2007-06-26 I decided to remove
132  // this because of CMSSW rules. but keep the commented way I used to
133  // do it...
134  // DO NOT UNCOMMENT FOR ANY RELEASE; ONLY FOR DEBUGGING! try
135  // {
136  SAX2Parser_->setContentHandler(expHandler_);
137  expHandler_->setNameSpace( getNameSpace(filename) );
138  // std::cout << "0) namespace = " << getNameSpace(filename) << std::endl;
139  LogDebug ("DDLParser") << "ParseOneFile() Parsing: " << fileNames_[fIndex].second << std::endl;
140  parseFile ( fIndex );
141 
142  // }
143  // DO NOT UNCOMMENT FOR ANY RELEASE; ONLY FOR DEBUGGING! catch (const XMLException& toCatch) {
144  // edm::LogError ("DDLParser") << "\nDDLParser::ParseOneFile, PASS1: XMLException while processing files... \n"
145  // << "Exception message is: \n"
146  // << StrX(toCatch.getMessage()) << "\n" ;
147  // cms::concurrency::xercesTerminate();
148  // throw (DDException(" See XMLException above. "));
149  // }
150 
151  // PASS 2:
152 
153  DCOUT_V('P', "DDLParser::ParseOneFile(): PASS2: Just before setting Xerces content and error handlers... ");
154 
155  // DO NOT UNCOMMENT FOR ANY RELEASE; ONLY FOR DEBUGGING! try
156  // {
157 
158  SAX2Parser_->setContentHandler(fileHandler_);
159  // std::cout << "currFileName = " << currFileName_ << std::endl;
161  // std::cout << "1) namespace = " << getNameSpace(currFileName_) << std::endl;
162  parseFile ( fIndex );
163  parsed_[fIndex] = true;
164 
165  // }
166  // DO NOT UNCOMMENT FOR ANY RELEASE; ONLY FOR DEBUGGING! catch (const XMLException& toCatch) {
167  // edm::LogError ("DDLParser") << "\nDDLParser::ParseOneFile, PASS2: XMLException while processing files... \n"
168  // << "Exception message is: \n"
169  // << StrX(toCatch.getMessage()) << "\n" ;
170  // cms::concurrency::xercesTerminate();
171  // throw (DDException(" See XMLException above."));
172  // }
173  }
174  else // was found and is parsed...
175  {
176  DCOUT('P', " WARNING: DDLParser::ParseOneFile() file " + filename
177  + " was already parsed as " + fileNames_[foundFile].second);
178  return true;
179  }
180  return false;
181 }
182 
183 // This is for parsing the content of a blob stored in the conditions system of CMS.
184 void
185 DDLParser::parse( const std::vector<unsigned char>& ablob, unsigned int bsize )
186 {
187  char* dummy(0);
188  MemBufInputSource mbis( &*ablob.begin(), bsize, dummy );
189  SAX2Parser_->parse(mbis);
190 }
191 
192 std::vector < std::string >
194 {
195  std::vector<std::string> flist;
196  for (FileNameHolder::const_iterator fit = fileNames_.begin(); fit != fileNames_.end(); ++fit)
197  {
198  flist.push_back(fit->second.first); // was .second (mec: 2003:02:19
199  }
200  return flist;
201 }
202 
203 int
205 {
206  // edm::LogInfo ("DDLParser") << "Start Parsing. Validation is set to " << dp.doValidation() << "." << std::endl;
207  edm::LogInfo ("DDLParser") << "Start Parsing. Validation is set off for the time being." << std::endl;
208  // prep for pass 1 through DDD XML
209  // // Since this block does nothing for CMSSW right now, I have taken it all out
210  // This clean-up involves interface changes such as the removal of doValidation() everywhere (OR NOT
211  // if I decide to keep it for other testing reasons.)
212  // if (dp.doValidation())
213  // {
214  // // DCOUT_V('P', "WARNING: PARSER VALIDATION IS TURNED OFF REGARDLESS OF <Schema... ELEMENT");
215  // SAX2Parser_->setFeature(XMLUni::fgSAX2CoreValidation, true);
216  // SAX2Parser_->setFeature(XMLUni::fgSAX2CoreNameSpaces, true);
217  // // // SAX2Parser_->setFeature(XMLUni::fgXercesSchemaFullChecking, true);
218  // }
219  // else
220  // {
221  SAX2Parser_->setFeature(XMLUni::fgSAX2CoreValidation, false);
222  SAX2Parser_->setFeature(XMLUni::fgSAX2CoreNameSpaces, false);
223  // // SAX2Parser_->setFeature(XMLUni::fgXercesSchemaFullChecking, false);
224 
225  // }
226 
227  // This need be only done once, so might as well to it here.
228  size_t fileIndex = 0;
229  std::vector<std::string> fullFileName;
230 
231  for (; fileIndex < (dp.getFileList()).size(); ++fileIndex)
232  {
233  std::string ts = dp.getURLList()[fileIndex];
234  std::string tf = dp.getFileList()[fileIndex];
235  if ( ts.size() > 0 ) {
236  if ( ts[ts.size() - 1] == '/') {
237  fullFileName.push_back( ts + tf );
238  } else {
239  fullFileName.push_back( ts + "/" + tf );
240  }
241  } else {
242  fullFileName.push_back( tf );
243  }
244  }
245 
246  for (std::vector<std::string>::const_iterator fnit = fullFileName.begin();
247  fnit != fullFileName.end();
248  ++fnit)
249  {
250  size_t foundFile = isFound(extractFileName( *fnit ));
251 
252  if (!foundFile)
253  {
254  pair <std::string, std::string> pss;
255  pss.first = extractFileName( *fnit );
256  pss.second = *fnit;
257  fileNames_[nFiles_++] = pss;
258  parsed_[nFiles_ - 1]=false;
259  }
260  }
261 
262  // Start processing the files found in the config file.
263 
264  // PASS 1: This was added later (historically) to implement the DDD
265  // requirement for Expressions.
266  DCOUT('P', "DDLParser::parse(): PASS1: Just before setting Xerces content and error handlers... ");
267 
268 
269  // in cleaning up try-catch blocks 2007-06-26 I decided to remove
270  // this because of CMSSW rules. but keep the commented way I used to
271  // do it...
272  // DO NOT UNCOMMENT FOR ANY RELEASE; ONLY FOR DEBUGGING! try
273  // {
274  SAX2Parser_->setContentHandler(expHandler_);
275  for (size_t i = 0; i < fileNames_.size(); ++i)
276  {
277  if (!parsed_[i])
278  {
279  currFileName_ = fileNames_[i].second;
280  // std::cout << "currFileName = " << currFileName_ << std::endl;
282  // std::cout << "2) namespace = " << getNameSpace(extractFileName(currFileName_)) << std::endl;
283  parseFile(i);
284  }
285  }
287  // }
288  // DO NOT UNCOMMENT FOR ANY RELEASE; ONLY FOR DEBUGGING! catch (const XMLException& toCatch) {
289  // edm::LogInfo ("DDLParser") << "\nPASS1: XMLException while processing files... \n"
290  // << "Exception message is: \n"
291  // << StrX(toCatch.getMessage()) << "\n" ;
292  // cms::concurrency::xercesTerminate();
293  // // FIX use this after DEPRECATED stuff removed: throw(DDException("See XML Exception above"));
294  // return -1;
295  // }
296  // PASS 2:
297 
298  DCOUT('P', "DDLParser::parse(): PASS2: Just before setting Xerces content and error handlers... ");
299 
300  // in cleaning up try-catch blocks 2007-06-26 I decided to remove
301  // this because of CMSSW rules. but keep the commented way I used to
302  // do it...
303  // DO NOT UNCOMMENT FOR ANY RELEASE; ONLY FOR DEBUGGING! try
304  // {
305  SAX2Parser_->setContentHandler(fileHandler_);
306 
307  // No need to validate (regardless of user's doValidation
308  // because the files have already been validated on the first pass.
309  // This optimization suggested by Martin Liendl.
310  // SAX2Parser_->setFeature(StrX("http://xml.org/sax/features/validation"), false); // optional
311  // SAX2Parser_->setFeature(StrX("http://xml.org/sax/features/namespaces"), false); // optional
312  // SAX2Parser_->setFeature(StrX("http://apache.org/xml/features/validation/dynamic"), false);
313 
314 
315  // Process files again.
316  for (size_t i = 0; i < fileNames_.size(); ++i)
317  {
318  // seal::SealTimer t("DDLParser: parsing all elements of file " +fileNames_[i].first);
319  if (!parsed_[i]) {
320  currFileName_ = fileNames_[i].second;
321  // std::cout << "currFileName = " << currFileName_ << std::endl;
323  // std::cout << "3) namespace = " << getNameSpace(extractFileName(currFileName_)) << std::endl;
324  parseFile(i);
325  parsed_[i] = true;
326  pair<std::string, std::string> namePair = fileNames_[i];
327  LogDebug ("DDLParser") << "Completed parsing file " << namePair.second << std::endl;
328  }
329  }
330  // }
331  // DO NOT UNCOMMENT FOR ANY RELEASE; ONLY FOR DEBUGGING! catch (const XMLException& toCatch) {
332  // edm::LogError ("DDLParser") << "\nPASS2: XMLException while processing files... \n"
333  // << "Exception message is: \n"
334  // << StrX(toCatch.getMessage()) << "\n" ;
335  // cms::concurrency::xercesTerminate();
336  // return -1;
337  // }
338  return 0;
339 }
340 
341 void
342 DDLParser::parseFile( const int& numtoproc )
343 {
344  if (!parsed_[numtoproc])
345  {
346  const std::string & fname = fileNames_[numtoproc].second;
347 
348  // in cleaning up try-catch blocks 2007-06-26 I decided to remove
349  // this because of CMSSW rules. but keep the commented way I used to
350  // do it...
351  // DO NOT UNCOMMENT FOR ANY RELEASE; ONLY FOR DEBUGGING! try
352  // {
354  SAX2Parser_->parse(currFileName_.c_str());
355  // }
356  // DO NOT UNCOMMENT FOR ANY RELEASE; ONLY FOR DEBUGGING! catch (const XMLException& toCatch)
357  // {
358  // std::string e("\nWARNING: DDLParser::parseFile, File: '");
359  // e += currFileName_ + "'\n"
360  // + "Exception message is: \n"
361  // + std::string(StrX(toCatch.getMessage()).localForm()) + "\n";
362  // throw(DDException(e));
363  // }
364  }
365  else
366  {
367  DCOUT('P', "\nWARNING: File " + fileNames_[numtoproc].first
368  + " has already been processed as " + fileNames_[numtoproc].second);
369  }
370 }
371 
372 void
374 {
375  fileNames_.clear();
376  parsed_.clear();
377 }
378 
381 {
382  std::string ret = "";
383  size_t bit = fullname.rfind('/');
384  if ( bit < fullname.size() - 2 ) {
385  ret=fullname.substr(bit+1);
386  }
387  return ret;
388 }
389 
392 {
393  size_t j = 0;
394  std::string ret="";
395  while (j < fname.size() && fname[j] != '.')
396  ++j;
397  if (j < fname.size() && fname[j] == '.')
398  ret = fname.substr(0, j);
399  return ret;
400 }
#define LogDebug(id)
int i
Definition: DBlmapReader.cc:9
int parse(const DDLDocumentProvider &dp)
Parse all files. Return is meaningless.
Definition: DDLParser.cc:204
std::map< int, bool > parsed_
Parse status of a given file.
Definition: DDLParser.h:152
std::pair< ALIstring, ALIstring > pss
Definition: Fit.h:27
std::string getNameSpace(const std::string &fname)
Definition: DDLParser.cc:391
void xercesTerminate()
Definition: Xerces.cc:22
std::string extractFileName(std::string fullname)
Definition: DDLParser.cc:380
DDLSAX2FileHandler * fileHandler_
Definition: DDLParser.h:163
SAX2XMLReader * SAX2Parser_
SAX2XMLReader is one way of parsing.
Definition: DDLParser.h:161
std::string currFileName_
Which file is currently being processed.
Definition: DDLParser.h:158
FileNameHolder fileNames_
List of files to be processed, obtained from the DDLDocumentProvider.
Definition: DDLParser.h:149
void xercesInitialize()
Definition: Xerces.cc:17
type of data representation of DDCompactView
Definition: DDCompactView.h:77
~DDLParser()
Destructor terminates the XMLPlatformUtils (as required by Xerces)
Definition: DDLParser.cc:52
DDLSAX2FileHandler is the SAX2 Handler for XML files found in the configuration file.
virtual const std::vector< std::string > & getFileList(void) const =0
Return a list of files as a vector of strings.
U second(std::pair< T, U > const &p)
void dumpElementTypeCounter()
This dumps some statistics on elements encountered in the file.
size_t isFound(const std::string &filename)
Is the file already known by the DDLParser? Returns 0 if not found, and index if found.
Definition: DDLParser.cc:79
DDLSAX2ExpressionHandler is the first pass SAX2 Handler for XML files found in the configuration file...
DDLSAX2ExpressionHandler * expHandler_
Definition: DDLParser.h:164
bool parseOneFile(const std::string &filename)
Process a single files.
Definition: DDLParser.cc:110
DDLSAX2Handler * errHandler_
Definition: DDLParser.h:165
int j
Definition: DBlmapReader.cc:9
void clearFiles()
Clear the file list - see Warning!
Definition: DDLParser.cc:373
DDLSAX2FileHandler * getDDLSAX2FileHandler()
To get the parent this class allows access to the handler.
Definition: DDLParser.cc:73
virtual const std::vector< std::string > & getURLList(void) const =0
Return a list of urls as a vector of strings.
void parseFile(const int &numtoproc)
Parse File. Just to hold some common looking code.
Definition: DDLParser.cc:342
#define DCOUT_V(M_v_Y, M_v_S)
Definition: DDdebug.h:54
std::vector< std::string > getFileList()
Return list of files.
Definition: DDLParser.cc:193
SAX2XMLReader * getXMLParser()
Get the SAX2Parser from the DDLParser. USE WITH CAUTION. Set your own handler, etc.
Definition: DDLParser.cc:67
string fname
main script
virtual void setNameSpace(const std::string &nms)
DDLDocumentProvider provides a set of URLs and filenames.
tuple filename
Definition: lut2db_cfg.py:20
DDLSAX2Handler inherits from Xerces C++ DefaultHandler.
std::string fullPath() const
Definition: FileInPath.cc:165
#define DCOUT(M_v_Y, M_v_S)
Definition: DDdebug.h:53
tuple size
Write out results.
bool isParsed(const std::string &filename)
Is the file already parsed?
Definition: DDLParser.cc:99
int nFiles_
Number of files + 1.
Definition: DDLParser.h:155