diff options
author | qi1988.yang <qi1988.yang@samsung.com> | 2015-11-17 17:02:41 +0800 |
---|---|---|
committer | Seonah Moon <seonah1.moon@samsung.com> | 2016-06-08 14:47:08 +0900 |
commit | 20f8439bd295bba52247c19f86db9bf574dcee4b (patch) | |
tree | 65416e2301925af6a1cc92863194cd6d35c412c9 | |
parent | c623aae597da21fb6e1bf9fe9e1255274a4cf2ad (diff) | |
download | libsoup-20f8439bd295bba52247c19f86db9bf574dcee4b.tar.gz libsoup-20f8439bd295bba52247c19f86db9bf574dcee4b.tar.bz2 libsoup-20f8439bd295bba52247c19f86db9bf574dcee4b.zip |
Maintain a DNS cache in soup library to reduce DNS request time
[Problem] Prefetch DNS need supporting of DNS Cache
[Cause] Support DNS Cache in libsoup
[Solution] Maintain a DNS cache in soup library to reduce DNS request time.
Change-Id: Ic4d580cda32baaba97bf285c4286f4543000bcba
Signed-off-by: qi1988.yang <qi1988.yang@samsung.com>
-rw-r--r--[-rwxr-xr-x] | configure.ac | 16 | ||||
-rw-r--r-- | libsoup/soup-address.c | 131 | ||||
-rw-r--r--[-rwxr-xr-x] | packaging/libsoup.spec | 1 |
3 files changed, 145 insertions, 3 deletions
diff --git a/configure.ac b/configure.ac index 125c0d71..1520c238 100755..100644 --- a/configure.ac +++ b/configure.ac @@ -370,6 +370,22 @@ AC_MSG_RESULT($enable_tizen_disable_mime_sniff) AM_CONDITIONAL(TIZEN_TV_DISABLE_MIME_SNIFF, [test $enable_tizen_disable_mime_sniff = yes]) +dnl **************************** +dnl *** Tizen soup store dns *** +dnl **************************** + +AC_ARG_ENABLE(tizen-soup-store-dns, + AS_HELP_STRING([--enable-tizen-soup-store-dns], [Enable Tizen soup store dns ]), , + enable_tizen_soup_store_dns=no) + +AC_MSG_CHECKING([for Tizen soup store dns]) +if test $enable_tizen_soup_store_dns != no;then + AC_DEFINE(ENABLE_TIZEN_TV_SOUP_STORE_DNS, 1, [Maintain a DNS cache in soup library to reduce DNS request time]) +fi +AC_MSG_RESULT($enable_tizen_soup_store_dns) + +AM_CONDITIONAL(TIZEN_TV_SOUP_STORE_DNS, [test $enable_tizen_soup_store_dns = yes]) + dnl *********************************************** dnl *** Tizen support soup immediate requesting *** dnl *********************************************** diff --git a/libsoup/soup-address.c b/libsoup/soup-address.c index b2d1647a..4479f7b6 100644 --- a/libsoup/soup-address.c +++ b/libsoup/soup-address.c @@ -16,6 +16,14 @@ #include "soup-address.h" #include "soup.h" #include "soup-misc-private.h" +#include "TIZEN.h" + +#if ENABLE(TIZEN_TV_SOUP_STORE_DNS) +#include <sys/socket.h> +#include <time.h> +#include "soup-session.h" +#include "glib.h" +#endif /** * SECTION:soup-address @@ -53,6 +61,16 @@ typedef struct { GMutex lock; } SoupAddressPrivate; + +#if ENABLE(TIZEN_TV_SOUP_STORE_DNS) +typedef struct { + gchar *key; + gchar *ip; + time_t time; + guint port; +} IPAndPort; +#endif + #define SOUP_ADDRESS_GET_PRIVATE(o) (G_TYPE_INSTANCE_GET_PRIVATE ((o), SOUP_TYPE_ADDRESS, SoupAddressPrivate)) /* sockaddr generic macros */ @@ -94,6 +112,14 @@ typedef struct { #define SOUP_ADDRESS_SET_DATA(priv, data, length) \ memcpy (SOUP_ADDRESS_GET_DATA (priv), data, length) +#if ENABLE(TIZEN_TV_SOUP_STORE_DNS) +#define DNS_CACHE_HASHTABLE_MAX_COUNT 30 +#define DNS_CACHE_MAX_TIME_SECOND 60 +static GHashTable *dns_cache = NULL; +static GList *hostkey = NULL; +static IPAndPort* ipandport_cache_new (gchar *key, gchar *ip, time_t time, guint port); +static void ipandport_cache_free (IPAndPort* ipandport); +#endif static void soup_address_connectable_iface_init (GSocketConnectableIface *connectable_iface); @@ -621,6 +647,16 @@ update_addrs (SoupAddress *addr, GList *addrs, GError *error) GSocketAddress *gsa; int i; +#if ENABLE(TIZEN_TV_SOUP_STORE_DNS) + IPAndPort *ipandport = NULL; + IPAndPort *oldipandport = NULL; + IPAndPort *deloldipandport = NULL; + gchar *tempIPaddress = NULL; + time_t timep; + int hashtablecount = 0; + GList *templist = NULL; +#endif + if (error) { if (error->domain == G_IO_ERROR && error->code == G_IO_ERROR_CANCELLED) @@ -636,6 +672,40 @@ update_addrs (SoupAddress *addr, GList *addrs, GError *error) priv->sockaddr = g_new (struct sockaddr_storage, priv->n_addrs); for (i = 0; addrs; addrs = addrs->next, i++) { gia = addrs->data; +#if ENABLE(TIZEN_TV_SOUP_STORE_DNS) + if ((0 == i) && (!addrs->next) && (dns_cache)) { + tempIPaddress = g_inet_address_to_string (gia); + oldipandport = g_hash_table_lookup (dns_cache, priv->name); + if (oldipandport) { + time (&timep); + hostkey = g_list_remove (hostkey, oldipandport->key); + oldipandport->time = timep; + hostkey = g_list_append (hostkey, oldipandport->key); + } else { + hashtablecount = g_hash_table_size (dns_cache); + if (hashtablecount < DNS_CACHE_HASHTABLE_MAX_COUNT) { + time (&timep); + ipandport = ipandport_cache_new (priv->name, tempIPaddress, timep, priv->port ); + g_hash_table_insert (dns_cache, ipandport->key, ipandport); + hostkey = g_list_append (hostkey, ipandport->key); + } else { + templist = g_list_first (hostkey); + if (templist) { + deloldipandport = g_hash_table_lookup (dns_cache, templist->data); + if (deloldipandport) { + time (&timep); + hostkey = g_list_remove (hostkey, deloldipandport->key); + g_hash_table_remove (dns_cache, deloldipandport->key); + ipandport_cache_free (deloldipandport); + ipandport = ipandport_cache_new (priv->name, tempIPaddress, timep, priv->port); + g_hash_table_insert (dns_cache, ipandport->key, ipandport); + hostkey = g_list_append (hostkey, ipandport->key); + } + } + } + } + } +#endif gsa = g_inet_socket_address_new (gia, priv->port); if (!g_socket_address_to_native (gsa, &priv->sockaddr[i], @@ -754,6 +824,30 @@ idle_complete_resolve (gpointer res_data) return FALSE; } +#if ENABLE(TIZEN_TV_SOUP_STORE_DNS) +static IPAndPort* ipandport_cache_new (gchar *key, gchar *ip, time_t time, guint port) +{ + IPAndPort *ipandport; + ipandport = g_new (IPAndPort, 1); + ipandport->key = g_strdup (key); + ipandport->ip = g_strdup (ip); + ipandport->time = time; + ipandport->port = port; + return ipandport; +} + +static void ipandport_cache_free (IPAndPort* ipandport) +{ + g_return_if_fail (ipandport != NULL); + g_free (ipandport->key); + g_free (ipandport->ip); + g_free (ipandport); + ipandport->key = NULL; + ipandport->ip = NULL; + ipandport = NULL; +} +#endif + /** * SoupAddressCallback: * @addr: the #SoupAddress that was resolved @@ -797,6 +891,13 @@ soup_address_resolve_async (SoupAddress *addr, GMainContext *async_context, SoupAddressResolveAsyncData *res_data; GResolver *resolver; +#if ENABLE(TIZEN_TV_SOUP_STORE_DNS) + IPAndPort *ipandport = NULL; + time_t timep; + GList *addrs; + guint status; +#endif + g_return_if_fail (SOUP_IS_ADDRESS (addr)); priv = SOUP_ADDRESS_GET_PRIVATE (addr); g_return_if_fail (priv->name || priv->sockaddr); @@ -823,10 +924,34 @@ soup_address_resolve_async (SoupAddress *addr, GMainContext *async_context, else { resolver = g_resolver_get_default (); +#if ENABLE(TIZEN_TV_SOUP_STORE_DNS) + if (!dns_cache) + dns_cache = g_hash_table_new (g_str_hash, g_str_equal); +#endif + if (priv->name) { - g_resolver_lookup_by_name_async (resolver, priv->name, - cancellable, - lookup_resolved, res_data); +#if ENABLE(TIZEN_TV_SOUP_STORE_DNS) + if (dns_cache) + ipandport = g_hash_table_lookup (dns_cache, priv->name); + if (ipandport) { + time (&timep); + if((timep - ipandport->time) <= DNS_CACHE_MAX_TIME_SECOND){ + addrs = g_resolver_lookup_by_name (resolver, ipandport->ip, cancellable, NULL); + status = update_addrs (res_data->addr, addrs, NULL); + complete_resolve_async (res_data, status); + } else { + g_resolver_lookup_by_name_async (resolver, priv->name, + cancellable, + lookup_resolved, res_data); + } + } else { +#endif + g_resolver_lookup_by_name_async (resolver, priv->name, + cancellable, + lookup_resolved, res_data); +#if ENABLE(TIZEN_TV_SOUP_STORE_DNS) + } +#endif } else { GInetAddress *gia; diff --git a/packaging/libsoup.spec b/packaging/libsoup.spec index 5c077c8e..12c3672f 100755..100644 --- a/packaging/libsoup.spec +++ b/packaging/libsoup.spec @@ -106,6 +106,7 @@ chmod +x autogen.sh --enable-tizen-tv-force-preload-tlsdb \ --enable-tizen-tv-no-cache-about-video-and-audio \ --enable-tizen-performance-test-log \ + --enable-tizen-soup-store-dns \ %endif --disable-static make %{?_smp_mflags} |