X-Git-Url: http://review.tizen.org/git/?a=blobdiff_plain;f=gio%2Fgnetworkservice.c;h=497d6fd35bec575981ded89e6a08f6ea796cfe4f;hb=4482977238ae80f64c2fe318d1500f4662c73980;hp=cfecccaad816747e9e47720d973b248b8b46671a;hpb=30132c44c18d9a08e4c6a9b4834366bd8628ecfa;p=platform%2Fupstream%2Fglib.git diff --git a/gio/gnetworkservice.c b/gio/gnetworkservice.c index cfeccca..497d6fd 100644 --- a/gio/gnetworkservice.c +++ b/gio/gnetworkservice.c @@ -15,9 +15,7 @@ * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General - * Public License along with this library; if not, write to the - * Free Software Foundation, Inc., 59 Temple Place, Suite 330, - * Boston, MA 02111-1307, USA. + * Public License along with this library; if not, see . */ #include "config.h" @@ -33,7 +31,7 @@ #include "gnetworkaddress.h" #include "gnetworkingprivate.h" #include "gresolver.h" -#include "gsimpleasyncresult.h" +#include "gtask.h" #include "gsocketaddressenumerator.h" #include "gsocketconnectable.h" #include "gsrvtarget.h" @@ -93,6 +91,7 @@ static GSocketAddressEnumerator *g_network_service_connectable_enumerate static GSocketAddressEnumerator *g_network_service_connectable_proxy_enumerate (GSocketConnectable *connectable); G_DEFINE_TYPE_WITH_CODE (GNetworkService, g_network_service, G_TYPE_OBJECT, + G_ADD_PRIVATE (GNetworkService) G_IMPLEMENT_INTERFACE (G_TYPE_SOCKET_CONNECTABLE, g_network_service_connectable_iface_init)) @@ -117,8 +116,6 @@ g_network_service_class_init (GNetworkServiceClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS (klass); - g_type_class_add_private (klass, sizeof (GNetworkServicePrivate)); - gobject_class->set_property = g_network_service_set_property; gobject_class->get_property = g_network_service_get_property; gobject_class->finalize = g_network_service_finalize; @@ -167,8 +164,7 @@ g_network_service_connectable_iface_init (GSocketConnectableIface *connectable_i static void g_network_service_init (GNetworkService *srv) { - srv->priv = G_TYPE_INSTANCE_GET_PRIVATE (srv, G_TYPE_NETWORK_SERVICE, - GNetworkServicePrivate); + srv->priv = g_network_service_get_instance_private (srv); } static void @@ -245,7 +241,7 @@ g_network_service_get_property (GObject *object, * @protocol, and @domain. This will initially be unresolved; use the * #GSocketConnectable interface to resolve it. * - * Return value: (transfer full): a new #GNetworkService + * Returns: (transfer full) (type GNetworkService): a new #GNetworkService * * Since: 2.22 */ @@ -267,7 +263,7 @@ g_network_service_new (const gchar *service, * * Gets @srv's service name (eg, "ldap"). * - * Return value: @srv's service name + * Returns: @srv's service name * * Since: 2.22 */ @@ -285,7 +281,7 @@ g_network_service_get_service (GNetworkService *srv) * * Gets @srv's protocol name (eg, "tcp"). * - * Return value: @srv's protocol name + * Returns: @srv's protocol name * * Since: 2.22 */ @@ -304,7 +300,7 @@ g_network_service_get_protocol (GNetworkService *srv) * Gets the domain that @srv serves. This might be either UTF-8 or * ASCII-encoded, depending on what @srv was created with. * - * Return value: @srv's domain name + * Returns: @srv's domain name * * Since: 2.22 */ @@ -323,7 +319,7 @@ g_network_service_get_domain (GNetworkService *srv) * Get's the URI scheme used to resolve proxies. By default, the service name * is used as scheme. * - * Return value: @srv's scheme name + * Returns: @srv's scheme name * * Since: 2.26 */ @@ -354,13 +350,31 @@ g_network_service_set_scheme (GNetworkService *srv, { g_return_if_fail (G_IS_NETWORK_SERVICE (srv)); - if (srv->priv->scheme) - g_free (srv->priv->scheme); + g_free (srv->priv->scheme); srv->priv->scheme = g_strdup (scheme); g_object_notify (G_OBJECT (srv), "scheme"); } +static GList * +g_network_service_fallback_targets (GNetworkService *srv) +{ + GSrvTarget *target; + struct servent *entry; + guint16 port; + + entry = getservbyname (srv->priv->service, "tcp"); + port = entry ? g_ntohs (entry->s_port) : 0; +#ifdef HAVE_ENDSERVENT + endservent (); +#endif + + if (entry == NULL) + return NULL; + + target = g_srv_target_new (srv->priv->domain, port, 0, 0); + return g_list_append (NULL, target); +} #define G_TYPE_NETWORK_SERVICE_ADDRESS_ENUMERATOR (_g_network_service_address_enumerator_get_type ()) #define G_NETWORK_SERVICE_ADDRESS_ENUMERATOR(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), G_TYPE_NETWORK_SERVICE_ADDRESS_ENUMERATOR, GNetworkServiceAddressEnumerator)) @@ -376,9 +390,6 @@ typedef struct { GError *error; - /* For async operation */ - GCancellable *cancellable; - GSimpleAsyncResult *result; } GNetworkServiceAddressEnumerator; typedef struct { @@ -386,6 +397,7 @@ typedef struct { } GNetworkServiceAddressEnumeratorClass; +static GType _g_network_service_address_enumerator_get_type (void); G_DEFINE_TYPE (GNetworkServiceAddressEnumerator, _g_network_service_address_enumerator, G_TYPE_SOCKET_ADDRESS_ENUMERATOR) static GSocketAddress * @@ -401,14 +413,26 @@ g_network_service_address_enumerator_next (GSocketAddressEnumerator *enumerator if (!srv_enum->srv->priv->targets) { GList *targets; + GError *my_error = NULL; targets = g_resolver_lookup_service (srv_enum->resolver, srv_enum->srv->priv->service, srv_enum->srv->priv->protocol, srv_enum->srv->priv->domain, - cancellable, error); - if (!targets) - return NULL; + cancellable, &my_error); + if (!targets && g_error_matches (my_error, G_RESOLVER_ERROR, + G_RESOLVER_ERROR_NOT_FOUND)) + { + targets = g_network_service_fallback_targets (srv_enum->srv); + if (targets) + g_clear_error (&my_error); + } + + if (my_error) + { + g_propagate_error (error, my_error); + return NULL; + } srv_enum->srv->priv->targets = targets; srv_enum->t = srv_enum->srv->priv->targets; @@ -478,7 +502,10 @@ g_network_service_address_enumerator_next (GSocketAddressEnumerator *enumerator srv_enum->error = error; else g_error_free (error); + } + if (!ret) + { g_object_unref (srv_enum->addr_enum); srv_enum->addr_enum = NULL; } @@ -495,13 +522,13 @@ g_network_service_address_enumerator_next (GSocketAddressEnumerator *enumerator return ret; } -static void next_async_resolved_targets (GObject *source_object, - GAsyncResult *result, - gpointer user_data); -static void next_async_have_targets (GNetworkServiceAddressEnumerator *srv_enum); -static void next_async_have_address (GObject *source_object, - GAsyncResult *result, - gpointer user_data); +static void next_async_resolved_targets (GObject *source_object, + GAsyncResult *result, + gpointer user_data); +static void next_async_have_targets (GTask *srv_enum); +static void next_async_have_address (GObject *source_object, + GAsyncResult *result, + gpointer user_data); static void g_network_service_address_enumerator_next_async (GSocketAddressEnumerator *enumerator, @@ -511,15 +538,9 @@ g_network_service_address_enumerator_next_async (GSocketAddressEnumerator *enum { GNetworkServiceAddressEnumerator *srv_enum = G_NETWORK_SERVICE_ADDRESS_ENUMERATOR (enumerator); + GTask *task; - g_return_if_fail (srv_enum->result == NULL); - - srv_enum->result = g_simple_async_result_new (G_OBJECT (enumerator), - callback, user_data, - g_network_service_address_enumerator_next_async); - - if (cancellable) - srv_enum->cancellable = g_object_ref (cancellable); + task = g_task_new (enumerator, cancellable, callback, user_data); /* If we haven't yet resolved srv, do that */ if (!srv_enum->srv->priv->targets) @@ -530,10 +551,10 @@ g_network_service_address_enumerator_next_async (GSocketAddressEnumerator *enum srv_enum->srv->priv->domain, cancellable, next_async_resolved_targets, - srv_enum); + task); } else - next_async_have_targets (srv_enum); + next_async_have_targets (task); } static void @@ -541,32 +562,39 @@ next_async_resolved_targets (GObject *source_object, GAsyncResult *result, gpointer user_data) { - GNetworkServiceAddressEnumerator *srv_enum = user_data; + GTask *task = user_data; + GNetworkServiceAddressEnumerator *srv_enum = g_task_get_source_object (task); GError *error = NULL; + GList *targets; - srv_enum->srv->priv->targets = - g_resolver_lookup_service_finish (srv_enum->resolver, result, &error); + targets = g_resolver_lookup_service_finish (srv_enum->resolver, + result, &error); - if (error) + if (!targets && g_error_matches (error, G_RESOLVER_ERROR, + G_RESOLVER_ERROR_NOT_FOUND)) { - GSimpleAsyncResult *simple = srv_enum->result; + targets = g_network_service_fallback_targets (srv_enum->srv); + if (targets) + g_clear_error (&error); + } - srv_enum->result = NULL; - g_simple_async_result_set_from_error (simple, error); - g_error_free (error); - g_simple_async_result_complete (simple); - g_object_unref (simple); + if (error) + { + g_task_return_error (task, error); + g_object_unref (task); } else { - srv_enum->t = srv_enum->srv->priv->targets; - next_async_have_targets (srv_enum); + srv_enum->t = srv_enum->srv->priv->targets = targets; + next_async_have_targets (task); } } static void -next_async_have_targets (GNetworkServiceAddressEnumerator *srv_enum) +next_async_have_targets (GTask *task) { + GNetworkServiceAddressEnumerator *srv_enum = g_task_get_source_object (task); + /* Delegate to GNetworkAddress */ if (srv_enum->addr_enum == NULL && srv_enum->t) { @@ -588,24 +616,21 @@ next_async_have_targets (GNetworkServiceAddressEnumerator *srv_enum) if (srv_enum->addr_enum) { g_socket_address_enumerator_next_async (srv_enum->addr_enum, - srv_enum->cancellable, + g_task_get_cancellable (task), next_async_have_address, - srv_enum); + task); } else { - GSimpleAsyncResult *simple = srv_enum->result; - srv_enum->result = NULL; - if (srv_enum->error) { - g_simple_async_result_set_from_error (simple, srv_enum->error); - g_error_free (srv_enum->error); + g_task_return_error (task, srv_enum->error); srv_enum->error = NULL; } + else + g_task_return_pointer (task, NULL, NULL); - g_simple_async_result_complete (simple); - g_object_unref (simple); + g_object_unref (task); } } @@ -614,7 +639,8 @@ next_async_have_address (GObject *source_object, GAsyncResult *result, gpointer user_data) { - GNetworkServiceAddressEnumerator *srv_enum = user_data; + GTask *task = user_data; + GNetworkServiceAddressEnumerator *srv_enum = g_task_get_source_object (task); GSocketAddress *address; GError *error = NULL; @@ -628,24 +654,19 @@ next_async_have_address (GObject *source_object, srv_enum->error = error; else g_error_free (error); + } + if (!address) + { g_object_unref (srv_enum->addr_enum); srv_enum->addr_enum = NULL; - next_async_have_targets (srv_enum); + next_async_have_targets (task); } else { - GSimpleAsyncResult *simple = srv_enum->result; - - srv_enum->result = NULL; - - if (address) - g_simple_async_result_set_op_res_gpointer (simple, - address, g_object_unref); - - g_simple_async_result_complete (simple); - g_object_unref (simple); + g_task_return_pointer (task, address, g_object_unref); + g_object_unref (task); } } @@ -654,14 +675,7 @@ g_network_service_address_enumerator_next_finish (GSocketAddressEnumerator *enu GAsyncResult *result, GError **error) { - GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (result); - GSocketAddress *sockaddr; - - if (g_simple_async_result_propagate_error (simple, error)) - return NULL; - - sockaddr = g_simple_async_result_get_op_res_gpointer (simple); - return sockaddr ? g_object_ref (sockaddr) : NULL; + return g_task_propagate_pointer (G_TASK (result), error); } static void @@ -684,12 +698,6 @@ g_network_service_address_enumerator_finalize (GObject *object) if (srv_enum->resolver) g_object_unref (srv_enum->resolver); - if (srv_enum->result) - g_object_unref (srv_enum->result); - - if (srv_enum->cancellable) - g_object_unref (srv_enum->cancellable); - if (srv_enum->error) g_error_free (srv_enum->error);