Back to home page

Project CMSSW displayed by LXR

 
 

    


File indexing completed on 2023-03-17 11:10:30

0001 #include "xercesc/sax2/SAX2XMLReader.hpp"
0002 #include <xercesc/sax2/XMLReaderFactory.hpp>
0003 #include "xercesc/sax2/DefaultHandler.hpp"
0004 #include "xercesc/sax2/Attributes.hpp"
0005 #include "FWCore/Utilities/interface/Exception.h"
0006 #include <xercesc/framework/MemBufInputSource.hpp>
0007 XERCES_CPP_NAMESPACE_USE
0008 #include "IORawData/CaloPatterns/interface/HcalPatternXMLParser.h"
0009 #include <ostream>
0010 
0011 class HcalPatternXMLParserImpl {
0012 public:
0013   std::unique_ptr<SAX2XMLReader> parser;
0014 };
0015 
0016 HcalPatternXMLParser::HcalPatternXMLParser() { m_parser = nullptr; }
0017 HcalPatternXMLParser::~HcalPatternXMLParser() {
0018   if (m_parser != nullptr)
0019     delete m_parser;
0020 }
0021 
0022 /*
0023     Example
0024     <pre>
0025     <CFGBrick>
0026       <Parameter name='IETA' type='int'>14</Parameter>
0027       <Parameter name='IPHI' type='int'>2</Parameter>
0028       <Parameter name='DEPTH' type='int'>1</Parameter>
0029       <Parameter name='CRATE' type='int'>1</Parameter>
0030       <Parameter name='SLOT' type='int'>8</Parameter>
0031       <Parameter name='TOPBOTTOM' type='int'>0</Parameter>
0032       <Parameter name='CHANNEL' type='int'>6</Parameter>
0033       <Parameter name='LUT_TYPE' type='int'>1</Parameter>
0034       <Parameter name='CREATIONTAG' type='string'>Identity</Parameter>
0035       <Parameter name='CREATIONSTAMP' type='string'>2005-03-08 11:44:34</Parameter>
0036       <Parameter name='FORMATREVISION' type='string'>1</Parameter>
0037       <Parameter name='TARGETFIRMWARE' type='string'>0</Parameter>
0038       <Parameter name='GENERALIZEDINDEX' type='int'>140211</Parameter>
0039       <Data elements='128' encoding='hex'> .. </Data>
0040     </CFGBrick>
0041     </pre>
0042   */
0043 
0044 class ConfigurationDBHandler : public DefaultHandler {
0045   enum { md_Idle, md_Parameter, md_Data } m_mode;
0046 
0047 public:
0048   ConfigurationDBHandler(std::map<std::string, std::string>& parameters,
0049                          std::vector<std::string>& items,
0050                          std::string& encoding)
0051       : m_dataEncoding(encoding), m_items(items), m_parameters(parameters) {
0052     m_mode = md_Idle;
0053     xc_Parameter = XMLString::transcode("Parameter");
0054     xc_Data = XMLString::transcode("Data");
0055     xc_name = XMLString::transcode("name");
0056     xc_type = XMLString::transcode("type");
0057     xc_elements = XMLString::transcode("elements");
0058     xc_encoding = XMLString::transcode("encoding");
0059     m_items.clear();
0060     m_parameters.clear();
0061   }
0062   ~ConfigurationDBHandler() override {
0063     XMLString::release(&xc_Parameter);
0064     XMLString::release(&xc_Data);
0065     XMLString::release(&xc_name);
0066     XMLString::release(&xc_type);
0067     XMLString::release(&xc_elements);
0068     XMLString::release(&xc_encoding);
0069   }
0070   void startElement(const XMLCh* const uri,
0071                     const XMLCh* const localname,
0072                     const XMLCh* const qname,
0073                     const Attributes& attrs) override;
0074   void endElement(const XMLCh* const uri, const XMLCh* const localname, const XMLCh* const qname) override;
0075   void characters(const XMLCh* const chars, const XMLSize_t length) override;
0076   void ignorableWhitespace(const XMLCh* const chars, const XMLSize_t length) override;
0077 
0078 private:
0079   inline bool cvt2String(const XMLCh* val, std::string& ou) {
0080     if (val == nullptr)
0081       return false;
0082     char* tool = XMLString::transcode(val);
0083     ou = tool;
0084     XMLString::release(&tool);
0085     return true;
0086   }
0087   XMLCh *xc_Parameter, *xc_Data, *xc_name, *xc_type, *xc_elements, *xc_encoding;
0088   std::string m_pname, m_ptype, m_text;
0089   int n_elements;
0090   std::string& m_dataEncoding;
0091   std::vector<std::string>& m_items;
0092   std::map<std::string, std::string>& m_parameters;
0093   char m_workc[512];
0094   XMLCh m_workx[256];
0095 };
0096 
0097 void ConfigurationDBHandler::startElement(const XMLCh* const uri,
0098                                           const XMLCh* const localname,
0099                                           const XMLCh* const qname,
0100                                           const Attributes& attrs) {
0101   if (m_mode != md_Idle)
0102     return;
0103   if (!XMLString::compareIString(localname, xc_Parameter)) {
0104     // parameter name
0105     if (!cvt2String(attrs.getValue(xc_name), m_pname))
0106       return;
0107     // parameter type
0108     if (!cvt2String(attrs.getValue(xc_type), m_ptype))
0109       return;
0110     // switch mode
0111     m_mode = md_Parameter;
0112     m_text = "";
0113   } else if (!XMLString::compareIString(localname, xc_Data)) {
0114     // elements
0115     std::string strElements;
0116     if (!cvt2String(attrs.getValue(xc_elements), strElements))
0117       return;
0118     n_elements = atoi(strElements.c_str());
0119     // encoding
0120     m_dataEncoding = "";
0121     cvt2String(attrs.getValue(xc_encoding), m_dataEncoding);
0122     // switch mode
0123     m_mode = md_Data;
0124     m_text = "";
0125   }
0126 }
0127 void ConfigurationDBHandler::endElement(const XMLCh* const uri,
0128                                         const XMLCh* const localname,
0129                                         const XMLCh* const qname) {
0130   if (m_mode == md_Idle)
0131     return;
0132 
0133   if (m_mode == md_Parameter) {
0134     m_parameters[m_pname] = m_text;  // ignore the type for now...
0135   } else if (m_mode == md_Data) {
0136     // parse the text
0137     std::string entry;
0138     for (std::string::iterator q = m_text.begin(); q != m_text.end(); q++) {
0139       if (isspace(*q)) {
0140         if (entry.empty())
0141           continue;
0142         m_items.push_back(entry);
0143         entry = "";
0144       } else
0145         entry += *q;
0146     }
0147   }
0148 
0149   m_mode = md_Idle;
0150 }
0151 void ConfigurationDBHandler::ignorableWhitespace(const XMLCh* chars, const XMLSize_t length) {
0152   if (m_mode == md_Idle)
0153     return;
0154   m_text += ' ';
0155 }
0156 void ConfigurationDBHandler::characters(const XMLCh* chars, const XMLSize_t length) {
0157   if (m_mode == md_Idle)
0158     return;
0159   unsigned int offset = 0;
0160   while (offset < length) {
0161     unsigned int i = 0;
0162     for (i = 0; i < length - offset && i < 255; i++)
0163       m_workx[i] = chars[i + offset];
0164     m_workx[i] = 0;  // terminate string
0165     XMLString::transcode(m_workx, m_workc, 511);
0166     m_text += m_workc;
0167     offset += i;
0168   }
0169 }
0170 
0171 void HcalPatternXMLParser::parse(const std::string& xmlDocument,
0172                                  std::map<std::string, std::string>& parameters,
0173                                  std::vector<std::string>& items,
0174                                  std::string& encoding) {
0175   // uses XERCES SAX2 parser
0176   ConfigurationDBHandler handler(parameters, items, encoding);
0177 
0178   try {
0179     if (m_parser == nullptr) {
0180       m_parser = new HcalPatternXMLParserImpl();
0181       m_parser->parser = std::unique_ptr<xercesc::SAX2XMLReader>(xercesc::XMLReaderFactory::createXMLReader());
0182     }
0183 
0184     MemBufInputSource src((const unsigned char*)xmlDocument.c_str(), xmlDocument.length(), "hcal::PatternReader");
0185     m_parser->parser->setContentHandler(&handler);
0186     m_parser->parser->parse(src);
0187   } catch (std::exception& ex) {
0188     throw cms::Exception("ParseError") << ex.what();
0189   }
0190 }
0191 
0192 void HcalPatternXMLParser::parse(const std::string& xmlDocument,
0193                                  std::map<std::string, std::string>& parameters,
0194                                  std::vector<uint32_t>& data) {
0195   std::vector<std::string> items;
0196   std::string encoding;
0197 
0198   this->parse(xmlDocument, parameters, items, encoding);
0199   int formatting = 0;
0200   if (encoding == "dec")
0201     formatting = 10;
0202   if (encoding == "hex")
0203     formatting = 16;
0204 
0205   data.clear();
0206   for (std::vector<std::string>::const_iterator i = items.begin(); i != items.end(); i++)
0207     data.push_back(strtol(i->c_str(), nullptr, formatting));
0208 }