Beispiel #1
0
static int
AT_Cmp(void *addr, void *ep)
{
    mib2_ipNetToMediaEntry_t *mp = (mib2_ipNetToMediaEntry_t *) ep;
    int             ret = -1;
    oid             index;

#ifdef NETSNMP_INCLUDE_IFTABLE_REWRITES
    mp->ipNetToMediaIfIndex.o_bytes[mp->ipNetToMediaIfIndex.o_length] = '\0';
    index = netsnmp_access_interface_index_find(
                    mp->ipNetToMediaIfIndex.o_bytes);
#else
    index = Interface_Index_By_Name(mp->ipNetToMediaIfIndex.o_bytes,
                                    mp->ipNetToMediaIfIndex.o_length);
#endif
    DEBUGMSGTL(("mibII/at", "......... AT_Cmp %lx<>%lx %d<>%d (%.5s)\n",
                mp->ipNetToMediaNetAddress, ((if_ip_t *) addr)->ipAddr,
                ((if_ip_t *) addr)->ifIdx, index,
                mp->ipNetToMediaIfIndex.o_bytes));
    if (mp->ipNetToMediaNetAddress != ((if_ip_t *) addr)->ipAddr)
        ret = 1;
    else if (((if_ip_t *) addr)->ifIdx != index)
        ret = 1;
    else
        ret = 0;
    DEBUGMSGTL(("mibII/at", "......... AT_Cmp returns %d\n", ret));
    return ret;
}
Beispiel #2
0
netsnmp_interface_entry *
netsnmp_access_interface_entry_create(const char *name, oid if_index)
{
    netsnmp_interface_entry *entry =
        SNMP_MALLOC_TYPEDEF(netsnmp_interface_entry);

    DEBUGMSGTL(("access:interface:entry", "create\n"));
    netsnmp_assert(1 == _access_interface_init);

    if(NULL == entry)
        return NULL;

    if(NULL != name)
        entry->name = strdup(name);

    /*
     * get if index, and save name for reverse lookup
     */
#ifndef NETSNMP_ACCESS_INTERFACE_NOARCH
    if (0 == if_index)
        entry->index = netsnmp_access_interface_index_find(name);
    else
#endif
        entry->index = if_index;
    _access_interface_entry_save_name(name, entry->index);

    if (name)
        entry->descr = strdup(name);

    /*
     * make some assumptions
     */
    entry->connector_present = 1;

    entry->oid_index.len = 1;
    entry->oid_index.oids = (oid *) & entry->index;

    return entry;
}
Beispiel #3
0
static void
ARP_Scan_Init(void)
{
#ifndef NETSNMP_CAN_USE_SYSCTL
#ifndef linux
#ifdef hpux11

    int             fd;
    struct nmparms  p;
    int             val;
    unsigned int    ulen;
    int             ret;

    if (at)
        free(at);
    at = (mib_ipNetToMediaEnt *) 0;
    arptab_size = 0;

    if ((fd = open_mib("/dev/ip", O_RDONLY, 0, NM_ASYNC_OFF)) >= 0) {
        p.objid = ID_ipNetToMediaTableNum;
        p.buffer = (void *) &val;
        ulen = sizeof(int);
        p.len = &ulen;
        if ((ret = get_mib_info(fd, &p)) == 0)
            arptab_size = val;

        if (arptab_size > 0) {
            ulen = (unsigned) arptab_size *sizeof(mib_ipNetToMediaEnt);
            at = (mib_ipNetToMediaEnt *) malloc(ulen);
            p.objid = ID_ipNetToMediaTable;
            p.buffer = (void *) at;
            p.len = &ulen;
            if ((ret = get_mib_info(fd, &p)) < 0)
                arptab_size = 0;
        }

        close_mib(fd);
    }

    arptab_current = 0;

#else                           /* hpux11 */

    if (!at) {
#ifdef ARPTAB_SIZE_SYMBOL
        auto_nlist(ARPTAB_SIZE_SYMBOL, (char *) &arptab_size,
                   sizeof arptab_size);
#ifdef STRUCT_ARPHD_HAS_AT_NEXT
        at = (struct arphd *) malloc(arptab_size * sizeof(struct arphd));
#else
        at = (struct arptab *) malloc(arptab_size * sizeof(struct arptab));
#endif
#else
        return;
#endif
    }
#ifdef STRUCT_ARPHD_HAS_AT_NEXT
    auto_nlist(ARPTAB_SYMBOL, (char *) at,
               arptab_size * sizeof(struct arphd));
    at_ptr = at[0].at_next;
#else
    auto_nlist(ARPTAB_SYMBOL, (char *) at,
               arptab_size * sizeof(struct arptab));
#endif
    arptab_current = 0;

#endif                          /* hpux11 */
#else                           /* linux */

    static time_t   tm = 0;     /* Time of last scan */
    FILE           *in;
    int             i, j;
    char            line[128];
    int             za, zb, zc, zd;
    char            ifname[21];
    char            mac[3*MAX_MAC_ADDR_LEN+1];
    char           *tok;

    arptab_current = 0;         /* Anytime this is called we need to reset 'current' */

    if (time(NULL) < tm + 1) {  /*Our cool one second cache implementation :-) */
        return;
    }

    in = fopen("/proc/net/arp", "r");
    if (!in) {
        snmp_log(LOG_ERR, "snmpd: Cannot open /proc/net/arp\n");
        arptab_size = 0;
        return;
    }

    /*
     * Get rid of the header line 
     */
    fgets(line, sizeof(line), in);

    i = 0;
    while (fgets(line, sizeof(line), in)) {
        u_long          tmp_a;
        int             tmp_flags;
        if (i >= arptab_curr_max_size) {
            struct arptab  *newtab = (struct arptab *)
                realloc(at, (sizeof(struct arptab) *
                             (arptab_curr_max_size + ARP_CACHE_INCR)));
            if (newtab == at) {
                snmp_log(LOG_ERR,
                         "Error allocating more space for arpcache.  "
                         "Cache will continue to be limited to %d entries",
                         arptab_curr_max_size);
                break;
            } else {
                arptab_curr_max_size += ARP_CACHE_INCR;
                at = newtab;
            }
        }
        if (7 !=
            sscanf(line,
                   "%d.%d.%d.%d 0x%*x 0x%x %s %*[^ ] %20s\n",
                   &za, &zb, &zc, &zd, &tmp_flags, mac, ifname)) {
            snmp_log(LOG_ERR, "Bad line in /proc/net/arp: %s", line);
            continue;
        }
        /*
         * Invalidated entries have their flag set to 0.
         * * We want to ignore them 
         */
        if (tmp_flags == 0) {
            continue;
        }
        ifname[sizeof(ifname)-1] = 0; /* make sure name is null terminated */
        at[i].at_flags = tmp_flags;
        tmp_a = ((u_long) za << 24) |
            ((u_long) zb << 16) | ((u_long) zc << 8) | ((u_long) zd);
        at[i].at_iaddr.s_addr = htonl(tmp_a);
        at[i].if_index = netsnmp_access_interface_index_find(ifname);
        
        for (j=0,tok=strtok(mac, ":"); tok != NULL; tok=strtok(NULL, ":"),j++) {
        	at[i].at_enaddr[j] = strtol(tok, NULL, 16);
        }
        at[i].at_enaddr_len = j;
        i++;
    }
    arptab_size = i;

    fclose(in);
    time(&tm);
#endif                          /* linux */
#else                           /* NETSNMP_CAN_USE_SYSCTL */

    int             mib[6];
    size_t          needed;

    mib[0] = CTL_NET;
    mib[1] = PF_ROUTE;
    mib[2] = 0;
    mib[3] = AF_INET;
    mib[4] = NET_RT_FLAGS;
    mib[5] = RTF_LLINFO;

    if (at)
        free(at);
    rtnext = lim = at = 0;

    if (sysctl(mib, 6, NULL, &needed, NULL, 0) < 0)
        snmp_log_perror("route-sysctl-estimate");
    else {
        if ((at = malloc(needed ? needed : 1)) == NULL)
            snmp_log_perror("malloc");
        else {
            if (sysctl(mib, 6, at, &needed, NULL, 0) < 0)
                snmp_log_perror("actual retrieval of routing table");
            else {
                lim = at + needed;
                rtnext = at;
            }
        }
    }

#endif                          /* NETSNMP_CAN_USE_SYSCTL */
}
Beispiel #4
0
u_char         *
var_atEntry(struct variable * vp,
            oid * name,
            size_t * length,
            int exact, size_t * var_len, WriteMethod ** write_method)
{
    /*
     * object identifier is of form:
     * 1.3.6.1.2.1.3.1.1.1.interface.1.A.B.C.D,  where A.B.C.D is IP address.
     * Interface is at offset 10,
     * IPADDR starts at offset 12.
     */
#define AT_MAX_NAME_LENGTH	16
#define AT_IFINDEX_OFF	10
    u_char         *cp;
    oid            *op;
    oid             lowest[AT_MAX_NAME_LENGTH];
    oid             current[AT_MAX_NAME_LENGTH];
    if_ip_t         NextAddr;
    mib2_ipNetToMediaEntry_t entry;
    static mib2_ipNetToMediaEntry_t Lowentry;
    int             Found = 0;
    req_e           req_type;
    int             offset, olength;
    static in_addr_t      addr_ret;

    /*
     * fill in object part of name for current (less sizeof instance part) 
     */

    DEBUGMSGTL(("mibII/at", "var_atEntry: "));
    DEBUGMSGOID(("mibII/at", vp->name, vp->namelen));
    DEBUGMSG(("mibII/at", " %d\n", exact));

    memset(&Lowentry, 0, sizeof(Lowentry));
    memcpy((char *) current, (char *) vp->name, vp->namelen * sizeof(oid));
    lowest[0] = 1024;
    for (NextAddr.ipAddr = (u_long) - 1, NextAddr.ifIdx = 255, req_type =
         GET_FIRST;;
         NextAddr.ipAddr = entry.ipNetToMediaNetAddress, NextAddr.ifIdx =
         current[AT_IFINDEX_OFF], req_type = GET_NEXT) {
        if (getMibstat
            (MIB_IP_NET, &entry, sizeof(mib2_ipNetToMediaEntry_t),
             req_type, &AT_Cmp, &NextAddr) != 0)
            break;
#ifdef NETSNMP_INCLUDE_IFTABLE_REWRITES
        entry.ipNetToMediaIfIndex.o_bytes[entry.ipNetToMediaIfIndex.o_length] = '\0';
        current[AT_IFINDEX_OFF] = netsnmp_access_interface_index_find(
           entry.ipNetToMediaIfIndex.o_bytes);
#else
        current[AT_IFINDEX_OFF] = 
           Interface_Index_By_Name(entry.ipNetToMediaIfIndex.o_bytes,
                                   entry.ipNetToMediaIfIndex.o_length);
#endif
        if (current[6] == 3) {  /* AT group oid */
            current[AT_IFINDEX_OFF + 1] = 1;
            offset = AT_IFINDEX_OFF + 2;
            olength = AT_IFINDEX_OFF + 6;
        } else {
            offset = AT_IFINDEX_OFF + 1;
            olength = AT_IFINDEX_OFF + 5;
        }
        COPY_IPADDR(cp, (u_char *) & entry.ipNetToMediaNetAddress, op,
                    current + offset);
        if (exact) {
            if (snmp_oid_compare(current, olength, name, *length) == 0) {
                memcpy((char *) lowest, (char *) current,
                       olength * sizeof(oid));
                Lowentry = entry;
                Found++;
                break;          /* no need to search further */
            }
        } else {
            if (snmp_oid_compare(current, olength, name, *length) > 0
                && snmp_oid_compare(current, olength, lowest,
                                    *length) < 0) {
                /*
                 * if new one is greater than input and closer to input than
                 * previous lowest, and is not equal to it, save this one as the "next" one.
                 */
                memcpy((char *) lowest, (char *) current,
                       olength * sizeof(oid));
                Lowentry = entry;
                Found++;
            }
        }
    }
    DEBUGMSGTL(("mibII/at", "... Found = %d\n", Found));
    if (Found == 0)
        return (NULL);
    memcpy((char *) name, (char *) lowest, olength * sizeof(oid));
    *length = olength;
    *write_method = 0;
    switch (vp->magic) {
    case IPMEDIAIFINDEX:
        *var_len = sizeof long_return;
#ifdef NETSNMP_INCLUDE_IFTABLE_REWRITES
        Lowentry.ipNetToMediaIfIndex.o_bytes[
            Lowentry.ipNetToMediaIfIndex.o_length] = '\0';
        long_return = netsnmp_access_interface_index_find(
            Lowentry.ipNetToMediaIfIndex.o_bytes);
#else
        long_return = Interface_Index_By_Name(
            Lowentry.ipNetToMediaIfIndex.o_bytes,
            Lowentry.ipNetToMediaIfIndex.o_length);
#endif
        return (u_char *) & long_return;
    case IPMEDIAPHYSADDRESS:
        *var_len = Lowentry.ipNetToMediaPhysAddress.o_length;
        return Lowentry.ipNetToMediaPhysAddress.o_bytes;
    case IPMEDIANETADDRESS:
        *var_len = sizeof(addr_ret);
        addr_ret = Lowentry.ipNetToMediaNetAddress;
        return (u_char *) &addr_ret;
    case IPMEDIATYPE:
        *var_len = sizeof long_return;
        long_return = Lowentry.ipNetToMediaType;
        return (u_char *) & long_return;
    default:
        DEBUGMSGTL(("snmpd", "unknown sub-id %d in var_atEntry\n",
                    vp->magic));
    }
    return NULL;
}
Beispiel #5
0
int
_load_v4(netsnmp_container *container, int idx_offset)
{
    FILE           *in;
    char            line[128];
    int             rc = 0;
    netsnmp_arp_entry *entry;
    
    netsnmp_assert(NULL != container);

#define PROCFILE "/proc/net/arp"
    if (!(in = fopen(PROCFILE, "r"))) {
        snmp_log(LOG_ERR,"could not open " PROCFILE "\n");
        return -2;
    }

    /*
     * Get rid of the header line 
     */
    fgets(line, sizeof(line), in);

    /*
     * IP address | HW | Flag | HW address      | Mask | Device
     * 192.168.1.4  0x1  0x2   00:40:63:CC:1C:8C  *      eth0
     */
    while (fgets(line, sizeof(line), in)) {
        
        int             za, zb, zc, zd, ze, zf, zg, zh, zi, zj;
        int             tmp_flags;
        char            ifname[21];

        rc = sscanf(line,
                    "%d.%d.%d.%d 0x%*x 0x%x %x:%x:%x:%x:%x:%x %*[^ ] %20s\n",
                    &za, &zb, &zc, &zd, &tmp_flags, &ze, &zf, &zg, &zh, &zi,
                    &zj, ifname);
        if (12 != rc) {            
            snmp_log(LOG_ERR, PROCFILE " data format error (%d!=12)\n", rc);
            snmp_log(LOG_ERR, " line ==|%s|\n", line);
            continue;
        }
        DEBUGMSGTL(("access:arp:container",
                    "ip addr %d.%d.%d.%d, flags 0x%X, hw addr "
                    "%x:%x:%x:%x:%x:%x, name %s\n",
                    za,zb,zc,zd, tmp_flags, ze,zf,zg,zh,zi,zj, ifname ));

        /*
         */
        entry = netsnmp_access_arp_entry_create();
        if(NULL == entry) {
            rc = -3;
            break;
        }

        /*
         * look up ifIndex
         */
        entry->if_index = netsnmp_access_interface_index_find(ifname);
        if(0 == entry->if_index) {
            snmp_log(LOG_ERR,"couldn't find ifIndex for '%s', skipping\n",
                     ifname);
            netsnmp_access_arp_entry_free(entry);
            continue;
        }

        /*
         * now that we've passed all the possible 'continue', assign
         * index offset.
         */
        entry->ns_arp_index = ++idx_offset;

        /*
         * parse ip addr
         */
        entry->arp_ipaddress[0] = za;
        entry->arp_ipaddress[1] = zb;
        entry->arp_ipaddress[2] = zc;
        entry->arp_ipaddress[3] = zd;
        entry->arp_ipaddress_len = 4;

        /*
         * parse hw addr
         */
        entry->arp_physaddress[0] = ze;
        entry->arp_physaddress[1] = zf;
        entry->arp_physaddress[2] = zg;
        entry->arp_physaddress[3] = zh;
        entry->arp_physaddress[4] = zi;
        entry->arp_physaddress[5] = zj;
        entry->arp_physaddress_len = 6;

        /*
         * what can we do with hw? from arp manpage:

         default  value  of  this  parameter is ether (i.e. hardware code
         0x01 for  IEEE  802.3  10Mbps  Ethernet).   Other  values  might
         include  network  technologies  such as ARCnet (arcnet) , PROnet
         (pronet) , AX.25 (ax25) and NET/ROM (netrom).
        */

        /*
         * parse mask
         */
        /* xxx-rks: what is mask? how to interpret '*'? */


        /*
         * process type
         */
        if(tmp_flags & ATF_PERM)
            entry->arp_type = INETNETTOMEDIATYPE_STATIC;
        else
            entry->arp_type = INETNETTOMEDIATYPE_DYNAMIC;

        /*
         * process status
         * if flags are 0, we can't tell the difference between
         * stale or incomplete.
         */
        if(tmp_flags & ATF_COM)
            entry->arp_state = INETNETTOMEDIASTATE_REACHABLE;
        else
            entry->arp_state = INETNETTOMEDIASTATE_UNKNOWN;

        /*
         * add entry to container
         */
        CONTAINER_INSERT(container, entry);
    }

    fclose(in);
    if( rc < 0 )
        return rc;

    return idx_offset;
}
int
_load_v6(netsnmp_container *container, int idx_offset)
{
    FILE           *in;
    char            line[80], addr[33], if_name[IFNAMSIZ];
    u_char          *buf;
    int             if_index, pfx_len, scope, flags, rc = 0;
    size_t          in_len, out_len;
    netsnmp_ipaddress_entry *entry;
    _ioctl_extras           *extras;
    static int      log_open_err = 1;
    
    netsnmp_assert(NULL != container);

#define PROCFILE "/proc/net/if_inet6"
    if (!(in = fopen(PROCFILE, "r"))) {
        if (1 == log_open_err) {
            snmp_log(LOG_ERR,"could not open " PROCFILE "\n");
            log_open_err = 0;
        }
        return -2;
    }
    /*
     * if we hadn't been able to open file and turned of err logging,
     * turn it back on now that we opened the file.
     */
    if (0 == log_open_err)
        log_open_err = 1;

    /*
     * address index prefix_len scope status if_name
     */
    while (fgets(line, sizeof(line), in)) {
        /*
         * fe800000000000000200e8fffe5b5c93 05 40 20 80 eth0
         *             A                    D  P  S  F  I
         * A: address
         * D: device number
         * P: prefix len
         * S: scope (see include/net/ipv6.h, net/ipv6/addrconf.c)
         * F: flags (see include/linux/rtnetlink.h, net/ipv6/addrconf.c)
         * I: interface
         */
        rc = sscanf(line, "%32s %02x %02x %02x %02x %8s\n",
                    addr, &if_index, &pfx_len, &scope, &flags, if_name);
        if( 6 != rc ) {
            snmp_log(LOG_ERR, PROCFILE " data format error (%d!=6), line ==|%s|\n",
                     rc, line);
            continue;
        }
        DEBUGMSGTL(("access:ipaddress:container",
                    "addr %s, index %d, pfx %d, scope %d, flags 0x%X, name %s\n",
                    addr, if_index, pfx_len, scope, flags, if_name));
        /*
         */
        entry = netsnmp_access_ipaddress_entry_create();
        if(NULL == entry) {
            rc = -3;
            break;
        }

        in_len = entry->ia_address_len = sizeof(entry->ia_address);
        netsnmp_assert(16 == in_len);
        out_len = 0;
        buf = entry->ia_address;
        if(1 != snmp_hex_to_binary(&buf,
                                   &in_len, &out_len, 0, addr)) {
            snmp_log(LOG_ERR,"error parsing '%s', skipping\n",
                     entry->ia_address);
            netsnmp_access_ipaddress_entry_free(entry);
            continue;
        }
        netsnmp_assert(16 == out_len);
        entry->ia_address_len = out_len;

        entry->ns_ia_index = ++idx_offset;

        /*
         * save if name
         */
        extras = netsnmp_ioctl_ipaddress_extras_get(entry);
        memcpy(extras->name, if_name, sizeof(extras->name));
        extras->flags = flags;

        /*
         * yyy-rks: optimization: create a socket outside the loop and use
         * netsnmp_access_interface_ioctl_ifindex_get() here, since
         * netsnmp_access_interface_index_find will open/close a socket
         * every time it is called.
         */
        entry->if_index = netsnmp_access_interface_index_find(if_name);

        /*
          #define IPADDRESSSTATUSTC_PREFERRED  1
          #define IPADDRESSSTATUSTC_DEPRECATED  2
          #define IPADDRESSSTATUSTC_INVALID  3
          #define IPADDRESSSTATUSTC_INACCESSIBLE  4
          #define IPADDRESSSTATUSTC_UNKNOWN  5
          #define IPADDRESSSTATUSTC_TENTATIVE  6
          #define IPADDRESSSTATUSTC_DUPLICATE  7
        */
        if(flags & IFA_F_PERMANENT)
            entry->ia_status = IPADDRESSSTATUSTC_PREFERRED; /* ?? */
        else if(flags & IFA_F_DEPRECATED)
            entry->ia_status = IPADDRESSSTATUSTC_DEPRECATED;
        else if(flags & IFA_F_TENTATIVE)
            entry->ia_status = IPADDRESSSTATUSTC_TENTATIVE;
        else {
            entry->ia_status = IPADDRESSSTATUSTC_UNKNOWN;
            DEBUGMSGTL(("access:ipaddress:ipv6",
                        "unknown flags 0x%x\n", flags));
        }

        /*
         * if it's not multi, it must be uni.
         *  (an ipv6 address is never broadcast)
         */
        if (IN6_IS_ADDR_MULTICAST(entry->ia_address))
            entry->ia_type = IPADDRESSTYPE_ANYCAST;
        else
            entry->ia_type = IPADDRESSTYPE_UNICAST;


        entry->ia_prefix_len = pfx_len;

        /*
         * can we figure out if an address is from DHCP?
         * use manual until then...
         *
         *#define IPADDRESSORIGINTC_OTHER  1
         *#define IPADDRESSORIGINTC_MANUAL  2
         *#define IPADDRESSORIGINTC_DHCP  4
         *#define IPADDRESSORIGINTC_LINKLAYER  5
         *#define IPADDRESSORIGINTC_RANDOM  6
         *
         * are 'local' address assigned by link layer??
         */
        if (IN6_IS_ADDR_LINKLOCAL(entry->ia_address) ||
            IN6_IS_ADDR_SITELOCAL(entry->ia_address))
            entry->ia_origin = IPADDRESSORIGINTC_LINKLAYER;
        else
            entry->ia_origin = IPADDRESSORIGINTC_MANUAL;

        /* xxx-rks: what can we do with scope? */

        /*
         * add entry to container
         */
        CONTAINER_INSERT(container, entry);
    }

    fclose(in);

    if(rc<0)
        return rc;

    return idx_offset;
}
Beispiel #7
0
static int mib_ipRouteTable_updateTable(void)
{
	FILE            *in;
    s8              line[256];
    struct rtentry  *rt;
    s8              name[16];
    static u32      Time_Of_Last_Reload = 0;
	in_addr_t new_ipRouteDest;
	struct ipRouteTable_entry *new_entry;
    if(Time_Of_Last_Reload + CACHE_TIME > time(NULL))
    {
        return ERROR_SUCCESS;
    }
    else
    {
        while(ipRouteTable_head)
        {
            mib_ipRouteTable_removeEntry(ipRouteTable_head);
        }
    }

    Time_Of_Last_Reload = time(NULL);

    if (!rthead)
    {
        rthead = (struct rtentry **) calloc(100, sizeof(struct rtentry *));
        if (!rthead)
        {
            return ERROR_SYSTEM;
        }
        rtallocate = 100;
    }
    rtsize = 0;

    if (!(in = fopen(ROUTE_FILE, "r")))
    {
        return ERROR_SYSTEM;
    }

    while (fgets(line, sizeof(line), in))
    {
        struct rtentry  rtent;
        s8              rtent_name[32];
        s32             refcnt, flags, metric;
        u32             use;

        rt = &rtent;
        memset((s8 *) rt, (0), sizeof(*rt));
        rt->rt_dev = rtent_name;

        if (8 != sscanf(line, "%s %x %x %x %u %d %d %x %*d %*d %*d\n",
                        rt->rt_dev,
                        &(((struct sockaddr_in *) &(rtent.rt_dst))->sin_addr.s_addr),
                        &(((struct sockaddr_in *) &(rtent.rt_gateway))->sin_addr.s_addr),
                        &flags, &refcnt, &use, &metric,
                        &(((struct sockaddr_in *) &(rtent.rt_genmask))->sin_addr.s_addr)))
        {
            continue;
        }
		new_ipRouteDest= ((struct sockaddr_in *) &(rtent.rt_dst))->sin_addr.s_addr;
		new_entry = mib_ipRouteTable_createEntry(new_ipRouteDest);
        if(!new_entry)
        {
            return ERROR_SYSTEM;
        }
		strncpy(name, rt->rt_dev, sizeof(name));
        name[sizeof(name) - 1] = 0;
		new_entry->ipRouteIfIndex = netsnmp_access_interface_index_find(name);
        if(flags & RTF_GATEWAY)
        {
            new_entry->ipRouteMetric1 = 1;
        }
        else
        {
            new_entry->ipRouteMetric1 = 0;
        }
		new_entry->ipRouteNextHop = ((struct sockaddr_in *) &(rtent.rt_gateway))->sin_addr.s_addr;
		
	    if (flags & RTF_GATEWAY)
        {
            new_entry->ipRouteType = 4;
        }
        else
        {
            new_entry->ipRouteType = 3;
        }
		
		if (flags & RTF_DYNAMIC)
        {
            new_entry->ipRouteProto = 4;
        }
        else
        {
            new_entry->ipRouteProto = 2;
        }
		
		if (((struct sockaddr_in *) &(rtent.rt_dst))->sin_addr.s_addr == 0)
		{
			new_entry->ipRouteMask = 0;
		}
		else
		{
			new_entry->ipRouteMask = ((struct sockaddr_in *) &(rtent.rt_genmask))->sin_addr.s_addr;
		}
		memcpy(new_entry->ipRouteInfo,nullOid,sizeof(new_entry->ipRouteInfo));
		new_entry->ipRouteInfo_len = nullOidLen;

		new_entry->ipRouteAge = 0;
		new_entry->ipRouteMetric2 = 0;
		new_entry->ipRouteMetric3 = 0;
		new_entry->ipRouteMetric4 = 0;
		new_entry->ipRouteMetric5 = 0;
    }
    fclose(in);
    return ERROR_SUCCESS;
}
Beispiel #8
0
static int mib_ipAddrTable_getList(void)
{
    s32 num_interfaces = 0;
    ifc.ifc_len = 0;
    SNMP_FREE(ifc.ifc_buf);
    ifr_counter = 0;
	struct ifnet   ifnet_store;
    s32            fd;
    in_addr_t new_ipAdEntAddr;
	static u32      Time_Of_Last_Reload = 0;

    struct ipAddrTable_entry *new_entry;
	
    if(Time_Of_Last_Reload + CACHE_TIME > time(NULL))
    {
        return ERROR_SUCCESS;
    }
    else
    {
        while(ipAddrTable_head)
        {
            mib_ipAddrTable_removeEntry(ipAddrTable_head);
        }
    }

    Time_Of_Last_Reload = time(NULL);

    do
    {
        if ((fd = socket(AF_INET, SOCK_DGRAM, 0)) < 0)
        {
            return ERROR_SYSTEM;
        }
        num_interfaces += 16;

        ifc.ifc_len = sizeof(struct ifreq) * num_interfaces;
        ifc.ifc_buf = (s8*) realloc(ifc.ifc_buf, ifc.ifc_len);

        if (ioctl(fd, SIOCGIFCONF, &ifc) < 0)
        {
            ifr = NULL;
            close(fd);
            return ERROR_SYSTEM;
        }
        close(fd);
    }while (ifc.ifc_len >= (sizeof(struct ifreq) * num_interfaces));

    ifr = ifc.ifc_req;
    if ((fd = socket(AF_INET, SOCK_DGRAM, 0)) < 0)
    {
        return(0);
    }

    while (ifr)
    {
        ifnet_store.if_addr = ifr->ifr_addr;
		new_ipAdEntAddr=((struct sockaddr_in *)&(ifnet_store.if_addr))->sin_addr.s_addr;
		new_entry = mib_ipAddrTable_createEntry(new_ipAdEntAddr);
        if(!new_entry)
        {
            return ERROR_SYSTEM;
        }

        if (ioctl(fd, SIOCGIFBRDADDR, ifr) < 0)
        {
            memset((s8 *) &new_entry->ipAdEntBcastAddr, 0, sizeof(new_entry->ipAdEntBcastAddr));
        }
        else
        {
			new_entry->ipAdEntBcastAddr = ((struct sockaddr_in *)&(ifr->ifr_broadaddr))->sin_addr.s_addr;
        }

        if (ioctl(fd, SIOCGIFNETMASK, ifr) < 0)
        {
            memset((s8 *) &new_entry->ipAdEntNetMask, 0, sizeof(new_entry->ipAdEntBcastAddr));
        }
        else
        {
            new_entry->ipAdEntNetMask = ((struct sockaddr_in *)&(ifr->ifr_netmask))->sin_addr.s_addr;
        }
        
        ifr->ifr_addr = ifnet_store.if_addr;
		new_entry->ipAdEntIfIndex = netsnmp_access_interface_index_find(ifr->ifr_name);
		new_entry->ipAdEntReasmMaxSize = -1;
        ifr++;
        ifr_counter += sizeof(struct ifreq);
        if (ifr_counter >= ifc.ifc_len)
        {
            ifr = NULL;
        }
      
    }
    
    close(fd);
    return (0); 

}
Beispiel #9
0
int
_load_v6(netsnmp_container *container, int idx_offset)
{
#ifndef HAVE_LINUX_RTNETLINK_H
    DEBUGMSGTL(("access:ipaddress:container",
                "cannot get ip address information"
                "as netlink socket is not available\n"));
    return -1;
#else
    FILE           *in;
    char            line[80], addr[40];
    char            if_name[IFNAMSIZ+1];/* +1 for '\0' because of the ugly sscanf below */ 
    u_char          *buf;
    int             if_index, pfx_len, scope, flags, rc = 0;
    size_t          in_len, out_len;
    netsnmp_ipaddress_entry *entry;
    _ioctl_extras           *extras;
    struct address_flag_info addr_info;
    
    netsnmp_assert(NULL != container);

#define PROCFILE "/proc/net/if_inet6"
    if (!(in = fopen(PROCFILE, "r"))) {
        DEBUGMSGTL(("access:ipaddress:container","could not open " PROCFILE "\n"));
        return -2;
    }

    /*
     * address index prefix_len scope status if_name
     */
    while (fgets(line, sizeof(line), in)) {
        /*
         * fe800000000000000200e8fffe5b5c93 05 40 20 80 eth0
         *             A                    D  P  S  F  I
         * A: address
         * D: device number
         * P: prefix len
         * S: scope (see include/net/ipv6.h, net/ipv6/addrconf.c)
         * F: flags (see include/linux/rtnetlink.h, net/ipv6/addrconf.c)
         * I: interface
         */
        rc = sscanf(line, "%39s %08x %08x %04x %02x %" SNMP_MACRO_VAL_TO_STR(IFNAMSIZ) "s\n",
                    addr, &if_index, &pfx_len, &scope, &flags, if_name);
        if( 6 != rc ) {
            snmp_log(LOG_ERR, PROCFILE " data format error (%d!=6), line ==|%s|\n",
                     rc, line);
            continue;
        }
        DEBUGMSGTL(("access:ipaddress:container",
                    "addr %s, index %d, pfx %d, scope %d, flags 0x%X, name %s\n",
                    addr, if_index, pfx_len, scope, flags, if_name));
        /*
         */
        entry = netsnmp_access_ipaddress_entry_create();
        if(NULL == entry) {
            rc = -3;
            break;
        }

        in_len = entry->ia_address_len = sizeof(entry->ia_address);
        netsnmp_assert(16 == in_len);
        out_len = 0;
        entry->flags = flags;
        buf = entry->ia_address;
        if(1 != netsnmp_hex_to_binary(&buf, &in_len,
                                      &out_len, 0, addr, ":")) {
            snmp_log(LOG_ERR,"error parsing '%s', skipping\n",
                     entry->ia_address);
            netsnmp_access_ipaddress_entry_free(entry);
            continue;
        }
        netsnmp_assert(16 == out_len);
        entry->ia_address_len = out_len;

        entry->ns_ia_index = ++idx_offset;

        /*
         * save if name
         */
        extras = netsnmp_ioctl_ipaddress_extras_get(entry);
        memcpy(extras->name, if_name, sizeof(extras->name));
        extras->flags = flags;

        /*
         * yyy-rks: optimization: create a socket outside the loop and use
         * netsnmp_access_interface_ioctl_ifindex_get() here, since
         * netsnmp_access_interface_index_find will open/close a socket
         * every time it is called.
         */
        entry->if_index = netsnmp_access_interface_index_find(if_name);
        memset(&addr_info, 0, sizeof(struct address_flag_info));
        addr_info = netsnmp_access_other_info_get(entry->if_index, AF_INET6);

        /*
          #define IPADDRESSSTATUSTC_PREFERRED  1
          #define IPADDRESSSTATUSTC_DEPRECATED  2
          #define IPADDRESSSTATUSTC_INVALID  3
          #define IPADDRESSSTATUSTC_INACCESSIBLE  4
          #define IPADDRESSSTATUSTC_UNKNOWN  5
          #define IPADDRESSSTATUSTC_TENTATIVE  6
          #define IPADDRESSSTATUSTC_DUPLICATE  7
        */
        if((flags & IFA_F_PERMANENT) || (!flags))
            entry->ia_status = IPADDRESSSTATUSTC_PREFERRED; /* ?? */
#ifdef IFA_F_TEMPORARY
        else if(flags & IFA_F_TEMPORARY)
            entry->ia_status = IPADDRESSSTATUSTC_PREFERRED; /* ?? */
#endif
        else if(flags & IFA_F_DEPRECATED)
            entry->ia_status = IPADDRESSSTATUSTC_DEPRECATED;
        else if(flags & IFA_F_TENTATIVE)
            entry->ia_status = IPADDRESSSTATUSTC_TENTATIVE;
        else {
            entry->ia_status = IPADDRESSSTATUSTC_UNKNOWN;
            DEBUGMSGTL(("access:ipaddress:ipv6",
                        "unknown flags 0x%x\n", flags));
        }

        /*
         * if it's not multi, it must be uni.
         *  (an ipv6 address is never broadcast)
         */
        if(addr_info.anycastflg)
            entry->ia_type = IPADDRESSTYPE_ANYCAST;
        else
            entry->ia_type = IPADDRESSTYPE_UNICAST;


        entry->ia_prefix_len = pfx_len;

        /*
         * can we figure out if an address is from DHCP?
         * use manual until then...
         *
         *#define IPADDRESSORIGINTC_OTHER  1
         *#define IPADDRESSORIGINTC_MANUAL  2
         *#define IPADDRESSORIGINTC_DHCP  4
         *#define IPADDRESSORIGINTC_LINKLAYER  5
         *#define IPADDRESSORIGINTC_RANDOM  6
         *
         * are 'local' address assigned by link layer??
         */
         if (!flags)
             entry->ia_origin = IPADDRESSORIGINTC_LINKLAYER;
#ifdef IFA_F_TEMPORARY
         else if (flags & IFA_F_TEMPORARY)
             entry->ia_origin = IPADDRESSORIGINTC_RANDOM;
#endif
         else if (IN6_IS_ADDR_LINKLOCAL(entry->ia_address))
             entry->ia_origin = IPADDRESSORIGINTC_LINKLAYER;
         else
             entry->ia_origin = IPADDRESSORIGINTC_MANUAL;

         if(entry->ia_origin == IPADDRESSORIGINTC_LINKLAYER)
            entry->ia_storagetype = STORAGETYPE_PERMANENT;

        /* xxx-rks: what can we do with scope? */
#ifdef HAVE_LINUX_RTNETLINK_H
        if(netsnmp_access_ipaddress_extra_prefix_info(entry->if_index, &entry->ia_prefered_lifetime
                                                      ,&entry->ia_valid_lifetime, addr) < 0){
           DEBUGMSGTL(("access:ipaddress:container", "unable to fetch extra prefix info\n"));
        }
#else
        entry->ia_prefered_lifetime = 0;
        entry->ia_valid_lifetime = 0;
#endif
#ifdef SUPPORT_PREFIX_FLAGS
        {
        prefix_cbx      prefix_val;
        memset(&prefix_val, 0, sizeof(prefix_cbx));
        if(net_snmp_find_prefix_info(&prefix_head_list, addr, &prefix_val) < 0) {
           DEBUGMSGTL(("access:ipaddress:container", "unable to find info\n"));
           entry->ia_onlink_flag = 1;  /*Set by default as true*/
           entry->ia_autonomous_flag = 2; /*Set by default as false*/

        } else {
           entry->ia_onlink_flag = prefix_val.ipAddressPrefixOnLinkFlag; 
           entry->ia_autonomous_flag = prefix_val.ipAddressPrefixAutonomousFlag;
        }
        }
#else
        entry->ia_onlink_flag = 1;  /*Set by default as true*/
        entry->ia_autonomous_flag = 2; /*Set by default as false*/
#endif

        /*
         * add entry to container
         */
        if (CONTAINER_INSERT(container, entry) < 0) {
            DEBUGMSGTL(("access:ipaddress:container","error with ipaddress_entry: insert into container failed.\n"));
            netsnmp_access_ipaddress_entry_free(entry);
            continue;
        }
    }

    fclose(in);

    if(rc<0)
        return rc;

    return idx_offset;
}
Beispiel #10
0
static int _load_v6 (netsnmp_container * container, int idx_offset)
{
    mib2_ipv6AddrEntry_t ip6ae;

    netsnmp_ipaddress_entry *entry;

    req_e req = GET_FIRST;

    int rc = 0;

    DEBUGMSGTL (("access:ipaddress:container", "loading v6... cache %d\n", MIB_IP6_ADDR));
    while ((rc = getMibstat (MIB_IP6_ADDR, &ip6ae, sizeof (ip6ae), req, &Get_everything, NULL)) == 0)
    {
        req = GET_NEXT;
        entry = netsnmp_access_ipaddress_entry_create ();
        if (entry == NULL)
            return (-1);
        if (memcmp ((const void *) &ip6ae.ipv6AddrAddress,
                    (const void *) &in6addr_any, sizeof (ip6ae.ipv6AddrAddress)) == 0)
            continue;

        ip6ae.ipv6AddrIfIndex.o_bytes[ip6ae.ipv6AddrIfIndex.o_length] = '\0';
        DEBUGMSGTL (("access:ipaddress:container", "found if %s\n", ip6ae.ipv6AddrIfIndex.o_bytes));

        /* Obtain interface index */
        entry->if_index = netsnmp_access_interface_index_find (ip6ae.ipv6AddrIfIndex.o_bytes);
        if (entry->if_index == 0)
        {
            DEBUGMSGTL (("access:ipaddress:container", "cannot find if %s\n", ip6ae.ipv6AddrIfIndex.o_bytes));
            netsnmp_access_ipaddress_entry_free (entry);
            return (-2);
        }

        /* Get the address */
        entry->ia_address_len = sizeof (ip6ae.ipv6AddrAddress);
        netsnmp_assert (entry->ia_address_len == 16 && entry->ia_address_len <= sizeof (entry->ia_address));
        memcpy (&entry->ia_address, &ip6ae.ipv6AddrAddress, entry->ia_address_len);

        /* prefix */
        entry->ia_prefix_len = ip6ae.ipv6AddrPfxLength;

        /* type is anycast? (mib2.h: 1 = yes, 2 = no) */
        entry->ia_type = (ip6ae.ipv6AddrAnycastFlag == 1) ? IPADDRESSTYPE_ANYCAST : IPADDRESSTYPE_UNICAST;

        /* origin (mib2.h: 1 = stateless, 2 = stateful, 3 = unknown) */
        DEBUGMSGTL (("access:ipaddress:container", "origin %d\n", ip6ae.ipv6AddrType));
        if (ip6ae.ipv6AddrType == 1)
            entry->ia_origin = IPADDRESSORIGINTC_LINKLAYER;
        else if (ip6ae.ipv6AddrInfo.ae_flags & IFF_DHCPRUNNING)
            entry->ia_origin = IPADDRESSORIGINTC_DHCP;
        else
            entry->ia_origin = IPADDRESSORIGINTC_MANUAL;

        /* status */
        entry->ia_status = ip6ae.ipv6AddrStatus;

        entry->ns_ia_index = ++idx_offset;

        DEBUGMSGTL (("access:ipaddress:container", "insert if %" NETSNMP_PRIo "u, addrlen %d\n",
                     entry->if_index, entry->ia_address_len));

        if (CONTAINER_INSERT (container, entry) < 0)
        {
            DEBUGMSGTL (("access:ipaddress:container", "unable to insert %s\n", ip6ae.ipv6AddrIfIndex.o_bytes));
            netsnmp_access_ipaddress_entry_free (entry);
            return (-3);
        }
    }
    return (idx_offset);
}
Beispiel #11
0
/*
 * @retval >=idx_offset ok
 * @retval -1 memory allocation error
 * @retval -2 interface lookup error
 * @retval -3 container error
 */
static int _load_v4 (netsnmp_container * container, int idx_offset)
{
    mib2_ipAddrEntry_t ipae;

    netsnmp_ipaddress_entry *entry;

    req_e req = GET_FIRST;

    int rc = 0;

    DEBUGMSGTL (("access:ipaddress:container", "loading v4\n"));
    while ((rc = getMibstat (MIB_IP_ADDR, &ipae, sizeof (ipae), req, &Get_everything, NULL)) == 0)
    {
        req = GET_NEXT;
        entry = netsnmp_access_ipaddress_entry_create ();
        if (entry == NULL)
            return (-1);
        if (ipae.ipAdEntAddr == INADDR_ANY)
            continue;

        ipae.ipAdEntIfIndex.o_bytes[ipae.ipAdEntIfIndex.o_length] = '\0';
        DEBUGMSGTL (("access:ipaddress:container", "found if %s\n", ipae.ipAdEntIfIndex.o_bytes));
        /* Obtain interface index */
        entry->if_index = netsnmp_access_interface_index_find (ipae.ipAdEntIfIndex.o_bytes);
        if (entry->if_index == 0)
        {
            DEBUGMSGTL (("access:ipaddress:container", "cannot find if %s\n", ipae.ipAdEntIfIndex.o_bytes));
            netsnmp_access_ipaddress_entry_free (entry);
            return (-2);
        }

        if (strchr ((const char *) &ipae.ipAdEntIfIndex.o_bytes, ':') != 0)
            entry->flags |= NETSNMP_ACCESS_IPADDRESS_ISALIAS;

        /* Get the address */
        entry->ia_address_len = sizeof (ipae.ipAdEntAddr);
        netsnmp_assert (entry->ia_address_len == 4 && entry->ia_address_len <= sizeof (entry->ia_address));
        memcpy (&entry->ia_address, &ipae.ipAdEntAddr, entry->ia_address_len);

        /* prefix */
        entry->ia_prefix_len = ipae.ipAdEntInfo.ae_subnet_len;

        /* set the Origin */
        if (ipae.ipAdEntInfo.ae_flags & IFF_DHCPRUNNING)
            entry->ia_origin = IPADDRESSORIGINTC_DHCP;
        else
            entry->ia_origin = IPADDRESSORIGINTC_MANUAL;

        /* set ipv4 constants */
        entry->ia_type = IPADDRESSTYPE_UNICAST;
        entry->ia_status = IPADDRESSSTATUSTC_PREFERRED;

        entry->ns_ia_index = ++idx_offset;

        DEBUGMSGTL (("access:ipaddress:container", "insert if %" NETSNMP_PRIo "u, addrlen %d\n",
                     entry->if_index, entry->ia_address_len));

        if (CONTAINER_INSERT (container, entry) < 0)
        {
            DEBUGMSGTL (("access:ipaddress:container", "unable to insert %s\n", ipae.ipAdEntIfIndex.o_bytes));
            netsnmp_access_ipaddress_entry_free (entry);
            return (-3);
        }
    }
    return (idx_offset);
}
Beispiel #12
0
static int
_load_v4(netsnmp_arp_access *access)
{
    FILE           *in;
    char            line[128];
    int             rc = 0;
    netsnmp_arp_entry *entry;
    char           arp[3*NETSNMP_ACCESS_ARP_PHYSADDR_BUF_SIZE+1];
    char           *arp_token;
    int             i;

    netsnmp_assert(NULL != access);

#define PROCFILE "/proc/net/arp"
    if (!(in = fopen(PROCFILE, "r"))) {
        snmp_log(LOG_DEBUG,"could not open " PROCFILE "\n");
        return -2;
    }

    /*
     * Get rid of the header line 
     */
    fgets(line, sizeof(line), in);

    /*
     * IP address | HW | Flag | HW address      | Mask | Device
     * 192.168.1.4  0x1  0x2   00:40:63:CC:1C:8C  *      eth0
     */
    while (fgets(line, sizeof(line), in)) {
        
        int             za, zb, zc, zd;
        unsigned int    tmp_flags;
        char            ifname[21];

        rc = sscanf(line,
                    "%d.%d.%d.%d 0x%*x 0x%x %96s %*[^ ] %20s\n",
                    &za, &zb, &zc, &zd, &tmp_flags, arp, ifname);
        if (7 != rc) {
            snmp_log(LOG_ERR, PROCFILE " data format error (%d!=12)\n", rc);
            snmp_log(LOG_ERR, " line ==|%s|\n", line);
            continue;
        }
        DEBUGMSGTL(("access:arp:container",
                    "ip addr %d.%d.%d.%d, flags 0x%X, hw addr "
                    "%s, name %s\n",
                    za,zb,zc,zd, tmp_flags, arp, ifname ));

        /*
         */
        entry = netsnmp_access_arp_entry_create();
        if(NULL == entry) {
            rc = -3;
            break;
        }

        /*
         * look up ifIndex
         */
        entry->generation = access->generation;
        entry->if_index = netsnmp_access_interface_index_find(ifname);
        if(0 == entry->if_index) {
            snmp_log(LOG_ERR,"couldn't find ifIndex for '%s', skipping\n",
                     ifname);
            netsnmp_access_arp_entry_free(entry);
            continue;
        }

        /*
         * now that we've passed all the possible 'continue', assign
         * index offset.
         */
        /* entry->ns_arp_index = ++idx_offset; */

        /*
         * parse ip addr
         */
        entry->arp_ipaddress[0] = za;
        entry->arp_ipaddress[1] = zb;
        entry->arp_ipaddress[2] = zc;
        entry->arp_ipaddress[3] = zd;
        entry->arp_ipaddress_len = 4;

        /*
         * parse hw addr
         */
        for (arp_token = strtok(arp, ":"), i=0; arp_token != NULL; arp_token = strtok(NULL, ":"), i++) {
            entry->arp_physaddress[i] = strtol(arp_token, NULL, 16);
        }
        entry->arp_physaddress_len = i;

        /*
         * what can we do with hw? from arp manpage:

         default  value  of  this  parameter is ether (i.e. hardware code
         0x01 for  IEEE  802.3  10Mbps  Ethernet).   Other  values  might
         include  network  technologies  such as ARCnet (arcnet) , PROnet
         (pronet) , AX.25 (ax25) and NET/ROM (netrom).
        */

        /*
         * parse mask
         */
        /* xxx-rks: what is mask? how to interpret '*'? */


        /*
         * process type
         */
        if(tmp_flags & ATF_PERM)
            entry->arp_type = INETNETTOMEDIATYPE_STATIC;
        else
            entry->arp_type = INETNETTOMEDIATYPE_DYNAMIC;

        /*
         * process status
         * if flags are 0, we can't tell the difference between
         * stale or incomplete.
         */
        if(tmp_flags & ATF_COM)
            entry->arp_state = INETNETTOMEDIASTATE_REACHABLE;
        else
            entry->arp_state = INETNETTOMEDIASTATE_UNKNOWN;

        /*
         * add entry to container
         */
        access->update_hook(access, entry);
    }

    fclose(in);
    return 0;
}