📄 snmp_api.c
字号:
if (session->engineBoots || session->engineTime) { set_enginetime(session->securityEngineID, session->securityEngineIDLen, session->engineBoots, session->engineTime, TRUE); } if (create_user_from_session(slp->session) != SNMPERR_SUCCESS) { in_session->s_snmp_errno = SNMPERR_UNKNOWN_USER_NAME; /* XX?? */ DEBUGMSGTL(("snmp_api", "snmp_sess_open(): failed(2) to create a new user from session\n")); return 0; } } return 1;}/*******************************************************************-o-****** * snmp_sess_open * * Parameters: * *in_session * * Returns: * Pointer to a session in the session list -OR- FIX -- right? * NULL on failure. * * The "spin-free" version of snmp_open. */static void *_sess_open(netsnmp_session * in_session){ struct session_list *slp; netsnmp_session *session; in_session->s_snmp_errno = 0; in_session->s_errno = 0; _init_snmp(); if ((slp = snmp_sess_copy(in_session)) == NULL) { return (NULL); } session = slp->session; slp->transport = NULL; if (session->flags & SNMP_FLAGS_STREAM_SOCKET) { slp->transport = netsnmp_tdomain_transport(session->peername, session->local_port, "tcp"); } else { slp->transport = netsnmp_tdomain_transport(session->peername, session->local_port, "udp"); } if (slp->transport == NULL) { DEBUGMSGTL(("_sess_open", "couldn't interpret peername\n")); in_session->s_snmp_errno = SNMPERR_BAD_ADDRESS; in_session->s_errno = errno; snmp_set_detail(session->peername); snmp_sess_close(slp); return NULL; } session->rcvMsgMaxSize = slp->transport->msgMaxSize; if (!snmpv3_engineID_probe(slp, in_session)) { snmp_sess_close(slp); return 0; } return (void *) slp;} /* end snmp_sess_open() *//* * EXPERIMENTAL API EXTENSIONS ------------------------------------------ * * snmp_sess_add_ex, snmp_sess_add, snmp_add * * Analogous to snmp_open family of functions, but taking a netsnmp_transport * pointer as an extra argument. Unlike snmp_open et al. it doesn't attempt * to interpret the in_session->peername as a transport endpoint specifier, * but instead uses the supplied transport. JBPN * */netsnmp_session *snmp_add(netsnmp_session * in_session, netsnmp_transport *transport, int (*fpre_parse) (netsnmp_session *, netsnmp_transport *, void *, int), int (*fpost_parse) (netsnmp_session *, netsnmp_pdu *, int)){ struct session_list *slp; slp = (struct session_list *) snmp_sess_add_ex(in_session, transport, fpre_parse, NULL, fpost_parse, NULL, NULL, NULL, NULL); if (slp == NULL) { return NULL; } snmp_res_lock(MT_LIBRARY_ID, MT_LIB_SESSION); slp->next = Sessions; Sessions = slp; snmp_res_unlock(MT_LIBRARY_ID, MT_LIB_SESSION); return (slp->session);}netsnmp_session *snmp_add_full(netsnmp_session * in_session, netsnmp_transport *transport, int (*fpre_parse) (netsnmp_session *, netsnmp_transport *, void *, int), int (*fparse) (netsnmp_session *, netsnmp_pdu *, u_char *, size_t), int (*fpost_parse) (netsnmp_session *, netsnmp_pdu *, int), int (*fbuild) (netsnmp_session *, netsnmp_pdu *, u_char *, size_t *), int (*frbuild) (netsnmp_session *, netsnmp_pdu *, u_char **, size_t *, size_t *), int (*fcheck) (u_char *, size_t), netsnmp_pdu *(*fcreate_pdu) (netsnmp_transport *, void *, size_t)){ struct session_list *slp; slp = (struct session_list *) snmp_sess_add_ex(in_session, transport, fpre_parse, fparse, fpost_parse, fbuild, frbuild, fcheck, fcreate_pdu); if (slp == NULL) { return NULL; } snmp_res_lock(MT_LIBRARY_ID, MT_LIB_SESSION); slp->next = Sessions; Sessions = slp; snmp_res_unlock(MT_LIBRARY_ID, MT_LIB_SESSION); return (slp->session);}void *snmp_sess_add_ex(netsnmp_session * in_session, netsnmp_transport *transport, int (*fpre_parse) (netsnmp_session *, netsnmp_transport *, void *, int), int (*fparse) (netsnmp_session *, netsnmp_pdu *, u_char *, size_t), int (*fpost_parse) (netsnmp_session *, netsnmp_pdu *, int), int (*fbuild) (netsnmp_session *, netsnmp_pdu *, u_char *, size_t *), int (*frbuild) (netsnmp_session *, netsnmp_pdu *, u_char **, size_t *, size_t *), int (*fcheck) (u_char *, size_t), netsnmp_pdu *(*fcreate_pdu) (netsnmp_transport *, void *, size_t)){ struct session_list *slp; _init_snmp(); if (in_session == NULL || transport == NULL) { return NULL; } DEBUGMSGTL(("snmp_sess_add", "fd %d\n", transport->sock)); if ((slp = snmp_sess_copy(in_session)) == NULL) { return (NULL); } slp->transport = transport; slp->internal->hook_pre = fpre_parse; slp->internal->hook_parse = fparse; slp->internal->hook_post = fpost_parse; slp->internal->hook_build = fbuild; slp->internal->hook_realloc_build = frbuild; slp->internal->check_packet = fcheck; slp->internal->hook_create_pdu = fcreate_pdu; slp->session->rcvMsgMaxSize = transport->msgMaxSize; if (slp->session->version == SNMP_VERSION_3) { DEBUGMSGTL(("snmp_sess_add", "adding v3 session -- engineID probe now\n")); if (!snmpv3_engineID_probe(slp, in_session)) { DEBUGMSGTL(("snmp_sess_add", "engine ID probe failed\n")); snmp_sess_close(slp); slp = NULL; } } return (void *) slp;} /* end snmp_sess_add_ex() */void *snmp_sess_add(netsnmp_session * in_session, netsnmp_transport *transport, int (*fpre_parse) (netsnmp_session *, netsnmp_transport *, void *, int), int (*fpost_parse) (netsnmp_session *, netsnmp_pdu *, int)){ return snmp_sess_add_ex(in_session, transport, fpre_parse, NULL, fpost_parse, NULL, NULL, NULL, NULL);}void *snmp_sess_open(netsnmp_session * pss){ void *pvoid; pvoid = _sess_open(pss); if (!pvoid) { SET_SNMP_ERROR(pss->s_snmp_errno); } return pvoid;}/* * create_user_from_session(netsnmp_session *session): * * creates a user in the usm table from the information in a session. * If the user already exists, it is updated with the current * information from the session * * Parameters: * session -- IN: pointer to the session to use when creating the user. * * Returns: * SNMPERR_SUCCESS * SNMPERR_GENERR */intcreate_user_from_session(netsnmp_session * session){ struct usmUser *user; int user_just_created = 0; /* * now that we have the engineID, create an entry in the USM list * for this user using the information in the session */ user = usm_get_user_from_list(session->securityEngineID, session->securityEngineIDLen, session->securityName, usm_get_userList(), 0); if (user == NULL) { DEBUGMSGTL(("snmp_api", "Building user %s...\n", session->securityName)); /* * user doesn't exist so we create and add it */ user = (struct usmUser *) calloc(1, sizeof(struct usmUser)); if (user == NULL) return SNMPERR_GENERR; /* * copy in the securityName */ if (session->securityName) { user->name = strdup(session->securityName); user->secName = strdup(session->securityName); if (user->name == NULL || user->secName == NULL) { usm_free_user(user); return SNMPERR_GENERR; } } /* * copy in the engineID */ if (memdup(&user->engineID, session->securityEngineID, session->securityEngineIDLen) != SNMPERR_SUCCESS) { usm_free_user(user); return SNMPERR_GENERR; } user->engineIDLen = session->securityEngineIDLen; user_just_created = 1; } /* * copy the auth protocol */ if (session->securityAuthProto != NULL) { SNMP_FREE(user->authProtocol); user->authProtocol = snmp_duplicate_objid(session->securityAuthProto, session->securityAuthProtoLen); if (user->authProtocol == NULL) { usm_free_user(user); return SNMPERR_GENERR; } user->authProtocolLen = session->securityAuthProtoLen; } /* * copy the priv protocol */ if (session->securityPrivProto != NULL) { SNMP_FREE(user->privProtocol); user->privProtocol = snmp_duplicate_objid(session->securityPrivProto, session->securityPrivProtoLen); if (user->privProtocol == NULL) { usm_free_user(user); return SNMPERR_GENERR; } user->privProtocolLen = session->securityPrivProtoLen; } /* * copy in the authentication Key, and convert to the localized version */ if (session->securityAuthKey != NULL && session->securityAuthKeyLen != 0) { SNMP_FREE(user->authKey); user->authKey = (u_char *) calloc(1, USM_LENGTH_KU_HASHBLOCK); if (user->authKey == NULL) { usm_free_user(user); return SNMPERR_GENERR; } user->authKeyLen = USM_LENGTH_KU_HASHBLOCK; if (generate_kul(user->authProtocol, user->authProtocolLen, session->securityEngineID, session->securityEngineIDLen, session->securityAuthKey, session->securityAuthKeyLen, user->authKey, &user->authKeyLen) != SNMPERR_SUCCESS) { usm_free_user(user); return SNMPERR_GENERR; } } /* * copy in the privacy Key, and convert to the localized version */ if (session->securityPrivKey != NULL && session->securityPrivKeyLen != 0) { SNMP_FREE(user->privKey); user->privKey = (u_char *) calloc(1, USM_LENGTH_KU_HASHBLOCK); if (user->privKey == NULL) { usm_free_user(user); return SNMPERR_GENERR; } user->privKeyLen = USM_LENGTH_KU_HASHBLOCK; if (generate_kul(user->authProtocol, user->authProtocolLen, session->securityEngineID, session->securityEngineIDLen, session->securityPrivKey, session->securityPrivKeyLen, user->privKey, &user->privKeyLen) != SNMPERR_SUCCESS) { usm_free_user(user); return SNMPERR_GENERR; } } user->userStatus = RS_ACTIVE; user->userStorageType = ST_READONLY; if (user_just_created) { /* * add the user into the database */ usm_add_user(user); } return SNMPERR_SUCCESS;} /* end create_user_from_session() *//* * Do a "deep free()" of a netsnmp_session. * * CAUTION: SHOULD ONLY BE USED FROM snmp_sess_close() OR SIMILAR. * (hence it is static) */static voidsnmp_free_session(netsnmp_session * s){ if (s) { SNMP_FREE(s->peername); SNMP_FREE(s->community); SNMP_FREE(s->contextEngineID); SNMP_FREE(s->contextName); SNMP_FREE(s->securityEngineID); SNMP_FREE(s->securityName); SNMP_FREE(s->securityAuthProto); SNMP_FREE(s->securityPrivProto); free((char *) s); }}/* * Close the input session. Frees all data allocated for the session,
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -