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

📄 discnodc.c

📁 嵌入式RMON,RMON为Remote monitor的缩写,基于SNMP为网络提供主动监控及错误告警,智能交换路由必备协议
💻 C
📖 第 1 页 / 共 2 页
字号:
/* Beholder RMON ethernet network monitor,Copyright (C) 1993 DNPAP group *//* See file COPYING 'GNU General Public Licence' for copyright details   */#include <stdlib.h>#include <limits.h>#include <memory.h>#include <dnpap.h>#include <timer.h>#include <config.h>#include <message.h>#include <mac.h>#include <hash.h>#include <dmath.h>#include <dtime.h>#include <sysmib.h>#include <protocol.h>#include <channel.h>#include "discd.h"#include "disce.h"#include "discnodc.h"IMPORT BOOLEAN BeholderStrictRMON;static LONG DiscNodeMaxNrNodes = 8000;static LONG DiscNodeTimeout = 10000;static BOOLEAN DiscNodeCallback(MAC_COLL *collector, PROT_PKT *pkt);static BOOLEAN DiscNodeUpdateTables(DISCNODE_CONTROL *discnodecontrol, INT type, BYTE *src, INT srclen, BYTE *dst, INT dstlen, LWORD size, ULONG now);static BOOLEAN DiscNodeUpdateTablesPerNode(DISCNODE_CONTROL *discnodecontrol, INT type, BYTE *node, INT nodelen, INT direction, LWORD size, ULONG now);static VOID DiscNodeRemoveEntry(DISCNODE_CONTROL *discnodecontrol, DISCNODE *olddisc);static BOOLEAN DiscNodeAddLexList(INT type, DISCNODE **lexlist, DISCNODE *disc);static BOOLEAN DiscNodeRemoveLexList(DISCNODE **lexlist, DISCNODE *disc);static DISCNODE *DiscNodeAddLRUList(DISCNODE_CONTROL *discnodecontrol, DISCNODE *disc);static BOOLEAN DiscNodeUpdateLRUList(DISCNODE_CONTROL *discnodecontrol, DISCNODE *disc);static BOOLEAN DiscNodeRemoveLRUList(DISCNODE_CONTROL *discnodecontrol, DISCNODE *disc);static BOOLEAN DiscNodeAddTimeList(DISCNODE_CONTROL *discnodecontrol, INT type, DISCNODE **timelist, DISCNODE **timelast, DISCNODE *disc);static BOOLEAN DiscNodeRemoveTimeList(DISCNODE_CONTROL *discnodecontrol, INT type, DISCNODE **timelist, DISCNODE **timelast, DISCNODE *disc);static BOOLEAN DiscNodeUpdateTimeTables(DISCNODE_CONTROL *discnodecontrol);static BOOLEAN DiscNodeUpdateSpecificTimeTable(DISCNODE *timelist, DISCNODE **timetable, LONG size);static VOID LRUTimerCallback(TIMER_DESCR *timer, ULONG now, VOID *param);static VOID DelDiscNodes(DISCNODE_CONTROL *discnodecontrol, DISCNODE **lexlist);static INT NodeLen(INT type);BOOLEAN DiscNodeConfigInit(VOID){	ConfigGetLong("beholder.discnode.maxnrnodes", &DiscNodeMaxNrNodes);	if (DiscNodeMaxNrNodes < 2)    {        DnpapMessage(DMC_WARNING, DISC_MAX, "discnodecontrol: beholder.disc.maxnrnodes < 2, setting it to 2");        DiscNodeMaxNrNodes = 2;    }	ConfigGetLong("beholder.discnode.timeout", &DiscNodeTimeout);    	if (DiscNodeTimeout < 2)    {        DnpapMessage(DMC_WARNING, DISC_MAX, "discnodecontrol: beholder.discnode.timeout < 2, setting it to 2");        DiscNodeTimeout = 2;    }	return TRUE;}BOOLEAN DiscNodeCInit(DISCNODE_CONTROL *discnodecontrol){LONG source[] = {1,3,6,1,2,1,2,2,1,1,1};    memcpy(discnodecontrol->Source, source, sizeof(source));    discnodecontrol->SourceLen = sizeof(source)/sizeof(source[0]);    discnodecontrol->Channel = FALSE;    discnodecontrol->ChannelType = 0;    discnodecontrol->ChannelAccept = TRUE;    discnodecontrol->AddressLen = 0;    discnodecontrol->EthTableSize = 0;    discnodecontrol->IPTableSize = 0;    discnodecontrol->UDPTableSize = 0;    discnodecontrol->TCPTableSize = 0;    discnodecontrol->TableSize = 0;    discnodecontrol->TurnOnTime = 0;    discnodecontrol->LastDeleteTime = 0;    discnodecontrol->Owner[0] = '\0';    discnodecontrol->OwnerLen = 0;    discnodecontrol->Status = SNMP_INVALID;        if ((discnodecontrol->Iface =        MacIfaceGet((WORD) discnodecontrol->Source[discnodecontrol->SourceLen-1])) == NULL)    {        DnpapMessage(DMC_ERROR, DISC_NETINIT, "discnodecontrol: network initialisation failed");        return (FALSE);    }	    discnodecontrol->Table = NULL;        discnodecontrol->EthLexList = NULL;    discnodecontrol->IPLexList = NULL;    discnodecontrol->UDPLexList = NULL;    discnodecontrol->TCPLexList = NULL;    	discnodecontrol->LRUList = NULL;	discnodecontrol->LRULast = NULL;	    discnodecontrol->EthTimeList = NULL;    discnodecontrol->EthTimeLast = NULL;    discnodecontrol->EthTimeTable = NULL;    discnodecontrol->EthTimeListUpdated = FALSE;    discnodecontrol->IPTimeList = NULL;    discnodecontrol->IPTimeLast = NULL;    discnodecontrol->IPTimeTable = NULL;    discnodecontrol->IPTimeListUpdated = FALSE;    discnodecontrol->UDPTimeList = NULL;    discnodecontrol->UDPTimeLast = NULL;    discnodecontrol->UDPTimeTable = NULL;    discnodecontrol->UDPTimeListUpdated = FALSE;    discnodecontrol->TCPTimeList = NULL;    discnodecontrol->TCPTimeLast = NULL;    discnodecontrol->TCPTimeTable = NULL;    discnodecontrol->TCPTimeListUpdated = FALSE;        discnodecontrol->LRUTimer = NULL;    discnodecontrol->LastLRUEntry = NULL;    	BooleanSetAllTrue(discnodecontrol->ObjectSet);	BooleanSetFalse(discnodecontrol->ObjectSet, DISC_BOOLEAN_DATASOURCE);	BooleanSetFalse(discnodecontrol->ObjectSet, DISC_BOOLEAN_OWNER);	return TRUE;}BOOLEAN DiscNodeCStart(DISCNODE_CONTROL *discnodecontrol){	if (BeholderStrictRMON && !BooleanCheckAllTrue(discnodecontrol->ObjectSet))		return FALSE;	if (discnodecontrol->Channel == FALSE)	{	    discnodecontrol->Coll.Rcve       = DiscNodeCallback;	    discnodecontrol->Coll.specific   = discnodecontrol;	    if (!MacCollRegister(&(discnodecontrol->Coll)))	    {	        DnpapMessage(DMC_ERROR, DISC_NETERR, "discnodecontrol: network initialisation failed");	        return FALSE;	    }    }    if ((discnodecontrol->Table = NewHash(DiscNodeMaxNrNodes/2+11, NULL)) == NULL)    {        DnpapMessage(DMC_ERROR, DISC_HASHERR, "discnodecontrol: can not create hashtable");        return FALSE;    }    if ((discnodecontrol->EthTimeTable = (DISCNODE**)DnpapMalloc(DiscNodeMaxNrNodes*sizeof(DISCNODE*))) == NULL)    {        DnpapMessage(DMC_ERROR, DISC_TIMETABLE, "discnodecontrol: can not create time ordered Ethernet table");        return FALSE;    }    if ((discnodecontrol->IPTimeTable = (DISCNODE**)DnpapMalloc(DiscNodeMaxNrNodes*sizeof(DISCNODE*))) == NULL)    {        DnpapMessage(DMC_ERROR, DISC_TIMETABLE, "discnodecontrol: can not create time ordered IP table");        return FALSE;    }    if ((discnodecontrol->UDPTimeTable = (DISCNODE**)DnpapMalloc(DiscNodeMaxNrNodes*sizeof(DISCNODE*))) == NULL)    {        DnpapMessage(DMC_ERROR, DISC_TIMETABLE, "discnodecontrol: can not create time ordered UDP table");        return FALSE;    }    if ((discnodecontrol->TCPTimeTable = (DISCNODE**)DnpapMalloc(DiscNodeMaxNrNodes*sizeof(DISCNODE*))) == NULL)    {        DnpapMessage(DMC_ERROR, DISC_TIMETABLE, "discnodecontrol: can not create time ordered TCP table");        return FALSE;    }    if ((discnodecontrol->LRUTimer = TimerRegister(LRUTimerCallback, discnodecontrol, DiscNodeTimeout, TIMER_FOREVER, TIMER_TYPE_RECOVER)) == NULL)    {        DnpapMessage(DMC_ERROR, DISC_TIMER, "discnodecontrol: can not set LRU timer");        return FALSE;    }	discnodecontrol->TurnOnTime = TimeUsec();	    return TRUE;}BOOLEAN DiscNodeCStop(DISCNODE_CONTROL *discnodecontrol){    TimerRemove(discnodecontrol->LRUTimer);        MacCollRemove(&(discnodecontrol->Coll));    DelHash(discnodecontrol->Table);    DelDiscNodes(discnodecontrol, &discnodecontrol->EthLexList);    DelDiscNodes(discnodecontrol, &discnodecontrol->IPLexList);    DelDiscNodes(discnodecontrol, &discnodecontrol->UDPLexList);    DelDiscNodes(discnodecontrol, &discnodecontrol->TCPLexList);    DnpapFree(discnodecontrol->EthTimeTable);    DnpapFree(discnodecontrol->IPTimeTable);    DnpapFree(discnodecontrol->UDPTimeTable);    DnpapFree(discnodecontrol->TCPTimeTable);        return TRUE;}BOOLEAN DiscNodeCallback(MAC_COLL *collector, PROT_PKT *pkt){DISCNODE_CONTROL *discnodecontrol = collector->specific;PROT_OBJ Interface = {0, {1,2}};    if (ProtGetField(pkt,&Interface) == TRUE &&        Interface.Syntax.LngInt == discnodecontrol->Source[discnodecontrol->SourceLen-1])		DiscNodeHandlePkt(discnodecontrol, pkt);			return TRUE;}VOID DiscNodeHandlePkt(DISCNODE_CONTROL *discnodecontrol, PROT_PKT *pkt){PROT_OBJ EthDst = {1, {2,1}};PROT_OBJ EthSrc = {1, {2,2}};PROT_OBJ EthSize = {0, {1,4}};PROT_OBJ EthTime = {0, {1,6}};PROT_OBJ IPSize = {2, {3,4}};PROT_OBJ IPOffset = {2, {3,7}};PROT_OBJ IPSrc = {2, {3,11}};PROT_OBJ IPDst = {2, {3,12}};PROT_OBJ UDPSrc = {3, {5,1}};PROT_OBJ UDPDst = {3, {5,2}};PROT_OBJ UDPSize = {3, {5,3}};PROT_OBJ TCPSrc = {3, {4,1}};PROT_OBJ TCPDst = {3, {4,2}};PROT_OBJ TCPSize = {3, {4,5}};ULONG now;BYTE src[DISC_SIZE_NODE], dst[DISC_SIZE_NODE];LWORD size;INT type;    if (discnodecontrol->Channel == FALSE)        type = discnodecontrol->Iface->type;    else    {        type = discnodecontrol->ChannelType;        if (type == 0)        {            type = ChannelType(discnodecontrol->Source[discnodecontrol->SourceLen-1]);            if (type == 0)                return;            discnodecontrol->ChannelType = type;        }    }	if (type != MAC_TYPE_ETHERNET_CSMACD && type != MAC_TYPE_88023_CSMACD)		return;    if (ProtGetField(pkt,&EthSize) == TRUE &&        ProtGetField(pkt,&EthTime) == TRUE &&        ProtGetField(pkt,&EthSrc) == TRUE &&        ProtGetField(pkt,&EthDst) == TRUE)    {        size = EthSize.Syntax.LngUns + 4L;    	now = EthTime.Syntax.LngUns - discnodecontrol->TurnOnTime;    	        if (EthSrc.SyntaxLen != DISC_SIZE_ETHADDR || EthDst.SyntaxLen != DISC_SIZE_ETHADDR)        {            DnpapMessage(DMC_ERROR, DISC_INVPACKET, "discnodecontrol: invalid packet");            return;        }                                       memcpy(src, EthSrc.Syntax.BufChr, DISC_SIZE_ETHADDR);        memcpy(dst, EthDst.Syntax.BufChr, DISC_SIZE_ETHADDR);        DiscNodeUpdateTables(discnodecontrol, DISC_TYPE_ETH, src, DISC_SIZE_ETHADDR, dst, DISC_SIZE_ETHADDR, size, now);        if (ProtGetField(pkt,&IPSize) == TRUE &&            ProtGetField(pkt,&IPSrc) == TRUE &&            ProtGetField(pkt,&IPDst) == TRUE)        {            size = IPSize.Syntax.LngUns;            NETLVALUEPTR2BYTES(src+DISC_SIZE_ETHADDR, IPSrc.Syntax.BufChr);            NETLVALUEPTR2BYTES(dst+DISC_SIZE_ETHADDR, IPDst.Syntax.BufChr);            DiscNodeUpdateTables(discnodecontrol, DISC_TYPE_IP, src, DISC_SIZE_TOIPADDR, dst, DISC_SIZE_TOIPADDR, size, now);            if (ProtGetField(pkt,&IPOffset) == TRUE &&                IPOffset.Syntax.LngUns == 0)            {                if (ProtGetField(pkt,&UDPSize) == TRUE &&                    ProtGetField(pkt,&UDPSrc) == TRUE &&                    ProtGetField(pkt,&UDPDst) == TRUE)                {                    size = UDPSize.Syntax.LngUns;                    VALUE2BYTES(src+DISC_SIZE_TOIPADDR, UDPSrc.Syntax.LngInt);                    VALUE2BYTES(dst+DISC_SIZE_TOIPADDR, UDPDst.Syntax.LngInt);                    DiscNodeUpdateTables(discnodecontrol, DISC_TYPE_UDP, src, DISC_SIZE_TOUDPADDR, dst, DISC_SIZE_TOUDPADDR, size, now);                }                else                if (ProtGetField(pkt,&TCPSize) == TRUE &&                    ProtGetField(pkt,&TCPSrc) == TRUE &&                    ProtGetField(pkt,&TCPDst) == TRUE)                {                    size = TCPSize.Syntax.LngUns;                    VALUE2BYTES(src+DISC_SIZE_TOIPADDR, TCPSrc.Syntax.LngInt);                    VALUE2BYTES(dst+DISC_SIZE_TOIPADDR, TCPDst.Syntax.LngInt);                    DiscNodeUpdateTables(discnodecontrol, DISC_TYPE_TCP, src, DISC_SIZE_TOTCPADDR, dst, DISC_SIZE_TOTCPADDR, size, now);                }            }        }    }    return;}BOOLEAN DiscNodeUpdateTables(DISCNODE_CONTROL *discnodecontrol, INT type, BYTE *src, INT srclen, BYTE *dst, INT dstlen, LWORD size, ULONG now){             BOOLEAN rc = TRUE;                  if (DiscNodeUpdateTablesPerNode(discnodecontrol, type, src, srclen, DISC_TYPE_SOURCE, size, now) == FALSE)        rc = FALSE;    if (DiscNodeUpdateTablesPerNode(discnodecontrol, type, dst, dstlen, DISC_TYPE_DEST, size, now) == FALSE)        rc = FALSE;    return rc;} BOOLEAN DiscNodeUpdateTablesPerNode(DISCNODE_CONTROL *discnodecontrol, INT type, BYTE *node, INT nodelen, INT direction, LWORD size, ULONG now){            DISCNODE *disc, *olddisc;    if ((disc = HashSearch(discnodecontrol->Table, node, nodelen)) == NULL)    {        /*  first try to add the new disc  */        if ((disc = DnpapMalloc(sizeof(DISCNODE))) != NULL)        {            memset(disc, 0, sizeof(DISCNODE));            memcpy(disc->Address, node, (disc->AddressLen = nodelen));            disc->Type = (BYTE)type;            if (HashAdd(discnodecontrol->Table, disc->Address, nodelen, disc) == NULL)            {                DnpapMessage(DMC_WARNING, DISC_NADD, "discnodecontrol: node could not be added to the hash table");                DnpapFree(disc);                disc = NULL;            }            else            {                   switch (type)                {                case DISC_TYPE_ETH:                    DiscNodeAddLexList(type, &discnodecontrol->EthLexList, disc);                    DiscNodeAddTimeList(discnodecontrol, type,                        &discnodecontrol->EthTimeList, &discnodecontrol->EthTimeLast, disc);                    discnodecontrol->EthTableSize++;                    break;                case DISC_TYPE_IP:                    DiscNodeAddLexList(type, &discnodecontrol->IPLexList, disc);                    DiscNodeAddTimeList(discnodecontrol, type,                        &discnodecontrol->IPTimeList, &discnodecontrol->IPTimeLast, disc);                    discnodecontrol->IPTableSize++;                    break;                case DISC_TYPE_UDP:                    DiscNodeAddLexList(type, &discnodecontrol->UDPLexList, disc);                    DiscNodeAddTimeList(discnodecontrol, type,                        &discnodecontrol->UDPTimeList, &discnodecontrol->UDPTimeLast, disc);                    discnodecontrol->UDPTableSize++;                    break;                case DISC_TYPE_TCP:                    DiscNodeAddLexList(type, &discnodecontrol->TCPLexList, disc);                    DiscNodeAddTimeList(discnodecontrol, type,                        &discnodecontrol->TCPTimeList, &discnodecontrol->TCPTimeLast, disc);                    discnodecontrol->TCPTableSize++;                    break;                default:                    DnpapMessage(DMC_FATAL, DISC_TYPE, "discnodecontrol: unknown type");                    DnpapExit(DISC_TYPE);                }                                olddisc = DiscNodeAddLRUList(discnodecontrol, disc);                discnodecontrol->TableSize++;                if (discnodecontrol->TableSize > (LONG)DiscNodeMaxNrNodes)                    DiscNodeRemoveEntry(discnodecontrol, olddisc);            }        }    }        if (disc != NULL)    {        switch (direction)        {        case DISC_TYPE_SOURCE:            disc->OutPkts++;            disc->OutOctets += size;            break;        case DISC_TYPE_DEST:            disc->InPkts++;            disc->InOctets += size;            break;        }        disc->LRUTime = now;        DiscNodeUpdateLRUList(discnodecontrol, disc);    }    return TRUE;}VOID DiscNodeRemoveEntry(DISCNODE_CONTROL *discnodecontrol, DISCNODE *olddisc)    {                  INT type;    DiscNodeRemoveLRUList(discnodecontrol, olddisc);        switch (type = olddisc->Type)    {    case DISC_TYPE_ETH:        DiscNodeRemoveTimeList(discnodecontrol, type,            &discnodecontrol->EthTimeList, &discnodecontrol->EthTimeLast, olddisc);        DiscNodeRemoveLexList(&discnodecontrol->EthLexList, olddisc);        discnodecontrol->EthTableSize--;        break;    case DISC_TYPE_IP:        DiscNodeRemoveTimeList(discnodecontrol, type,            &discnodecontrol->IPTimeList, &discnodecontrol->IPTimeLast, olddisc);        DiscNodeRemoveLexList(&discnodecontrol->IPLexList, olddisc);        discnodecontrol->IPTableSize--;        break;    case DISC_TYPE_UDP:        DiscNodeRemoveTimeList(discnodecontrol, type,            &discnodecontrol->UDPTimeList, &discnodecontrol->UDPTimeLast, olddisc);        DiscNodeRemoveLexList(&discnodecontrol->UDPLexList, olddisc);        discnodecontrol->UDPTableSize--;        break;    case DISC_TYPE_TCP:        DiscNodeRemoveTimeList(discnodecontrol, type,            &discnodecontrol->TCPTimeList, &discnodecontrol->TCPTimeLast, olddisc);        DiscNodeRemoveLexList(&discnodecontrol->TCPLexList, olddisc);        discnodecontrol->TCPTableSize--;        break;    }        HashRemove(discnodecontrol->Table, olddisc->Address, olddisc->AddressLen);    DnpapFree(olddisc);    discnodecontrol->LastDeleteTime = SysTime();    discnodecontrol->TableSize--;                 }BOOLEAN DiscNodeAddLexList(INT type, DISCNODE **lexlist, DISCNODE *disc){

⌨️ 快捷键说明

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