1 /* $Id: getifstats.c,v 1.11 2012/04/06 15:26:45 nanard Exp $ */
3 * http://miniupnp.free.fr/ or http://miniupnp.tuxfamily.org/
4 * (c) 2006-2012 Thomas Bernard
5 * This software is subject to the conditions detailed
6 * in the LICENCE file provided within the distribution */
14 #include "../config.h"
15 #include "../getifstats.h"
18 getifstats(const char * ifname
, struct ifdata
* data
)
26 #ifdef ENABLE_GETIFSTATS_CACHING
27 static time_t cache_timestamp
= 0;
28 static struct ifdata cache_data
;
33 data
->baudrate
= 4200000; /* that is the answer */
38 if(!ifname
|| ifname
[0]=='\0')
40 #ifdef ENABLE_GETIFSTATS_CACHING
41 current_time
= time(NULL
);
42 if(current_time
== ((time_t)-1)) {
43 syslog(LOG_ERR
, "getifstats() : time() error : %m");
45 if(current_time
< cache_timestamp
+ GETIFSTATS_CACHING_DURATION
) {
46 /* return cached data */
47 memcpy(data
, &cache_data
, sizeof(struct ifdata
));
52 f
= fopen("/proc/net/dev", "r");
54 syslog(LOG_ERR
, "getifstats() : cannot open /proc/net/dev : %m");
57 /* discard the two header lines */
58 if(!fgets(line
, sizeof(line
), f
) || !fgets(line
, sizeof(line
), f
)) {
59 syslog(LOG_ERR
, "getifstats() : error reading /proc/net/dev : %m");
61 while(fgets(line
, sizeof(line
), f
)) {
65 while(ifname
[i
] == *p
) {
68 /* TODO : how to handle aliases ? */
69 if(ifname
[i
] || *p
!= ':')
73 data
->ibytes
= strtoul(p
, &p
, 0);
75 data
->ipackets
= strtoul(p
, &p
, 0);
77 for(i
=6; i
>0 && *p
!='\0'; i
--) {
79 while(*p
!=' ' && *p
) p
++;
82 data
->obytes
= strtoul(p
, &p
, 0);
84 data
->opackets
= strtoul(p
, &p
, 0);
89 /* get interface speed */
90 snprintf(fname
, sizeof(fname
), "/sys/class/net/%s/speed", ifname
);
91 f
= fopen(fname
, "r");
93 if(fgets(line
, sizeof(line
), f
)) {
94 i
= atoi(line
); /* 65535 means unknown */
95 if(i
> 0 && i
< 65535)
96 data
->baudrate
= 1000000*i
;
100 syslog(LOG_INFO
, "cannot read %s file : %m", fname
);
102 #ifdef ENABLE_GETIFSTATS_CACHING
103 if(r
==0 && current_time
!=((time_t)-1)) {
104 /* cache the new data */
105 cache_timestamp
= current_time
;
106 memcpy(&cache_data
, data
, sizeof(struct ifdata
));