📄 snmprequesthandler.java
字号:
/* * @(#)file SnmpRequestHandler.java * @(#)author Sun Microsystems, Inc. * @(#)version 4.32 * @(#)date 08/09/12 * * Copyright 2006 Sun Microsystems, Inc. All rights reserved. * SUN PROPRIETARY/CONFIDENTIAL. Use is subject to license terms. * */package com.sun.jmx.snmp.daemon;// java import//import java.util.Vector;import java.util.Enumeration;import java.util.Hashtable;import java.io.InterruptedIOException;import java.net.DatagramSocket;import java.net.DatagramPacket;import java.net.SocketException;// jmx imports//import javax.management.MBeanServer;import javax.management.ObjectName;import com.sun.jmx.snmp.SnmpMessage;import com.sun.jmx.snmp.SnmpPduFactory;import com.sun.jmx.snmp.SnmpPduBulk;import com.sun.jmx.snmp.SnmpPduPacket;import com.sun.jmx.snmp.SnmpPduRequest;import com.sun.jmx.snmp.SnmpPduTrap;import com.sun.jmx.snmp.SnmpValue;import com.sun.jmx.snmp.SnmpVarBind;import com.sun.jmx.snmp.SnmpVarBindList;import com.sun.jmx.snmp.SnmpDefinitions;import com.sun.jmx.snmp.SnmpStatusException;import com.sun.jmx.snmp.SnmpTooBigException;import com.sun.jmx.snmp.SnmpDataTypeEnums;// RI imports//import com.sun.jmx.trace.Trace;// SNMP runtime import//import com.sun.jmx.snmp.agent.SnmpMibAgent;import com.sun.jmx.snmp.agent.SnmpUserDataFactory;//import com.sun.jmx.snmp.IPAcl.IPAcl;import com.sun.jmx.snmp.InetAddressAcl;class SnmpRequestHandler extends ClientHandler implements SnmpDefinitions { private transient DatagramSocket socket = null ; private transient DatagramPacket packet = null ; private transient Vector mibs = null ; /** * Contains the list of sub-requests associated to the current request. */ private transient Hashtable subs = null ; /** * Reference on the MIBS */ private transient SnmpMibTree root; private transient Object ipacl = null ; private transient SnmpPduFactory pduFactory = null ; private transient SnmpUserDataFactory userDataFactory = null ; private transient SnmpAdaptorServer adaptor = null; /** * Full constructor */ public SnmpRequestHandler(SnmpAdaptorServer server, int id, DatagramSocket s, DatagramPacket p, SnmpMibTree tree, Vector m, Object a, SnmpPduFactory factory, SnmpUserDataFactory dataFactory, MBeanServer f, ObjectName n) { super(server, id, f, n); // Need a reference on SnmpAdaptorServer for getNext & getBulk, // in case of oid equality (mib overlapping). // adaptor = server; socket = s; packet = p; root= tree; mibs = (Vector) m.clone(); subs= new Hashtable(mibs.size()); ipacl = a; pduFactory = factory ; userDataFactory = dataFactory ; //thread.start(); } /** * Treat the request available in 'packet' and send the result * back to the client. * Note: we overwrite 'packet' with the response bytes. */ public void doRun() { // Trace the input packet // if (isTraceOn()) { trace("doRun", "Packet received:\n" + SnmpMessage.dumpHexBuffer(packet.getData(), 0, packet.getLength())); } // Let's build the response packet // DatagramPacket respPacket = makeResponsePacket(packet) ; // Trace the output packet // if (isTraceOn() && (respPacket != null)) { trace("doRun", "Packet to be sent:\n" + SnmpMessage.dumpHexBuffer(respPacket.getData(), 0, respPacket.getLength())); } // Send the response packet if any // if (respPacket != null) { try { socket.send(respPacket) ; } catch (SocketException e) { if (isDebugOn()) { if (e.getMessage().equals(InterruptSysCallMsg)) debug("doRun", "interrupted"); else { debug("doRun", "i/o exception"); debug("doRun", e); } } } catch(InterruptedIOException e) { if (isDebugOn()) { debug("doRun", "interrupted"); } } catch(Exception e) { if (isDebugOn()) { debug("doRun", "failure when sending response"); debug("doRun", e); } } } } /** * Here we make a response packet from a request packet. * We return null if there no response packet to sent. */ private DatagramPacket makeResponsePacket(DatagramPacket reqPacket) { DatagramPacket respPacket = null ; // Transform the request packet into a request SnmpMessage // SnmpMessage reqMsg = new SnmpMessage() ; try { reqMsg.decodeMessage(reqPacket.getData(), reqPacket.getLength()) ; reqMsg.address = reqPacket.getAddress() ; reqMsg.port = reqPacket.getPort() ; } catch(SnmpStatusException x) { if (isDebugOn()) { debug("makeResponsePacket", "packet decoding failed"); debug("makeResponsePacket", x); } reqMsg = null ; ((SnmpAdaptorServer)adaptorServer).incSnmpInASNParseErrs(1) ; } // Make the response SnmpMessage if any // SnmpMessage respMsg = null ; if (reqMsg != null) { respMsg = makeResponseMessage(reqMsg) ; } // Try to transform the response SnmpMessage into response packet. // NOTE: we overwrite the request packet. // if (respMsg != null) { try { reqPacket.setLength(respMsg.encodeMessage(reqPacket.getData())) ; respPacket = reqPacket ; } catch(SnmpTooBigException x) { if (isDebugOn()) { debug("makeResponsePacket", "response message is too big"); } try { respMsg = newTooBigMessage(reqMsg) ; reqPacket.setLength(respMsg.encodeMessage(reqPacket.getData())) ; respPacket = reqPacket ; } catch(SnmpTooBigException xx) { if (isDebugOn()) { debug("makeResponsePacket", "'too big' is 'too big' !!!"); } adaptor.incSnmpSilentDrops(1); } } } return respPacket ; } /** * Here we make a response message from a request message. * We return null if there is no message to reply. */ private SnmpMessage makeResponseMessage(SnmpMessage reqMsg) { SnmpMessage respMsg = null ; // Transform the request message into a request pdu // SnmpPduPacket reqPdu = null ; Object userData = null; try { reqPdu = (SnmpPduPacket)pduFactory.decodeSnmpPdu(reqMsg) ; if (reqPdu != null && userDataFactory != null) userData = userDataFactory.allocateUserData(reqPdu); } catch(SnmpStatusException x) { reqPdu = null ; SnmpAdaptorServer snmpServer = (SnmpAdaptorServer)adaptorServer ; snmpServer.incSnmpInASNParseErrs(1) ; if (x.getStatus()== SnmpDefinitions.snmpWrongSnmpVersion) snmpServer.incSnmpInBadVersions(1) ; if (isDebugOn()) { debug("makeResponseMessage", "message decoding failed"); debug("makeResponseMessage",x); } } // Make the response pdu if any // SnmpPduPacket respPdu = null ; if (reqPdu != null) { respPdu = makeResponsePdu(reqPdu,userData) ; try { if (userDataFactory != null) userDataFactory.releaseUserData(userData,respPdu); } catch (SnmpStatusException x) { respPdu = null; } } // Try to transform the response pdu into a response message if any // if (respPdu != null) { try { respMsg = (SnmpMessage)pduFactory. encodeSnmpPdu(respPdu, packet.getData().length) ; } catch(SnmpStatusException x) { respMsg = null ; if (isDebugOn()) { debug("makeResponseMessage", "failure when encoding the response message"); debug("makeResponseMessage", x); } } catch(SnmpTooBigException x) { if (isDebugOn()) { debug("makeResponseMessage", "response message is too big"); } try { // if the PDU is too small, why should we try to do // recovery ? // if (packet.getData().length <=32) throw x; int pos= x.getVarBindCount(); if (isDebugOn()) { debug("makeResponseMessage", "fail on element" + pos); } int old= 0; while (true) { try { respPdu = reduceResponsePdu(reqPdu, respPdu, pos) ; respMsg = (SnmpMessage)pduFactory. encodeSnmpPdu(respPdu, packet.getData().length -32) ; break; } catch (SnmpTooBigException xx) { if (isDebugOn()) { debug("makeResponseMessage", "response message is still too big"); } old= pos; pos= xx.getVarBindCount(); if (isDebugOn()) { debug("makeResponseMessage", "fail on element" + pos); } if (pos == old) { // we can not go any further in trying to // reduce the message ! // throw xx; } } }// end of loop } catch(SnmpStatusException xx) { respMsg = null ; if (isDebugOn()) { debug("makeResponseMessage", "failure when encoding the response message"); debug("makeResponseMessage", xx); } } catch(SnmpTooBigException xx) { try { respPdu = newTooBigPdu(reqPdu) ; respMsg = (SnmpMessage)pduFactory. encodeSnmpPdu(respPdu, packet.getData().length) ; } catch(SnmpTooBigException xxx) { respMsg = null ; if (isDebugOn()) { debug("makeResponseMessage", "'too big' is 'too big' !!!"); } adaptor.incSnmpSilentDrops(1); } catch(Exception xxx) { debug("makeResponseMessage", xxx); respMsg = null ; } } catch(Exception xx) { debug("makeResponseMessage", xx); respMsg = null ; } } } return respMsg ; } /** * Here we make a response pdu from a request pdu. * We return null if there is no pdu to reply. */ private SnmpPduPacket makeResponsePdu(SnmpPduPacket reqPdu, Object userData) { SnmpAdaptorServer snmpServer = (SnmpAdaptorServer)adaptorServer ; SnmpPduPacket respPdu = null ; snmpServer.updateRequestCounters(reqPdu.type) ; if (reqPdu.varBindList != null) snmpServer.updateVarCounters(reqPdu.type, reqPdu.varBindList.length) ; if (checkPduType(reqPdu)) { respPdu = checkAcl(reqPdu) ; if (respPdu == null) { // reqPdu is accepted by ACLs if (mibs.size() < 1) { if (isTraceOn()) { trace("makeResponsePdu", "Request " + reqPdu.requestId + " received but no MIB registered."); } return makeNoMibErrorPdu((SnmpPduRequest)reqPdu, userData); } switch(reqPdu.type) { case SnmpPduPacket.pduGetRequestPdu: case SnmpPduPacket.pduGetNextRequestPdu: case SnmpPduPacket.pduSetRequestPdu: respPdu = makeGetSetResponsePdu((SnmpPduRequest)reqPdu, userData) ; break ;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -