error_t snmpParseGetRequestPdu(SnmpAgentContext *context, const uint8_t *p, size_t length) { error_t error; size_t n; uint_t index; SnmpVarBind var; //Debug message if(context->request.pduType == SNMP_PDU_GET_REQUEST) { TRACE_INFO("Parsing GetRequest-PDU...\r\n"); } else if(context->request.pduType == SNMP_PDU_GET_NEXT_REQUEST) { TRACE_INFO("Parsing GetNextRequest-PDU...\r\n"); } //Verify community name error = snmpCheckCommunity(context, MIB_ACCESS_READ_ONLY); //Wrong community name? if(error) return error; //Parse PDU header error = snmpParsePduHeader(context, p, length); //Failed to parse PDU header? if(error) return error; //Point to the first variable binding of the request p = context->request.varBindList; length = context->request.varBindListLen; //Lock access to MIB bases snmpLockMib(context); //Loop through the list for(index = 1; length > 0; index++) { //Parse variable binding error = snmpParseVarBinding(p, length, &var, &n); //Failed to parse variable binding? if(error) break; //GetRequest-PDU? if(context->request.pduType == SNMP_PDU_GET_REQUEST) { //Retrieve object value error = snmpGetObjectValue(context, &var); } //GetNextRequest-PDU? else { //Search the MIB for the next object error = snmpGetNextObject(context, &var); //SNMPv1 version? if(context->version == SNMP_VERSION_1) { //Check status code if(error == NO_ERROR) { //Retrieve object value error = snmpGetObjectValue(context, &var); } else { //Stop immediately break; } } //SNMPv2c version? else { //Check status code if(error == NO_ERROR) { //Retrieve object value error = snmpGetObjectValue(context, &var); } else if(error == ERROR_OBJECT_NOT_FOUND) { //The variable binding's value field is set to endOfMibView var.class = ASN1_CLASS_CONTEXT_SPECIFIC; var.type = SNMP_EXCEPTION_END_OF_MIB_VIEW; var.valueLen = 0; //Catch exception error = NO_ERROR; } else { //Stop immediately break; } } }
error_t snmpProcessGetRequestPdu(SnmpAgentContext *context) { error_t error; int_t index; size_t n; size_t length; const uint8_t *p; SnmpVarBind var; //Check PDU type if(context->request.pduType == SNMP_PDU_GET_REQUEST) { //Debug message TRACE_INFO("Parsing GetRequest-PDU...\r\n"); //Total number of SNMP Get-Request PDUs which have been accepted and //processed by the SNMP protocol entity MIB2_INC_COUNTER32(mib2Base.snmpGroup.snmpInGetRequests, 1); } else if(context->request.pduType == SNMP_PDU_GET_NEXT_REQUEST) { //Debug message TRACE_INFO("Parsing GetNextRequest-PDU...\r\n"); //Total number of SNMP Get-NextRequest PDUs which have been accepted //and processed by the SNMP protocol entity MIB2_INC_COUNTER32(mib2Base.snmpGroup.snmpInGetNexts, 1); } //Enforce access policy if(context->user->mode != SNMP_ACCESS_READ_ONLY && context->user->mode != SNMP_ACCESS_READ_WRITE) { //Total number of SNMP messages delivered to the SNMP protocol entity //which represented an SNMP operation which was not allowed by the SNMP MIB2_INC_COUNTER32(mib2Base.snmpGroup.snmpInBadCommunityUses, 1); //Report an error return ERROR_ACCESS_DENIED; } //Initialize response message error = snmpInitResponse(context); //Any error to report? if(error) return error; //Point to the first variable binding of the request p = context->request.varBindList; length = context->request.varBindListLen; //Lock access to MIB bases snmpLockMib(context); //Loop through the list for(index = 1; length > 0; index++) { //Parse variable binding error = snmpParseVarBinding(p, length, &var, &n); //Failed to parse variable binding? if(error) break; //Make sure that the object identifier is valid error = oidCheck(var.oid, var.oidLen); //Invalid object identifier? if(error) break; //GetRequest-PDU? if(context->request.pduType == SNMP_PDU_GET_REQUEST) { //Retrieve object value error = snmpGetObjectValue(context, &var); } //GetNextRequest-PDU? else { //Search the MIB for the next object error = snmpGetNextObject(context, &var); //SNMPv1 version? if(context->request.version == SNMP_VERSION_1) { //Check status code if(error == NO_ERROR) { //Retrieve object value error = snmpGetObjectValue(context, &var); } else { //Stop immediately break; } } //SNMPv2c or SNMPv3 version? else { //Check status code if(error == NO_ERROR) { //Retrieve object value error = snmpGetObjectValue(context, &var); } else if(error == ERROR_OBJECT_NOT_FOUND) { //The variable binding's value field is set to endOfMibView var.class = ASN1_CLASS_CONTEXT_SPECIFIC; var.type = SNMP_EXCEPTION_END_OF_MIB_VIEW; var.valueLen = 0; //Catch exception error = NO_ERROR; } else { //Stop immediately break; } } }