~ubuntu-branches/ubuntu/trusty/net-snmp/trusty

« back to all changes in this revision

Viewing changes to agent/mibgroup/if-mib/data_access/interface_linux.c

  • Committer: Bazaar Package Importer
  • Author(s): Steve Kowalik
  • Date: 2007-12-08 14:59:50 UTC
  • mfrom: (1.1.6 upstream)
  • Revision ID: james.westby@ubuntu.com-20071208145950-u1tykhpw56nyzqik
Tags: 5.4.1~dfsg-4ubuntu1
* Merge from debian unstable.
* Remaining Ubuntu changes:
  - Remove stop links from rc0 and rc6
  - Munge Maintainer field as per spec.
* Ubuntu changes dropped:
  - Symlink common files between the packages, CDBS ought to handle that
    for us automatically.
* The latest Debian changes has dropped history from the changelog. Slot in
  the Ubuntu changes as best I can. 

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
1
/*
2
2
 *  Interface MIB architecture support
3
3
 *
4
 
 * $Id: interface_linux.c,v 1.28.2.4 2006/04/25 17:39:54 hardaker Exp $
 
4
 * $Id: interface_linux.c 16595 2007-07-06 21:14:03Z rstory $
5
5
 */
6
6
#include <net-snmp/net-snmp-config.h>
7
7
#include <net-snmp/net-snmp-includes.h>
 
8
 
 
9
#ifdef HAVE_LINUX_ETHTOOL_H
 
10
#include <linux/types.h>
 
11
typedef __u64 u64;         /* hack, so we may include kernel's ethtool.h */
 
12
typedef __u32 u32;         /* ditto */
 
13
typedef __u16 u16;         /* ditto */
 
14
typedef __u8 u8;           /* ditto */
 
15
#include <linux/ethtool.h>
 
16
#endif /* HAVE_LINUX_ETHTOOL_H */
 
17
 
8
18
#include "mibII/mibII_common.h"
9
19
#include "if-mib/ifTable/ifTable_constants.h"
10
20
 
22
32
#include "interface_ioctl.h"
23
33
 
24
34
#include <sys/types.h>
 
35
#include <sys/stat.h>
 
36
#include <unistd.h>
25
37
 
26
 
#ifdef HAVE_LINUX_ETHTOOL_H
27
 
#include <sys/types.h>
28
 
typedef unsigned long long u64;         /* hack, so we may include kernel's ethtool.h */
29
 
typedef __uint32_t u32;         /* ditto */
30
 
typedef __uint16_t u16;         /* ditto */
31
 
typedef __uint8_t u8;           /* ditto */
32
 
#include <linux/ethtool.h>
33
 
#endif /* HAVE_LINUX_ETHTOOL_H */
34
38
#include <linux/sockios.h>
35
39
 
 
40
#ifndef IF_NAMESIZE
 
41
#define IF_NAMESIZE 16
 
42
#endif
 
43
 
36
44
unsigned int
37
45
netsnmp_linux_interface_get_if_speed(int fd, const char *name);
38
46
#ifdef HAVE_LINUX_ETHTOOL_H
40
48
netsnmp_linux_interface_get_if_speed_mii(int fd, const char *name);
41
49
#endif
42
50
 
43
 
 
 
51
#define PROC_SYS_NET_IPVx_NEIGH_RETRANS_TIME_MS "/proc/sys/net/ipv%d/neigh/%s/retrans_time_ms"
 
52
#define PROC_SYS_NET_IPVx_NEIGH_RETRANS_TIME    "/proc/sys/net/ipv%d/neigh/%s/retrans_time"
 
53
static const char *proc_sys_retrans_time;
 
54
static unsigned short retrans_time_factor = 1;
 
55
 
 
56
 
 
57
#define PROC_SYS_NET_IPVx_BASE_REACHABLE_TIME_MS "/proc/sys/net/ipv%d/neigh/%s/base_reachable_time_ms"
 
58
#define PROC_SYS_NET_IPVx_BASE_REACHABLE_TIME "/proc/sys/net/ipv%d/neigh/%s/base_reachable_time"
 
59
static const char *proc_sys_basereachable_time;
 
60
static unsigned short basereachable_time_ms = 0;
44
61
void
45
62
netsnmp_arch_interface_init(void)
46
63
{
47
64
    /*
48
 
     * nothing to do
 
65
     * Check which retransmit time interface is available
49
66
     */
 
67
    char proc_path[ 64+IF_NAMESIZE];
 
68
    char proc_path2[64+IF_NAMESIZE];
 
69
    struct stat st;
 
70
 
 
71
    snprintf(proc_path,  sizeof(proc_path),
 
72
             PROC_SYS_NET_IPVx_NEIGH_RETRANS_TIME_MS, 6, "default");
 
73
    snprintf(proc_path2, sizeof(proc_path2),
 
74
             PROC_SYS_NET_IPVx_NEIGH_RETRANS_TIME_MS, 4, "default");
 
75
 
 
76
    if ((stat(proc_path, &st) == 0) || (stat(proc_path2, &st) == 0)) {
 
77
        proc_sys_retrans_time = PROC_SYS_NET_IPVx_NEIGH_RETRANS_TIME_MS;
 
78
    } else {
 
79
        proc_sys_retrans_time = PROC_SYS_NET_IPVx_NEIGH_RETRANS_TIME;
 
80
        retrans_time_factor = 10;
 
81
    }
 
82
 
 
83
    snprintf(proc_path,  sizeof(proc_path),  PROC_SYS_NET_IPVx_BASE_REACHABLE_TIME_MS, 6, "default");
 
84
    snprintf(proc_path2,  sizeof(proc_path),  PROC_SYS_NET_IPVx_BASE_REACHABLE_TIME, 4, "default");
 
85
 
 
86
    if ((stat(proc_path, &st) == 0) || (stat(proc_path2, &st) == 0)) {
 
87
        proc_sys_basereachable_time = PROC_SYS_NET_IPVx_BASE_REACHABLE_TIME_MS;
 
88
        basereachable_time_ms = 1;
 
89
    }
 
90
    else {
 
91
        proc_sys_basereachable_time = PROC_SYS_NET_IPVx_BASE_REACHABLE_TIME;
 
92
    }
50
93
}
51
94
 
52
95
/*
72
115
_arch_interface_has_ipv6(oid if_index, u_int *flags,
73
116
                         netsnmp_container *addr_container)
74
117
{
75
 
#ifdef INET6
 
118
#ifdef NETSNMP_ENABLE_IPV6
76
119
    netsnmp_ipaddress_entry *addr_entry = NULL;
77
120
    netsnmp_iterator        *addr_it = NULL;
78
121
    u_int                    addr_container_flags = 0; /* must init to 0 */
83
126
 
84
127
    *flags &= ~NETSNMP_INTERFACE_FLAGS_HAS_IPV6;
85
128
 
86
 
#ifdef INET6
 
129
#ifdef NETSNMP_ENABLE_IPV6
87
130
    /*
88
131
     * get ipv6 addresses
89
132
     */
161
204
    /*
162
205
     * get the retransmit time
163
206
     */
164
 
    snprintf(line,sizeof(line),"/proc/sys/net/ipv4/neigh/%s/retrans_time",
 
207
    snprintf(line,sizeof(line), proc_sys_retrans_time, 4,
165
208
             entry->name);
166
209
    if (!(fin = fopen(line, "r"))) {
167
210
        DEBUGMSGTL(("access:interface",
169
212
    }
170
213
    else {
171
214
        if (fgets(line, sizeof(line), fin)) {
172
 
            entry->retransmit_v4 = atoi(line) * 100;
 
215
            entry->retransmit_v4 = atoi(line) * retrans_time_factor;
173
216
            entry->ns_flags |= NETSNMP_INTERFACE_FLAGS_HAS_V4_RETRANSMIT;
174
217
        }
175
218
        fclose(fin);
177
220
}
178
221
 
179
222
 
180
 
#ifdef INET6
 
223
#ifdef NETSNMP_ENABLE_IPV6
181
224
/**
182
225
 * @internal
183
226
 */
190
233
    /*
191
234
     * get the retransmit time
192
235
     */
193
 
    snprintf(line,sizeof(line),"/proc/sys/net/ipv6/neigh/%s/retrans_time",
 
236
    snprintf(line,sizeof(line), proc_sys_retrans_time, 6,
194
237
             entry->name);
195
238
    if (!(fin = fopen(line, "r"))) {
196
239
        DEBUGMSGTL(("access:interface",
198
241
    }
199
242
    else {
200
243
        if (fgets(line, sizeof(line), fin)) {
201
 
            entry->retransmit_v6 = atoi(line);
 
244
            entry->retransmit_v6 = atoi(line) * retrans_time_factor;
202
245
            entry->ns_flags |= NETSNMP_INTERFACE_FLAGS_HAS_V6_RETRANSMIT;
203
246
        }
204
247
        fclose(fin);
207
250
    /*
208
251
     * get the forwarding status
209
252
     */
210
 
    snprintf(line,sizeof(line),"/proc/sys/net/ipv6/conf/%s/forwarding",
 
253
    snprintf(line, sizeof(line), "/proc/sys/net/ipv6/conf/%s/forwarding",
211
254
             entry->name);
212
255
    if (!(fin = fopen(line, "r"))) {
213
256
        DEBUGMSGTL(("access:interface",
224
267
    /*
225
268
     * get the reachable time
226
269
     */
227
 
    snprintf(line,sizeof(line),"/proc/sys/net/ipv6/neigh/%s/base_reachable_time",
228
 
             entry->name);
 
270
    snprintf(line, sizeof(line), proc_sys_basereachable_time, 6, entry->name);
229
271
    if (!(fin = fopen(line, "r"))) {
230
272
        DEBUGMSGTL(("access:interface",
231
273
                    "Failed to open %s\n", line));
232
274
    }
233
275
    else {
234
276
        if (fgets(line, sizeof(line), fin)) {
235
 
            entry->reachable_time = atoi(line) * 1000; /* sec to millisec */
 
277
            if (basereachable_time_ms) {
 
278
                entry->reachable_time = atoi(line); /* millisec */
 
279
            } else {
 
280
                entry->reachable_time = atoi(line)*1000; /* sec to  millisec */
 
281
            }
 
282
 
236
283
            entry->ns_flags |= NETSNMP_INTERFACE_FLAGS_HAS_V6_REACHABLE;
237
284
        }
238
285
        fclose(fin);
239
286
    }
240
287
}
241
 
#endif /* INET6 */
 
288
#endif /* NETSNMP_ENABLE_IPV6 */
242
289
 
243
290
/**
244
291
 * @internal
286
333
    while (*stats == ' ')
287
334
        stats++;
288
335
 
 
336
    if ((*stats == 'N') &&
 
337
        (0 == strncmp(stats, "No statistics available",
 
338
                      sizeof("No statistics available"))))
 
339
        return -1;
 
340
 
289
341
    /*
290
342
     * Now parse the rest of the line (i.e. starting from 'stats')
291
343
     *      to extract the relevant statistics, and populate
326
378
        snmp_log(LOG_ERR,
327
379
                 "error scanning interface data (expected %d, got %d)\n",
328
380
                 expected, scan_count);
329
 
        netsnmp_access_interface_entry_free(entry);
330
381
        return scan_count;
331
382
    }
332
383
    entry->ns_flags |= NETSNMP_INTERFACE_FLAGS_ACTIVE;
363
414
    
364
415
    /*
365
416
     * calculated stats.
366
 
         *
367
 
         *  we have imcast, but not ibcast.
368
 
         */
 
417
     *
 
418
     *  we have imcast, but not ibcast.
 
419
     */
369
420
    entry->stats.inucast = entry->stats.imcast.low +
370
421
        entry->stats.ibcast.low;
 
422
    entry->stats.onucast = entry->stats.omcast.low +
 
423
        entry->stats.obcast.low;
371
424
    
372
425
    return 0;
373
426
}
388
441
    netsnmp_interface_entry *entry = NULL;
389
442
    static char     scan_expected = 0;
390
443
    int             fd;
391
 
#ifdef INET6
 
444
#ifdef NETSNMP_ENABLE_IPV6
392
445
    netsnmp_container *addr_container;
393
446
#endif
394
447
 
416
469
        return -2;
417
470
    }
418
471
 
419
 
#ifdef INET6
 
472
#ifdef NETSNMP_ENABLE_IPV6
420
473
    /*
421
474
     * get ipv6 addresses
422
475
     */
454
507
     */
455
508
    while (fgets(line, sizeof(line), devin)) {
456
509
        char           *stats, *ifstart = line;
457
 
        int             flags;
 
510
        u_int           flags;
458
511
        oid             if_index;
459
512
 
460
513
        flags = 0;
492
545
         * ip version is to look for ip addresses. If anyone
493
546
         * knows a better way, put it here!
494
547
         */
495
 
#ifdef INET6
 
548
#ifdef NETSNMP_ENABLE_IPV6
496
549
        _arch_interface_has_ipv6(if_index, &flags, addr_container);
497
550
#endif
498
551
        netsnmp_access_interface_ioctl_has_ipv4(fd, ifstart, 0, &flags);
512
565
 
513
566
        entry = netsnmp_access_interface_entry_create(ifstart, 0);
514
567
        if(NULL == entry) {
515
 
#ifdef INET6
 
568
#ifdef NETSNMP_ENABLE_IPV6
516
569
            netsnmp_access_ipaddress_container_free(addr_container, 0);
517
570
#endif
518
571
            netsnmp_access_interface_container_free(container,
612
665
         * hardcoded max packet size
613
666
         * (see ip_frag_reasm: if(len > 65535) goto out_oversize;)
614
667
         */
615
 
        entry->reasm_max = 65535;
 
668
        entry->reasm_max_v4 = entry->reasm_max_v6 = 65535;
 
669
        entry->ns_flags |= 
 
670
            NETSNMP_INTERFACE_FLAGS_HAS_V4_REASMMAX |
 
671
            NETSNMP_INTERFACE_FLAGS_HAS_V6_REASMMAX;
616
672
 
617
673
        netsnmp_access_interface_entry_overrides(entry);
618
674
 
624
680
        if (flags & NETSNMP_INTERFACE_FLAGS_HAS_IPV4)
625
681
            _arch_interface_flags_v4_get(entry);
626
682
 
627
 
#ifdef INET6
 
683
#ifdef NETSNMP_ENABLE_IPV6
628
684
        if (flags & NETSNMP_INTERFACE_FLAGS_HAS_IPV6)
629
685
            _arch_interface_flags_v6_get(entry);
630
 
#endif /* INET6 */
 
686
#endif /* NETSNMP_ENABLE_IPV6 */
631
687
 
632
688
        /*
633
689
         * add to container
634
690
         */
635
691
        CONTAINER_INSERT(container, entry);
636
692
    }
637
 
#ifdef INET6
 
693
#ifdef NETSNMP_ENABLE_IPV6
638
694
    netsnmp_access_ipaddress_container_free(addr_container, 0);
639
695
#endif
640
696
    fclose(devin);