SNMP对话的结构:
struct snmp_session {
int Version; /* SNMP Version for this session */
u_char *community; /* community for outgoing requests. */
int community_len; /* Length of community name. */
int retries; /* Number of retries before timeout. */
int timeout; /* Number of uS until first timeout */
char *peername; /* Domain name or dotted IP address of default peer */
u_short remote_port; /* UDP port number of peer. */
u_short local_port; /* My UDP port number */
u_char *(*authenticator)();
/* Function to interpret incoming data */
int (*callback)(int, struct snmp_session *, int, struct snmp_pdu *, void *);
/* Pointer to data that the callback function may consider important */
void *callback_magic;
struct synch_state * snmp_synch_state;
int s_errno; /* copy of system errno */
int s_snmp_errno; /* copy of library errno */
};
/* fully decleartion of snmp_session. from snmp_api.h. all right, types.h actually*/
struct snmp_session {
/*
* Protocol-version independent fields
*/
/** snmp version */
long version;
/** Number of retries before timeout. */
int retries;
/** Number of uS until first timeout, then exponential backoff */
long timeout;
u_long flags;
struct snmp_session *subsession;
struct snmp_session *next;
/** name or address of default peer (may include transport specifier and/or port number) */
char *peername;
/** UDP port number of peer. (NO LONGER USED - USE peername INSTEAD) */
u_short remote_port;
/** My Domain name or dotted IP address, 0 for default */
char *localname;
/** My UDP port number, 0 for default, picked randomly */
u_short local_port;
/**
* Authentication function or NULL if null authentication is used
*/
u_char *(*authenticator) (u_char *, size_t *, u_char *, size_t);
/** Function to interpret incoming data */
netsnmp_callback callback;
/**
* Pointer to data that the callback function may consider important
*/
void *callback_magic;
/** copy of system errno */
int s_errno;
/** copy of library errno */
int s_snmp_errno;
/** Session id - AgentX only */
long sessid;
/*
* SNMPv1 & SNMPv2c fields
*/
/** community for outgoing requests. */
u_char *community;
/** Length of community name. */
size_t community_len;
/** Largest message to try to receive. */
size_t rcvMsgMaxSize;
/** Largest message to try to send. */
size_t sndMsgMaxSize;
/*
* SNMPv3 fields
*/
/** are we the authoritative engine? */
u_char isAuthoritative;
/** authoritative snmpEngineID */
u_char *contextEngineID;
/** Length of contextEngineID */
size_t contextEngineIDLen;
/** initial engineBoots for remote engine */
u_int engineBoots;
/** initial engineTime for remote engine */
u_int engineTime;
/** authoritative contextName */
char *contextName;
/** Length of contextName */
size_t contextNameLen;
/** authoritative snmpEngineID */
u_char *securityEngineID;
/** Length of contextEngineID */
size_t securityEngineIDLen;
/** on behalf of this principal */
char *securityName;
/** Length of securityName. */
size_t securityNameLen;
/** auth protocol oid */
oid *securityAuthProto;
/** Length of auth protocol oid */
size_t securityAuthProtoLen;
/** Ku for auth protocol XXX */
u_char securityAuthKey[USM_AUTH_KU_LEN];
/** Length of Ku for auth protocol */
size_t securityAuthKeyLen;
/** Kul for auth protocol */
u_char *securityAuthLocalKey;
/** Length of Kul for auth protocol XXX */
size_t securityAuthLocalKeyLen;
/** priv protocol oid */
oid *securityPrivProto;
/** Length of priv protocol oid */
size_t securityPrivProtoLen;
/** Ku for privacy protocol XXX */
u_char securityPrivKey[USM_PRIV_KU_LEN];
/** Length of Ku for priv protocol */
size_t securityPrivKeyLen;
/** Kul for priv protocol */
u_char *securityPrivLocalKey;
/** Length of Kul for priv protocol XXX */
size_t securityPrivLocalKeyLen;
/** snmp security model, v1, v2c, usm */
int securityModel;
/** noAuthNoPriv, authNoPriv, authPriv */
int securityLevel;
/** target param name */
char *paramName;
/**
* security module specific
*/
void *securityInfo;
/**
* transport specific configuration
*/
struct netsnmp_container_s *transport_configuration;
/**
* use as you want data
*
* used by 'SNMP_FLAGS_RESP_CALLBACK' handling in the agent
* XXX: or should we add a new field into this structure?
*/
void *myvoid;
};
/*end*/
SNMP PDU结构
struct snmp_pdu {
int command; /* Type of this PDU */
ipaddr address; /* Address of peer */
int reqid; /* Integer32: Request id */
int errstat; /* INTEGER: Error status */
int errindex; /* INTEGER: Error index */
struct variable_list *variables; /* Variable Bindings */
/* SNMPv2 Bulk Request */
int non_repeaters; /* INTEGER: */
int max_repetitions; /* INTEGER: */
/* Trap information */
oid *enterprise; /* System OID */
int enterprise_length;
ipaddr agent_addr; /* address of object generating trap */
int trap_type; /* generic trap type */
int specific_type; /* specific type */
u_int time; /* Uptime */
};
变量绑定表结构
struct variable_list
{
struct variable_list*next_variable; /* NULL for last variable */
oid *name; /* Object identifier of variable */
int name_length; /* number of subid's in name */
u_char type; /* ASN type of variable */
union
{ /* value of variable */
int *integer;
u_char *string;
oid *objid;
} val;
int val_len;
};
SNMP网管协议简单剖析
过程解释:
InitialMIB:根据环境变量、注册表确定MIB文件路径,对此MIB文件进行语法分析,并把MIB中的所有变量读入一二叉树中。
WinsockStartup:调用WSAStartup()初始化Socket。
Init _Snmp_Session:初始化SNMP对话Snmp_Session结构。
Snmp_Open :建立 SNMP 对话。包括建立 UDP Socket 连接,本地端口绑定等
Snmp_PDU_Create:根据传入的参数生成相应的PDU,但没有绑定变量。
Read_ObjId:根据输入的变量名,查找相应的Oid。
Snmp_Add_Null_Var:把变量Oid和值(对于Set操作)绑定到PDU上。
Snmp_Synch_Response:把PDU组装成SNMP报文,发送SNMP报文,等待接收Response报文,并对接收的报文解释以进行出错判断处理。
Receive_Response_PDU:从Response报文中取出ResponsePDU。
GetResult:从ResponsePDU中取出所需的数据,传递给界面。
Snmp_Free_PDU:释放ResponsePDU。
Snmp_Close:释放Snmp_Session等资源,关闭Socket连接。