25 #include "exceptions.h" 27 #include <interface/interface.h> 28 #include <libxml++/libxml++.h> 29 #include <utils/misc/string_conversions.h> 35 using namespace xmlpp;
47 dom =
new DomParser();
49 dom->set_substitute_entities();
50 dom->parse_file(config_filename);
51 root = dom->get_document()->get_root_node();
69 std::vector<InterfaceField>
72 vector<InterfaceField> result;
73 NodeSet set = node->find(
"field");
74 for (NodeSet::iterator i = set.begin(); i != set.end(); ++i) {
77 const Element *el = dynamic_cast<const Element *>(*i);
80 const Element::AttributeList &attrs = el->get_attributes();
81 for (Element::AttributeList::const_iterator iter = attrs.begin(); iter != attrs.end();
83 const Attribute *attr = *iter;
92 NodeSet nameset = (*i)->find(
"text()");
93 if (nameset.size() == 0) {
97 const TextNode *comment_node = dynamic_cast<const TextNode *>(nameset[0]);
104 f.
valid(reserved_names);
107 for (vector<InterfaceField>::iterator i = result.begin(); i != result.end(); ++i) {
108 for (vector<InterfaceField>::iterator j = i + 1; j != result.end(); ++j) {
109 if ((*i).getName() == (*j).getName()) {
124 std::vector<InterfacePseudoMap>
127 vector<InterfacePseudoMap> result;
128 NodeSet set = node->find(
"pseudomap");
129 for (NodeSet::iterator i = set.begin(); i != set.end(); ++i) {
130 const Element *el = dynamic_cast<const Element *>(*i);
131 std::string pm_name, pm_type, pm_keytype;
135 attr = el->get_attribute(
"name");
138 pm_name = attr->get_value();
140 attr = el->get_attribute(
"type");
143 pm_type = attr->get_value();
145 attr = el->get_attribute(
"keytype");
148 pm_keytype = attr->get_value();
153 NodeSet comment_set = (*i)->find(
"text()");
154 if (comment_set.size() == 0) {
157 std::string pm_comment =
"";
158 const TextNode *comment_node = dynamic_cast<const TextNode *>(comment_set[0]);
160 pm_comment = comment_node->get_content();
167 NodeSet ref_nodes = (*i)->find(
"mapref");
168 for (NodeSet::iterator r = ref_nodes.begin(); r != ref_nodes.end(); ++r) {
169 NodeSet ref_set = (*r)->find(
"text()");
170 if (ref_set.size() == 0) {
174 const Element *el = dynamic_cast<const Element *>(*r);
176 attr = el->get_attribute(
"key");
179 std::string mapref_key = attr->get_value();
181 const TextNode *text_node = dynamic_cast<const TextNode *>(ref_set[0]);
185 for (vector<InterfaceField>::iterator j = fields.begin(); j != fields.end(); ++j) {
186 if ((*j).getName() == text_node->get_content()) {
188 if (j->getLengthValue() > 0) {
190 "pseudomap references may only point to non-map types");
192 pm.
addRef(text_node->get_content(), mapref_key);
208 result.push_back(pm);
213 for (vector<InterfacePseudoMap>::iterator i = result.begin(); i != result.end(); ++i) {
214 for (vector<InterfacePseudoMap>::iterator j = i + 1; j != result.end(); ++j) {
215 if ((*i).getName() == (*j).getName()) {
219 for (vector<InterfaceField>::iterator f = fields.begin(); f != fields.end(); ++f) {
220 if (i->getName() == f->getName()) {
236 for (vector<InterfaceField>::iterator i = fields.begin(); i != fields.end(); ++i) {
237 cout <<
" Field: name=" << (*i).getName() <<
" type=" << (*i).getType();
238 if ((*i).getLength() !=
"") {
239 cout <<
" length=" << (*i).getLength();
241 if ((*i).getValidFor() !=
"") {
242 cout <<
" validfor=" << (*i).getValidFor();
244 if ((*i).getDefaultValue() !=
"") {
245 cout <<
" default=" << (*i).getDefaultValue();
247 vector<string> flags = (*i).getFlags();
248 if (flags.size() > 0) {
250 vector<string>::iterator j = flags.begin();
251 while (j != flags.end()) {
254 if (j != flags.end()) {
269 for (vector<InterfacePseudoMap>::iterator i = pseudo_maps.begin(); i != pseudo_maps.end(); ++i) {
270 cout <<
" PseudoMap: name=" << i->getName() <<
" type=" << i->getType()
271 <<
" keytype=" << i->getKeyType() << endl;
274 InterfacePseudoMap::RefList::iterator j;
275 for (j = reflist.begin(); j != reflist.end(); ++j) {
276 cout <<
" Ref: field=" << j->first <<
" key=" << j->second << endl;
292 vector<InterfaceEnumConstant> &enum_constants,
293 vector<InterfaceField> & data_fields,
294 vector<InterfacePseudoMap> & pseudo_maps,
295 vector<InterfaceMessage> & messages)
297 cout <<
"Constants" << endl;
298 for (vector<InterfaceConstant>::iterator i = constants.begin(); i != constants.end(); ++i) {
299 cout <<
" Constant: name=" << (*i).getName() <<
" type=" << (*i).getType()
300 <<
" value=" << (*i).getValue() << endl;
303 cout <<
"EnumConstants" << endl;
304 for (vector<InterfaceEnumConstant>::iterator i = enum_constants.begin();
305 i != enum_constants.end();
307 cout <<
" EnumConstant: name=" << (*i).get_name() << endl;
308 vector<InterfaceEnumConstant::EnumItem> items = (*i).get_items();
309 vector<InterfaceEnumConstant::EnumItem>::iterator j;
310 for (j = items.begin(); j != items.end(); ++j) {
311 cout <<
" Item: " << j->name <<
"(" << j->comment <<
")" << endl;
315 cout <<
"Data block" << endl;
316 printFields(data_fields);
317 printPseudoMaps(pseudo_maps);
318 for (vector<InterfaceMessage>::iterator i = messages.begin(); i != messages.end(); ++i) {
319 cout <<
"Message: name=" << (*i).getName() << endl;
320 vector<InterfaceField> msg_fields = (*i).getFields();
321 printFields(msg_fields);
329 printParsed(constants, enum_constants, data_fields, pseudo_maps, messages);
339 enum_constants.clear();
347 const Element *el = dynamic_cast<const Element *>(root);
351 attr = el->get_attribute(
"name");
355 name = attr->get_value();
356 if (name.length() > INTERFACE_TYPE_SIZE_) {
358 INTERFACE_TYPE_SIZE_);
361 attr = el->get_attribute(
"author");
363 author = attr->get_value();
365 attr = el->get_attribute(
"year");
367 year = attr->get_value();
369 attr = el->get_attribute(
"created");
371 creation_date = attr->get_value();
381 NodeSet constants_set = root->find(
"/interface/constants");
382 if (constants_set.size() > 1) {
385 if (constants_set.size() == 1) {
387 set = constants_set[0]->find(
"constant");
388 for (NodeSet::iterator i = set.begin(); i != set.end(); ++i) {
390 NodeSet nameset = (*i)->find(
"text()");
391 if (nameset.size() == 0) {
394 const TextNode *comment_node = dynamic_cast<const TextNode *>(nameset[0]);
398 std::string const_comment = comment_node->get_content();
404 std::string const_name;
406 el = dynamic_cast<const Element *>(*i);
410 attr = el->get_attribute(
"type");
414 type = attr->get_value();
416 attr = el->get_attribute(
"name");
420 const_name = attr->get_value();
422 attr = el->get_attribute(
"value");
426 value = attr->get_value();
434 constants.push_back(constant);
441 for (vector<InterfaceConstant>::iterator i = constants.begin(); i != constants.end(); ++i) {
442 for (vector<InterfaceConstant>::iterator j = i + 1; j != constants.end(); ++j) {
443 if ((*i).getName() == (*j).getName()) {
453 set = constants_set[0]->find(
"enum");
454 for (NodeSet::iterator i = set.begin(); i != set.end(); ++i) {
455 std::string enum_comment;
456 NodeSet comment_set = (*i)->find(
"comment/text()");
457 if (comment_set.size() == 0) {
460 const TextNode *comment_node = dynamic_cast<const TextNode *>(comment_set[0]);
462 enum_comment = comment_node->get_content();
469 el = dynamic_cast<const Element *>(*i);
473 attr = el->get_attribute(
"name");
477 enum_name = attr->get_value();
486 NodeSet items = (*i)->find(
"item");
487 if (items.size() == 0) {
491 for (NodeSet::iterator j = items.begin(); j != items.end(); ++j) {
492 std::string item_name;
493 std::string item_value;
494 el = dynamic_cast<const Element *>(*j);
498 attr = el->get_attribute(
"name");
502 item_name = attr->get_value();
505 val_attr = el->get_attribute(
"value");
507 item_value = val_attr->get_value();
514 comment_set = (*j)->find(
"text()");
515 if (comment_set.size() == 0) {
518 const TextNode *comment_node = dynamic_cast<const TextNode *>(comment_set[0]);
520 if (item_value !=
"") {
522 comment_node->get_content(),
525 enum_constant.
add_item(item_name, comment_node->get_content());
532 enum_constants.push_back(enum_constant);
534 vector<InterfaceEnumConstant>::iterator i;
535 for (i = enum_constants.begin(); i != enum_constants.end(); ++i) {
536 vector<InterfaceEnumConstant>::iterator j;
537 for (j = i + 1; j != enum_constants.end(); ++j) {
538 if (i->get_name() == j->get_name()) {
549 set = root->find(
"/interface/data");
550 if (set.size() > 1) {
552 }
else if (set.size() == 0) {
556 data_fields = getFields(set[0], reserved_names_interface());
557 if (data_fields.size() == 0) {
561 pseudo_maps = getPseudoMaps(set[0], data_fields);
563 NodeSet comment_set = root->find(
"/interface/data/comment/text()");
564 if (comment_set.size() == 0) {
567 const TextNode *comment_node = dynamic_cast<const TextNode *>(comment_set[0]);
569 data_comment = comment_node->get_content();
578 set = root->find(
"/interface/message");
579 for (NodeSet::iterator i = set.begin(); i != set.end(); ++i) {
580 std::string msg_name;
581 std::string msg_comment;
583 el = dynamic_cast<const Element *>(*i);
586 attr = el->get_attribute(
"name");
590 msg_name = attr->get_value();
595 comment_set = (*i)->find(
"text()");
596 if (comment_set.size() == 0) {
599 comment_node = dynamic_cast<const TextNode *>(comment_set[0]);
601 msg_comment = comment_node->get_content();
606 vector<InterfaceField> msg_fields = getFields(*i, reserved_names_message());
608 NodeSet ref_nodes = (*i)->find(
"ref/text()");
609 for (NodeSet::iterator r = ref_nodes.begin(); r != ref_nodes.end(); ++r) {
610 const TextNode *text_node = dynamic_cast<const TextNode *>(*r);
614 for (vector<InterfaceField>::iterator j = data_fields.begin(); j != data_fields.end();
616 if ((*j).getName() == text_node->get_content()) {
618 msg_fields.push_back(*j);
630 for (vector<InterfaceField>::iterator k = msg_fields.begin(); k != msg_fields.end(); ++k) {
631 for (vector<InterfaceField>::iterator j = k + 1; j != msg_fields.end(); ++j) {
632 if ((*k).getName() == (*j).getName()) {
641 messages.push_back(msg);
682 return creation_date;
689 std::vector<InterfaceConstant>
699 std::vector<InterfaceEnumConstant>
702 return enum_constants;
709 std::vector<InterfaceField>
719 std::vector<InterfacePseudoMap>
739 std::vector<InterfaceMessage>
InterfaceParser(std::string config_filename)
Constructor.
void setFields(const std::vector< InterfaceField > &fields)
Set fields of message.
Thrown if document contains illegal content.
Interface generator internal representation of a constant as parsed from the XML template file.
void printParsed(std::vector< InterfaceConstant > &constants, std::vector< InterfaceEnumConstant > &enum_constants, std::vector< InterfaceField > &data_fields, std::vector< InterfacePseudoMap > &pseudo_maps, std::vector< InterfaceMessage > &messages)
Print parsed config.
void parse()
Parse config.
Interface generator internal representation of a enum constant as parsed from the XML template file.
void printPseudoMaps(std::vector< InterfacePseudoMap > &pseudo_maps)
Print pseudo maps.
std::vector< InterfaceField > getFields(xmlpp::Node *node, const std::set< std::string > &reserved_names)
Get parsed fields.
void printFields(std::vector< InterfaceField > &fields)
Print fields.
std::string getName() const
Get name of field.
Interface generator internal representation of a field as parsed from the XML template file.
void print()
Print parsed data.
Interface generator internal representation of a message as parsed from the XML template file.
static int to_int(std::string s)
Convert string to an int value.
Thrown if illegal value is supplied.
std::vector< InterfacePseudoMap > getPseudoMaps()
Get data pseudo maps.
~InterfaceParser()
Destructor.
std::string getInterfaceAuthor()
Get interface author.
std::string getDataComment()
Get data comment.
Base class for exceptions in Fawkes.
std::list< std::pair< std::string, std::string > > RefList
Reference list.
Thrown if name is ambiguous.
void setComment(const std::string &comment)
Set comment of field.
std::vector< InterfaceMessage > getMessages()
Get messages.
std::vector< InterfaceField > getDataFields()
Get data fields.
Interface generator internal representation of a pseudo map as parsed from the XML template file.
void valid(const std::set< std::string > &reserved_names)
Assert validity.
std::string getInterfaceCreationDate()
Get interface creation date as string Only valid after parse().
void print_trace()
Prints trace to stderr.
void addRef(std::string fieldname, std::string key)
Add reference.
std::string getInterfaceName()
Get interface name.
Thrown if document was invalid.
std::vector< InterfaceEnumConstant > getEnumConstants()
Get enum constants.
void valid()
Assert validity.
std::string getInterfaceYear()
Get interface copyright year.
void add_item(std::string name, std::string comment)
Add an item without custom value.
std::vector< InterfaceConstant > getConstants()
Get constants.
void setAttribute(const std::string &attr_name, const std::string &attr_value)
Set attribute.
Thrown if illegal type is supplied.