加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 大数据 > 正文

NET-SNMP开发实践

发布时间:2020-12-16 00:31:42 所属栏目:大数据 来源:网络整理
导读:? 【摘 要】最近项目中需要用SNMP实现对APACHE http server的监控,由于项目后台开发使用C语言,故选择使用NET-SNMP包来实现对SNMP的开发与实现。对于NET-SNMP本人才刚入门,总会碰到N多的问题,网上对于NET-SNMP的资料就更少了,特别是缺少NET-SNMP的所涉及
?
【摘 要】最近项目中需要用SNMP实现对APACHE http server的监控,由于项目后台开发使用C语言,故选择使用NET-SNMP包来实现对SNMP的开发与实现。对于NET-SNMP本人才刚入门,总会碰到N多的问题,网上对于NET-SNMP的资料就更少了,特别是缺少NET-SNMP的所涉及的整个开发过程。所以就有了一个冲动就是把学习中的过程写下来。本文将从NET-SNMP的安装配置、SNMP get、set、trap等主要三个用例的实现来描述使用NET-SNMP开发的全过程。
?
【关键字】SNMP、MIB、ASN1、OID
?
【系统环境】由于移植及运行环境等原因,本文的程序代码及命令的使用环境及版本如下:
OS: SunOS solaris 5.9 Generic_112234-12 i86pc i386 i86pc
Perl: This is perl,v5.6.1 built for i86pc-solaris-64int
Net-snmp: Version:? 5.4.1
GCC:Reading specs from /usr/local/lib/gcc/i386-pc-solaris2.9/3.4.1/specs gcc version 3.4.1
?
1 NET-SNMP基本介绍
?
为了节约篇幅,关于SNMP(简单网络管理协议)的相关内容这里就不用介绍了。
?
目前关于SNMP的开发包主要有NET-SNMP(for C)、SNMP++(for C++)、SNMP4J(snmp++的JAVA版本)、SNMPJ(NET-SNMP的JAVA版本)。NET-SNMP的早期版本(5.X以前)叫ucd-snmp,源自于卡耐基·梅隆大学的SNMP软件包CMU snmp 2.1.2.1,由加州大学Davis分校(University of California at Davis)开发与维护,后来由SourceForge ( [url]www.sourceforge.net[/url])开发维护管理,并更名为net-snmp(5.X及以后版本),其最新版本为5.4.1。
?
NET-SNMP的主要内容包括:
· 完整的API用于SNMP(支持V1、V2、V3版本)应用开发(包括c、perl、Python等的API)
· 一个可扩展的SNMP代理程序(snmpd);开发员可以扩展自己的代理程序
· 一套工具命令集(snmpget、snmpset、snmptrap、snmpwalk、snmp等)
· 一个trap接收进程,用于接收和显示trap。并可以将trap记录到日志文件里
· 一个图形化的MIB浏览工具(tkmib:基于Tk/Perl的)
?
?
2 NET-SNMP的安装、配置
?
2.1 NET-SNMP的安装
?
NET-SNMP包目前可以移植的版本包括各种UNIX(基于SYSTEM V内核及基于BSD内核)、LINUX、WINX版本。
?
目前NET-SNMP包的安装主要有程序编译安装与二进制文件安装两种方式,源程序安装可以从NET-SNMP的官网下载然后按照常规的configure,make,make install三个步骤就可成功编译安装。其相关的二进制安装可以到其官网及各OS厂商的网站下载。
?
FOR SOLARIS 9的安装请到SUN的官网下载:
gcc-3.4.1-sol9-intel-local.gz、libgcc-3.4.1-sol9-intel-local.gz、
netsnmp-5.4.1-sol9-x86-local.gz、openssl-0.9.8h-sol9-x86-local.gz。
?
其遵循的安装过程为:
·gzip –d xxx.gz (解压缩)
·tar –xvf *.tar (如果有打包文件,请解包)
·pkgadd –d ./xxxx(安装)
安装完毕后,请在/etc/profile中设置好BIN的PATH路径。
?
2.2 NET-SNMP的配置
?
2.2.1 snmpconf配置
?
我们使用/usr/local/bin/ snmpconf,其由perl编写,所以在运行前,请确认您的PERL安装路径,并更改snmpconf的第1行PERL脚本BIN路径。Snmpconf脚本主要用来配置snmpd.conf、snmptrapd.conf。snmpconf运行后是一个可以交互的配置设置过程,主要设置:
·System information setup ——包括位置、联系人信息等。
·Access control setup —— community name、
·Agent Operating Mode ——AGENT IP、PORT等。
?
设置完毕后,用户可以自己修改snmpd.conf文件中的参数信息。
?
2.2.2 启动snmpd
?
使用NET-SNMP的snmpd可扩展的代理进程替换OS的snmpd。
?
为了方便系统启动时,自动运行net-snmp代理程序,生成/etc/rc3.d/ S78net-snmp shell文件(solaris的多用户运行等级为3):S78net-snmp 此SHELL脚本请参考 S78net-snmp。
屏蔽原来OS的SNMPD的配置文件/etc/rc3.d/ S76snmpdx及S77dmi文件。
启动NET-SNMP的代理程序:./ S78net-snmp start。
停止NET-SNMP的代理程序:./ S78net-snmp stop。
?
2.2.3 测试NET-SNMP snmpd
?
# snmpget -v 1 -c public localhost sysDescr.0
SNMPv2-MIB::sysDescr.0 = STRING: SunOS solaris 5.9 Generic_112234-12 i86pc
# snmpget -v 1 -c public localhost sysLocation.0
SNMPv2-MIB::sysLocation.0 = STRING: wangzuxiang
至此NET-SNMP的安装、配置完成。
?
3 NET-SNMP的开发
?
3.1 SNMP GET开发
?
获取MIB中OID对象值(snmpget操作)的开发非常简单,其大致的过程为:
· 初始化一个SNMP会话;
· 定义会话属性;
· 增加一个MIB到当前的MIB目录树中(可选项);
· 创建一个PDU包 (Primary Data Unit) ;
· 设置OID(或多个)到PDU中;
· 发送请求并等待响应;
· 根据响应值处理业务数据;
· 释放PDU资源;
· 关闭会话。
?
mydemo.c范例为获取MIB表sysDescr对象(该对象表示设备的描述信息)、sysName、sysLocation等对象值,也可以使用snmptranslate -On将其名称转换为OID。例如:
% snmptranslate .1.3.6.1.2.1.1.3.0(转换OID名称)
???????? SNMPv2-MIB::sysUpTime.0
% snmptranslate -On SNMPv2-MIB::sysUpTime.0(转换OID)
???????? .1.3.6.1.2.1.1.3.0
??? % snmptranslate -Tp -IR system(显示MIB树结构)
+--system(1)
????? |
????? +-- -R-- String??? sysDescr(1)
????? |??????? Textual Convention: DisplayString
????? +-- -R-- ObjID???? sysObjectID(2)
????? +-- -R-- TimeTicks sysUpTime(3)
????? +-- -RW- String??? sysContact(4)
编译mydemo.c:
Gcc –o mydemo mydemo.c -lsnmp
运行mydemo:
./mydemo
SNMPv2-MIB::sysDescr.0 = STRING: SunOS solaris 5.9 Generic_112234-12 i86pc
SNMPv2-MIB::sysName.0 = STRING: solaris
SNMPv2-MIB::sysLocation.0 = STRING: wangzuxiang
值 #1 是一个字符串: SunOS solaris 5.9 Generic_112234-12 i86pc
值 #2 是一个字符串: solaris
值 #3 是一个字符串: wangzuxiang
?
注意:在实际的开发过程中,如果轮询多个agent上的MIB OID对象时,可以使用异步的多路复用技术来实现。类似代码如下:
while (active_hosts) {/*轮询某个AGENT*/
??? int fds = 0,block = 1;
??? fd_set fdset;
??? struct timeval timeout;
??? FD_ZERO(&fdset);
??? snmp_select_info(&fds,&fdset,&timeout,&block);
??? fds = select(fds,NULL,block ? NULL : &timeout);
??? if (fds < 0) {
??????? perror("select failed");
??????? exit(1);
??? }
??? if (fds)
??????? snmp_read(&fdset);
??? else??????? snmp_timeout();
? }
?
3.2 SNMP agent开发
?
扩展Agent的开发,NET-SNMP提供了三种方式:
· 动态联编(此方法需要NET-SNMP的源程序)。
· 动态加载库。
· 子代理的方式。
?
接下来将重点描述动态加载库的方式,其他的方式我目前还没有去实验,大家可以参考其官网上的例子进行。下面的例子将在AGENT中实现,GET/SET的方法接口。
?
3.2.1 准备MIB文件
?
为了方便,我们使用的MIB还是官网上的 NET-SNMP-TUTORIAL-MIB.txt。
?
将NET-SNMP-TUTORIAL-MIB.txt拷贝到/usr/local/share/snmp/mibs。
修改/usr/local/share/snmp/snmp.conf,在最后一行增加:mibs +NET-SNMP-TUTORIAL-MIB
或者在SHELL环境变量中定义:export MIBS=+NET-SNMP-TUTORIAL-MIB。
否则在运行程序或做SNMP操作时,会出现MIB无法找到等错误现象。
?
3.2.2 编译动态库
?
NET-SNMP的usr/local/bin/mib2c工具能够将使用MIB2C工具程序把MIB库模块文件转换成C源代码。假设MIB库模块为modulename,执行mib2c modulename此时,MIB2C会在当前目录下生成两个C源文件:modulename.h 和modulename.c,这两个文件是根据所设计的MIB库模块转换而成的,也是需要加入到NET-SNMP软件包实现SNMP Agent功能扩展的源代码。注意,MIB2C为PERL脚本编写,为了让PERL支持SNMP,您需要下载PERL CPAN FOR SNMP的包。
?
Mib2c需要为-c操作指定一个配置文件,此配置文件感觉为预生成的模板文件,如果要写scalars则用mib2c.scalar.conf文件,如果要写Table则用mib2c.mfd.conf,如果带有TRAP则用mib2c.notify.conf。
?
%mib2c -c mib2c.scalar.conf ?nstAgentPluginObject
?
MIB2C将生成的文件为 nstAgentPluginObject.c和 nstAgentPluginObject.h文件。
?
在nstAgentPluginObject.c文件中为实现SET/GET操作,可以在switch (reqinfo->mode)下的MODE_SET_COMMIT(SET操作)与MODE_GET(GET操作)实现。
?
编译成.so文件:
gcc –I. -c -o nstAgentPluginObject.o nstAgentPluginObject.c
gcc -g -fPIC -shared -o nstAgentPluginObject.so nstAgentPluginObject.o(编译成SO库)
?
3.2.3 加载动态库
?
Net-snmp的snmpd加载动态库以实现agent的扩展有2种加载方式:
?
(1)不停止SNMPD进程的情况下加载。
UCD-DLMOD-MIB.txt定义了MIB条目的模块名,动态库路径及状态。使用此方法可以在不重起代理的情况下配置各动态模块加载与卸载。
其详细的MIB定义:cat /usr/local/share/snmp/mibs/UCD*DLMOD*.txt。
?
· 查看哪些.so被加载
#snmpget -v 1 -c public localhost UCD-DLMOD-MIB::dlmodStatus.1
?
· 尝试获取某个MIB的OID值
#Snmpget-v2c -c public localhost NET-SNMP-TUTORIAL-MIB::nstAgentPluginObject.0
NET-SNMP-TUTORIAL-MIB::nstAgentPluginObject.0 = No Such Object available on this agent at this OID(其表示没有找到)
?
· UCD-DLMOD-MIB表中创建一个模块实例
#snmpset -v 1 -c private localhost UCD-DLMOD-MIB::dlmodStatus.1 i create
?????? UCD-DLMOD-MIB::dlmodStatus.1 = INTEGER: create(6)
?
· 获取dlmodStatus值
#snmpget -v 1 -c public localhost UCD-DLMOD-MIB::dlmodStatus.1
UCD-DLMOD-MIB::dlmodStatus.1 = INTEGER: unloaded(2)
说明模块实例已经存在,但没有被加载
?
· 设置需装载模块的名称及路径
#snmpset -v 1 -c private localhost UCD-DLMOD-MIB::dlmodName.1 s "nstAgentPluginObject" UCD-DLMOD-MIB::dlmodPath.1 s "/oracle/agent/plugin/nstAgentPluginObject.so"
?????? UCD-DLMOD-MIB::dlmodName.1 = STRING: nstAgentPluginObject
UCD-DLMOD-MIB::dlmodPath.1 = STRING: /oracle/agent/plugin/nstAgentPluginObject.so
?
· 装载模块
# snmpset -v 1 -c private localhost UCD-DLMOD-MIB::dlmodStatus.1 i load
UCD-DLMOD-MIB::dlmodStatus.1 = INTEGER: load(4)
?
· 确认模块被加载
#snmpget -v 1 -c public localhost UCD-DLMOD-MIB::dlmodStatus.1
UCD-DLMOD-MIB::dlmodStatus.1 = INTEGER: loaded(1)
?
· 测试新加载的.so是否成功
#snmpget -v 1 -c public localhost NET-SNMP-TUTORIAL-MIB::nstAgentPluginObject.0
?????? NET-SNMP-TUTORIAL-MIB::nstAgentPluginObject.0 = INTEGER: 3
?
(2)修改配置文件snmpd.conf加载
在/usr/local/share/snmp/snmpd.conf文件中增加一行:
dlmod nstAgentPluginObject /oracle/agent/plugin/nstAgentPluginObject.so
?
3.2.4 测试代理
?
$snmpget -v 1 -c public localhost NET-SNMP-TUTORIAL-MIB::nstAgentPluginObject.0
NET-SNMP-TUTORIAL-MIB::nstAgentPluginObject.0 = INTEGER: 123456
$snmpset -v 1 -c private localhost NET-SNMP-TUTORIAL-MIB::nstAgentPluginObject.0 i 1000
NET-SNMP-TUTORIAL-MIB::nstAgentPluginObject.0 = INTEGER: 1000
调用设置后,你会发现在/oracle/agent/plugin/test.log中的内容增加一行: 1000 mode=0x3
?
3.3 Trap的开发
?
3.3.1 准备MIB文件
?
在SNMPV1版本中MIB的TRAP定义与V2版本中不完全一样,V2版本开始叫notification。我们使用比较简单的V1版本来定义含有TRAP功能的MIB文件 UCD-TRAP-TEST-MIB.txt。
?
在/usr/local/share/snmp/snmp.conf中增加一行:mibs +UCD-TRAP-TEST-MIB
将UCD-TRAP-TEST-MIB.txt拷贝到/usr/local/share/snmp/mibs目录中。
?
3.3.2 Send trap
?
Trap的发送有几种实现情况,用户可以用snmp_add_var以及snmp_send等API编写应用来触发TRAP事件,也可以在MIB2C中mib2c.notify.conf配置模板在代理中实现TRAP的发送。发送TRAP的代码可以详细参考 mytrap.c。
编译:Gcc –o mytrap mytrap.c –lsnmp
执行:./mytrap
?
3.3.3 启动SNMPTRAPD进程
?
· 修改snmptrapd.conf文件:
修改或产生/usr/loc1的snmptrapd进程默认下不接收任何TRAP,所以需要配置此文件,内容如下:al/share/snmp/snmptrapd.conf文件(在NET-SNMP5.4.1中好象没有自动生成此文件。)
authCommunity log,execute,net public
?
· 启动trapd进程
snmptrapd -P 或者snmptrapd? -f -Le
此命令将snmptrapd不做为后台进程运行,并将接收到的TRAP信息,以标准输出设备输出。
?
· 接收TRAP
2008-06-27 15:18:53 localhost [UDP: [127.0.0.1]:32787]:
DISMAN-EVENT-MIB::sysUpTimeInstance = Timeticks: (1052691) 2:55:26.91?? SNMPv2-M
IB::sysLocation.0 = STRING: 我在家。。。??????? UCD-TRAP-TEST-MIB::demotraps# =
INTEGER: 1230?? SNMPv2-MIB::snmpTrapOID.0 = OID: ccitt.1
?
3.4 程序清单
?
本文中使用的文件清单如下:
?

?
3.5 结束语
?
接触NET-SNMP时间较少,所以还有很多内容需要去发现与了解,不对之处,欢迎大家多多指正,不胜感激。
?
在本文中,您已经了解了使用 Net-SNMP的大致过程。本文介绍了如下几个方面:
(1)NET-SNMP的安装与配置。描述了NET-SNMP的安装以及配置情况。
(2)NET-SNMP的get、set、trap的操作。用代码实践了使用NET-SNMP API的操作全过程。
(3)使用NET-SNMP如何编写自己的代理(agent),本文详细介绍了使用动态库开发代理的方法,有机会将介绍其他两种方法。
?
SNMP协议本身是非常复杂的,使用NET-SNMP或其他SNMP的开发包,将使您忽略协议本身的细节,专注应用开发。

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读