void callback( int reason, Snmp *snmp, Pdu &pdu, SnmpTarget &target, void *cd) { Vb nextVb; int pdu_error; cout << "reason: " << reason << endl << "msg: " << snmp->error_msg(reason) << endl; pdu_error = pdu.get_error_status(); if (pdu_error) { cout << "Response contains error: " << snmp->error_msg(pdu_error)<< endl; } for (int i=0; i<pdu.get_vb_count(); i++) { pdu.get_vb(nextVb, i); cout << "Oid: " << nextVb.get_printable_oid() << endl << "Val: " << nextVb.get_printable_value() << endl; } if (pdu.get_type() == sNMP_PDU_INFORM) { cout << "pdu type: " << pdu.get_type() << endl; cout << "sending response to inform: " << endl; nextVb.set_value("This is the response."); pdu.set_vb(nextVb, 0); snmp->response(pdu, target); } cout << endl; }
// callback : have received a Pdu from the target host with given read comm str // this is really simplistic, but gives the general idea int agent_impl::handle_get( Pdu &pdu, UdpTarget &target) { ACE_TRACE("agent_impl::handle_get"); OctetStr mgr_rd_str, agent_rd_str; target.get_read_community(mgr_rd_str); // requster's read community string tgt_.get_read_community(agent_rd_str); // this agent's read community string // 1. verify we have a valid read string else drop pdu (no response to caller) if (mgr_rd_str != agent_rd_str) { ACE_DEBUG((LM_DEBUG, "agent_impl::handle_get: invalid read community recvd\n")); return 0; } // 2. iterate over each varbind in the pdu, filling providing responses int fdone = 0; for (int i = 0; (i < pdu.get_vb_count()) && !fdone; i++) { Vb vb; pdu.get_vb(vb, i); if (get_response(vb)) { // set a value for the oid if we can else set_error_status(&pdu, SNMP_ERROR_NO_SUCH_NAME); // these ought to be member set_error_index(&pdu, i); // functions but are not yet... fdone++; // trigger flag to exit loop early } else // failed, return noSuch error pdu.set_vb(vb, i); } // 3. lastly, return the pkt to the caller return respond(pdu, target); }
void MainWindow::async_callback(int reason, Snmp * /*snmp*/, Pdu &pdu, SnmpTarget &target) { Vb nextVb; int pdu_error; QString prefix_text; QString notify_text; push_button_get_next->setEnabled(true); // What is the reason for this callback? if (reason == SNMP_CLASS_NOTIFICATION) { prefix_text = "Trap: "; // get the notify id for traps Oid id; pdu.get_notify_id(id); notify_text = QString(" ID: %1 Type %2 -- ").arg(id.get_printable()) .arg(pdu.get_type()); } else if (reason == SNMP_CLASS_ASYNC_RESPONSE) { prefix_text = "Response "; } else if (reason == SNMP_CLASS_TIMEOUT) { prefix_text = "Timeout "; } else { QString err = QString("\nDid not receive async response/trap: (%1) %2\n") .arg(reason).arg(Snmp::error_msg(reason)); text_edit_output->append(err); } // Look at the error status of the Pdu pdu_error = pdu.get_error_status(); if (pdu_error) { QString err = "\nResponse contains error:\n"; err += Snmp::error_msg(pdu_error); text_edit_output->append(err); return; } // The Pdu must contain at least one Vb if (pdu.get_vb_count() == 0) { QString err = "\nPdu is empty\n"; text_edit_output->append(err); return; } for (int i=0; i<pdu.get_vb_count(); i++) { // Get the Vb of the Pdu pdu.get_vb(nextVb, i); // Get Oid and value from the Vb and display it line_edit_obj_id->setText(nextVb.get_printable_oid()); line_edit_value->setText(nextVb.get_printable_value()); text_edit_output->append(prefix_text + target.get_address().get_printable() + " -- " + notify_text + line_edit_obj_id->text() + " = " + line_edit_value->text() + "\n"); } // If we received a inform pdu, we have to send a response if (pdu.get_type() == sNMP_PDU_INFORM) { text_edit_output->append("Sending response to inform.\n"); // just change the value of the first vb pdu.get_vb(nextVb, 0); nextVb.set_value("This is the response."); pdu.set_vb(nextVb, 0); snmp->response(pdu, target); } }
const list<pair<string,string> > & SnmpDG::GetMibTable(const snmp_version version, const SnmpPara& spr, const string oid) const { m_mib_table.clear(); if(!m_inited_success) { return m_mib_table; } Snmp::socket_startup(); // Initialize socket subsystem UdpAddress address( spr.ip.c_str()); Oid myoid(oid.c_str()); // default is sysDescr if( !myoid.valid()) {// check validity of user oid return m_mib_table; } Pdu pdu; // construct a Pdu object Vb vb; // construct a Vb object(SNMP++ Variable Binding) vb.set_oid(myoid);//oid.c_str()); pdu += vb; CTarget ctarget(address); ctarget.set_version( version ); ctarget.set_retry(spr.retry); ctarget.set_timeout(spr.timeout); ctarget.set_readcommunity(spr.community.c_str()); SnmpTarget *target; target = &ctarget; int status; Snmp snmp(status, 0, false); if (status == SNMP_CLASS_SUCCESS) { DWORD dwStartTime_ttl = GetTickCount(); DWORD dwStartTime = 0, dwEndTime = 0; while ( (status = snmp.get_next(pdu, *target)) == SNMP_CLASS_SUCCESS) //get_next命令是按列遍历oid { pdu.get_vb(vb, 0); Oid oid_tmp = vb.get_oid();//.get_printable_oid();该表项的oid string str_oid_tmp = oid_tmp.get_printable(); if(oid_tmp.nCompare(myoid.len(), myoid) != 0)//判断是否已越界,如果是则结束循环 { break; } bool bNew = true; string value_tmp = vb.get_printable_value(); for(std::list<pair<string,string> >::iterator item = m_mib_table.begin(); item != m_mib_table.end(); item++) { if(item->first == str_oid_tmp)//value_tmp)//去掉重复的oid { bNew = false; cout << "ip:" + spr.ip + ",repeat oid:" + str_oid_tmp; break; } } if(bNew) { dwStartTime = GetTickCount(); m_mib_table.push_back(make_pair(str_oid_tmp,value_tmp)); vb.set_oid(oid_tmp); vb.set_null(); pdu.set_vb(vb,0); } else { // if ( GetTickCount() - dwStartTime > 10000 ) //10s //{ // cout << "Timeout because read repeat data " << endl; break; //} } if ( GetTickCount() - dwStartTime_ttl > 300000 ) //5min { cout << "Timeout because read operation " << endl; break; } } } else { cout << "SNMP++ Session Create Fail, " << snmp.error_msg(status) << "\n"; SetLastError(status); } Snmp::socket_cleanup(); // Shut down socket subsystem return m_mib_table; }