⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 iftable.c

📁 snmp的源代码,已经在我的ubuntu下编译通过
💻 C
📖 第 1 页 / 共 3 页
字号:
        break;    }    return SNMP_ERR_NOERROR;}        /*         * Architecture-independent routines to locate         *  and/or create the entry for a given interface         */netsnmp_ifentry *ifTable_ifentry_get_by_name(netsnmp_cache * cache, char *name, int create){    netsnmp_ifentry tmp;    netsnmp_ifentry *entry;    netsnmp_container *container, *container_by_name;    if ((NULL == cache) || (NULL == cache->magic)) {        snmp_log(LOG_ERR, "invalid cache for ifTable\n");        return NULL;    }    container = (netsnmp_container *) cache->magic;    container_by_name = container->next;    if (NULL == container_by_name) {        snmp_log(LOG_ERR,                 "invalid cache for ifTable_ifentry_get_by_name\n");        return NULL;    }    tmp.if_name = name;    entry = CONTAINER_FIND(container_by_name, &tmp);    if ((NULL == entry) && (create)) {        entry = SNMP_MALLOC_TYPEDEF(netsnmp_ifentry);        entry->if_name = strdup(name);        /*         * XXX - initialise the "static" information         *  a) Using the configure overrides         *  b) Via (architecture-specific) utility routines         */        ifTable_ifentry_info_init(entry);        /*         * If we've met this interface before, use the same index.         * Otherwise find an unused index value and use that.         */        entry->index = se_find_value_in_slist("interfaces", name);        if (entry->index == SE_DNE) {            entry->index = se_find_free_value_in_slist("interfaces");            if (entry->index == SE_DNE)                entry->index = 1;       /* Completely new list! */            se_add_pair_to_slist("interfaces", strdup(name), entry->index);        }        /*         * inserting in container will also handle container_by_name          */        CONTAINER_INSERT(container, entry);        DEBUGMSGTL(("mibII/ifTable", "Creating entry for %s (%d)\n",                    name, entry->index));    }    if (entry)        entry->flags &= NETSNMP_IF_FLAGS_ACTIVE;    return entry;}netsnmp_ifentry *ifTable_ifentry_get_by_index(netsnmp_cache * cache, int index){    netsnmp_index   tmp;    netsnmp_container *container;    if ((NULL == cache) || (NULL == cache->magic)) {        snmp_log(LOG_ERR,                 "invalid cache for ifTable_ifentry_get_by_index\n");        return NULL;    }    container = (netsnmp_container *) cache->magic;    tmp.len = 1;    tmp.oids = (oid *) & index;    return (netsnmp_ifentry *) CONTAINER_FIND(container, &tmp);}        /*         * The cache-handler loading routines are the         *     main place for architecture-specific code         *         * This is actually split into two for each architecture.         * ifTable_load identifies the list of interfaces that         *     are currently present, and retrieves the dynamic         *     information for them (mostly statistic counters).         * ifTable_info_init sets up the static information for a         *     given interface, and this will typically be         *     retained even after the interface disappears.         */#ifdef linuxunsigned long longget_ifspeed(netsnmp_ifentry * entry){    return 10000000;}intget_iftype(netsnmp_ifentry * entry){    return 6;}intifTable_ifentry_info_init(netsnmp_ifentry * entry){    if (!entry)        return -1;    entry->oid_index.len = 1;    entry->oid_index.oids = (oid *) & entry->index;    if (!entry->if_speed)        entry->if_speed = get_ifspeed(entry);    if (!entry->if_type)        entry->if_type = get_iftype(entry);    entry->if_descr = strdup(entry->if_name);    return 0;}intifTable_load(netsnmp_cache * cache, void *vmagic){    FILE           *devin;    char            line[256];    const char     *scan_line_2_2 =        "%llu %llu %llu %llu %*llu %*llu %*llu %*llu %llu %llu %llu %llu %*llu %llu";    const char     *scan_line_2_0 =        "%lu %lu %*lu %*lu %*lu %lu %lu %*lu %*lu %lu";    const char     *scan_line_to_use;    int             scan_count;    unsigned long long int rec_pkt, rec_oct, rec_err, rec_drop;    unsigned long long int snd_pkt, snd_oct, snd_err, snd_drop, coll;    netsnmp_ifentry *entry;    netsnmp_container *container;    if ((NULL == cache) || (NULL == cache->magic)) {        snmp_log(LOG_ERR, "invalid cache for ifTable_load\n");        return -1;    }    DEBUGMSGTL(("ifTable/cache", "ifTable_load %p/%p\n",                cache, cache->magic));    container = (netsnmp_container *) cache->magic;    if (cache->valid)        ifTable_free(cache, NULL);    if (!(devin = fopen("/proc/net/dev", "r"))) {        DEBUGMSGTL(("mibII/ifTable",                    "Failed to load Interface Table (linux1)\n"));        snmp_log(LOG_ERR, "snmpd: cannot open /proc/net/dev ...\n");        return -1;    }    /*     * Read the first two lines of the file, containing the header     * This indicates which version of the kernel we're working with,     * and hence which statistics are actually available.     *    xxx - couldn't this result be cached at startup? can the format     *          change without a reboot??     *     * Wes originally suggested parsing the field names in this header     * to detect the position of individual fields directly,     * but I suspect this is probably more trouble than it's worth.     *     * Robert suggests that once we have the table index, we could store the     * raw data and save the parsing for later. Wouldn't save much work during     * a walk, but if there are lots of interfaces and only a few are being     * polled, it would save some parsing...     */    fgets(line, sizeof(line), devin);    fgets(line, sizeof(line), devin);    /*     * XXX - What's the format for the 2.6 kernel ?     */    if (strstr(line, "compressed")) {        scan_line_to_use = scan_line_2_2;        DEBUGMSGTL(("mibII/ifTable",                    "using linux 2.2 kernel /proc/net/dev\n"));    } else {        scan_line_to_use = scan_line_2_0;        DEBUGMSGTL(("mibII/ifTable",                    "using linux 2.0 kernel /proc/net/dev\n"));    }    /*     * The rest of the file provides the statistics for each interface.     * Read in each line in turn, isolate the interface name     *   and retrieve (or create) the corresponding data structure.     */    while (fgets(line, sizeof(line), devin)) {        char           *stats, *ifstart = line;        if (line[strlen(line) - 1] == '\n')            line[strlen(line) - 1] = '\0';        while (*ifstart && *ifstart == ' ')            ifstart++;        if (!*ifstart || ((stats = strrchr(ifstart, ':')) == NULL)) {            snmp_log(LOG_ERR,                     "/proc/net/dev data format error, line ==|%s|", line);            continue;        }        if ((scan_line_to_use == scan_line_2_2) && ((stats - line) < 6)) {            snmp_log(LOG_ERR,                     "/proc/net/dev data format error, line ==|%s|", line);        }        *stats = 0;        entry = ifTable_ifentry_get_by_name(cache, ifstart, 1);        *stats++ = ':';        while (*stats == ' ')            stats++;        /*         * OK - we've now got (or created) the data structure for         *      this interface, including any "static" information.         * Now parse the rest of the line (i.e. starting from 'stats')         *      to extract the relevant statistics, and populate         *      data structure accordingly.         * Use the flags field to indicate which counters are valid         */        /*         * XXX - may need another block for the 2.6 kernel         */        rec_pkt = rec_oct = rec_err = rec_drop = 0;        snd_pkt = snd_oct = snd_err = snd_drop = coll = 0;        if (scan_line_to_use == scan_line_2_2) {            scan_count = sscanf(stats, scan_line_to_use,                                &rec_oct, &rec_pkt, &rec_err, &rec_drop,                                &snd_oct, &snd_pkt, &snd_err, &snd_drop,                                &coll);            if (scan_count == 9) {                entry->flags |= NETSNMP_IF_FLAGS_ACTIVE;                entry->flags |= NETSNMP_IF_FLAGS_HAS_BYTES;                entry->flags |= NETSNMP_IF_FLAGS_HAS_DROPS;                /*                 *  2.4 kernel includes a single multicast (input) counter?                 */                entry->flags |= NETSNMP_IF_FLAGS_HAS_MCAST_PKTS;                entry->flags |= NETSNMP_IF_FLAGS_HAS_HIGH_SPEED;                entry->flags |= NETSNMP_IF_FLAGS_HAS_HIGH_BYTES;                entry->flags |= NETSNMP_IF_FLAGS_HAS_HIGH_PACKETS;            }        } else {            scan_count = sscanf(stats, scan_line_to_use,                                &rec_pkt, &rec_err,                                &snd_pkt, &snd_err, &coll);            if (scan_count == 5) {                entry->flags |= NETSNMP_IF_FLAGS_ACTIVE;                entry->flags &= ~NETSNMP_IF_FLAGS_HAS_MCAST_PKTS;                rec_oct = rec_drop = 0;                snd_oct = snd_drop = 0;            }        }        /*         * linux previous to 1.3.~13 may miss transmitted loopback pkts:          */        if (!strcmp(entry->if_name, "lo") && rec_pkt > 0 && !snd_pkt)            snd_pkt = rec_pkt;        if (entry->flags & NETSNMP_IF_FLAGS_ACTIVE) {            entry->if_ibytes.low = rec_oct & 0xffffffff;            entry->if_ibytes.high = rec_oct >> 32;            entry->if_iucast.low = rec_pkt & 0xffffffff;            entry->if_iucast.high = rec_pkt >> 32;            entry->if_ierrors = rec_err;            entry->if_idiscards = rec_drop;            entry->if_obytes.low = snd_oct & 0xffffffff;            entry->if_obytes.high = snd_oct >> 32;            entry->if_oucast.low = snd_pkt & 0xffffffff;            entry->if_oucast.high = snd_pkt >> 32;            entry->if_oerrors = snd_err;            entry->if_odiscards = snd_drop;            entry->if_collisions = coll;        }    }    fclose(devin);    return 0;}#endif                          /* linux */

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -