Introduce a new function to help to get interface IPv6 address. Signed-off-by: Luyao Huang <lhuang@xxxxxxxxxx> --- src/libvirt_private.syms | 1 + src/util/virnetdev.c | 70 ++++++++++++++++++++++++++++++++++++++++++++++++ src/util/virnetdev.h | 2 ++ 3 files changed, 73 insertions(+) diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms index 645aef1..f60911c 100644 --- a/src/libvirt_private.syms +++ b/src/libvirt_private.syms @@ -1659,6 +1659,7 @@ virNetDevDelMulti; virNetDevExists; virNetDevGetIndex; virNetDevGetIPv4Address; +virNetDevGetIPv6Address; virNetDevGetLinkInfo; virNetDevGetMAC; virNetDevGetMTU; diff --git a/src/util/virnetdev.c b/src/util/virnetdev.c index 2a0eb43..c1a588e 100644 --- a/src/util/virnetdev.c +++ b/src/util/virnetdev.c @@ -33,6 +33,10 @@ #include "virstring.h" #include "virutil.h" +#if defined(HAVE_GETIFADDRS) +# include <ifaddrs.h> +#endif + #include <sys/ioctl.h> #include <net/if.h> #include <fcntl.h> @@ -1432,6 +1436,72 @@ int virNetDevGetIPv4Address(const char *ifname ATTRIBUTE_UNUSED, #endif /* ! SIOCGIFADDR */ +/** + *virNetDevGetIPv6Address: + *@ifname: name of the interface whose IP address we want + *@addr: filled with the IPv6 address + * + *This function gets the IPv6 address for the interface @ifname + *and stores it in @addr + * + *Returns 0 on success, -1 on failure. + */ +#if defined(HAVE_GETIFADDRS) +int virNetDevGetIPv6Address(const char *ifname, + virSocketAddrPtr addr) +{ + struct ifaddrs *ifap, *ifa; + int ret = -1; + bool found_one = false; + + if (getifaddrs(&ifap) < 0) { + virReportSystemError(errno, "%s", + _("Could not get interface list")); + return -1; + } + + for (ifa = ifap; ifa; ifa = ifa->ifa_next) { + if (STRNEQ(ifa->ifa_name, ifname)) + continue; + found_one = true; + if (ifa->ifa_addr->sa_family == AF_INET6) + break; + } + + if (!ifa) { + if (found_one) + virReportError(VIR_ERR_INTERNAL_ERROR, + _("Interface '%s' do not have a IPv6 address"), + ifname); + else + virReportError(VIR_ERR_INTERNAL_ERROR, + _("Interface '%s' not found"), + ifname); + goto cleanup; + } + + addr->data.stor.ss_family = AF_INET6; + addr->len = sizeof(addr->data.inet6); + memcpy(&addr->data.inet6, ifa->ifa_addr, addr->len); + ret = 0; + + cleanup: + freeifaddrs(ifap); + return ret; +} + +#else + +int virNetDevGetIPv6Address(const char *ifname ATTRIBUTE_UNUSED, + virSocketAddrPtr addr ATTRIBUTE_UNUSED) +{ + virReportSystemError(ENOSYS, "%s", + _("Unable to get IPv6 address on this platform")); + return -1; +} + +#endif + /** * virNetDevValidateConfig: diff --git a/src/util/virnetdev.h b/src/util/virnetdev.h index de8b480..c065381 100644 --- a/src/util/virnetdev.h +++ b/src/util/virnetdev.h @@ -104,6 +104,8 @@ int virNetDevClearIPAddress(const char *ifname, ATTRIBUTE_NONNULL(1) ATTRIBUTE_NONNULL(2) ATTRIBUTE_RETURN_CHECK; int virNetDevGetIPv4Address(const char *ifname, virSocketAddrPtr addr) ATTRIBUTE_NONNULL(1) ATTRIBUTE_NONNULL(2) ATTRIBUTE_RETURN_CHECK; +int virNetDevGetIPv6Address(const char *ifname, virSocketAddrPtr addr) + ATTRIBUTE_NONNULL(1) ATTRIBUTE_NONNULL(2) ATTRIBUTE_RETURN_CHECK; int virNetDevSetMAC(const char *ifname, -- 1.8.3.1 -- libvir-list mailing list libvir-list@xxxxxxxxxx https://www.redhat.com/mailman/listinfo/libvir-list