From 7041d070f10e2681025e52972afac5bdbdcc6405 Mon Sep 17 00:00:00 2001 From: Adam Stokes Date: Mon, 28 Feb 2011 09:46:33 -0500 Subject: [PATCH] - Update list network interfaces win32 variant Some utilities such as netsh require a friendly name when doing any administrative tasks such as stop/start network interfaces. Currently sigar list network interfaces as 'ethX, lo, laX'. This is fine for read only purposes but in order to make further use of the network interfaces on windows we need a friendlyname or at least the interface description. --- include/sigar.h | 12 +++++--- src/os/win32/win32_sigar.c | 62 ++++++++++++++++++++++++++++++++++++-- 2 files changed, 67 insertions(+), 7 deletions(-) diff --git a/include/sigar.h b/include/sigar.h index 48974ed4..3b26cb89 100644 --- a/include/sigar.h +++ b/include/sigar.h @@ -23,6 +23,10 @@ #include +#ifndef MAX_INTERFACE_NAME_LEN +#define MAX_INTERFACE_NAME_LEN 256 +#endif + #ifdef __cplusplus extern "C" { #endif @@ -529,7 +533,7 @@ typedef struct { typedef struct { char default_gateway[SIGAR_INET6_ADDRSTRLEN]; - char default_gateway_interface[16]; + char default_gateway_interface[MAX_INTERFACE_NAME_LEN]; char host_name[SIGAR_MAXHOSTNAMELEN]; char domain_name[SIGAR_MAXDOMAINNAMELEN]; char primary_dns[SIGAR_INET6_ADDRSTRLEN]; @@ -556,7 +560,7 @@ typedef struct { mtu, window, irtt; - char ifname[16]; + char ifname[MAX_INTERFACE_NAME_LEN]; } sigar_net_route_t; typedef struct { @@ -602,7 +606,7 @@ SIGAR_DECLARE(int) sigar_net_route_list_destroy(sigar_t *sigar, #define SIGAR_IPV6_ADDR_COMPATv4 0x0080 typedef struct { - char name[16]; + char name[MAX_INTERFACE_NAME_LEN]; char type[64]; char description[256]; sigar_net_address_t hwaddr; @@ -847,7 +851,7 @@ sigar_net_listen_address_get(sigar_t *sigar, sigar_net_address_t *address); typedef struct { - char ifname[16]; + char ifname[MAX_INTERFACE_NAME_LEN]; char type[64]; sigar_net_address_t hwaddr; sigar_net_address_t address; diff --git a/src/os/win32/win32_sigar.c b/src/os/win32/win32_sigar.c index 87076c84..f5b55644 100755 --- a/src/os/win32/win32_sigar.c +++ b/src/os/win32/win32_sigar.c @@ -2671,6 +2671,42 @@ static int netif_hash(char *s) #define IF_TYPE_IEEE80211 71 #endif +SIGAR_DECLARE(char *) +sigar_net_interface_name_get(sigar_t *sigar, MIB_IFROW *ifr) +{ + char *match = NULL; + PIP_ADAPTER_ADDRESSES address_list, iter; + int lpc = 0; + + sigar_t *peek = sigar_new(); + int status = sigar_get_adapters_addresses(peek, AF_UNSPEC, GAA_FLAG_INCLUDE_PREFIX, &address_list); + if (status != SIGAR_OK) { + goto done; + } + + for (iter = address_list; iter != NULL; iter = iter->Next) { + for(lpc = 0; lpc < iter->PhysicalAddressLength; lpc++) { + if(iter->PhysicalAddress[lpc] != ifr->bPhysAddr[lpc]) { + break; + } + } + + if(lpc == iter->PhysicalAddressLength) { + match = malloc(MAX_INTERFACE_NAME_LEN); + wcstombs(match, iter->FriendlyName, MAX_INTERFACE_NAME_LEN); + match[MAX_INTERFACE_NAME_LEN-1] = 0; + goto done; + } + } + + done: + sigar_close(peek); + if(match == NULL) { + fprintf(stderr, "No match found\n"); + } + return match; +} + SIGAR_DECLARE(int) sigar_net_interface_list_get(sigar_t *sigar, sigar_net_interface_list_t *iflist) @@ -2701,22 +2737,42 @@ sigar_net_interface_list_get(sigar_t *sigar, } for (i=0; idwNumEntries; i++) { - char name[16]; + char name[MAX_INTERFACE_NAME_LEN]; int key; MIB_IFROW *ifr = ift->table + i; sigar_cache_entry_t *entry; + char *friendly = NULL; if (strEQ(ifr->bDescr, MS_LOOPBACK_ADAPTER)) { /* special-case */ sprintf(name, NETIF_LA "%d", la++); } else if (ifr->dwType == MIB_IF_TYPE_LOOPBACK) { - sprintf(name, "lo%d", lo++); + friendly = sigar_net_interface_name_get(sigar, ifr); + if(friendly == NULL) { + sprintf(name, "lo%d", lo++); + } else { + snprintf(name, MAX_INTERFACE_NAME_LEN, "%s", friendly); + } + name[MAX_INTERFACE_NAME_LEN] = 0; + free(friendly); } else if ((ifr->dwType == MIB_IF_TYPE_ETHERNET) || (ifr->dwType == IF_TYPE_IEEE80211)) { - sprintf(name, "eth%d", eth++); + + if(strstr(ifr->bDescr, "Scheduler") == NULL + && strstr(ifr->bDescr, "Filter") == NULL) { + friendly = sigar_net_interface_name_get(sigar, ifr); + } + + if(friendly == NULL) { + snprintf(name, ifr->dwDescrLen, "%s", ifr->bDescr); + } else { + snprintf(name, MAX_INTERFACE_NAME_LEN, "%s", friendly); + } + name[MAX_INTERFACE_NAME_LEN] = 0; + free(friendly); } else { continue; /*XXX*/