mp_v3.cpp

来自「JdonFramework need above jdk 1.4.0 This」· C++ 代码 · 共 1,081 行 · 第 1/2 页

CPP
1,081
字号
	LOG_BEGIN(INFO_LOG | 10);	LOG("v3MP::Cache: Moving entry (from) (to)");	LOG(entries);	LOG(i);	LOG_END;      }      return;    }  LOG_BEGIN(INFO_LOG | 8);  LOG("v3MP::Cache: Entry to delete not found (req id) (msg id) (type)");  LOG(req_id);  LOG(msg_id);  LOG(local_request ? "local" : "remote");  LOG_END;  return;}// Search the cache for a message id, return it and remove it from the cacheint v3MP::Cache::get_entry(int searchedID, bool local_request,                           struct Cache::Entry_T *res){  if ((!table) || (!res)) return SNMPv3_MP_ERROR;  BEGIN_REENTRANT_CODE_BLOCK;  for (int i=0; i < entries; i++)    if ((table[i].msg_id == searchedID) &&        (table[i].local_request == local_request))    {      res->msg_id            = table[i].msg_id;      res->req_id            = table[i].req_id;      res->local_request     = table[i].local_request;      res->sec_engine_id     = table[i].sec_engine_id;      res->sec_model         = table[i].sec_model;      res->sec_name          = table[i].sec_name;      res->sec_level         = table[i].sec_level;      res->context_engine_id = table[i].context_engine_id;      res->context_name      = table[i].context_name;      res->sec_state_ref     = table[i].sec_state_ref;      res->error_code        = table[i].error_code;      LOG_BEGIN(INFO_LOG | 8);      LOG("v3MP::Cache: Found entry (n) (msg id) (type)");      LOG(i);      LOG(searchedID);      LOG(local_request ? "local" : "remote");      LOG_END;      entries--;      if (entries > i)      {        table[i] = table[entries];	LOG_BEGIN(INFO_LOG | 10);	LOG("v3MP::Cache: Moving entry (from) (to)");	LOG(entries);	LOG(i);	LOG_END;      }      return SNMPv3_MP_OK;    }  LOG_BEGIN(WARNING_LOG | 5);  LOG("v3MP::Cache: Entry not found (msg id) (type)");  LOG(searchedID);  LOG(local_request ? "local" : "remote");  LOG_END;  return SNMPv3_MP_ERROR;}void v3MP::Cache::delete_content(struct v3MP::Cache::Entry_T &ce){  if (ce.sec_state_ref)    usm->delete_sec_state_reference(ce.sec_state_ref);}// ==========================[ class v3MP ]===============================// Initialize the v3MP.v3MP::v3MP(const OctetStr& snmpEngineID,           unsigned int engineBoots, int &construct_status)  : own_engine_id(0), usm(0){  if (I)  {    debugprintf(0, "v3MP: You must not create two object of this class!");    construct_status = SNMPv3_MP_ERROR;    return;  }  I = this;  snmpUnknownSecurityModels = 0;  snmpInvalidMsgs = 0;  snmpUnknownPDUHandlers = 0;  int length = snmpEngineID.len();  if (length > MAXLENGTH_ENGINEID)    length = MAXLENGTH_ENGINEID;  own_engine_id = v3strcpy(snmpEngineID.data(), length);  own_engine_id_len = length;  own_engine_id_oct = snmpEngineID;  int result;  usm = new USM(engineBoots, snmpEngineID, this, &cur_msg_id, result);  if ((!own_engine_id) || (!usm) || (result != SNMPv3_USM_OK))  {    construct_status = SNMPv3_MP_ERROR;    return;  }  cache.set_usm(usm);  construct_status = SNMPv3_MP_OK;}// Free all allocated ressources of the v3MP.v3MP::~v3MP(){  if (own_engine_id)    delete [] own_engine_id;  own_engine_id = 0;  if (usm)  {    delete usm;    usm = 0;  }  I = 0;}// Remove all occurences of this engine id from v3MP and USM.int v3MP::remove_engine_id(const OctetStr &engine_id){  int retval1, retval2;  retval1 = engine_id_table.delete_entry(engine_id);  retval2 = usm->remove_engine_id(engine_id);  if ((retval1 == SNMPv3_MP_NOT_INITIALIZED) ||      (retval2 == SNMPv3_USM_ERROR))    return SNMPv3_MP_NOT_INITIALIZED;  return SNMPv3_MP_OK;}// Send a report message.int v3MP::send_report(unsigned char* scopedPDU, int scopedPDULength,		      struct snmp_pdu *pdu, int errorCode, int sLevel,		      int sModel, OctetStr &sName,		      UdpAddress &destination, Snmp *snmp_session){  debugprintf(2, "v3MP::send_report: Sending report message.");  unsigned char *data;  int dataLength;  int pdu_type = 0;  unsigned char cEngineID[MAXLENGTH_ENGINEID+1];  unsigned char cName[MAXLENGTH_CONTEXT_NAME+1];  int cEngineIDLength = MAXLENGTH_ENGINEID+1;  int cNameLength = MAXLENGTH_CONTEXT_NAME+1;  if (scopedPDULength != MAX_SNMP_PACKET)  {    // try to get scopedPDU and PDU    data = asn1_parse_scoped_pdu(scopedPDU, &scopedPDULength,				 cEngineID, &cEngineIDLength,				 cName, &cNameLength);    if (data == NULL) {      debugprintf(1, "mp: Error while trying to parse  scopedPDU!");      cEngineID[0] = '\0';      cEngineIDLength = 0;      cName[0] = '\0';      cNameLength = 0;      // Dont send encrypted report if decryption failed:      if (sLevel == SNMP_SECURITY_LEVEL_AUTH_PRIV)        sLevel = SNMP_SECURITY_LEVEL_AUTH_NOPRIV;    }    else { // data != NULL      dataLength = scopedPDULength;      // parse data of scopedPDU      snmp_parse_data_pdu(pdu, data, dataLength);      pdu_type = pdu->command;      if (!data) {        debugprintf(0, "mp: Error while trying to parse PDU!");      }    } // end of: if (data == NULL)  } // end if (scopedPDULength != MAX_SNMP_PACKET)  else { // scopedPDULength == MAX_SNMP_PACKET    cEngineID[0] = '\0';    cEngineIDLength = 0;    cName[0] = '\0';    cNameLength = 0;    pdu->reqid = 0;  }  clear_pdu(pdu);   // Clear pdu and free all content  debugprintf(4, "pdu->reqid = 0x%lx",pdu->reqid);  pdu->errstat = 0;  pdu->errindex = 0;  pdu->command = REPORT_MSG;  Vb counterVb;  Oid counterOid;  SmiLPOID smioid;  SmiVALUE smival;  switch (errorCode) {    case SNMPv3_MP_INVALID_MESSAGE:    case SNMPv3_USM_PARSE_ERROR: {      counterVb.set_oid(oidSnmpInvalidMsgs);      counterVb.set_value(Counter32(get_stats_invalid_msgs()));      break;    }    case SNMPv3_USM_NOT_IN_TIME_WINDOW:    case SNMPv3_MP_NOT_IN_TIME_WINDOW: {      counterVb.set_oid(oidUsmStatsNotInTimeWindows);      counterVb.set_value(Counter32(usm->get_stats_not_in_time_windows()));      break;    }    case SNMPv3_USM_DECRYPTION_ERROR: {      counterVb.set_oid(oidUsmStatsDecryptionErrors);      counterVb.set_value(Counter32(usm->get_stats_decryption_errors()));      sLevel = SNMP_SECURITY_LEVEL_NOAUTH_NOPRIV;      break;    }    case SNMPv3_USM_AUTHENTICATION_ERROR:    case SNMPv3_USM_AUTHENTICATION_FAILURE: {      counterVb.set_oid(oidUsmStatsWrongDigests);      counterVb.set_value(Counter32(usm->get_stats_wrong_digests()));      sLevel = SNMP_SECURITY_LEVEL_NOAUTH_NOPRIV;      break;    }    case SNMPv3_USM_UNKNOWN_ENGINEID:    case SNMPv3_MP_INVALID_ENGINEID: {      sLevel = SNMP_SECURITY_LEVEL_NOAUTH_NOPRIV;      counterVb.set_oid(oidUsmStatsUnknownEngineIDs);      counterVb.set_value(Counter32(usm->get_stats_unknown_engine_ids()));      break;    }    case SNMPv3_MP_UNSUPPORTED_SECURITY_MODEL: {      counterVb.set_oid(oidSnmpUnknownSecurityModels);      counterVb.set_value(Counter32(get_stats_unknown_security_models()));      sModel = SecurityModel_USM;      sLevel = SNMP_SECURITY_LEVEL_NOAUTH_NOPRIV;    break;    }    case SNMPv3_USM_UNKNOWN_SECURITY_NAME: {      counterVb.set_oid(oidUsmStatsUnknownUserNames);      counterVb.set_value(Counter32(usm->get_stats_unknown_user_names()));      sLevel = SNMP_SECURITY_LEVEL_NOAUTH_NOPRIV;      debugprintf(2, "Report: SecurityName: %s",sName.get_printable());      break;    }    case SNMPv3_USM_UNSUPPORTED_SECURITY_LEVEL: {      counterVb.set_oid(oidUsmStatsUnsupportedSecLevels);      counterVb.set_value(Counter32(usm->get_stats_unsupported_sec_levels()));      sLevel = SNMP_SECURITY_LEVEL_NOAUTH_NOPRIV;      break;    }    default: {      counterVb.set_oid(oidSnmpInvalidMsgs);      counterVb.set_value(Counter32(get_stats_invalid_msgs()));      sModel = SecurityModel_USM;      sLevel = SNMP_SECURITY_LEVEL_NOAUTH_NOPRIV;      sName.set_data(0, 0);      debugprintf(2, "ErrorCode was %i in snmp_parse", errorCode);    }  } // end switch  counterVb.get_oid(counterOid);  smioid = counterOid.oidval();  int status = convertVbToSmival(counterVb, &smival);  if (status != SNMP_CLASS_SUCCESS) {    return SNMPv3_MP_ERROR;  }  snmp_add_var(pdu, smioid->ptr,               (int) smioid->len, &smival);  freeSmivalDescriptor(&smival);  Buffer<unsigned char> sendbuffer(MAX_SNMP_PACKET);  int sendbufferlen= MAX_SNMP_PACKET;  status = snmp_build( pdu, sendbuffer.get_ptr(), &sendbufferlen,		       own_engine_id_oct, sName, sModel, sLevel,		       OctetStr(cEngineID, cEngineIDLength),		       OctetStr(cName, cNameLength));  if (status != SNMPv3_MP_OK) {    debugprintf(2, "v3MP::send_report: error serializing message (mpSnmpBuild returns: %i).", status);    return SNMPv3_MP_ERROR;  }  SnmpSocket send_fd = INVALID_SOCKET;  if (pdu_type == sNMP_PDU_INFORM)  {    debugprintf(4, "Received a snmpInform pdu.");    if (snmp_session->eventListHolder->notifyEventList())      send_fd = snmp_session->eventListHolder->notifyEventList()->get_notify_fd();  }  status = snmp_session->send_raw_data(sendbuffer.get_ptr(),                                       (size_t)sendbufferlen,// pdu to send			               destination,          // target address			               send_fd);             // the fd to use  if ( status != 0)  {    debugprintf(1, "v3MP::send_report: error sending message (%i)", status);    return SNMPv3_MP_ERROR;  }  debugprintf(3, "v3MP::send_report: Report sent.");  return SNMPv3_MP_OK;}// Parse the given buffer as a SNMPv3-Message.int v3MP::snmp_parse(Snmp *snmp_session,                     struct snmp_pdu *pdu,                     unsigned char *inBuf,                     int inBufLength,                     OctetStr &securityEngineID,                     OctetStr &securityName,                     OctetStr &contextEngineID,                     OctetStr &contextName,                     long     &securityLevel,                     long     &msgSecurityModel,                     snmp_version &spp_version,                     UdpAddress from_address){  debugprintf(3, "mp is parsing incoming message:");  debughexprintf(25, inBuf, inBufLength);  if (inBufLength > MAX_SNMP_PACKET)    return  SNMPv3_MP_ERROR;  unsigned char type;  long version;  int origLength = inBufLength;  unsigned char *inBufPtr = inBuf;  long msgID, msgMaxSize;  unsigned char msgFlags;  Buffer<unsigned char> msgSecurityParameters(MAX_SNMP_PACKET);  Buffer<unsigned char> msgData(MAX_SNMP_PACKET);  int msgSecurityParametersLength = inBufLength,   msgDataLength = inBufLength;  Buffer<unsigned char> scopedPDU(MAX_SNMP_PACKET);  int scopedPDULength = MAX_SNMP_PACKET;  long  maxSizeResponseScopedPDU = 0;  struct SecurityStateReference *securityStateReference = NULL;  int securityParametersPosition;  int rc;  int errorCode = 0;  // get the type  inBuf = asn_parse_header( inBuf, &inBufLength, &type);  if (inBuf == NULL){    debugprintf(0, "snmp_parse: bad header");    return SNMPv3_MP_PARSE_ERROR;  }  if (type != (ASN_SEQ_CON)){    debugprintf(0, "snmp_parse: wrong auth header type");    return SNMPv3_MP_PARSE_ERROR;  }  if (origLength != inBufLength + (inBuf - inBufPtr)) {    debugprintf(0, "snmp_parse: wrong length of received packet");    return SNMPv3_MP_PARSE_ERROR;  }  // get the version  inBuf = asn_parse_int(inBuf, &inBufLength,                        &type, &version, sizeof(version));  if (inBuf == NULL){    debugprintf(0, "snmp_parse: bad parse of version");    return SNMPv3_MP_PARSE_ERROR;  }  debugprintf(3, "Parsed length(%x), version(0x%lx)", inBufLength, version);  if ( version != SNMP_VERSION_3 )    return SNMPv3_MP_PARSE_ERROR;  spp_version = (snmp_version) version;  inBuf = asn1_parse_header_data(inBuf, &inBufLength,				 &msgID, &msgMaxSize,				 &msgFlags, &msgSecurityModel);  if (inBuf == NULL){    debugprintf(0, "snmp_parse: bad parse of msgHeaderData");    return SNMPv3_MP_PARSE_ERROR;  }  pdu->msgid = msgID;  if ((msgMaxSize < 484) || (msgMaxSize > 0x7FFFFFFF)) {    debugprintf(0, "snmp_parse: bad parse of msgMaxSize");    return SNMPv3_MP_PARSE_ERROR;  }  // do not allow larger messages than this entity can handle  if (msgMaxSize > MAX_SNMP_PACKET) msgMaxSize = MAX_SNMP_PACKET;  pdu->maxsize_scopedpdu = msgMaxSize;  inBuf = asn_parse_string( inBuf, &inBufLength, &type,                            msgSecurityParameters.get_ptr(),                            &msgSecurityParametersLength);  if (inBuf == NULL){    debugprintf(0, "snmp_parse: bad parse of msgSecurityParameters");    return SNMPv3_MP_PARSE_ERROR;  }  securityParametersPosition= SAFE_INT_CAST(inBuf - inBufPtr) - msgSecurityParametersLength;  // the rest of the message is passed directly to the security module  msgDataLength = origLength - SAFE_INT_CAST(inBuf - inBufPtr);  memcpy(msgData.get_ptr(), inBuf, msgDataLength);  debugprintf(3, "Parsed msgdata length(0x%x), "	      "msgSecurityParameters length(0x%x)", msgDataLength,	      msgSecurityParametersLength);  switch (msgFlags & 0x03) {    case 3:  { securityLevel = SNMP_SECURITY_LEVEL_AUTH_PRIV;     break;}    case 0:  { securityLevel = SNMP_SECURITY_LEVEL_NOAUTH_NOPRIV; break;}    case 1:  { securityLevel = SNMP_SECURITY_LEVEL_AUTH_NOPRIV;   break;}    default: { securityLevel = SNMP_SECURITY_LEVEL_NOAUTH_NOPRIV;               snmpInvalidMsgs++;               // do not send back report               return SNMPv3_MP_INVALID_MESSAGE;               break;             }  }  bool reportableFlag;  if (msgFlags & 0x04) reportableFlag = TRUE;  else                 reportableFlag = FALSE;  securityStateReference = usm->get_new_sec_state_reference();  if (!securityStateReference)    return SNMPv3_MP_ERROR;  switch (msgSecurityModel) {    case SecurityModel_USM:      {        rc = usm->process_msg(                           msgMaxSize,                           msgSecurityParameters.get_ptr(),			   msgSecurityParametersLength,                           securityParametersPosition,                           securityLevel,                           inBufPtr, origLength, //wholeMsg                           msgData.get_ptr(), msgDataLength,                           securityEngineID,                           securityName,                           scopedPDU.get_ptr(), &scopedPDULength,                           &maxSizeResponseScopedPDU,                           securityStateReference,			   from_address);        pdu->maxsize_scopedpdu = maxSizeResponseScopedPDU;        if (rc != SNMPv3_USM_OK) {          if (rc == SNMPv3_USM_NOT_IN_TIME_WINDOW) {            errorCode = SNMPv3_MP_NOT_IN_TIME_WINDOW;          }          else {            // error handling! rfc2262 page 31            debugprintf(0, "mp: error while executing USM::process_msg");            errorCode = rc;          }        }        if (errorCode != SNMPv3_USM_PARSE_ERROR)          if (securityEngineID.len() == 0)            errorCode = SNMPv3_MP_INVALID_ENGINEID;        break;      }    default: {        snmpUnknownSecurityModels++;	usm->delete_sec_state_reference(securityStateReference);        debugprintf(0, "SecurityModel of incomming Message not supported!");        // Message should be dropped without a report        return SNMPv3_MP_UNSUPPORTED_SECURITY_MODEL;      }  }  // process scopedPDU  debughexcprintf(21, "scoped PDU", scopedPDU.get_ptr(), scopedPDULength);  unsigned char *scopedPDUPtr= scopedPDU.get_ptr();  unsigned char tmp_contextEngineID[MAXLENGTH_ENGINEID];  unsigned char tmp_contextName[MAXLENGTH_CONTEXT_NAME];  int tmp_contextEngineIDLength = MAXLENGTH_ENGINEID;  int tmp_contextNameLength     = MAXLENGTH_CONTEXT_NAME;  unsigned char *data;  int dataLength;  debugprintf(1,"ErrorCode is %i",errorCode);  if (!errorCode) {    data = asn1_parse_scoped_pdu(scopedPDUPtr, &scopedPDULength,				 tmp_contextEngineID,				 &tmp_contextEngineIDLength,				 tmp_contextName, &tmp_contextNameLength);    if (data == NULL) {      debugprintf(0, "mp: Error Parsing scopedPDU!");      usm->delete_sec_state_reference(securityStateReference);      return SNMPv3_MP_PARSE_ERROR;    }    dataLength = scopedPDULength;    contextEngineID.set_data(tmp_contextEngineID, tmp_contextEngineIDLength);    contextName.set_data(tmp_contextName, tmp_contextNameLength);    // parse data of scopedPDU    if (snmp_parse_data_pdu(pdu, data, dataLength) != SNMP_CLASS_SUCCESS) {      debugprintf(0, "mp: Error parsing PDU!");      usm->delete_sec_state_reference(securityStateReference);      return SNMPv3_MP_PARSE_ERROR;    }    if (SNMP_CLASS_SUCCESS != snmp_parse_vb(pdu, data, dataLength)) {      debugprintf(0, "mp: Error parsing Vb");      usm->delete_sec_state_reference(securityStateReference);      return SNMPv3_MP_PARSE_ERROR;    }    if ((tmp_contextEngineIDLength == 0) &&        ((pdu->command == GET_REQ_MSG) || (pdu->command == GETNEXT_REQ_MSG) ||         (pdu->command == SET_REQ_MSG) || (pdu->command == GETBULK_REQ_MSG) ||         (pdu->command == TRP_REQ_MSG) || (pdu->command == INFORM_REQ_MSG)  ||         (pdu->command == TRP2_REQ_MSG)))    {      //  RFC 2572 

⌨️ 快捷键说明

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