[libvirt] [PATCH 15/17] nss: directly use getnameinfo/getaddrinfo

Daniel P. Berrangé berrange at redhat.com
Thu Aug 1 15:00:17 UTC 2019


Use the plain libc socket APIs to avoid a dependancy on the main
libvirt code from the nss module.

Signed-off-by: Daniel P. Berrangé <berrange at redhat.com>
---
 tools/nss/libvirt_nss.c        | 36 ++++++++++++++++------
 tools/nss/libvirt_nss_leases.c | 56 +++++++++++++++++++++++++---------
 2 files changed, 69 insertions(+), 23 deletions(-)

diff --git a/tools/nss/libvirt_nss.c b/tools/nss/libvirt_nss.c
index 47d2ba9435..2719e19cda 100644
--- a/tools/nss/libvirt_nss.c
+++ b/tools/nss/libvirt_nss.c
@@ -38,7 +38,6 @@
 
 #include "viralloc.h"
 #include "virtime.h"
-#include "virsocketaddr.h"
 #include "configmake.h"
 
 #include "libvirt_nss_leases.h"
@@ -474,25 +473,45 @@ aiforaf(const char *name, int af, struct addrinfo *pai, struct addrinfo **aip)
 
     addrList = resolved.h_addr_list;
     while (*addrList) {
-        virSocketAddr sa;
-        char *ipAddr = NULL;
+        union {
+            struct sockaddr sa;
+            struct sockaddr_in sin;
+            struct sockaddr_in6 sin6;
+        } sa;
+        socklen_t salen;
         void *address = *addrList;
+        char host[NI_MAXHOST];
+        char port[NI_MAXSERV];
 
         memset(&sa, 0, sizeof(sa));
         if (resolved.h_addrtype == AF_INET) {
-            virSocketAddrSetIPv4AddrNetOrder(&sa, *((uint32_t *) address));
+            sa.sin.sin_family = AF_INET;
+            memcpy(&sa.sin.sin_addr.s_addr,
+                   address,
+                   FAMILY_ADDRESS_SIZE(AF_INET));
+            salen = sizeof(sa.sin);
         } else {
-            virSocketAddrSetIPv6AddrNetOrder(&sa, address);
+            sa.sin6.sin6_family = AF_INET6;
+            memcpy(&sa.sin6.sin6_addr.s6_addr,
+                   address,
+                   FAMILY_ADDRESS_SIZE(AF_INET6));
+            salen = sizeof(sa.sin6);
         }
 
-        ipAddr = virSocketAddrFormat(&sa);
+        if ((err = getnameinfo(&sa.sa, salen,
+                               host, sizeof(host),
+                               port, sizeof(port),
+                               NI_NUMERICHOST | NI_NUMERICSERV)) != 0) {
+            ERROR("Cannot convert socket address to string: %s",
+                  gai_strerror(err));
+            continue;
+        }
 
         hints = *pai;
         hints.ai_flags = AI_NUMERICHOST;
         hints.ai_family = af;
 
-        if (getaddrinfo(ipAddr, NULL, &hints, &res0)) {
-            VIR_FREE(ipAddr);
+        if (getaddrinfo(host, NULL, &hints, &res0)) {
             addrList++;
             continue;
         }
@@ -504,7 +523,6 @@ aiforaf(const char *name, int af, struct addrinfo *pai, struct addrinfo **aip)
         while ((*aip)->ai_next)
            *aip = (*aip)->ai_next;
 
-        VIR_FREE(ipAddr);
         addrList++;
     }
 }
diff --git a/tools/nss/libvirt_nss_leases.c b/tools/nss/libvirt_nss_leases.c
index 44089af313..803b14cc55 100644
--- a/tools/nss/libvirt_nss_leases.c
+++ b/tools/nss/libvirt_nss_leases.c
@@ -30,7 +30,6 @@
 
 #include "libvirt_nss_leases.h"
 #include "libvirt_nss.h"
-#include "virsocketaddr.h"
 #include "viralloc.h"
 
 enum {
@@ -69,18 +68,47 @@ appendAddr(const char *name ATTRIBUTE_UNUSED,
            long long expirytime,
            int af)
 {
-    virSocketAddr sa;
     int family;
     size_t i;
+    struct addrinfo hints = {0};
+    struct addrinfo *res = NULL;
+    union {
+        struct sockaddr sa;
+        struct sockaddr_in sin;
+        struct sockaddr_in6 sin6;
+    } sa;
+    unsigned char addr[16];
+    int err;
 
     DEBUG("IP address: %s", ipAddr);
-    if (virSocketAddrParse(&sa, ipAddr, AF_UNSPEC) < 0) {
-        ERROR("Unable to parse %s", ipAddr);
+
+    hints.ai_family = AF_UNSPEC;
+    hints.ai_flags = AI_NUMERICHOST;
+
+    if ((err = getaddrinfo(ipAddr, NULL, &hints, &res)) != 0) {
+        ERROR("Cannot parse socket address '%s': %s",
+              ipAddr, gai_strerror(err));
+        return -1;
+    }
+
+    if (!res) {
+        ERROR("No resolved address for '%s'", ipAddr);
         return -1;
     }
+    family = res->ai_family;
+    memcpy(&sa, res->ai_addr, res->ai_addrlen);
+    freeaddrinfo(res);
+
+    if (family == AF_INET) {
+        memcpy(addr, &sa.sin.sin_addr, sizeof(sa.sin.sin_addr));
+    } else if (family == AF_INET6) {
+        memcpy(addr, &sa.sin6.sin6_addr, sizeof(sa.sin6.sin6_addr));
+    } else {
+        DEBUG("Skipping unexpected family %d", family);
+        return 0;
+    }
 
-    family = VIR_SOCKET_ADDR_FAMILY(&sa);
-    if (af != AF_UNSPEC && af != family) {
+     if (af != AF_UNSPEC && af != family) {
         DEBUG("Skipping address which family is %d, %d requested", family, af);
         return 0;
     }
@@ -88,15 +116,15 @@ appendAddr(const char *name ATTRIBUTE_UNUSED,
     for (i = 0; i < *ntmpAddress; i++) {
         if (family == AF_INET) {
             if (memcmp((*tmpAddress)[i].addr,
-                       &sa.data.inet4.sin_addr.s_addr,
-                       sizeof(sa.data.inet4.sin_addr.s_addr)) == 0) {
+                       &sa.sin.sin_addr,
+                       sizeof(sa.sin.sin_addr)) == 0) {
                 DEBUG("IP address already in the list");
                 return 0;
             }
         } else {
             if (memcmp((*tmpAddress)[i].addr,
-                       &sa.data.inet6.sin6_addr.s6_addr,
-                       sizeof(sa.data.inet6.sin6_addr.s6_addr)) == 0) {
+                       &sa.sin6.sin6_addr,
+                       sizeof(sa.sin6.sin6_addr)) == 0) {
                 DEBUG("IP address already in the list");
                 return 0;
             }
@@ -112,12 +140,12 @@ appendAddr(const char *name ATTRIBUTE_UNUSED,
     (*tmpAddress)[*ntmpAddress].af = family;
     if (family == AF_INET)
         memcpy((*tmpAddress)[*ntmpAddress].addr,
-               &sa.data.inet4.sin_addr.s_addr,
-               sizeof(sa.data.inet4.sin_addr.s_addr));
+               &sa.sin.sin_addr,
+               sizeof(sa.sin.sin_addr));
     else
         memcpy((*tmpAddress)[*ntmpAddress].addr,
-               &sa.data.inet6.sin6_addr.s6_addr,
-               sizeof(sa.data.inet6.sin6_addr.s6_addr));
+               &sa.sin6.sin6_addr,
+               sizeof(sa.sin6.sin6_addr));
     (*ntmpAddress)++;
     return 0;
 }
-- 
2.21.0




More information about the libvir-list mailing list