X-Git-Url: http://info.iut-bm.univ-fcomte.fr/pub/gitweb/simgrid.git/blobdiff_plain/f11b7e2b68cf873f304062d21d49419899093aec..df7dd242cb1d449653076cc87a6020b2c6a8cbf5:/src/surf/xml/surfxml_sax_cb.cpp diff --git a/src/surf/xml/surfxml_sax_cb.cpp b/src/surf/xml/surfxml_sax_cb.cpp index b7f147c737..dfcc8c91ea 100644 --- a/src/surf/xml/surfxml_sax_cb.cpp +++ b/src/surf/xml/surfxml_sax_cb.cpp @@ -7,23 +7,37 @@ #include "simgrid/sg_config.h" #include "src/kernel/routing/NetPoint.hpp" #include "src/surf/network_interface.hpp" -#include "xbt/file.h" +#include "xbt/file.hpp" #include "src/surf/xml/platf_private.hpp" #include #include #include +#include #include +#include +#include +#include XBT_LOG_NEW_DEFAULT_SUBCATEGORY(surf_parse, surf, "Logging specific to the SURF parsing module"); -SG_BEGIN_DECL() +extern "C" { int ETag_surfxml_include_state(); #include "simgrid_dtd.c" -char* surf_parsed_filename = nullptr; // to locate parse error messages +/* + * Stuff relative to the tag + */ +static std::vector surf_input_buffer_stack; +static std::vector surf_file_to_parse_stack; +static std::vector surf_parsed_filename_stack; + +static inline const char* surf_parsed_filename() // to locate parse error messages +{ + return surf_parsed_filename_stack.empty() ? nullptr : surf_parsed_filename_stack.back().c_str(); +} std::vector parsed_link_list; /* temporary store of current list link of a route */ @@ -35,7 +49,7 @@ void surf_parse_assert(bool cond, std::string msg) if (not cond) { int lineno = surf_parse_lineno; cleanup(); - XBT_ERROR("Parse error at %s:%d: %s", surf_parsed_filename, lineno, msg.c_str()); + XBT_ERROR("Parse error at %s:%d: %s", surf_parsed_filename(), lineno, msg.c_str()); surf_exit(); xbt_die("Exiting now"); } @@ -45,7 +59,7 @@ void surf_parse_error(std::string msg) { int lineno = surf_parse_lineno; cleanup(); - XBT_ERROR("Parse error at %s:%d: %s", surf_parsed_filename, lineno, msg.c_str()); + XBT_ERROR("Parse error at %s:%d: %s", surf_parsed_filename(), lineno, msg.c_str()); surf_exit(); xbt_die("Exiting now"); } @@ -59,9 +73,8 @@ void surf_parse_assert_netpoint(std::string hostname, std::string pre, std::stri std::vector list; simgrid::s4u::Engine::getInstance()->getNetpointList(&list); - std::sort(list.begin(), list.end(), - [](simgrid::kernel::routing::NetPoint* a, simgrid::kernel::routing::NetPoint* b) { - return a->name() < b->name(); + std::sort(list.begin(), list.end(), [](simgrid::kernel::routing::NetPoint* a, simgrid::kernel::routing::NetPoint* b) { + return a->getName() < b->getName(); }); bool first = true; for (auto const& np : list) { @@ -71,7 +84,7 @@ void surf_parse_assert_netpoint(std::string hostname, std::string pre, std::stri if (not first) msg += ","; first = false; - msg += "'" + np->name() + "'"; + msg += "'" + np->getName() + "'"; if (msg.length() > 4096) { msg.pop_back(); // remove trailing quote msg += "...(list truncated)......"; @@ -83,7 +96,7 @@ void surf_parse_assert_netpoint(std::string hostname, std::string pre, std::stri void surf_parse_warn(std::string msg) { - XBT_WARN("%s:%d: %s", surf_parsed_filename, surf_parse_lineno, msg.c_str()); + XBT_WARN("%s:%d: %s", surf_parsed_filename(), surf_parse_lineno, msg.c_str()); } double surf_parse_get_double(std::string s) @@ -138,18 +151,51 @@ static std::vector* explodesRadical(std::string radicals) return exploded; } -struct unit_scale { - const char *unit; - double scale; +namespace { +class unit_scale : public std::unordered_map { +public: + using std::unordered_map::unordered_map; + // tuples are : + explicit unit_scale(std::initializer_list> generators); }; +unit_scale::unit_scale(std::initializer_list> generators) +{ + for (const auto& gen : generators) { + const std::string& unit = std::get<0>(gen); + double value = std::get<1>(gen); + const int base = std::get<2>(gen); + const bool abbrev = std::get<3>(gen); + double mult; + std::vector prefixes; + switch (base) { + case 2: + mult = 1024.0; + prefixes = abbrev ? std::vector{"Ki", "Mi", "Gi", "Ti", "Pi", "Ei", "Zi", "Yi"} + : std::vector{"kibi", "mebi", "gibi", "tebi", "pebi", "exbi", "zebi", "yobi"}; + break; + case 10: + mult = 1000.0; + prefixes = abbrev ? std::vector{"k", "M", "G", "T", "P", "E", "Z", "Y"} + : std::vector{"kilo", "mega", "giga", "tera", "peta", "exa", "zeta", "yotta"}; + break; + default: + THROW_IMPOSSIBLE; + } + emplace(unit, value); + for (const auto& prefix : prefixes) { + value *= mult; + emplace(prefix + unit, value); + } + } +} +} + /* Note: field `unit' for the last element of parameter `units' should be nullptr. */ -static double surf_parse_get_value_with_unit(const char* string, const struct unit_scale* units, - const char* entity_kind, std::string name, const char* error_msg, - const char* default_unit) +static double surf_parse_get_value_with_unit(const char* string, const unit_scale& units, const char* entity_kind, + std::string name, const char* error_msg, const char* default_unit) { char* ptr; - int i; errno = 0; double res = strtod(string, &ptr); if (errno == ERANGE) @@ -163,124 +209,46 @@ static double surf_parse_get_value_with_unit(const char* string, const struct un XBT_WARN("Deprecated unit-less value '%s' for %s %s. %s", string, entity_kind, name.c_str(), error_msg); ptr = (char*)default_unit; } - for (i = 0; units[i].unit != nullptr && strcmp(ptr, units[i].unit) != 0; i++); - - if (units[i].unit != nullptr) - res *= units[i].scale; - else + auto u = units.find(ptr); + if (u == units.end()) surf_parse_error(std::string("unknown unit: ") + ptr); - return res; + return res * u->second; } double surf_parse_get_time(const char* string, const char* entity_kind, std::string name) { - const struct unit_scale units[] = { - { "w", 7 * 24 * 60 * 60 }, - { "d", 24 * 60 * 60 }, - { "h", 60 * 60 }, - { "m", 60 }, - { "s", 1.0 }, - { "ms", 1e-3 }, - { "us", 1e-6 }, - { "ns", 1e-9 }, - { "ps", 1e-12 }, - { nullptr, 0 } - }; + static const unit_scale units{{"w", 7 * 24 * 60 * 60}, + {"d", 24 * 60 * 60}, + {"h", 60 * 60}, + {"m", 60}, + {"s", 1.0}, + {"ms", 1e-3}, + {"us", 1e-6}, + {"ns", 1e-9}, + {"ps", 1e-12}}; return surf_parse_get_value_with_unit(string, units, entity_kind, name, "Append 's' to your time to get seconds", "s"); } double surf_parse_get_size(const char* string, const char* entity_kind, std::string name) { - const struct unit_scale units[] = { - { "EiB", pow(1024, 6) }, - { "PiB", pow(1024, 5) }, - { "TiB", pow(1024, 4) }, - { "GiB", pow(1024, 3) }, - { "MiB", pow(1024, 2) }, - { "KiB", 1024 }, - { "EB", 1e18 }, - { "PB", 1e15 }, - { "TB", 1e12 }, - { "GB", 1e9 }, - { "MB", 1e6 }, - { "kB", 1e3 }, - { "B", 1.0 }, - { "Eib", 0.125 * pow(1024, 6) }, - { "Pib", 0.125 * pow(1024, 5) }, - { "Tib", 0.125 * pow(1024, 4) }, - { "Gib", 0.125 * pow(1024, 3) }, - { "Mib", 0.125 * pow(1024, 2) }, - { "Kib", 0.125 * 1024 }, - { "Eb", 0.125 * 1e18 }, - { "Pb", 0.125 * 1e15 }, - { "Tb", 0.125 * 1e12 }, - { "Gb", 0.125 * 1e9 }, - { "Mb", 0.125 * 1e6 }, - { "kb", 0.125 * 1e3 }, - { "b", 0.125 }, - { nullptr, 0 } - }; + static const unit_scale units{ + {"b", 0.125, 2, true}, {"b", 0.125, 10, true}, {"B", 1.0, 2, true}, {"B", 1.0, 10, true}}; return surf_parse_get_value_with_unit(string, units, entity_kind, name, "Append 'B' to get bytes (or 'b' for bits but 1B = 8b).", "B"); } double surf_parse_get_bandwidth(const char* string, const char* entity_kind, std::string name) { - const struct unit_scale units[] = { - { "EiBps", pow(1024, 6) }, - { "PiBps", pow(1024, 5) }, - { "TiBps", pow(1024, 4) }, - { "GiBps", pow(1024, 3) }, - { "MiBps", pow(1024, 2) }, - { "KiBps", 1024 }, - { "EBps", 1e18 }, - { "PBps", 1e15 }, - { "TBps", 1e12 }, - { "GBps", 1e9 }, - { "MBps", 1e6 }, - { "kBps", 1e3 }, - { "Bps", 1.0 }, - { "Eibps", 0.125 * pow(1024, 6) }, - { "Pibps", 0.125 * pow(1024, 5) }, - { "Tibps", 0.125 * pow(1024, 4) }, - { "Gibps", 0.125 * pow(1024, 3) }, - { "Mibps", 0.125 * pow(1024, 2) }, - { "Kibps", 0.125 * 1024 }, - { "Tbps", 0.125 * 1e12 }, - { "Gbps", 0.125 * 1e9 }, - { "Mbps", 0.125 * 1e6 }, - { "kbps", 0.125 * 1e3 }, - { "bps", 0.125 }, - { nullptr, 0 } - }; + static const unit_scale units{ + {"bps", 0.125, 2, true}, {"bps", 0.125, 10, true}, {"Bps", 1.0, 2, true}, {"Bps", 1.0, 10, true}}; return surf_parse_get_value_with_unit(string, units, entity_kind, name, "Append 'Bps' to get bytes per second (or 'bps' for bits but 1Bps = 8bps)", "Bps"); } double surf_parse_get_speed(const char* string, const char* entity_kind, std::string name) { - const struct unit_scale units[] = { - { "yottaflops", 1e24 }, - { "Yf", 1e24 }, - { "zettaflops", 1e21 }, - { "Zf", 1e21 }, - { "exaflops", 1e18 }, - { "Ef", 1e18 }, - { "petaflops", 1e15 }, - { "Pf", 1e15 }, - { "teraflops", 1e12 }, - { "Tf", 1e12 }, - { "gigaflops", 1e9 }, - { "Gf", 1e9 }, - { "megaflops", 1e6 }, - { "Mf", 1e6 }, - { "kiloflops", 1e3 }, - { "kf", 1e3 }, - { "flops", 1.0 }, - { "f", 1.0 }, - { nullptr, 0 } - }; + static const unit_scale units{{"f", 1.0, 10, true}, {"flops", 1.0, 10, false}}; return surf_parse_get_value_with_unit(string, units, entity_kind, name, "Append 'f' or 'flops' to your speed to get flop per second", "f"); } @@ -382,20 +350,12 @@ void ETag_surfxml_mount() sg_platf_new_mount(&mount); } -/* - * Stuff relative to the tag - */ -static std::vector surf_input_buffer_stack; -static std::vector surf_file_to_parse_stack; -static std::vector surf_parsed_filename_stack; - void STag_surfxml_include() { XBT_ERROR(" tag is deprecated, and will be removed in SimGrid v3.18. Please stop using it now (or tell us why you need it)."); parse_after_config(); XBT_DEBUG("STag_surfxml_include '%s'",A_surfxml_include_file); - surf_parsed_filename_stack.push_back(surf_parsed_filename); // save old file name - surf_parsed_filename = xbt_strdup(A_surfxml_include_file); + surf_parsed_filename_stack.emplace_back(A_surfxml_include_file); // save file name surf_file_to_parse_stack.push_back(surf_file_to_parse); // save old file descriptor @@ -440,7 +400,6 @@ int ETag_surfxml_include_state() surf_input_buffer_stack.pop_back(); // Restore the filename for error messages - free(surf_parsed_filename); surf_parsed_filename_stack.pop_back(); return 1; @@ -481,19 +440,19 @@ void STag_surfxml_platform() { "Use simgrid_update_xml to update your file automatically. " "This program is installed automatically with SimGrid, or " "available in the tools/ directory of the source archive.", - surf_parsed_filename, version); + surf_parsed_filename(), version); if (version < 4.1) { XBT_INFO("You're using a v%.1f XML file (%s) while the current standard is v4.1 " "That's fine, the new version is backward compatible. \n\n" "Use simgrid_update_xml to update your file automatically. " "This program is installed automatically with SimGrid, or " "available in the tools/ directory of the source archive.", - version, surf_parsed_filename); + version, surf_parsed_filename()); } xbt_assert(version <= 4.1, "******* FILE %s COMES FROM THE FUTURE (v:%.1f) *********\n " "The most recent formalism that this version of SimGrid understands is v4.1.\n" "Please update your code, or use another, more adapted, file.", - surf_parsed_filename, version); + surf_parsed_filename(), version); sg_platf_begin(); } @@ -842,6 +801,8 @@ void ETag_surfxml_zoneRoute() case A_surfxml_zoneRoute_symmetrical_NO: ASroute.symmetrical = false; break; + default: + THROW_IMPOSSIBLE; } sg_platf_new_route(&ASroute); @@ -1090,10 +1051,9 @@ void surf_parse_open(const char *file) { xbt_assert(file, "Cannot parse the nullptr file. Bypassing the parser is strongly deprecated nowadays."); - surf_parsed_filename = xbt_strdup(file); - char* dir = xbt_dirname(file); - surf_path.push_back(std::string(dir)); - xbt_free(dir); + surf_parsed_filename_stack.emplace_back(file); + std::string dir = simgrid::xbt::Path(file).getDirname(); + surf_path.push_back(dir); surf_file_to_parse = surf_fopen(file, "r"); if (surf_file_to_parse == nullptr) @@ -1105,12 +1065,11 @@ void surf_parse_open(const char *file) void surf_parse_close() { - if (surf_parsed_filename) { + if (surf_parsed_filename()) { surf_path.pop_back(); } - free(surf_parsed_filename); - surf_parsed_filename = nullptr; + surf_parsed_filename_stack.pop_back(); if (surf_file_to_parse) { surf_parse__delete_buffer(surf_input_buffer); @@ -1124,5 +1083,4 @@ int surf_parse() { return surf_parse_lex(); } - -SG_END_DECL() +}