Vaucanson  1.4.1
parsers.hxx
1 // parsers.hxx: this file is part of the Vaucanson project.
2 //
3 // Vaucanson, a generic library for finite state machines.
4 //
5 // Copyright (C) 2005, 2006, 2007, 2008, 2009 The Vaucanson Group.
6 //
7 // This program is free software; you can redistribute it and/or
8 // modify it under the terms of the GNU General Public License
9 // as published by the Free Software Foundation; either version 2
10 // of the License, or (at your option) any later version.
11 //
12 // The complete GNU General Public Licence Notice can be found as the
13 // `COPYING' file in the root directory.
14 //
15 // The Vaucanson Group consists of people listed in the `AUTHORS' file.
16 //
17 
18 #ifndef VCSN_XML_PARSERS_HXX
19 # define VCSN_XML_PARSERS_HXX
20 
21 # include <fstream>
22 # include <cstring>
23 # include <xercesc/sax2/XMLReaderFactory.hpp>
24 
26 
27 namespace vcsn
28 {
29  namespace xml
30  {
31  /*
32  * Parser class.
33  */
34  const std::string&
35  Parser::get_xsd_path ()
36  {
37  static std::string path;
38  static const char xsd[] = "vaucanson.xsd";
39 
40  // Do not probe the XSD path twice.
41  if (not path.empty())
42  return path;
43 
44  const char* base_path = getenv("VCSN_DATA_PATH");
45 
46  if (base_path == 0)
47  base_path = VCSN_DATA_PATH;
48 
49  while (*base_path)
50  {
51  const char* sep = strchr(base_path, ':');
52 
53  if (sep == base_path)
54  {
55  // Ignore an empty path.
56  ++ base_path;
57  continue;
58  }
59 
60  // Did we find a colon?
61  if (sep > 0)
62  path = std::string(base_path, sep - base_path);
63  else
64  path = std::string(base_path);
65  path = path + "/" + xsd;
66  base_path = sep + 1;
67 
68  // Is that the right directory?
69  if (std::ifstream(path.c_str()).good())
70  return path;
71 
72  // No colon found, do not loop.
73  if (sep == 0)
74  break;
75  }
76 
77  // Complain with the last directory used.
78  FAIL (std::string("Error: cannot open `") + path + "'.\n"
79  "Please set VCSN_DATA_PATH to the Vaucanson data directory,\n"
80  "containing `" + xsd + "'.");
81  return path;
82  }
83 
84  Parser::Parser (bool check)
85  : parser_(0), eq_()
86  {
87  using namespace xercesc;
88  parser_ = XMLReaderFactory::createXMLReader();
89 
90  if (check)
91  {
92  parser_->setFeature(XMLUni::fgSAX2CoreNameSpaces, true);
93  parser_->setFeature(XMLUni::fgSAX2CoreValidation, true);
94  parser_->setFeature(XMLUni::fgXercesSchema, true);
95  parser_->setFeature(XMLUni::fgXercesSchemaFullChecking, true);
96  parser_->setFeature(XMLUni::fgXercesValidationErrorAsFatal, true);
97  parser_->setFeature(XMLUni::fgXercesUseCachedGrammarInParse, true);
98  parser_->setFeature(XMLUni::fgXercesCacheGrammarFromParse, true);
99  XMLCh* xsd = transcode(VCSN_XMLNS " " + get_xsd_path());
100  parser_->setProperty(XMLUni::fgXercesSchemaExternalSchemaLocation, xsd);
101  XMLString::release(&xsd);
102  }
103 
104  err_handler_ = new ErrHandler();
105  parser_->setErrorHandler(err_handler_);
106  }
107 
108  Parser::~Parser ()
109  {
110  delete parser_;
111  delete err_handler_;
112  }
113 
114  /*
115  * AutParser class.
116  */
117  template <typename Auto>
118  AutParser<Auto>::AutParser (Auto& a, bool check)
119  : Parser(check), a_(a)
120  {
121  doc_handler_ = new DocAutHandler<Auto>(parser_, *err_handler_, a_, eq_);
122  parser_->setContentHandler(doc_handler_);
123  }
124 
125  template <typename Auto>
126  AutParser<Auto>::~AutParser ()
127  {
128  delete doc_handler_;
129  }
130 
131  template <typename Auto>
132  void
133  AutParser<Auto>::parse (std::istream& in)
134  {
135  CxxInputSource is(&in);
136  parser_->parse(is);
137  }
138 
139  /*
140  * RegExpParser class.
141  */
142  template <typename T>
143  RegExpParser<T>::RegExpParser (T& r, bool check)
144  : Parser(check), r_(r)
145  {
146  doc_handler_ = new DocRegExpHandler<T>(parser_, *err_handler_, r_, eq_);
147  parser_->setContentHandler(doc_handler_);
148  }
149 
150  template <typename T>
151  RegExpParser<T>::~RegExpParser ()
152  {
153  delete doc_handler_;
154  }
155 
156  template <typename T>
157  void
158  RegExpParser<T>::parse (std::istream& in)
159  {
160  CxxInputSource is(&in);
161  parser_->parse(is);
162  }
163  } // !xml
164 } // !vcsn
165 
166 #endif // !VCSN_XML_PARSERS_HXX