Hello community,

here is the log from the commit of package hplip for openSUSE:Factory checked 
in at 2016-08-31 14:27:42
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Comparing /work/SRC/openSUSE:Factory/hplip (Old)
 and      /work/SRC/openSUSE:Factory/.hplip.new (New)
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Package is "hplip"

Changes:
--------
--- /work/SRC/openSUSE:Factory/hplip/hplip.changes      2016-07-01 
09:50:44.000000000 +0200
+++ /work/SRC/openSUSE:Factory/.hplip.new/hplip.changes 2016-08-31 
14:27:44.000000000 +0200
@@ -1,0 +2,8 @@
+Fri Aug 26 15:13:30 UTC 2016 - martin.wi...@suse.com
+
+- Fixed device communication/detection problems with mdns/Bonjour
+  * added hplip-mdns.patch (MDNS send/receive on every iterface)
+  * added hplip-mdns-retry-query.patch (MDNS retry)
+  See https://bugs.launchpad.net/hplip/+bug/1616861
+
+-------------------------------------------------------------------

New:
----
  hplip-mdns-retry-query.patch
  hplip-mdns.patch

++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Other differences:
------------------
++++++ hplip.spec ++++++
--- /var/tmp/diff_new_pack.yhrzBK/_old  2016-08-31 14:27:45.000000000 +0200
+++ /var/tmp/diff_new_pack.yhrzBK/_new  2016-08-31 14:27:45.000000000 +0200
@@ -56,6 +56,10 @@
 # Patch108 add_missing_includes_and_define_GNU_SOURCE.patch adds missing 
'#include <...>'
 # and missing '#define _GNU_SOURCE' see 
https://bugs.launchpad.net/hplip/+bug/1456590
 Patch108:       add_missing_includes_and_define_GNU_SOURCE.patch
+# Patch200 fixes device communication and detection via MDNS in some network 
setups:
+Patch200:       hplip-mdns.patch
+# Patch201 makes MDNS lookups more robust by retrying queries:
+Patch201:       hplip-mdns-retry-query.patch
 # HPLIP's Python module cupsext.so has a build-time dependancy on the CUPS 
version:
 # It needs symbols (like ippFirstAttribute, ippNextAttribute, ippSetOperation 
etc)
 # that are defined only in libcups.so version > 1.5. For backward compatibility
@@ -350,6 +354,8 @@
 # Patch108 add_missing_includes_and_define_GNU_SOURCE.patch adds missing 
'#include <...>'
 # and missing '#define _GNU_SOURCE' see 
https://bugs.launchpad.net/hplip/+bug/1456590
 %patch108 -p1 -b .add_missing_includes_and_define_GNU_SOURCE.orig
+%patch200 -p1 -b .mdns
+%patch201 -p1 -b .mdns-retry
 
 %build
 # If AUTOMAKE='automake --foreign' is not set, autoreconf (in fact automake)
@@ -407,7 +413,8 @@
             --with-drvdir=%{_libexecdir}/cups/driver \
             --with-mimedir=%{_sysconfdir}/cups \
             --with-docdir=%{_defaultdocdir}/%{name} \
-            --with-htmldir==%{_defaultdocdir}/%{name}
+            --with-htmldir==%{_defaultdocdir}/%{name} \
+           CFLAGS='%{optflags}'
 make
 
 %install



++++++ hplip-mdns-retry-query.patch ++++++
diff --git a/protocol/discovery/mdns.c b/protocol/discovery/mdns.c
index 92e153a..75ef0ea 100644
--- a/protocol/discovery/mdns.c
+++ b/protocol/discovery/mdns.c
@@ -436,7 +436,7 @@ static int mdns_read_single_response(int udp_socket, char 
*recvbuffer, int recvb
     FD_SET(udp_socket, &master);
     maxfd = udp_socket;
     tmo.tv_sec = 0;
-    tmo.tv_usec = 300000;
+    tmo.tv_usec = 10000;
 
     readfd = master;
     ret = select(maxfd + 1, &readfd, NULL, NULL, &tmo);
@@ -549,6 +549,34 @@ static void mdns_rr_cleanup(DNS_RECORD *rr)
     }
 }
 
+static DNS_RECORD* send_and_receive(struct mdns_socket *mdns_sock,
+                                          const char *name,
+                                          int query_type, int read_mode)
+{
+    /* wait up to ~1s */
+    const useconds_t DELTA_T = 251000;
+    const int RETRIES = 8;
+    int retry = RETRIES;
+    DNS_RECORD *rr_list;
+
+    while (retry) {
+       if (mdns_send_query(mdns_sock, name, query_type) == MDNS_STATUS_OK) {
+           rr_list = mdns_read_responses(mdns_sock->socket, read_mode, name);
+           if (rr_list != NULL) {
+               DBG("send_and_receive: got response after %d retries\n",
+                   RETRIES - retry);
+               return rr_list;
+           }
+       }
+       /* MDNS servers delay responses. If the server just responded 
+        * to some query (maybe an earlier one we sent), we may need to wait. */
+       --retry;
+       usleep(DELTA_T);
+    }
+    BUG("send_and_receive: no response after %d retries\n", RETRIES);
+    return NULL;
+}
+
 int mdns_probe_nw_scanners(char* uris_buf, int buf_size, int *count)
 {
     int n = 0, bytes_read = 0;
@@ -562,11 +590,7 @@ int mdns_probe_nw_scanners(char* uris_buf, int buf_size, 
int *count)
     if (mdns_open_socket(&mdns_sock) != MDNS_STATUS_OK)
         goto bugout;
 
-    /* Send dns query */
-    mdns_send_query(&mdns_sock, scanner_name, QTYPE_PTR);
-
-    /* Read Responses */
-    rr_list = mdns_read_responses(mdns_sock.socket, MODE_READ_ALL, 
scanner_name);
+    rr_list = send_and_receive(&mdns_sock, scanner_name, QTYPE_PTR, 
MODE_READ_ALL);
 
     /* Update URIs buffer */
     bytes_read = mdns_update_uris(rr_list, uris_buf, buf_size, count);
@@ -598,10 +622,8 @@ int mdns_lookup(char* hostname, unsigned char* ip)
 
     /* Send dns query */
     sprintf(fqdn, "%s.local", hostname);
-    mdns_send_query(&mdns_sock, fqdn, QTYPE_A);
 
-    /* Read Responses */
-    rr_list = mdns_read_responses(mdns_sock.socket, MODE_READ_SINGLE, fqdn);
+    rr_list = send_and_receive(&mdns_sock, fqdn, QTYPE_A, MODE_READ_SINGLE);
 
     /* Update IP Address buffer */
     if(rr_list)
diff --git a/protocol/discovery/mdns.h b/protocol/discovery/mdns.h
index 34066fb..56d8847 100644
--- a/protocol/discovery/mdns.h
+++ b/protocol/discovery/mdns.h
@@ -102,5 +102,8 @@ static int   mdns_parse_respponse(unsigned char *Response, 
DNS_RECORD *rr);
 static void  mdns_rr_cleanup(DNS_RECORD *rr);
 static DNS_RECORD *mdns_read_responses(int udp_socket, int mode, const char 
*question);
 static unsigned char* mdns_readMDL(unsigned char *p, unsigned char 
*normalized_mdl, int len);
+static DNS_RECORD* send_and_receive(struct mdns_socket *mdns_sock, const char 
*name,
+                                   int query_type, int read_mode);
+static int get_ipv4_address(const char *iface, struct in_addr *addr);
 #endif // _DISCOVERY_MDNS_H
 
++++++ hplip-mdns.patch ++++++
diff --git a/base/mdns.py b/base/mdns.py
index 03bdb92..11d08b8 100644
--- a/base/mdns.py
+++ b/base/mdns.py
@@ -35,6 +35,17 @@ from .g import *
 from . import utils
 from .sixext import BytesIO, to_bytes_utf8, to_bytes_latin, to_string_latin
 
+if hasattr(socket, "if_nameindex"):
+    if_nameindex = socket.if_nameindex
+else:
+    def _if_nameindex():
+        """"Poor man's if_nameindex for Python 2."""
+        import os
+        sysdir = "/sys/class/net"
+        return sorted([ (int(open("%s/%s/ifindex" % (sysdir, iface), 
"r").read(), 0), iface)
+                        for iface in os.listdir(sysdir) ])
+    if_nameindex = _if_nameindex
+
 MAX_ANSWERS_PER_PACKET = 24
 
 QTYPE_A = 1
@@ -45,6 +56,8 @@ QTYPE_PTR = 12
 
 QCLASS_IN = 1
 
+MCAST_ADDR='224.0.0.251'
+
 # Caller needs to ensure, data should be in string format.
 def read_utf8(offset, data, l):
     return offset+l, data[offset:offset+l]
@@ -188,11 +201,6 @@ def createSocketsWithsetOption(ttl=4):
     s=None
     try:
         s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM, 
socket.IPPROTO_UDP)
-        x = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
-        x.connect(('1.2.3.4', 56))
-        intf = x.getsockname()[0]
-        x.close()
-
         s.setblocking(0)
         ttl = struct.pack('B', ttl)
     except socket.error:
@@ -209,14 +217,42 @@ def createSocketsWithsetOption(ttl=4):
 
     try:
         s.setsockopt(socket.SOL_IP, socket.IP_MULTICAST_TTL, ttl)
-        s.setsockopt(socket.SOL_IP, socket.IP_MULTICAST_IF, 
socket.inet_aton(intf) + socket.inet_aton('0.0.0.0'))
         s.setsockopt(socket.SOL_IP, socket.IP_MULTICAST_LOOP ,1)
     except Exception as e:
         log.error("Unable to setup multicast socket for mDNS: %s" % e)
         if s:
             s.close()
         return None
-    return s
+
+    ifaces = []
+    for idx, name in if_nameindex():
+        mreqn = struct.pack("=4sii", socket.inet_aton(MCAST_ADDR),
+                            socket.ntohl(socket.INADDR_ANY), idx)
+        try:
+            s.setsockopt(socket.SOL_IP, socket.IP_ADD_MEMBERSHIP, mreqn)
+        except Exception as e:
+            log.debug("Failed to join multicast group on interface %s: %s" %
+                        (name, e))
+        else:
+            log.debug("Joined multicast group on interface %s" % name)
+            ifaces.append((idx, name))
+
+    if len(ifaces) == 0:
+        log.error("failed to join multicast group on any interface")
+        s.close()
+        return None
+
+    return (s, ifaces)
+
+def closeSocket(s):
+    for idx, name in if_nameindex():
+        mreqn = struct.pack("=4sii", socket.inet_aton(MCAST_ADDR),
+                            socket.ntohl(socket.INADDR_ANY), idx)
+        try:
+            s.setsockopt(socket.SOL_IP, socket.IP_DROP_MEMBERSHIP, mreqn)
+        except Exception:
+            pass
+        s.close()
 
 def updateReceivedData(data, answers):
     update_spinner()
@@ -299,13 +335,22 @@ def updateReceivedData(data, answers):
             break
     return y, answers
 
+def send_packets(s, answers, name, mcast_addr, mcast_port):
+    for p in create_outgoing_packets(answers):
+        log.debug("Outgoing on %s: (%d)" % (name, len(p)))
+        log.log_data(p, width=16)
+        try:
+            s.sendto(p, 0, (mcast_addr, mcast_port))
+        except socket.error as e:
+            log.debug("Unable to send broadcast DNS packet on %s: %s" % (name, 
e))
+            raise
 
 def detectNetworkDevices(ttl=4, timeout=10):
-    mcast_addr, mcast_port ='224.0.0.251', 5353
+    mcast_addr, mcast_port =MCAST_ADDR, 5353
     found_devices = {}
     answers = []
 
-    s = createSocketsWithsetOption(ttl)
+    s, ifaces = createSocketsWithsetOption(ttl)
     if not s:
         return {}
 
@@ -321,14 +366,24 @@ def detectNetworkDevices(ttl=4, timeout=10):
             break
 
         if now >= next:
-            try:
-                for p in create_outgoing_packets(answers):
-                    log.debug("Outgoing: (%d)" % len(p))
-                    log.log_data(p, width=16)
-                    s.sendto(p, 0, (mcast_addr, mcast_port))
+            good = []
+            for idx, name in ifaces:
+                mreqn = struct.pack("=4sii", socket.inet_aton(mcast_addr),
+                                    socket.ntohl(socket.INADDR_ANY), idx)
+                try:
+                    s.setsockopt(socket.SOL_IP, socket.IP_MULTICAST_IF, mreqn)
+                except socket.error as e:
+                    log.debug("failed to set IP_MULTICAST_IF on %s" % name)
+                    continue
+                try:
+                    send_packets(s, answers, name, mcast_addr, mcast_port)
+                except socket.error:
+                    continue
+                else:
+                    good.append((idx, name))
 
-            except socket.error as e:
-                log.error("Unable to send broadcast DNS packet: %s" % e)
+            if len(good) == 0:
+                log.error("Failed to send MDNS packet on any interface")
 
             next += delay
             delay *= 2
@@ -347,7 +402,5 @@ def detectNetworkDevices(ttl=4, timeout=10):
             found_devices[y['ip']] = y
 
     log.debug("Found %d devices" % len(found_devices))
-    s.close()
+    closeSocket(s)
     return found_devices
-
-
diff --git a/protocol/discovery/mdns.c b/protocol/discovery/mdns.c
index 3324d2a..92e153a 100644
--- a/protocol/discovery/mdns.c
+++ b/protocol/discovery/mdns.c
@@ -1,3 +1,4 @@
+
 /*****************************************************************************
  mdns.c - mDNS related calls
  
@@ -29,14 +30,17 @@
 #endif
 
 #include <stdio.h>
+#include <stdlib.h>
 #include <string.h>
 #include <syslog.h>
 #include <sys/socket.h>
 #include <netinet/in.h>
 #include <netdb.h>
 #include <arpa/inet.h>
+#include <net/if.h>
 #include "mdns.h"
 #include <unistd.h>
+#include <sys/ioctl.h>
 
 /* Convert "www.google.com" to "3www6google3com". */
 static int mdns_convert_name_to_dns(const char *name, int name_size, char 
*dns_name)
@@ -71,14 +75,50 @@ static int mdns_convert_name_to_dns(const char *name, int 
name_size, char *dns_n
     return x; /* return length DOES include null termination */
 }
 
+#define MREQN_INIT(_mr, index) do {                                    \
+       (&(_mr))->imr_multiaddr.s_addr = inet_addr("224.0.0.251");      \
+       (&(_mr))->imr_address.s_addr = htonl(INADDR_ANY);               \
+       (&(_mr))->imr_ifindex = (index);                                \
+    } while(0)
+
+struct mdns_socket {
+    int socket;
+    struct if_nameindex *idx;
+    struct if_nameindex **good;
+};
+#define MDNS_SOCKET_INIT { .socket = -1, .idx = NULL, .good = NULL, }
+
+static int get_ipv4_address(const char *iface, struct in_addr *addr)
+{
+    int s, r;
+    struct ifreq ifr;
+
+    memset(&ifr, 0, sizeof(ifr));
+    strncpy(ifr.ifr_name, iface, IFNAMSIZ-1);
+
+    s = socket(AF_INET, SOCK_DGRAM, 0);
+    r = ioctl(s, SIOCGIFADDR, &ifr);
+    close(s);
+
+    if (r == -1) {
+       DBG("error in SIOCGIFADDR for %s: %m\n", iface);
+       return MDNS_STATUS_ERROR;
+    }
+
+    if (addr != NULL)
+       memcpy(addr, &((struct sockaddr_in *)&ifr.ifr_addr)->sin_addr,
+              sizeof(*addr));
+    return MDNS_STATUS_OK;
+}
 
-static int mdns_open_socket(int *psocket)
+static int mdns_open_socket(struct mdns_socket *mdns_sock)
 {
     int stat = MDNS_STATUS_ERROR;
-    int udp_socket = -1, yes = 1;
+    int udp_socket = -1, yes = 1, ifaces;
     char loop = 0, ttl = 255;
     struct sockaddr_in recv_addr , addr;
-    struct ip_mreq mreq;
+    struct ip_mreqn mreqn;
+    struct if_nameindex *idx;
 
     DBG("mdns_open_socket entry.\n");
 
@@ -120,24 +160,86 @@ static int mdns_open_socket(int *psocket)
         goto bugout;
     }
 
-    /* Join the .local multicast group */
-    mreq.imr_multiaddr.s_addr = inet_addr("224.0.0.251");
-    mreq.imr_interface.s_addr = htonl(INADDR_ANY);
-    if (setsockopt(udp_socket, IPPROTO_IP, IP_ADD_MEMBERSHIP, &mreq, 
sizeof(struct ip_mreq)) == -1) {
-        BUG("unable to add to multicast group: %m\n");
-        close(udp_socket);
+    mdns_sock->idx = if_nameindex();
+    if (mdns_sock->idx == NULL) {
+       BUG("if_nameindex failed: %m\n");
+       goto bugout;
+    }
+
+    for (idx = mdns_sock->idx, ifaces = 0;
+        idx && (idx->if_index != 0 || idx->if_name != NULL); idx++) {
+       ifaces ++;
+    }
+
+    mdns_sock->good = calloc(ifaces, sizeof(struct if_nameindex*));
+    if (mdns_sock->good == NULL)
+       goto bugout;
+
+    for (idx = mdns_sock->idx, ifaces = 0;
+        idx && (idx->if_index != 0 || idx->if_name != NULL); idx++) {
+
+       /* Skip lo and interfaces without IPv4 address */
+       if (!strcmp(idx->if_name, "lo"))
+           continue;
+       if (get_ipv4_address(idx->if_name, NULL) == MDNS_STATUS_ERROR)
+           continue;
+
+       /* Join the multicast group on each local interface */
+       MREQN_INIT(mreqn, idx->if_index);
+       if (setsockopt(udp_socket, IPPROTO_IP, IP_ADD_MEMBERSHIP, &mreqn,
+                      sizeof(struct ip_mreqn)) == -1) {
+           BUG("unable to add to multicast group for %s: %m\n", idx->if_name);
+       } else {
+           mdns_sock->good[ifaces++] = idx;
+           DBG("added multicast group on interface %s\n", idx->if_name);
+       }
+    }
+
+    if (ifaces == 0) {
+       BUG("no interfaces for multicast found\n");
         goto bugout;
     }
 
-    *psocket = udp_socket;
-    DBG("pSocket = [%d]: %m\n", *psocket);
+    mdns_sock->socket = udp_socket;
+    DBG("Socket = [%d]: %m\n", mdns_sock->socket);
     stat = MDNS_STATUS_OK;
 
 bugout:
+    if (stat != MDNS_STATUS_OK)
+       mdns_close_socket(mdns_sock);
     return stat;
 }
 
-static void mdns_create_query_packet(char* fqdn, int query_type, char* 
querybuf, int *length)
+static void mdns_close_socket(struct mdns_socket *mdns_sock)
+{
+    int i;
+    struct if_nameindex *idx;
+    struct ip_mreqn mreqn;
+    if (mdns_sock->socket != -1) {
+       for (i = 0; mdns_sock->good[i]; i++) {
+           idx = mdns_sock->good[i];
+           MREQN_INIT(mreqn, idx->if_index);
+           if (setsockopt(mdns_sock->socket, IPPROTO_IP, IP_DROP_MEMBERSHIP,
+                          &mreqn, sizeof(struct ip_mreqn)) == -1) {
+               BUG("unable to drop multicast group for %s: %m\n", 
idx->if_name);
+           };
+       }
+       close(mdns_sock->socket);
+       mdns_sock->socket = -1;
+    }
+
+    if (mdns_sock->idx != NULL) {
+       if_freenameindex(mdns_sock->idx);
+       mdns_sock->idx = NULL;
+    }
+
+    if (mdns_sock->good != NULL) {
+       free(mdns_sock->good);
+       mdns_sock->good = NULL;
+    }
+}
+
+static void mdns_create_query_packet(const char* fqdn, int query_type, char* 
querybuf, int *length)
 {
     int n = 0;
     char header[] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 
0x00, 0x00, 0x00 };
@@ -157,14 +259,14 @@ static void mdns_create_query_packet(char* fqdn, int 
query_type, char* querybuf,
     *length = n;
 }
 
-static int mdns_send_query(int udp_socket, char *fqdn, int query_type)
+static int mdns_send_query(struct mdns_socket *mdns_sock, const char *fqdn, 
int query_type)
 {
     char querybuf[256] = {0,};
-    int length = 0;
+    int length = 0, i, success;
     int stat = MDNS_STATUS_OK;
     struct sockaddr_in send_addr;
 
-    DBG("mdns_send_query entry.  send socket=%d len=%d\n", udp_socket, length);
+    DBG("mdns_send_query entry.  send socket=%d len=%d\n", mdns_sock->socket, 
length);
 
     mdns_create_query_packet(fqdn, query_type, querybuf, &length);
 
@@ -172,8 +274,26 @@ static int mdns_send_query(int udp_socket, char *fqdn, int 
query_type)
     send_addr.sin_family = AF_INET;
     send_addr.sin_addr.s_addr = inet_addr("224.0.0.251");
     send_addr.sin_port = htons(5353);
-    if (sendto(udp_socket, querybuf, length, 0, (struct sockaddr *) 
&send_addr, sizeof(send_addr)) < 0)
-        stat = MDNS_STATUS_ERROR;
+
+    for (i = 0, success = 0; mdns_sock->good[i]; i++) {
+       struct if_nameindex *idx;
+       struct ip_mreqn mreqn;
+       idx = mdns_sock->good[i];
+       MREQN_INIT(mreqn, idx->if_index);
+       if (setsockopt(mdns_sock->socket, IPPROTO_IP, IP_MULTICAST_IF, &mreqn, 
sizeof(mreqn))
+           == -1) {
+           DBG("failed to set IP_MULTICAST_IF to %s\n", idx->if_name);
+           continue;
+       }
+       if (sendto(mdns_sock->socket, querybuf, length, 0,
+                  (struct sockaddr *) &send_addr, sizeof(send_addr))< 0) {
+           DBG("failed to send on %s\n", idx->if_name);
+       } else
+           success++;
+    }
+
+    if (success == 0)
+       stat = MDNS_STATUS_ERROR;
 
     DBG("mdns_send_query returning with status(%d)...\n", stat);
     return stat;
@@ -252,7 +372,7 @@ static void mdns_read_header(char *Response, DNS_PKT_HEADER 
*h)
 
 }
 
-static void mdns_parse_respponse(unsigned char *Response, DNS_RECORD *rr)
+static int mdns_parse_respponse(unsigned char *Response, DNS_RECORD *rr)
 {
     unsigned char *p = Response;
     unsigned short type = 0, data_len = 0;
@@ -263,6 +383,11 @@ static void mdns_parse_respponse(unsigned char *Response, 
DNS_RECORD *rr)
     mdns_read_header(Response, &h);
     p += MDNS_HEADER_SIZE;
 
+    if (h.answers + h.additionals <= 0) {
+       DBG("mdns_parse_respponse: no answers");
+       return MDNS_STATUS_ERROR;
+    }
+
     for (i = 0; i < h.questions; i++)
     {
         p += mdns_readName(Response, p, rr->name);
@@ -295,6 +420,7 @@ static void mdns_parse_respponse(unsigned char *Response, 
DNS_RECORD *rr)
     }
 
     DBG("mdns_parse_respponse returning MDL = %s, IP = %s\n",rr->mdl, rr->ip);
+    return MDNS_STATUS_OK;
 }
 
 static int mdns_read_single_response(int udp_socket, char *recvbuffer, int 
recvbufsize)
@@ -328,7 +454,7 @@ static int mdns_read_single_response(int udp_socket, char 
*recvbuffer, int recvb
     return ret;
 }
 
-static DNS_RECORD *mdns_read_responses(int udp_socket, int mode)
+static DNS_RECORD *mdns_read_responses(int udp_socket, int mode, const char 
*question)
 {
     int retries = 3, ret = 0;
     char recvbuffer[MAX_MDNS_RESPONSE_LEN] =  { 0, };
@@ -351,17 +477,22 @@ static DNS_RECORD *mdns_read_responses(int udp_socket, 
int mode)
             temp = (DNS_RECORD *)malloc(sizeof(DNS_RECORD));
             if(temp)
             {
-                temp->next = NULL;
-                if(head == NULL)
-                    rr = head = temp;
-                else
-                {
-                    rr->next = temp;
-                    rr = rr->next;
-                }
-
-                memset(rr, 0, sizeof(DNS_RECORD));
-                mdns_parse_respponse(recvbuffer, rr);
+                memset(temp, 0, sizeof(DNS_RECORD));
+                if (mdns_parse_respponse(recvbuffer, temp) == MDNS_STATUS_OK &&
+                   (mode == MODE_READ_ALL || question == NULL ||
+                    !strncmp(question, temp->name, sizeof(temp->name)-1))) {
+                   if(head == NULL)
+                       rr = head = temp;
+                   else
+                   {
+                       rr->next = temp;
+                       rr = rr->next;
+                   }
+               } else {
+                   DBG("Parse error or wrong MDNS name");
+                   free(temp);
+                   continue;
+               }
 
                 if(mode == MODE_READ_SINGLE)
                     break;
@@ -421,28 +552,28 @@ static void mdns_rr_cleanup(DNS_RECORD *rr)
 int mdns_probe_nw_scanners(char* uris_buf, int buf_size, int *count)
 {
     int n = 0, bytes_read = 0;
-    int udp_socket = 0;
+    struct mdns_socket mdns_sock = MDNS_SOCKET_INIT;
     int stat = MDNS_STATUS_ERROR;
     DNS_RECORD *rr_list = NULL;
+    const char scanner_name[] = "_scanner._tcp.local";
 
     DBG("mdns_probe_nw_scanners entry.\n");
     /* Open UDP socket */
-    if (mdns_open_socket(&udp_socket) != MDNS_STATUS_OK)
+    if (mdns_open_socket(&mdns_sock) != MDNS_STATUS_OK)
         goto bugout;
 
     /* Send dns query */
-    mdns_send_query(udp_socket, "_scanner._tcp.local", QTYPE_PTR);
+    mdns_send_query(&mdns_sock, scanner_name, QTYPE_PTR);
 
     /* Read Responses */
-    rr_list = mdns_read_responses(udp_socket, MODE_READ_ALL);
+    rr_list = mdns_read_responses(mdns_sock.socket, MODE_READ_ALL, 
scanner_name);
 
     /* Update URIs buffer */
     bytes_read = mdns_update_uris(rr_list, uris_buf, buf_size, count);
     DBG("mdns_probe_nw_scanners returned with bytes_read = 
[%d].\n",bytes_read);
 
 bugout:
-    if (udp_socket >= 0)
-        close(udp_socket);
+    mdns_close_socket(&mdns_sock);
 
     mdns_rr_cleanup(rr_list);
 
@@ -455,22 +586,22 @@ bugout:
  */
 int mdns_lookup(char* hostname, unsigned char* ip)
 {
-    int udp_socket = 0;
+    struct mdns_socket mdns_sock = MDNS_SOCKET_INIT;
     int stat = MDNS_STATUS_ERROR;
     char fqdn[MAX_NAME_LENGTH] = {0};
     DNS_RECORD *rr_list = NULL;
 
     DBG("mdns_probe_nw_scanners entry.\n");
     /* Open UDP socket */
-    if (mdns_open_socket(&udp_socket) != MDNS_STATUS_OK)
+    if (mdns_open_socket(&mdns_sock) != MDNS_STATUS_OK)
         goto bugout;
 
     /* Send dns query */
     sprintf(fqdn, "%s.local", hostname);
-    mdns_send_query(udp_socket, fqdn, QTYPE_A);
+    mdns_send_query(&mdns_sock, fqdn, QTYPE_A);
 
     /* Read Responses */
-    rr_list = mdns_read_responses(udp_socket, MODE_READ_SINGLE);
+    rr_list = mdns_read_responses(mdns_sock.socket, MODE_READ_SINGLE, fqdn);
 
     /* Update IP Address buffer */
     if(rr_list)
@@ -481,8 +612,7 @@ int mdns_lookup(char* hostname, unsigned char* ip)
     }
 
 bugout:
-    if (udp_socket >= 0)
-        close(udp_socket);
+    mdns_close_socket(&mdns_sock);
 
     mdns_rr_cleanup(rr_list);
     return stat;
diff --git a/protocol/discovery/mdns.h b/protocol/discovery/mdns.h
index 8fccc82..34066fb 100644
--- a/protocol/discovery/mdns.h
+++ b/protocol/discovery/mdns.h
@@ -86,19 +86,21 @@ typedef struct _DNS_PKT_HEADER
 int   mdns_probe_nw_scanners(char* buf, int buf_size, int *count);
 int   mdns_lookup(char* hostname, unsigned char* ip);
 
+struct mdns_socket;
 
 /*Helper Function Prototypes*/
 static int   mdns_convert_name_to_dns(const char *name, int name_size, char 
*dns_name);
 static int   mdns_read_single_response(int udp_socket, char *recvbuffer, int 
recvbufsize);
-static int   mdns_open_socket(int *psocket);
-static int   mdns_send_query(int udp_socket, char *fqdn, int query_type);
+static int   mdns_open_socket(struct mdns_socket *mdns_sock);
+static void  mdns_close_socket(struct mdns_socket *mdns_sock);
+static int   mdns_send_query(struct mdns_socket *mdns_sock, const char *fqdn, 
int query_type);
 static int   mdns_readName(unsigned char* start, unsigned char *p, char *buf);
 static int   mdns_update_uris(DNS_RECORD *rr, char* uris_buf, int buf_size, 
int *count);
-static void  mdns_create_query_packet(char* fqdn, int query_type, char* 
dnsquery, int *length);
+static void  mdns_create_query_packet(const char* fqdn, int query_type, char* 
dnsquery, int *length);
 static void  mdns_read_header(char *Response, DNS_PKT_HEADER *h);
-static void  mdns_parse_respponse(unsigned char *Response, DNS_RECORD *rr);
+static int   mdns_parse_respponse(unsigned char *Response, DNS_RECORD *rr);
 static void  mdns_rr_cleanup(DNS_RECORD *rr);
-static DNS_RECORD *mdns_read_responses(int udp_socket, int mode);
+static DNS_RECORD *mdns_read_responses(int udp_socket, int mode, const char 
*question);
 static unsigned char* mdns_readMDL(unsigned char *p, unsigned char 
*normalized_mdl, int len);
 #endif // _DISCOVERY_MDNS_H
 


Reply via email to