SNMP用VC开发 联系客服

发布时间 : 星期二 文章SNMP用VC开发更新完毕开始阅读

smiINT sNumber; // SNMP_SYNTAX_INT // SNMP_SYNTAX_INT32

smiUINT32 uNumber; // SNMP_SYNTAX_UINT32 // SNMP_SYNTAX_CNTR32 // SNMP_SYNTAX_GAUGE32

// SNMP_SYNTAX_TIMETICKS

smiCNTR64 hNumber; // SNMP_SYNTAX_CNTR64 smiOCTETS string; // SNMP_SYNTAX_OCTETS // SNMP_SYNTAX_BITS // SNMP_SYNTAX_OPAQUE // SNMP_SYNTAX_IPADDR // SNMP_SYNTAX_NSAPADDR smiOID oid; // SNMP_SYNTAX_OID smiBYTE empty; // SNMP_SYNTAX_NULL // SNMP_SYNTAX_NOSUCHOBJECT // SNMP_SYNTAX_NOSUCHINSTANCE // SNMP_SYNTAX_ENDOFMIBVIEW } value; // union

} smiVALUE, *smiLPVALUE;

从整体上看,该结构有两个类型构成,一个是smiUINT32 syntax; 另一个看上去挺复杂,但仔细看却是一个共同体类型,是了,那么它们之间有什么联系呢?我们可以想象一下,一个车厢只接收一种类型的数据,该类型的数据又会 有他自己的值,如此就好解释了,syntax就是用来标志数据类型的,当该类型确定后,我们就从union中找到与它相对应的值value。SNMP中这 种设计是很巧妙的。从上面这个结构我们也就了解到在SNMP中所用到的基本数据类型了,也就是union中所列出的,在这提一下,通常有关网络设备描述的 值都是smiOCTETS类型。

再来看看我们已完成的工作,到目前为止我们已经有四个句炳了,1。会话句炳,2。实体句炳,3。上下文句炳,4。绑定列表句炳。还介绍了两个 结构。这两个结构全和变量绑定列表相关,现在火车的车厢和空间已经有了,车头也有了,还差给他装上轮子,找一个好司机了,需要他记住自己的使命。

11。要想将数据正确的发送到目的地,我们必须其按照特定的格式来发送,对于了解ip协议的编程人员来说,就不需要做过多地解释了。我们用函数HSNMP_PDU SnmpCreatePdu( HSNMP_SESSION session, // handle to the WinSNMP session smiINT PDU_type, // PDU type

smiINT32 request_id, // PDU request identifier

smiINT error_status, // valid only for SNMP_PDU_GETBULK requests smiINT error_index, // valid only for SNMP_PDU_GETBULK requests HSNMP_VBL varbindlist // handle to the variable bindings list

);来完成该功能。

第一个和最后一个参数是我们上面构造的会话句炳和变量绑定列表句炳,第二个参数很重要,他表示我们想要执行的操作方式,SNMP中有如下的选项: SNMP_PDU_GET SNMP_PDU_GETNEXT

SNMP_PDU_RESPONSE SNMP_PDU_SET

SNMP_PDU_V1TRAP SNMP_PDU_GETBULK SNMP_PDU_TRAP

对于这些操作,我建议读者最好找点有关书籍看看,在这里我只对部分操作大概讲解一下,SNMP_PDU_GET通常用来获得某一个特定的对象标 志符所对应的值,SNMP_PDU_GETNEXT是在编程人员不了解该表列情况下使用的用来获取一组值的操作。SNMP_PDU_RESPONSE一般 是SNMP代理填写的,表示应答发出操作请求的数据报。SNMP_PDU_SET是用来改变某一对象标志符的值的操作。SNMP_PDU_GETBULK 只能在V2版本以上使用,是用来解决SNMP_PDU_GETNEXT一次消息只能取得一个数据的缺点,可通过发一次消息取得一组数据。 SNMP_PDU_V1TRAP和SNMP_PDU_TRAP使用来发自陷消息的操作。

第三个参数request_id,对于同步实现消息机制的编程来说,几乎没有作用,但是对于异步操作,该参数有很重要的作用,你可以用它来标志某一个请求的消息,如果有几个消息都在消息队列中,你可以通过它来确定自己想要处理的消息,该值完全可以自己来设定。 error_status和error_index在SNMP_PDU_GETBULK操作中分别为PDU中non_repeaters域定一个值和PDU的max_repetitions域指定一个值。 在其他操作中都为0。

该函数返回一个PDU句炳。

万事俱备了,就让我们的火车启航吧。用下面的函数 12。 SNMPAPI_STATUS SnmpSendMsg(

HSNMP_SESSION session, // handle to the WinSNMP session HSNMP_ENTITY srcEntity, // handle to the source entity HSNMP_ENTITY dstEntity, // handle to the target entity HSNMP_CONTEXT context, // handle to the context HSNMP_PDU PDU // handle to the PDU );

看看这些参数,是不是我们都已经创建过了,添上他们。

以上就是整个发送过程,我们再来理顺一下,1。加载SNMP,2。建立会话,3。设置传输模式,4。创建实体,5。设置重传模式,6。设置超时 时间,7。设置重传次数,8。创建上下文句炳,9。创建变量捆绑列表,10。追加绑定列表,11。创建PDU,12。发送消息。当然你如果只须获得一个数 据,那么第10步就不需要了。

接下来我们要接收消息,并处理他们。

1。接收消息,用函数SNMPAPI_STATUS SnmpRecvMsg(

HSNMP_SESSION session, // handle to the WinSNMP session LPHSNMP_ENTITY srcEntity, // handle to the source entity LPHSNMP_ENTITY dstEntity, // handle to the target entity LPHSNMP_CONTEXT context, // handle to the context

LPHSNMP_PDU PDU // handle to the PDU

);

声明一下,该函数的参数和SnmpSendMsg好像是一样的,不错,但参数的进出不一样,SnmpRecvMsg除第一个参数是我们创建过 的以外,其他参数都是输出参数,就是用来接收的参数,好像很爽的样子,因为只需自己设定一个参数,其他的声明一个变量,只管接收就行了。仔细想想,还挺对 应的呢!

2。提取数据报,用函数SNMPAPI_STATUS SnmpGetPduData( HSNMP_PDU PDU, // handle to the PDU smiLPINT PDU_type, // PDU_type field of the PDU smiLPINT32 request_id, // request_id field of the PDU smiLPINT error_status, // error_status field of the PDU smiLPINT error_index, // error_index field of the PDU

LPHSNMP_VBL varbindlist // handle to the variable bindings list

);

也很爽,只有第一个参数是需要你输入的,而这已经通过SnmpRecvMsg得到了,其他的参数都是需要接收的,看到什么了,对了, request_id,如果你才用异步接收的话,它可很重要的啊,可以帮你标识发送的消息。还有error_status和error_index,记得 吗,用在SNMP_PDU_GETBULK操作中,他们的意义是不同的,除此之外,他们用来接收SNMP端返回的错误消息,如果返回全都是0,那就是正确 返回了,如果不是,那你就的查一查他们所代表的意思了,一般的SNMP书上都会有介绍。

3。计算返回列表数目,用函数SNMPAPI_STATUS SnmpCountVbl(

HSNMP_VBL vbl // handle to the variable bindings list );

将你上一步得到的varbindlist代到里面去就行了,他的返回只是一个整型,使你所得到的变量绑定列表返回的变量数。

4。取得返回结果,用函数SNMPAPI_STATUS SnmpGetVb(

HSNMP_VBL vbl, // handle to the variable bindings list smiUINT32 index, // position of the variable binding entry // in the list

smiLPOID name, // pointer to the structure to receive the // variable name

smiLPVALUE value // pointer to the structure to receive the // associated value );

既然在上一步已经得到了结果数,用一个简单的for循环一次将结果取出吧。该函数有四个参数,第一个在第三步已得到,第二个就是你for循环 中的变量值,记住取得变量是从0开始的,后两个参数想想是不是与前面某个函数的参数有点相似。对了,前面我们把他们都置为空,现在SNMP代理将返回值添 了进去,我们可以坐享其成了,定义两个变量,接收就行了。提醒一下,对ip地址的接收会有点不同,因为返回值将其封装为一个指针数组了,你需要一个一个的 取出来!

看上去工作是做完了,别急,还有一个很重要的环节,难道你没想过创建了这么多东西就不会占用资源吗?当然要占用,而且你不释放他它不会自动释 放,前面我们总共介绍了5个重要的句炳,只有会话句炳是在发送和接收消息时都用到的,所以在发送和接收消息以后,你要将其他四个句炳释放掉,那么会话句炳 何时释放呢?对了,应该在你应用程序退出的过程中释放掉,进而你会想到创建会话句炳的位置了吧,那就是在构造函数里。以上这些释放句炳资源的函数SNMP API都有提供,如SnmpFreeEntity,SnmpFreeContext,SnmpFreeVbl,SnmpFreePdu, SnmpClose,他们的参数只有一个,就是你要是放得句炳。最后你要清理整个现场,用函数SnmpCleanup()解决他们吧。

ok了,一且到此完结,大概步骤就这些了,呵呵,你也许对SNMP_PDU_SET和SNMP_PDU_TRAP有些不解,前者你可以在10。追加绑定列表中

改变变量值,当然要遵循smiVALUE的结构,将类型和值都添上,填好需要改变的对象标志符,11。创建PDU中将类型设为SNMP_PDU_SET就行了。

traps有些麻烦,因为它的数据报格式有点特别,本人对他也是一知半解,马马虎虎能够实现,待以后整理思路后在与大家交流!

对于想进行SNMP编程的人员,在下以菜鸟的身份给你们提个醒,SNMP编成的过程很死,但精心的设计会使你的程序更加的健壮、高效和容易扩 展,我强烈的建议你们看看hp的snmp++,他的源代码很有层次,极易扩展,我的网名本来是zqq_tt但不知被谁申请过了,于是我在csdn里申请的 名字是zqqq1,本人的qq号是81126700。非常愿意与大家交流! 由于自己的时间比较充裕,很想做一点兼职,能给机会者感激不尽!

简单SNMP管理程序的VC++代码实例实现

来源:blog 作者:mmpire 2005-12-19 出处:pcdog.com .net acl google http ilm 下一页 1 2

友情提醒:深入浅出Visual C++串口编程

SNMP(Simple Network Management Protocol)是基于TCP/IP的网络管理协议,关于其工作原理网上很多,百度一下或者看看MSDN,今天在这里记一下实现的步骤,本人工作环境是Windows XP professional SP2 + Microsoft Visual Studio .net 2003,不保证其他平台与本人的步骤一致。

一、安装SNMP服务

先查看系统中是否已经安装有SNMP服务,开始->运行->cmd->回车

输入命令“net start snmp”:

C:\\Documents and Settings\\mmpire>net start snmp