/** * Check whether path is an absolute path. */ bool is_absolute_path(const char *path) { g_assert(path != NULL); if (is_dir_separator(path[0])) return TRUE; /* On Windows also check for something like C:\ and x:/ */ return is_running_on_mingw() && is_ascii_alpha(path[0]) && ':' == path[1] && is_dir_separator(path[2]); }
static uint32 html_parse_entity(const struct array entity) { if (entity.size > 0) { const unsigned char c = entity.data[0]; if ('#' == c) { return parse_numeric_entity(entity); } else if (is_ascii_alpha(c)) { return parse_named_entity(entity); } } return -1; }
static enum html_attr parse_attribute(const struct array attr) { static const struct { const char *name; enum html_attr attr; } tab[] = { #define D(x) { #x, HTML_ATTR_ ## x, } D(ALT), D(HEIGHT), D(HREF), D(LANG), D(NAME), D(SRC), D(TARGET), D(WIDTH), #undef D }; size_t i, len; char name[32]; STATIC_ASSERT(N_ITEMS(tab) == NUM_HTML_ATTR - 1); len = 0; for (i = 0; i < attr.size; i++) { const unsigned char c = attr.data[i]; if (N_ITEMS(name) == len || !is_ascii_alpha(c)) break; name[len] = ascii_toupper(c); len++; } if (len > 0 && len < N_ITEMS(name)) { name[len] = '\0'; for (i = 0; i < N_ITEMS(tab); i++) { if (0 == strcmp(name, tab[i].name)) return tab[i].attr; } g_warning("%s(): unknown attribute: \"%s\"", G_STRFUNC, name); } return HTML_ATTR_UNKNOWN; }
/** * Parse gtk-gnutella's version number in User-Agent/Server string `str' * and extract relevant information into `ver'. * * @param str the version string to be parsed * @param ver the structure filled with parsed information * @param end filled with a pointer to the first unparsed character * * @returns TRUE if we parsed a gtk-gnutella version correctly, FALSE if we * were not facing a gtk-gnutella version, or if we did not recognize it. */ static bool version_parse(const char *str, version_t *ver, const char **end) { const char *v; int error; /* * Modern version numbers are formatted like this: * * gtk-gnutella/0.85 (04/04/2002; X11; FreeBSD 4.6-STABLE i386) * gtk-gnutella/0.90u (24/06/2002; X11; Linux 2.4.18-pre7 i686) * gtk-gnutella/0.90b (24/06/2002; X11; Linux 2.4.18-2emi i686) * gtk-gnutella/0.90b2 (24/06/2002; X11; Linux 2.4.18-2emi i686) * * The letter after the version number is either 'u' for unstable, 'a' * for alpha, 'b' for beta, or nothing for a stable release. It can be * followed by digits when present. * * In prevision for future possible extensions, we also parse * * gtk-gnutella/0.90.1b2 (24/06/2002; X11; Linux 2.4.18-2emi i686) * * where the third number is the "patchlevel". * * Starting 2006-08-26, the user-agent string includes the SVN revision * at the time of the build. To be compatible with the servents out * there, the version is included as an optional tag following the date. * * gtk-gnutella/0.85 (04/04/2002; r3404; X11; FreeBSD 4.6-STABLE i386) * * However, we also start parsing the new format that we shall use when * all current GTKG out there have expired: * * gtk-gnutella/0.85-3404 (04/04/2002; X11; FreeBSD 4.6-STABLE i386) * gtk-gnutella/0.90b2-3404 (04/04/2002; X11; FreeBSD 4.6-STABLE i386) * * where the '-3404' introduces the build number. * * Since switching to git (2011-09-11), the SVN build is no longer present * but rather the output of "git describe" is used to show any difference * with the latest release tag. * * A release would be described as: * * gtk-gnutella/0.97.1 (2011-09-11; GTK1; Linux i686) * * but any change on top of that would be seen as: * * gtk-gnutella/0.97.1-24-g844b7 (2011-09-11; GTK1; Linux i686) * * to indicate that 24 commits were made after the release, and the commit * ID is 844b7... (only enough hexadecimal digits are output to make the * string unique at the time it was generated. * * If furthermore a build is done from a dirty git repository, the string * "-dirty" is appended after the commit ID: * * gtk-gnutella/0.97.1-24-g844b7-dirty (2011-09-11; GTK1; Linux i686) */ if (NULL == (v = is_strprefix(str, GTA_PRODUCT_NAME "/"))) return FALSE; /* * Parse "major.minor", followed by optional ".patchlevel". */ ver->major = parse_uint32(v, &v, 10, &error); if (error) return FALSE; if (*v++ != '.') return FALSE; ver->minor = parse_uint32(v, &v, 10, &error); if (error) return FALSE; if ('.' == *v) { v++; ver->patchlevel = parse_uint32(v, &v, 10, &error); if (error) return FALSE; } else ver->patchlevel = 0; /* * Parse optional tag letter "x" followed by optional "taglevel". */ if (is_ascii_alpha(*v)) { ver->tag = *v++; if (is_ascii_digit(*v)) { ver->taglevel = parse_uint32(v, &v, 10, &error); if (error) return FALSE; } else ver->taglevel = 0; } else { ver->tag = '\0'; ver->taglevel = 0; } /* * Parse optional "-build" (legacy SVN) or "-change-bxxxxxxxx" (git * version scheme) to be able to sort identical versions with distinct * changes applied to them. */ if ('-' == *v) { v++; if (!is_strprefix(v, "dirty")) { ver->build = parse_uint32(v, &v, 10, &error); if (error) return FALSE; } } else ver->build = 0; if (end != NULL) *end = v; if (GNET_PROPERTY(version_debug) > 1) version_dump(str, ver, "#"); return TRUE; }