32#if CXX0X_UP_SUPPORTED == 0
33#define static_assert(x, y)
83static bool getAttribute(
const pugi::xml_node &node,
const std::string &attr_name, std::string &dst, Diagnostics &diag)
86 for (pugi::xml_attribute attr = node.first_attribute(); attr; attr = attr.next_attribute())
88 if (hasName(attr, attr_name))
97 diag.unexpectedNode(node, std::string(
"Duplicated attribute: ") + attr_name);
103static bool setAttribute(pugi::xml_node &node,
const std::string &attr_name,
const std::string &src, Diagnostics &diag)
105 node.append_attribute(attr_name.c_str()).set_value(src.c_str());
108static bool getAttribute(
const pugi::xml_node &node,
const std::string &attr_name,
int32_t &dst, Diagnostics &diag)
113 std::stringstream(val) >> dst;
116static bool setAttribute(pugi::xml_node &node,
const std::string &attr_name,
const int32_t &src, Diagnostics &diag)
118 static_assert(
sizeof(
int32_t) <=
sizeof(
long long),
119 "pugixml cannot handle int32_t natively. custom string conversion required");
120 node.append_attribute(attr_name.c_str()).set_value((
long long)src);
125bool parse<std::vector<etiss::fault::Fault>>(pugi::xml_node node, std::vector<etiss::fault::Fault> &dst,
129 std::string(
"> >(node, vector<Fault>, Diagnostics) called. "));
132 for (pugi::xml_node cnode = node.first_child(); cnode; cnode = cnode.next_sibling())
134 if (hasName(cnode,
"fault"))
137 if (parse<etiss::fault::Fault>(cnode, f, diag))
148 diag.ignoredNode(cnode,
"non \"fault\" node in fault list.");
155bool write<std::vector<etiss::fault::Fault>>(pugi::xml_node node,
const std::vector<etiss::fault::Fault> &src,
159 std::string(
"> >(node, vector<Fault>, Diagnostics) called. "));
162 for (
size_t i = 0; i < src.size(); ++i)
164 ret = ret && write(node.append_child(
"fault"), src[i], diag);
170bool parse<std::vector<etiss::fault::FaultRef>>(pugi::xml_node node, std::vector<etiss::fault::FaultRef> &dst,
174 std::string(
"> >(node, vector<FaultRef>, Diagnostics) called. "));
177 for (pugi::xml_node cnode = node.first_child(); cnode; cnode = cnode.next_sibling())
179 if (hasName(cnode,
"fault_ref"))
182 if (parse<etiss::fault::FaultRef>(cnode, f, diag))
193 diag.ignoredNode(cnode,
"non \"fault_ref\" node in list.");
200bool write<std::vector<etiss::fault::FaultRef>>(pugi::xml_node node,
const std::vector<etiss::fault::FaultRef> &src,
204 std::string(
"> >(node, vector<FaultRef>, Diagnostics) called. "));
207 for (
size_t i = 0; i < src.size(); ++i)
209 ret = ret && write(node.append_child(
"fault_ref"), src[i], diag);
220 static std::mutex mu;
221 std::lock_guard<std::mutex> lock(mu);
237 pugi::xml_document doc;
238 doc.load_string(
"<?xml version=\"1.0\"?>");
240 etiss::fault::xml::Diagnostics diag;
242 etiss::fault::xml::write<etiss::fault::Fault>(doc.append_child(
"fault"), *
this, diag);
244 std::stringstream ss;
254 for (std::vector<Trigger>::iterator iter =
triggers.begin(); iter !=
triggers.end(); ++iter)
256 iter->resolveTime(time);
261 for (std::vector<Trigger>::const_iterator iter =
triggers.begin(); iter !=
triggers.end(); ++iter)
263 if (!iter->isResolved())
272 pugi::xml_document doc;
273 doc.load_string(
"<?xml version=\"1.0\"?>");
275 etiss::fault::xml::Diagnostics diag;
277 etiss::fault::xml::write<etiss::fault::FaultRef>(doc.append_child(
"fault_ref"), *
this, diag);
279 std::stringstream ss;
297 if (it.second.name_ ==
name_)
309bool parseXML(std::vector<Fault> &vec,
const pugi::xml_document &doc, xml::Diagnostics &diag)
311 bool ret = parse(findSingleNode(doc.document_element(),
"definitions", diag), vec, diag);
316bool parseXML(std::vector<FaultRef> &vec,
const pugi::xml_document &doc, xml::Diagnostics &diag)
318 bool ret = parse(findSingleNode(doc.document_element(),
"initial", diag), vec, diag);
323bool writeXML(
const std::vector<Fault> &vec, std::ostream &out, std::ostream &diagnostics_out)
325 pugi::xml_document doc;
327 doc.load_string(
"<?xml version=\"1.0\"?>");
329 etiss::fault::xml::Diagnostics diag;
331 bool ret = write(doc.append_child(
"faults"), vec, diag);
335 diag.print(diagnostics_out);
344bool parse<etiss::fault::Fault>(pugi::xml_node node,
etiss::fault::Fault &f, Diagnostics &diag)
347 std::string(
"(node, Fault, Diagnostics) called. "));
351 for (pugi::xml_node cnode = node.first_child(); cnode; cnode = cnode.next_sibling())
353 if (hasName(cnode,
"triggers"))
355 for (pugi::xml_node ccnode = cnode.first_child(); ccnode; ccnode = ccnode.next_sibling())
357 if (hasName(ccnode,
"trigger"))
360 if (parse<etiss::fault::Trigger>(ccnode, t, diag))
371 diag.ignoredNode(ccnode,
"\"trigger\" node expected");
375 else if (hasName(cnode,
"actions"))
377 for (pugi::xml_node ccnode = cnode.first_child(); ccnode; ccnode = ccnode.next_sibling())
379 if (hasName(ccnode,
"action"))
382 if (parse<etiss::fault::Action>(ccnode, t, diag))
393 diag.ignoredNode(ccnode,
"\"trigger\" node expected");
399 diag.ignoredNode(cnode,
"unknown node");
406bool write<etiss::fault::Fault>(pugi::xml_node node,
const etiss::fault::Fault &f, Diagnostics &diag)
409 std::string(
"(node, Fault, Diagnostics) called. "));
413 pugi::xml_node triggers = node.append_child(
"triggers");
414 for (std::vector<etiss::fault::Trigger>::const_iterator iter = f.
triggers.begin(); iter != f.
triggers.end(); ++iter)
416 ok = ok && write<etiss::fault::Trigger>(triggers.append_child(
"trigger"), *iter, diag);
418 pugi::xml_node actions = node.append_child(
"actions");
419 for (std::vector<etiss::fault::Action>::const_iterator iter = f.
actions.begin(); iter != f.
actions.end(); ++iter)
421 ok = ok && write<etiss::fault::Action>(actions.append_child(
"action"), *iter, diag);
430 std::string(
"(node, Fault, Diagnostics) called. "));
440bool write<etiss::fault::FaultRef>(pugi::xml_node node,
const etiss::fault::FaultRef &fref, Diagnostics &diag)
443 std::string(
"(node, Fault, Diagnostics) called. "));
contains an action class that describes actions associated with a fault
contains the fault container class that stores triggers and actions for fault injection
contains a simple class that represents and resolves injector addresses as used by triggers (
contains the fault injector interface class.
contains the stressor class that loads and activates faults.
contains the Trigger class that defines conditions under which actions of a Fault need to be applied.
contains XML related functions.
static __inline__ uint64_t
static __inline__ int32_t
std::string toString() const
operator<< can be used.
bool set_fault_reference(const std::string &identifier)
std::string name_
string identifier, used to resolve actual reference via fault_
Fault fault_
referenced Fault, needs to be resolved during sim. runtime
bool resolve_reference() const
const std::string & get_name() const
bool isResoved() const
check all Triggers if they are resolved.
Fault()
Constructor: Generates a new Fault with unique ID.
std::string toString() const
operator<< can be used.
void resolveTime(uint64_t time)
Resolves time for all its Triggers.
std::vector< Trigger > triggers
contains the triggers for this fault
std::vector< Action > actions
contains the actions for this fault
static std::map< int32_t, Fault > & faults()
static map with all referencable faults.
static bool setAttribute(pugi::xml_node &node, const std::string &attr_name, const std::string &src, Diagnostics &diag)
static bool getAttribute(const pugi::xml_node &node, const std::string &attr_name, std::string &dst, Diagnostics &diag)
Parser/writer structure:
static int32_t uniqueFaultId()
bool writeXML(const std::vector< Fault > &vec, std::ostream &out, std::ostream &diagnostics_out=std::cout)
bool parseXML(pugi::xml_document &doc, std::istream &input, std::ostream &diagnostics_out=std::cout)
parse a XML document held in input stream and return as doc
void log(Verbosity level, std::string msg)
write log message at the given level.