# HG changeset patch # User Ankit Vani # Date 1371934391 -19800 # Node ID c6f90f6c65094d90e4a908caa109ad4a96b2f70e # Parent 59e3b109ab3801a49cd801ba50b0d0e7bccfe184# Parent de45cb0670a5590d8794fe5c36096644b1096116 Merged default branch diff -r 59e3b109ab38 -r c6f90f6c6509 libpurple/http.c --- a/libpurple/http.c Sat Jun 22 22:50:41 2013 +0530 +++ b/libpurple/http.c Sun Jun 23 02:23:11 2013 +0530 @@ -39,8 +39,6 @@ #define PURPLE_HTTP_REQUEST_DEFAULT_MAX_REDIRECTS 20 #define PURPLE_HTTP_REQUEST_DEFAULT_TIMEOUT 30 -typedef struct _PurpleHttpURL PurpleHttpURL; - typedef struct _PurpleHttpSocket PurpleHttpSocket; typedef struct _PurpleHttpHeaders PurpleHttpHeaders; @@ -169,12 +167,6 @@ static gchar * purple_http_cookie_jar_gen(PurpleHttpCookieJar *cookie_jar); gchar * purple_http_cookie_jar_dump(PurpleHttpCookieJar *cjar); -static PurpleHttpURL * purple_http_url_parse(const char *url); -static void purple_http_url_free(PurpleHttpURL *parsed_url); -static void purple_http_url_relative(PurpleHttpURL *base_url, - PurpleHttpURL *relative_url); -static gchar * purple_http_url_print(PurpleHttpURL *parsed_url); - static GRegex *purple_http_re_url, *purple_http_re_url_host, *purple_http_re_rfc1123; @@ -1278,7 +1270,7 @@ purple_debug_misc("http", "Performing new request %p.\n", hc); hc->url = purple_http_url_parse(request->url); - if (!hc->url || hc->url->host[0] == '\0') { + if (!hc->url || hc->url->host == NULL || hc->url->host[0] == '\0') { purple_debug_error("http", "Invalid URL requested.\n"); purple_http_connection_terminate(hc); return NULL; @@ -2062,7 +2054,8 @@ /*** URL functions ************************************************************/ -static PurpleHttpURL * purple_http_url_parse(const char *raw_url) +PurpleHttpURL * +purple_http_url_parse(const char *raw_url) { PurpleHttpURL *url; GMatchInfo *match_info; @@ -2174,7 +2167,8 @@ return url; } -static void purple_http_url_free(PurpleHttpURL *parsed_url) +void +purple_http_url_free(PurpleHttpURL *parsed_url) { if (parsed_url == NULL) return; @@ -2188,8 +2182,8 @@ g_free(parsed_url); } -static void purple_http_url_relative(PurpleHttpURL *base_url, - PurpleHttpURL *relative_url) +void +purple_http_url_relative(PurpleHttpURL *base_url, PurpleHttpURL *relative_url) { g_return_if_fail(base_url != NULL); g_return_if_fail(relative_url != NULL); @@ -2232,7 +2226,8 @@ base_url->fragment = g_strdup(relative_url->fragment); } -static gchar * purple_http_url_print(PurpleHttpURL *parsed_url) +gchar * +purple_http_url_print(PurpleHttpURL *parsed_url) { GString *url = g_string_new(""); gboolean before_host_printed = FALSE, host_printed = FALSE; @@ -2278,6 +2273,62 @@ return g_string_free(url, FALSE); } +const gchar * +purple_http_url_get_protocol(const PurpleHttpURL *parsed_url) +{ + g_return_val_if_fail(parsed_url != NULL, NULL); + + return parsed_url->protocol; +} + +const gchar * +purple_http_url_get_user(const PurpleHttpURL *parsed_url) +{ + g_return_val_if_fail(parsed_url != NULL, NULL); + + return parsed_url->user; +} + +const gchar * +purple_http_url_get_password(const PurpleHttpURL *parsed_url) +{ + g_return_val_if_fail(parsed_url != NULL, NULL); + + return parsed_url->password; +} + +const gchar * +purple_http_url_get_host(const PurpleHttpURL *parsed_url) +{ + g_return_val_if_fail(parsed_url != NULL, NULL); + + return parsed_url->host; +} + +int +purple_http_url_get_port(const PurpleHttpURL *parsed_url) +{ + g_return_val_if_fail(parsed_url != NULL, 0); + + return parsed_url->port; +} + +const gchar * +purple_http_url_get_path(const PurpleHttpURL *parsed_url) +{ + g_return_val_if_fail(parsed_url != NULL, NULL); + + return parsed_url->path; +} + +const gchar * +purple_http_url_get_fragment(const PurpleHttpURL *parsed_url) +{ + g_return_val_if_fail(parsed_url != NULL, NULL); + + return parsed_url->fragment; +} + /*** HTTP Subsystem ***********************************************************/ void purple_http_init(void) diff -r 59e3b109ab38 -r c6f90f6c6509 libpurple/http.h --- a/libpurple/http.h Sat Jun 22 22:50:41 2013 +0530 +++ b/libpurple/http.h Sun Jun 23 02:23:11 2013 +0530 @@ -48,6 +48,11 @@ typedef struct _PurpleHttpResponse PurpleHttpResponse; /** + * Parsed representation for the URL. + */ +typedef struct _PurpleHttpURL PurpleHttpURL; + +/** * An collection of cookies, got from HTTP response or provided for HTTP * request. */ @@ -216,6 +221,120 @@ /**************************************************************************/ +/** @name URL processing API */ +/**************************************************************************/ +/*@{*/ + +/** + * Parses a URL. + * + * The returned data must be freed with purple_http_url_free. + * + * @param url The URL to parse. + * @return The parsed url or NULL, if the URL is invalid. + */ +PurpleHttpURL * +purple_http_url_parse(const char *url); + +/** + * Frees the parsed URL struct. + * + * @param parsed_url The parsed URL struct, or NULL. + */ +void +purple_http_url_free(PurpleHttpURL *parsed_url); + +/** + * Converts the base URL to the absolute form of the provided relative URL. + * + * Example: "https://example.com/path/to/file.html" + "subdir/other-file.html" = + * "https://example.com/path/to/subdir/another-file.html" + * + * @param base_url The base URL. The result is stored here. + * @param relative_url The relative URL. + */ +void +purple_http_url_relative(PurpleHttpURL *base_url, PurpleHttpURL *relative_url); + +/** + * Converts the URL struct to the printable form. The result may not be a valid + * URL (in cases, when the struct doesn't have all fields filled properly). + * + * The result must be g_free'd. + * + * @param parsed_url The URL struct. + * @return The printable form of the URL. + */ +gchar * +purple_http_url_print(PurpleHttpURL *parsed_url); + +/** + * Gets the protocol part of URL. + * + * @param parsed_url The URL struct. + * @return The protocol. + */ +const gchar * +purple_http_url_get_protocol(const PurpleHttpURL *parsed_url); + +/** + * Gets the username part of URL. + * + * @param parsed_url The URL struct. + * @return The username. + */ +const gchar * +purple_http_url_get_user(const PurpleHttpURL *parsed_url); + +/** + * Gets the password part of URL. + * + * @param parsed_url The URL struct. + * @return The password. + */ +const gchar * +purple_http_url_get_password(const PurpleHttpURL *parsed_url); + +/** + * Gets the hostname part of URL. + * + * @param parsed_url The URL struct. + * @return The hostname. + */ +const gchar * +purple_http_url_get_host(const PurpleHttpURL *parsed_url); + +/** + * Gets the port part of URL. + * + * @param parsed_url The URL struct. + * @return The port number. + */ +int +purple_http_url_get_port(const PurpleHttpURL *parsed_url); + +/** + * Gets the path part of URL. + * + * @param parsed_url The URL struct. + * @return The path. + */ +const gchar * +purple_http_url_get_path(const PurpleHttpURL *parsed_url); + +/** + * Gets the fragment part of URL. + * + * @param parsed_url The URL struct. + * @return The fragment. + */ +const gchar * +purple_http_url_get_fragment(const PurpleHttpURL *parsed_url); + +/*@}*/ + + +/**************************************************************************/ /** @name Cookie jar API */ /**************************************************************************/ /*@{*/ diff -r 59e3b109ab38 -r c6f90f6c6509 libpurple/obsolete.c --- a/libpurple/obsolete.c Sat Jun 22 22:50:41 2013 +0530 +++ b/libpurple/obsolete.c Sun Jun 23 02:23:11 2013 +0530 @@ -774,3 +774,110 @@ g_free(gfud); } + +/* + * TODO: Should probably add a "gboolean *ret_ishttps" parameter that + * is set to TRUE if this URL is https, otherwise it is set to + * FALSE. But that change will break the API. + * + * This is important for Yahoo! web messenger login. They now + * force https login, and if you access the web messenger login + * page via http then it redirects you to the https version, but + * purple_util_fetch_url() ignores the "https" and attempts to + * fetch the URL via http again, which gets redirected again. + */ +gboolean +purple_url_parse(const char *url, char **ret_host, int *ret_port, + char **ret_path, char **ret_user, char **ret_passwd) +{ + gboolean is_https = FALSE; + const char * scan_info; + char port_str[6]; + int f; + const char *at, *slash; + const char *turl; + char host[256], path[256], user[256], passwd[256]; + int port = 0; + /* hyphen at end includes it in control set */ + +#define ADDR_CTRL "A-Za-z0-9.-" +#define PORT_CTRL "0-9" +#define PAGE_CTRL "A-Za-z0-9.,~_/:*!@&%%?=+^-" +#define USER_CTRL "A-Za-z0-9.,~_/*!&%%?=+^-" +#define PASSWD_CTRL "A-Za-z0-9.,~_/*!&%%?=+^-" + + g_return_val_if_fail(url != NULL, FALSE); + + if ((turl = purple_strcasestr(url, "http://")) != NULL) + { + turl += 7; + url = turl; + } + else if ((turl = purple_strcasestr(url, "https://")) != NULL) + { + is_https = TRUE; + turl += 8; + url = turl; + } + + /* parse out authentication information if supplied */ + /* Only care about @ char BEFORE the first / */ + at = strchr(url, '@'); + slash = strchr(url, '/'); + f = 0; + if (at && (!slash || at < slash)) { + scan_info = "%255[" USER_CTRL "]:%255[" PASSWD_CTRL "]^@"; + f = sscanf(url, scan_info, user, passwd); + + if (f == 1) { + /* No passwd, possibly just username supplied */ + scan_info = "%255[" USER_CTRL "]^@"; + f = sscanf(url, scan_info, user); + } + + url = at+1; /* move pointer after the @ char */ + } + + if (f < 1) { + *user = '\0'; + *passwd = '\0'; + } else if (f == 1) + *passwd = '\0'; + + scan_info = "%255[" ADDR_CTRL "]:%5[" PORT_CTRL "]/%255[" PAGE_CTRL "]"; + f = sscanf(url, scan_info, host, port_str, path); + + if (f == 1) + { + scan_info = "%255[" ADDR_CTRL "]/%255[" PAGE_CTRL "]"; + f = sscanf(url, scan_info, host, path); + /* Use the default port */ + if (is_https) + g_snprintf(port_str, sizeof(port_str), "443"); + else + g_snprintf(port_str, sizeof(port_str), "80"); + } + + if (f == 0) + *host = '\0'; + + if (f <= 1) + *path = '\0'; + + if (sscanf(port_str, "%d", &port) != 1) + purple_debug_error("util", "Error parsing URL port from %s\n", url); + + if (ret_host != NULL) *ret_host = g_strdup(host); + if (ret_port != NULL) *ret_port = port; + if (ret_path != NULL) *ret_path = g_strdup(path); + if (ret_user != NULL) *ret_user = g_strdup(user); + if (ret_passwd != NULL) *ret_passwd = g_strdup(passwd); + + return ((*host != '\0') ? TRUE : FALSE); + +#undef ADDR_CTRL +#undef PORT_CTRL +#undef PAGE_CTRL +#undef USER_CTRL +#undef PASSWD_CTRL +} diff -r 59e3b109ab38 -r c6f90f6c6509 libpurple/obsolete.h --- a/libpurple/obsolete.h Sat Jun 22 22:50:41 2013 +0530 +++ b/libpurple/obsolete.h Sun Jun 23 02:23:11 2013 +0530 @@ -104,6 +104,21 @@ */ void purple_util_fetch_url_cancel(PurpleUtilFetchUrlData *url_data); +/** + * Parses a URL, returning its host, port, file path, username and password. + * + * The returned data must be freed. + * + * @param url The URL to parse. + * @param ret_host The returned host. + * @param ret_port The returned port. + * @param ret_path The returned path. + * @param ret_user The returned username. + * @param ret_passwd The returned password. + */ +gboolean purple_url_parse(const char *url, char **ret_host, int *ret_port, + char **ret_path, char **ret_user, char **ret_passwd); + /*@}*/ diff -r 59e3b109ab38 -r c6f90f6c6509 libpurple/plugins/perl/common/Util.xs --- a/libpurple/plugins/perl/common/Util.xs Sat Jun 22 22:50:41 2013 +0530 +++ b/libpurple/plugins/perl/common/Util.xs Sun Jun 23 02:23:11 2013 +0530 @@ -110,37 +110,6 @@ purple_url_encode(str) const char *str - # XXX: this made perl assert()... - # - #gboolean - #purple_url_parse(url, OUTLIST gchar_own *ret_host, OUTLIST int ret_port, OUTLIST gchar_own *ret_path, OUTLIST gchar_own *ret_user, OUTLIST gchar_own *ret_passwd) - # const char *url - # PROTOTYPE: $ - -void -purple_url_parse(url) - const char *url - PREINIT: - char *ret_host; - int ret_port; - char *ret_path; - char *ret_user; - char *ret_passwd; - gboolean ret; - PPCODE: - ret = purple_url_parse(url, &ret_host, &ret_port, &ret_path, &ret_user, &ret_passwd); - XPUSHs(sv_2mortal(newSViv(ret))); - XPUSHs(ret_host ? sv_2mortal(newSVpv(ret_host, 0)) : sv_2mortal(newSV(0))); - XPUSHs(sv_2mortal(newSViv(ret_port))); - XPUSHs(ret_path ? sv_2mortal(newSVpv(ret_path, 0)) : sv_2mortal(newSV(0))); - XPUSHs(ret_user ? sv_2mortal(newSVpv(ret_user, 0)) : sv_2mortal(newSV(0))); - XPUSHs(ret_passwd ? sv_2mortal(newSVpv(ret_passwd, 0)) : sv_2mortal(newSV(0))); - g_free(ret_host); - g_free(ret_path); - g_free(ret_user); - g_free(ret_passwd); - - const char * purple_user_dir() diff -r 59e3b109ab38 -r c6f90f6c6509 libpurple/protocols/jabber/bosh.c --- a/libpurple/protocols/jabber/bosh.c Sat Jun 22 22:50:41 2013 +0530 +++ b/libpurple/protocols/jabber/bosh.c Sun Jun 23 02:23:11 2013 +0530 @@ -25,6 +25,7 @@ #include "core.h" #include "cipher.h" #include "debug.h" +#include "obsolete.h" #include "prpl.h" #include "util.h" #include "xmlnode.h" diff -r 59e3b109ab38 -r c6f90f6c6509 libpurple/protocols/jabber/oob.c --- a/libpurple/protocols/jabber/oob.c Sat Jun 22 22:50:41 2013 +0530 +++ b/libpurple/protocols/jabber/oob.c Sun Jun 23 02:23:11 2013 +0530 @@ -23,6 +23,7 @@ #include "internal.h" #include "debug.h" #include "ft.h" +#include "obsolete.h" #include "util.h" #include "jabber.h" diff -r 59e3b109ab38 -r c6f90f6c6509 libpurple/protocols/msn/soap.c --- a/libpurple/protocols/msn/soap.c Sat Jun 22 22:50:41 2013 +0530 +++ b/libpurple/protocols/msn/soap.c Sun Jun 23 02:23:11 2013 +0530 @@ -27,6 +27,7 @@ #include "soap.h" +#include "obsolete.h" #include "session.h" #include "debug.h" diff -r 59e3b109ab38 -r c6f90f6c6509 libpurple/protocols/yahoo/yahoo_filexfer.c --- a/libpurple/protocols/yahoo/yahoo_filexfer.c Sat Jun 22 22:50:41 2013 +0530 +++ b/libpurple/protocols/yahoo/yahoo_filexfer.c Sun Jun 23 02:23:11 2013 +0530 @@ -28,6 +28,7 @@ #include "debug.h" #include "network.h" #include "notify.h" +#include "obsolete.h" #include "proxy.h" #include "ft.h" #include "libymsg.h" diff -r 59e3b109ab38 -r c6f90f6c6509 libpurple/protocols/yahoo/yahoochat.c --- a/libpurple/protocols/yahoo/yahoochat.c Sat Jun 22 22:50:41 2013 +0530 +++ b/libpurple/protocols/yahoo/yahoochat.c Sun Jun 23 02:23:11 2013 +0530 @@ -33,6 +33,7 @@ #endif /* HAVE_CONFIG_H */ #include "debug.h" +#include "obsolete.h" #include "prpl.h" #include "conversation.h" diff -r 59e3b109ab38 -r c6f90f6c6509 libpurple/proxy.c --- a/libpurple/proxy.c Sat Jun 22 22:50:41 2013 +0530 +++ b/libpurple/proxy.c Sun Jun 23 02:23:11 2013 +0530 @@ -37,6 +37,7 @@ #include "dnsquery.h" #include "notify.h" #include "ntlm.h" +#include "obsolete.h" #include "prefs.h" #include "proxy.h" #include "util.h" diff -r 59e3b109ab38 -r c6f90f6c6509 libpurple/util.c --- a/libpurple/util.c Sat Jun 22 22:50:41 2013 +0530 +++ b/libpurple/util.c Sun Jun 23 02:23:11 2013 +0530 @@ -3872,114 +3872,6 @@ g_hash_table_destroy(params); } -/* - * TODO: Should probably add a "gboolean *ret_ishttps" parameter that - * is set to TRUE if this URL is https, otherwise it is set to - * FALSE. But that change will break the API. - * - * This is important for Yahoo! web messenger login. They now - * force https login, and if you access the web messenger login - * page via http then it redirects you to the https version, but - * purple_util_fetch_url() ignores the "https" and attempts to - * fetch the URL via http again, which gets redirected again. - */ -gboolean -purple_url_parse(const char *url, char **ret_host, int *ret_port, - char **ret_path, char **ret_user, char **ret_passwd) -{ - gboolean is_https = FALSE; - const char * scan_info; - char port_str[6]; - int f; - const char *at, *slash; - const char *turl; - char host[256], path[256], user[256], passwd[256]; - int port = 0; - /* hyphen at end includes it in control set */ - -#define ADDR_CTRL "A-Za-z0-9.-" -#define PORT_CTRL "0-9" -#define PAGE_CTRL "A-Za-z0-9.,~_/:*!@&%%?=+^-" -#define USER_CTRL "A-Za-z0-9.,~_/*!&%%?=+^-" -#define PASSWD_CTRL "A-Za-z0-9.,~_/*!&%%?=+^-" - - g_return_val_if_fail(url != NULL, FALSE); - - if ((turl = purple_strcasestr(url, "http://")) != NULL) - { - turl += 7; - url = turl; - } - else if ((turl = purple_strcasestr(url, "https://")) != NULL) - { - is_https = TRUE; - turl += 8; - url = turl; - } - - /* parse out authentication information if supplied */ - /* Only care about @ char BEFORE the first / */ - at = strchr(url, '@'); - slash = strchr(url, '/'); - f = 0; - if (at && (!slash || at < slash)) { - scan_info = "%255[" USER_CTRL "]:%255[" PASSWD_CTRL "]^@"; - f = sscanf(url, scan_info, user, passwd); - - if (f == 1) { - /* No passwd, possibly just username supplied */ - scan_info = "%255[" USER_CTRL "]^@"; - f = sscanf(url, scan_info, user); - } - - url = at+1; /* move pointer after the @ char */ - } - - if (f < 1) { - *user = '\0'; - *passwd = '\0'; - } else if (f == 1) - *passwd = '\0'; - - scan_info = "%255[" ADDR_CTRL "]:%5[" PORT_CTRL "]/%255[" PAGE_CTRL "]"; - f = sscanf(url, scan_info, host, port_str, path); - - if (f == 1) - { - scan_info = "%255[" ADDR_CTRL "]/%255[" PAGE_CTRL "]"; - f = sscanf(url, scan_info, host, path); - /* Use the default port */ - if (is_https) - g_snprintf(port_str, sizeof(port_str), "443"); - else - g_snprintf(port_str, sizeof(port_str), "80"); - } - - if (f == 0) - *host = '\0'; - - if (f <= 1) - *path = '\0'; - - if (sscanf(port_str, "%d", &port) != 1) - purple_debug_error("util", "Error parsing URL port from %s\n", url); - - if (ret_host != NULL) *ret_host = g_strdup(host); - if (ret_port != NULL) *ret_port = port; - if (ret_path != NULL) *ret_path = g_strdup(path); - if (ret_user != NULL) *ret_user = g_strdup(user); - if (ret_passwd != NULL) *ret_passwd = g_strdup(passwd); - - return ((*host != '\0') ? TRUE : FALSE); - -#undef ADDR_CTRL -#undef PORT_CTRL -#undef PAGE_CTRL -#undef USER_CTRL -#undef PASSWD_CTRL -} - - const char * purple_url_decode(const char *str) { diff -r 59e3b109ab38 -r c6f90f6c6509 libpurple/util.h --- a/libpurple/util.h Sat Jun 22 22:50:41 2013 +0530 +++ b/libpurple/util.h Sun Jun 23 02:23:11 2013 +0530 @@ -1170,21 +1170,6 @@ void purple_got_protocol_handler_uri(const char *uri); /** - * Parses a URL, returning its host, port, file path, username and password. - * - * The returned data must be freed. - * - * @param url The URL to parse. - * @param ret_host The returned host. - * @param ret_port The returned port. - * @param ret_path The returned path. - * @param ret_user The returned username. - * @param ret_passwd The returned password. - */ -gboolean purple_url_parse(const char *url, char **ret_host, int *ret_port, - char **ret_path, char **ret_user, char **ret_passwd); - -/** * Decodes a URL into a plain string. * * This will change hex codes and such to their ascii equivalents.