📄 interfaces.c
字号:
physaddrbuf = 0; return; }loop: ilen = len; cp = physaddrbuf; while (ilen > 0) { rtm = (struct rt_msghdr *)cp; if (rtm->rtm_version != RTM_VERSION || rtm->rtm_type != RTM_IFINFO) { free(physaddrs); physaddrs = 0; free(physaddrbuf); physaddrbuf = 0; } ifm = (struct if_msghdr *)rtm; ilen -= ifm->ifm_msglen; cp += ifm->ifm_msglen; rtm = (struct rt_msghdr *)cp; while (ilen > 0 && rtm->rtm_type == RTM_NEWADDR) { int is_alias = 0; ifam = (struct ifa_msghdr *)rtm; ilen -= sizeof(*ifam); cp += sizeof(*ifam); sa = (struct sockaddr *)cp;#define ROUND(x) (((x) + sizeof(long) - 1) & ~sizeof(long)) for (bit = 1; bit && ilen > 0; bit <<= 1) { if (!(ifam->ifam_addrs & bit)) continue; ilen -= ROUND(sa->sa_len); cp += ROUND(sa->sa_len); if (bit == RTA_IFA) { if (physaddrs)#define satosdl(sa) ((struct sockaddr_dl *)(sa)) physaddrs[naddrs++] = satosdl(sa); else naddrs++; } sa = (struct sockaddr *)cp; } rtm = (struct rt_msghdr *)cp; } } if (physaddrs) { nphysaddrs = naddrs; return; } physaddrs = malloc(naddrs * sizeof(*physaddrs)); if (physaddrs == 0) return; naddrs = 0; goto loop; }static intget_phys_address(int iindex, char **ap, int *len){ int i; int once = 1; do { for (i = 0; i < nphysaddrs; i++) { if (physaddrs[i]->sdl_index == iindex) break; } if (i < nphysaddrs) break; init_interfaces_setup(); } while (once--); if (i < nphysaddrs) { *ap = LLADDR(physaddrs[i]); *len = physaddrs[i]->sdl_alen; return 0; } return -1;}static intInterface_Scan_Get_Count (void){ static int count_oid[5] = { CTL_NET, PF_LINK, NETLINK_GENERIC, IFMIB_SYSTEM, IFMIB_IFCOUNT }; size_t len; int count; len = sizeof count; if (sysctl(count_oid, 5, &count, &len, (void *)0, (size_t)0) < 0) return -1; return count;}u_char *var_ifEntry(struct variable *vp, oid *name, size_t *length, int exact, size_t *var_len, WriteMethod **write_method){ int interface; static int sname[6] = { CTL_NET, PF_LINK, NETLINK_GENERIC, IFMIB_IFDATA, 0, IFDATA_GENERAL }; static struct ifmibdata ifmd; size_t len; char *cp; interface = header_ifEntry(vp, name, length, exact, var_len, write_method); if (interface == MATCH_FAILED) return NULL; sname[4] = interface; len = sizeof ifmd; if (sysctl(sname, 6, &ifmd, &len, 0, 0) < 0) return NULL; switch (vp->magic) { case IFINDEX: long_return = interface; return (u_char *) &long_return; case IFDESCR: cp = ifmd.ifmd_name; *var_len = strlen(cp); return (u_char *)cp; case IFTYPE: long_return = ifmd.ifmd_data.ifi_type; return (u_char *) &long_return; case IFMTU: long_return = (long) ifmd.ifmd_data.ifi_mtu; return (u_char *) &long_return; case IFSPEED: long_return = ifmd.ifmd_data.ifi_baudrate; return (u_char *) &long_return; case IFPHYSADDRESS: { char *cp; if (get_phys_address(interface, &cp, var_len)) return NULL; else return cp; } case IFADMINSTATUS: long_return = ifmd.ifmd_flags & IFF_UP ? 1 : 2; return (u_char *) &long_return; case IFOPERSTATUS: long_return = ifmd.ifmd_flags & IFF_RUNNING ? 1 : 2; return (u_char *) &long_return; case IFLASTCHANGE: if (ifmd.ifmd_data.ifi_lastchange.tv_sec == 0 && ifmd.ifmd_data.ifi_lastchange.tv_usec == 0) { long_return = 0; else if (ifmd.ifmd_data.ifi_lastchange.tv_sec < starttime.tv_sec) long_return = 0; } else { long_return = (u_long) ((ifmd.ifmd_data.ifi_lastchange.tv_sec - starttime.tv_sec) * 100 + ((ifmd.ifmd_data.ifi_lastchange.tv_usec - starttime.tv_usec) / 10000)); } return (u_char *) &long_return; case IFINOCTETS: long_return = (u_long) ifmd.ifmd_data.ifi_ibytes; return (u_char *) &long_return; case IFINUCASTPKTS: long_return = (u_long) ifmd.ifmd_data.ifi_ipackets; long_return -= (u_long) ifmd.ifmd_data.ifi_imcasts; return (u_char *) &long_return; case IFINNUCASTPKTS: long_return = (u_long) ifmd.ifmd_data.ifi_imcasts; return (u_char *) &long_return; case IFINDISCARDS: long_return = (u_long) ifmd.ifmd_data.ifi_iqdrops; return (u_char *) &long_return; case IFINERRORS: long_return = ifmd.ifmd_data.ifi_ierrors; return (u_char *) &long_return; case IFINUNKNOWNPROTOS: long_return = (u_long) ifmd.ifmd_data.ifi_noproto; return (u_char *) &long_return; case IFOUTOCTETS: long_return = (u_long) ifmd.ifmd_data.ifi_obytes; return (u_char *) &long_return; case IFOUTUCASTPKTS: long_return = (u_long) ifmd.ifmd_data.ifi_opackets; long_return -= (u_long) ifmd.ifmd_data.ifi_omcasts; return (u_char *) &long_return; case IFOUTNUCASTPKTS: long_return = (u_long) ifmd.ifmd_data.ifi_omcasts; return (u_char *) &long_return; case IFOUTDISCARDS: long_return = ifmd.ifmd_snd_drops; return (u_char *) &long_return; case IFOUTERRORS: long_return = ifmd.ifmd_data.ifi_oerrors; return (u_char *) &long_return; case IFOUTQLEN: long_return = ifmd.ifmd_snd_len; return (u_char *) &long_return; case IFSPECIFIC: *var_len = nullOidLen; return (u_char *) nullOid; default: DEBUGMSGTL(("snmpd", "unknown sub-id %d in var_ifEntry\n", vp->magic)); } return NULL;}#endif /* HAVE_NET_IF_MIB_H */#endif#else /* WIN32 */#include <iphlpapi.h>WriteMethod writeIfEntry;long admin_status = 0;long oldadmin_status = 0;static intheader_ifEntry(struct variable *vp, oid *name, size_t *length, int exact, size_t *var_len, WriteMethod **write_method){#define IFENTRY_NAME_LENGTH 10 oid newname[MAX_OID_LEN]; register int ifIndex; int result, count; DWORD status = NO_ERROR; DWORD statusRetry = NO_ERROR; DWORD dwActualSize = 0; PMIB_IFTABLE pIfTable = NULL; DEBUGMSGTL(("mibII/interfaces", "var_ifEntry: ")); DEBUGMSGOID(("mibII/interfaces", name, *length)); DEBUGMSG(("mibII/interfaces"," %d\n", exact)); memcpy( (char *)newname,(char *)vp->name, (int)vp->namelen * sizeof(oid)); /* find "next" ifIndex */ /* query for buffer size needed */ status = GetIfTable(pIfTable, &dwActualSize, TRUE); if (status == ERROR_INSUFFICIENT_BUFFER) { /* need more space */ pIfTable = (PMIB_IFTABLE) malloc(dwActualSize); if(pIfTable != NULL){ /* Get the sorted IF table */ GetIfTable(pIfTable, &dwActualSize, TRUE); } } count = pIfTable->dwNumEntries; for(ifIndex = 0; ifIndex < count; ifIndex++){ newname[IFENTRY_NAME_LENGTH] = (oid)pIfTable->table[ifIndex].dwIndex; result = snmp_oid_compare(name, *length, newname, (int)vp->namelen + 1); if ((exact && (result == 0)) || (!exact && (result < 0))) break; } if (ifIndex > count) { DEBUGMSGTL(("mibII/interfaces", "... index out of range\n")); return MATCH_FAILED; } memcpy( (char *)name,(char *)newname, ((int)vp->namelen + 1) * sizeof(oid)); *length = vp->namelen + 1; *write_method = 0; *var_len = sizeof(long); /* default to 'long' results */ DEBUGMSGTL(("mibII/interfaces", "... get I/F stats ")); DEBUGMSGOID(("mibII/interfaces", name, *length)); DEBUGMSG(("mibII/interfaces","\n")); count = pIfTable->table[ifIndex].dwIndex; free(pIfTable); return count;}u_char *var_interfaces(struct variable *vp, oid *name, size_t *length, int exact, size_t *var_len, WriteMethod **write_method){ if (header_generic(vp, name, length, exact, var_len, write_method) == MATCH_FAILED ) return NULL; switch (vp->magic) { case IFNUMBER: GetNumberOfInterfaces(&long_return); return (u_char *)&long_return; default: DEBUGMSGTL(("snmpd", "unknown sub-id %d in var_interfaces\n", vp->magic)); } return NULL;}u_char *var_ifEntry(struct variable *vp, oid *name, size_t *length, int exact, size_t *var_len, WriteMethod **write_method){ int ifIndex; static char Name[16]; conf_if_list *if_ptr = conf_list; static MIB_IFROW ifRow; ifIndex = header_ifEntry(vp, name, length, exact, var_len, write_method); if ( ifIndex == MATCH_FAILED ) return NULL; /* Get the If Table Row by passing index as argument */ ifRow.dwIndex = ifIndex; if(GetIfEntry(&ifRow) != NO_ERROR) return NULL; switch (vp->magic){ case IFINDEX: long_return = ifIndex; return (u_char *) &long_return; case IFDESCR: *var_len = ifRow.dwDescrLen; return (u_char *)ifRow.bDescr; case IFTYPE: long_return = ifRow.dwType; return (u_char *) &long_return; case IFMTU: long_return = (long) ifRow.dwMtu; return (u_char *) &long_return; case IFSPEED: long_return = (long) ifRow.dwSpeed; return (u_char *) &long_return; case IFPHYSADDRESS: *var_len = ifRow.dwPhysAddrLen; memcpy(return_buf, ifRow.bPhysAddr, *var_len); return(u_char *) return_buf; case IFADMINSTATUS: long_return = ifRow.dwAdminStatus; admin_status = long_return; *write_method = writeIfEntry; return (u_char *) &long_return; case IFOPERSTATUS: long_return = ifRow.dwOperStatus; return (u_char *) &long_return; case IFLASTCHANGE: long_return = ifRow.dwLastChange; return (u_char *) &long_return; case IFINOCTETS: long_return = ifRow.dwInOctets; return (u_char *) &long_return; case IFINUCASTPKTS: long_return = ifRow.dwInUcastPkts; return (u_char *) &long_return; case IFINNUCASTPKTS: long_return = ifRow.dwInNUcastPkts; return (u_char *) &long_return; case IFINDISCARDS: long_return = ifRow.dwInDiscards; return (u_char *) &long_return; case IFINERRORS: long_return = ifRow.dwInErrors; return (u_char *) &long_return; case IFINUNKNOWNPROTOS: long_return = ifRow.dwInUnknownProtos; return (u_char *) &long_return; case IFOUTOCTETS: long_return = ifRow.dwOutOctets; return (u_char *) &long_return; case IFOUTUCASTPKTS: long_return = ifRow.dwOutUcastPkts; return (u_char *) &long_return; case IFOUTNUCASTPKTS: long_return = ifRow.dwOutNUcastPkts; return (u_char *) &long_return; case IFOUTDISCARDS: long_return = ifRow.dwOutDiscards; return (u_char *) &long_return; case IFOUTERRORS: long_return = ifRow.dwOutErrors; return (u_char *) &long_return; case IFOUTQLEN: long_return = ifRow.dwOutQLen; return (u_char *) &long_return; case IFSPECIFIC: *var_len = nullOidLen; return (u_char *) nullOid; default: DEBUGMSGTL(("snmpd", "unknown sub-id %d in var_ifEntry\n", vp->magic)); } return NULL;}intwriteIfEntry(int action, u_char *var_val, u_char var_val_type, size_t var_val_len, u_char *statP, oid *name, size_t name_len){ MIB_IFROW ifEntryRow; if((char)name[9] != IFADMINSTATUS){ return SNMP_ERR_NOTWRITABLE; } switch ( action ) { case RESERVE1: /* Check values for acceptability */ if (var_val_type != ASN_INTEGER){ snmp_log(LOG_ERR, "not integer\n"); return SNMP_ERR_WRONGTYPE; } if (var_val_len > sizeof(int)){ snmp_log(LOG_ERR, "bad length\n"); return SNMP_ERR_WRONGLENGTH; } /* The dwAdminStatus member can be MIB_IF_ADMIN_STATUS_UP or MIB_IF_ADMIN_STATUS_DOWN */ if(!(((int)(*var_val) == MIB_IF_ADMIN_STATUS_UP) || ((int)(*var_val) == MIB_IF_ADMIN_STATUS_DOWN))){ snmp_log(LOG_ERR, "not supported admin state\n"); return SNMP_ERR_WRONGVALUE; } break; case RESERVE2: /* Allocate memory and similar resources */ break; case ACTION: /* Save the old value, in case of UNDO */ oldadmin_status = admin_status; admin_status = (int)*var_val; break; case UNDO: /* Reverse the SET action and free resources */ admin_status = oldadmin_status; break; case COMMIT: /* Confirm the SET, performing any irreversible actions, and free resources */ ifEntryRow.dwIndex = (int)name[10]; ifEntryRow.dwAdminStatus = admin_status; /* Only UP and DOWN status are supported. Thats why done in COMMIT */ if(SetIfEntry(&ifEntryRow) != NO_ERROR){ snmp_log(LOG_ERR, "Error in writeIfEntry case COMMIT with index: %d & adminStatus %d\n", ifEntryRow.dwIndex, ifEntryRow.dwAdminStatus); return SNMP_ERR_COMMITFAILED; } case FREE: /* Free any resources allocated */ /* No resources have been allocated */ break; } return SNMP_ERR_NOERROR;} /* end of writeIfEntry */#endif /* WIN32 */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -