// // C++ Implementation: gm_utils // // Description: // // // Author: Lorenzo Bettini , (C) 2004 // // Copyright: See COPYING file that comes with this distribution // // #ifdef HAVE_CONFIG_H #include "config.h" #endif #include #include #include "gm_utils.h" #include "ggo_options.h" #include "argsdef.h" #include "groups.h" using namespace std; extern groups_collection_t gengetopt_groups; char * canonize_names(const char *name) { char *pvar; char *p; pvar = strdup(name); for (p = pvar; *p; ++p) if (*p == '.' || *p == '-' || *p == '/') *p = '_'; return pvar; } // remove the path from the file name const string strip_path(const string &s) { string::size_type pos_of_sep; pos_of_sep = s.rfind("/"); if (pos_of_sep == string::npos) pos_of_sep = s.rfind("\\"); // try also with DOS path sep if (pos_of_sep == string::npos) return s; // no path return s.substr(pos_of_sep + 1); } const string to_upper(const string &old) { string upper = old; for (string::iterator s = upper.begin(); s != upper.end(); ++s) *s = toupper(*s); return upper; } const string canonize_name(const string &old) { string canonized = old; for (string::iterator s = canonized.begin(); s != canonized.end(); ++s) if (*s == '.' || *s == '-' || *s == ' ' || *s == '/') *s = '_'; return canonized; } const string canonize_enum(const string &old) { string canonized; for (string::const_iterator s = old.begin(); s != old.end(); ++s) if (*s == '-') canonized += "MINUS_"; else if (*s == '+') canonized += "PLUS_"; else canonized += *s; return canonized; } bool has_multiple_options_all_string() { if (!has_multiple_options()) return false; struct gengetopt_option * opt = 0; foropt { if (opt->multiple && (opt->type && opt->type != ARG_STRING)) return false; } return true; } bool has_multiple_options_string() { if (!has_multiple_options()) return false; struct gengetopt_option * opt = 0; foropt { if (opt->multiple && opt->type == ARG_STRING) return true; } return false; } bool has_multiple_options() { struct gengetopt_option * opt = 0; foropt { if (opt->multiple) return true; } return false; } bool has_multiple_options_with_type() { gengetopt_option * opt = 0; for (gengetopt_option_list::iterator it = gengetopt_options.begin(); it != gengetopt_options.end() && (opt = *it); ++it) if (opt->multiple && opt->type) return true; return false; } bool has_multiple_options_with_default() { gengetopt_option * opt = 0; for (gengetopt_option_list::iterator it = gengetopt_options.begin(); it != gengetopt_options.end() && (opt = *it); ++it) if (opt->multiple && opt->default_given) return true; return false; } bool has_options_with_details(bool strict_hidden) { gengetopt_option * opt = 0; for (gengetopt_option_list::iterator it = gengetopt_options.begin(); it != gengetopt_options.end() && (opt = *it); ++it) if (opt->details && (!strict_hidden || !opt->hidden)) return true; return false; } bool has_options_with_type() { gengetopt_option * opt = 0; for (gengetopt_option_list::iterator it = gengetopt_options.begin(); it != gengetopt_options.end() && (opt = *it); ++it) if (opt->type && opt->type != ARG_FLAG) return true; return false; } bool has_options_with_mode() { gengetopt_option * opt = 0; for (gengetopt_option_list::iterator it = gengetopt_options.begin(); it != gengetopt_options.end() && (opt = *it); ++it) if (opt->mode_value) return true; return false; } bool has_required() { struct gengetopt_option * opt = 0; foropt { if (opt->required) return true; } groups_collection_t::const_iterator end = gengetopt_groups.end(); for (groups_collection_t::const_iterator idx = gengetopt_groups.begin(); idx != end; ++idx) { if (idx->second.required) { return true; } } return false; } bool has_dependencies() { struct gengetopt_option * opt = 0; foropt { if (opt->dependon) return true; } return false; } bool has_options() { struct gengetopt_option * opt = 0; foropt { if (opt->short_opt) { if (opt->short_opt != 'h' && opt->short_opt != 'V') return true; } } return false; } bool has_hidden_options() { struct gengetopt_option * opt = 0; foropt { if (opt->hidden) { return true; } } return false; } bool has_values() { struct gengetopt_option * opt = 0; for (gengetopt_option_list::iterator it = gengetopt_options.begin(); it != gengetopt_options.end(); ++it) { opt = *it; if (opt->acceptedvalues) { return true; } } return false; } int not_newlines(const string &buf, int &num_of_newlines) { num_of_newlines = 0; // searches for the first non newline char string::size_type notnewline = buf.find_first_not_of("\r\n"); if (notnewline == string::npos) { // a string made only of newlines num_of_newlines = buf.size(); return num_of_newlines; } if (notnewline) { // everything before the non newline char is a newline num_of_newlines = notnewline; return notnewline; } return 0; } void wrap_cstr(string& wrapped, unsigned int from_column, unsigned int second_indent, const string &orig) { int next_space = from_column; string next_word; const char * out_buf = orig.c_str(); ostringstream stream; const unsigned int second_line_column = from_column + second_indent; string indent(second_line_column, ' '); int newline_chars = 0; int num_of_newlines = 0; while (*out_buf) { // check for a new line if ((newline_chars = not_newlines(out_buf, num_of_newlines))) { for (int i = 1; i <= num_of_newlines; ++i) stream << "\\n"; out_buf += newline_chars; if (*out_buf) { stream << indent; next_space = second_line_column; continue; } else break; } // find next word (including any preceeding spaces) bool had_word = false; while ((*out_buf) && (*out_buf != ' ' || !had_word) && !not_newlines(out_buf, num_of_newlines)) { had_word = *out_buf != ' '; next_word += *out_buf++; next_space++; } // wrap line if it's too long if (next_space > 79) { // trim leading spaces std::size_t pos = next_word.find_first_not_of(' '); if( pos == std::string::npos ) next_word.empty(); else if( pos ) next_word.erase( 0, pos ); stream << "\\n" << indent << next_word; next_space = second_line_column + next_word.size(); } else stream << next_word; // simply write word next_word = ""; } wrapped += stream.str(); } bool is_numeric(const gengetopt_option *opt) { switch (opt->type) { case ARG_INT: case ARG_SHORT: case ARG_LONG: case ARG_FLOAT: case ARG_DOUBLE: case ARG_LONGDOUBLE: case ARG_LONGLONG: return true; default: return false; } } bool string_contains(const char *s, const char *tofind) { if (!s) return false; return (strstr(s, tofind) != 0); }