use libperfstat for net_interface_stat when available

This commit is contained in:
Doug MacEachern 2006-07-07 00:19:50 +00:00
parent 98c1392db0
commit ea4f9c7ee4
2 changed files with 81 additions and 2 deletions

View File

@ -379,6 +379,23 @@ static int sigar_perfstat_init(sigar_t *sigar)
return ENOENT; return ENOENT;
} }
sigar->perfstat.ifstat =
(perfstat_ifstat_func_t)dlsym(handle,
"sigar_perfstat_netinterface");
if (!sigar->perfstat.ifstat) {
if (SIGAR_LOG_IS_DEBUG(sigar)) {
sigar_log_printf(sigar, SIGAR_LOG_DEBUG,
"dlsym(sigar_perfstat_netinterface) failed: %s",
dlerror());
}
dlclose(handle);
sigar->perfstat.avail = -1;
return ENOENT;
}
sigar->perfstat.avail = 1; sigar->perfstat.avail = 1;
sigar->perfstat.handle = handle; sigar->perfstat.handle = handle;
@ -1951,14 +1968,17 @@ int sigar_net_route_list_get(sigar_t *sigar,
return SIGAR_ENOTIMPL; return SIGAR_ENOTIMPL;
} }
int sigar_net_interface_stat_get(sigar_t *sigar, const char *name, static int sigar_net_interface_stat_get_kmem(sigar_t *sigar,
sigar_net_interface_stat_t *ifstat) const char *name,
sigar_net_interface_stat_t *ifstat)
{ {
int status; int status;
struct ifnet data; struct ifnet data;
caddr_t offset = 0; caddr_t offset = 0;
char if_name[32]; char if_name[32];
sigar_log(sigar, SIGAR_LOG_DEBUG, "[ifstat] using /dev/kmem");
status = kread(sigar, &offset, sizeof(offset), status = kread(sigar, &offset, sizeof(offset),
sigar->koffsets[KOFFSET_IFNET]); sigar->koffsets[KOFFSET_IFNET]);
@ -2008,6 +2028,61 @@ int sigar_net_interface_stat_get(sigar_t *sigar, const char *name,
return ENXIO; return ENXIO;
} }
static int sigar_net_interface_stat_get_perfstat(sigar_t *sigar,
const char *name,
sigar_net_interface_stat_t *ifstat)
{
perfstat_id_t id;
perfstat_netinterface_t data;
sigar_log(sigar, SIGAR_LOG_DEBUG, "[ifstat] using libperfstat");
SIGAR_SSTRCPY(id.name, name);
if (sigar->perfstat.ifstat(&id, &data) == 1) {
ifstat->rx_bytes = data.ibytes;
ifstat->rx_packets = data.ipackets;
ifstat->rx_errors = data.ierrors;
ifstat->rx_dropped = SIGAR_FIELD_NOTIMPL;
ifstat->rx_overruns = SIGAR_FIELD_NOTIMPL;
ifstat->rx_frame = SIGAR_FIELD_NOTIMPL;
ifstat->tx_bytes = data.obytes;
ifstat->tx_packets = data.opackets;
ifstat->tx_errors = data.oerrors;
ifstat->tx_dropped = SIGAR_FIELD_NOTIMPL;
ifstat->tx_overruns = SIGAR_FIELD_NOTIMPL;
ifstat->tx_collisions = data.collisions;
ifstat->tx_carrier = SIGAR_FIELD_NOTIMPL;
ifstat->speed = data.bitrate;
return SIGAR_OK;
}
if (SIGAR_LOG_IS_DEBUG(sigar)) {
sigar_log_printf(sigar, SIGAR_LOG_DEBUG,
"[ifstat] dev=%s query failed: %s",
name,
sigar_strerror(sigar, errno));
}
return sigar_net_interface_stat_get_kmem(sigar, name, ifstat);
}
int sigar_net_interface_stat_get(sigar_t *sigar, const char *name,
sigar_net_interface_stat_t *ifstat)
{
sigar_perfstat_init(sigar);
if (sigar->perfstat.ifstat) {
return sigar_net_interface_stat_get_perfstat(sigar, name, ifstat);
}
else {
return sigar_net_interface_stat_get_kmem(sigar, name, ifstat);
}
}
#define IS_TCP_SERVER(state, flags) \ #define IS_TCP_SERVER(state, flags) \
((flags & SIGAR_NETCONN_SERVER) && (state == TCPS_LISTEN)) ((flags & SIGAR_NETCONN_SERVER) && (state == TCPS_LISTEN))

View File

@ -44,6 +44,9 @@ typedef int (*perfstat_disk_func_t)(perfstat_id_t *,
perfstat_disk_t *, perfstat_disk_t *,
size_t, int); size_t, int);
typedef int (*perfstat_ifstat_func_t)(perfstat_id_t *,
perfstat_netinterface_t *);
typedef int (*thread_rusage_func_t)(struct rusage *, int); typedef int (*thread_rusage_func_t)(struct rusage *, int);
struct sigar_t { struct sigar_t {
@ -60,6 +63,7 @@ struct sigar_t {
perfstat_cpu_total_func_t cpu_total; perfstat_cpu_total_func_t cpu_total;
perfstat_swap_func_t swap; perfstat_swap_func_t swap;
perfstat_disk_func_t disk; perfstat_disk_func_t disk;
perfstat_ifstat_func_t ifstat;
thread_rusage_func_t thread_rusage; thread_rusage_func_t thread_rusage;
void *handle; void *handle;
} perfstat; } perfstat;