[gssdp] client: Add can_reach convenience function



commit 4ee853694173e3d06745a2abfa1f8e8a1185d5b6
Author: Jens Georg <mail jensge org>
Date:   Thu May 20 16:50:01 2021 +0200

    client: Add can_reach convenience function
    
    This can be used to decide if a peer can communicate with this client

 doc/gssdp-docs.xml         |  4 ++++
 doc/gssdp-sections.txt     |  1 +
 libgssdp/gssdp-client.c    | 37 ++++++++++++++++++++++++++++++-------
 libgssdp/gssdp-client.h    |  3 +++
 libgssdp/gssdp-net-posix.c |  8 +++++++-
 5 files changed, 45 insertions(+), 8 deletions(-)
---
diff --git a/doc/gssdp-docs.xml b/doc/gssdp-docs.xml
index bb631df..81834fb 100644
--- a/doc/gssdp-docs.xml
+++ b/doc/gssdp-docs.xml
@@ -76,5 +76,9 @@
     <xi:include href="xml/api-index-1.2.3.xml"><xi:fallback /></xi:include>
   </index>
 
+  <index id="api-index-1-2-4">
+    <title>Index of new symbols in 1.2.4</title>
+    <xi:include href="xml/api-index-1.2.3.xml"><xi:fallback /></xi:include>
+  </index>
 
 </book>
diff --git a/doc/gssdp-sections.txt b/doc/gssdp-sections.txt
index 4fab17a..65f788b 100644
--- a/doc/gssdp-sections.txt
+++ b/doc/gssdp-sections.txt
@@ -24,6 +24,7 @@ gssdp_client_clear_headers
 gssdp_client_remove_header
 gssdp_client_add_cache_entry
 gssdp_client_guess_user_agent
+gssdp_client_can_reach
 <SUBSECTION Standard>
 GSSDP_TYPE_UDA_VERSION
 gssdp_uda_version_get_type
diff --git a/libgssdp/gssdp-client.c b/libgssdp/gssdp-client.c
index 2cdb027..f3404b7 100644
--- a/libgssdp/gssdp-client.c
+++ b/libgssdp/gssdp-client.c
@@ -1252,6 +1252,34 @@ gssdp_client_set_config_id (GSSDPClient *client, gint32 config_id)
 
 }
 
+/**
+ * gssdp_client_can_reach:
+ * @client: A #GSSDPClient
+ * @address: A #GInetSocketAddress of the target. The port part of the address may be 0
+ *
+ * Check if the peer at @address is reachable using this @client.
+ *
+ * Since: 1.2.4
+ * Returns: %TRUE if considered reachable, %FALSE otherwise.
+ */
+gboolean
+gssdp_client_can_reach (GSSDPClient *client, GInetSocketAddress *address)
+{
+        g_return_val_if_fail (GSSDP_IS_CLIENT (client), FALSE);
+        g_return_val_if_fail (G_IS_INET_SOCKET_ADDRESS (address), FALSE);
+
+        GSSDPClientPrivate *priv = gssdp_client_get_instance_private (client);
+        gboolean retval = FALSE;
+
+        GInetAddress *addr = g_inet_socket_address_get_address (address);
+        if (g_inet_address_get_is_link_local (addr)) {
+                return g_inet_socket_address_get_scope_id (address) ==
+                       priv->device.index;
+        }
+
+        return g_inet_address_mask_matches (priv->device.host_mask, addr);
+}
+
 /**
  * _gssdp_client_send_message:
  * @client: A #GSSDPClient
@@ -1587,14 +1615,9 @@ socket_source_cb (GSSDPSocketSource *socket_source, GSSDPClient *client)
          * on this socket from a particular interface but AFAIK that is not
          * possible, at least not in a portable way.
          */
-        {
-                GInetAddress *inet_address;
-                GInetSocketAddress *sockaddr;
 
-                sockaddr = G_INET_SOCKET_ADDRESS (address);
-                inet_address = g_inet_socket_address_get_address (sockaddr);
-                if (!g_inet_address_mask_matches (priv->device.host_mask, inet_address))
-                        goto out;
+        if (!gssdp_client_can_reach (client, G_INET_SOCKET_ADDRESS(address))) {
+                goto out;
         }
 #endif
 
diff --git a/libgssdp/gssdp-client.h b/libgssdp/gssdp-client.h
index 1b1308e..0ce9bfa 100644
--- a/libgssdp/gssdp-client.h
+++ b/libgssdp/gssdp-client.h
@@ -133,6 +133,9 @@ void
 gssdp_client_set_config_id    (GSSDPClient *client,
                                gint32       config_id);
 
+gboolean
+gssdp_client_can_reach (GSSDPClient *client,
+                        GInetSocketAddress *address);
 
 G_END_DECLS
 
diff --git a/libgssdp/gssdp-net-posix.c b/libgssdp/gssdp-net-posix.c
index ca42838..5ca8f7c 100644
--- a/libgssdp/gssdp-net-posix.c
+++ b/libgssdp/gssdp-net-posix.c
@@ -58,7 +58,13 @@ int
 gssdp_net_query_ifindex (GSSDPNetworkDevice *device)
 {
 #if defined(HAVE_IFNAMETOINDEX)
-    return if_nametoindex (device->iface_name);
+        errno = 0;
+        int index = if_nametoindex (device->iface_name);
+        if (index == 0 && errno != 0) {
+                return -1;
+        } else {
+                return index;
+        }
 
 #elif defined(HAVE_SIOCGIFINDEX)
     int fd;


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]