コード例 #1
0
 def n_TrapV2cParams_exit(self, cbCtx, node):
     snmpEngine, ctx = cbCtx
     if 'informMode' in ctx:
         pdu = v2c.InformRequestPDU()
         v2c.apiPDU.setDefaults(pdu)
     else:
         pdu = v2c.TrapPDU()
         v2c.apiTrapPDU.setDefaults(pdu)
     v2c.apiPDU.setVarBinds(pdu,
                            [(v2c.ObjectIdentifier('1.3.6.1.2.1.1.3.0'),
                              v2c.TimeTicks(ctx['Uptime'])),
                             (v2c.ObjectIdentifier('1.3.6.1.6.3.1.1.4.1.0'),
                              v2c.ObjectIdentifier(ctx['TrapOid']))])
     ctx['pdu'] = pdu
コード例 #2
0
    def _ensureVarBinds(varBinds):
        # Add sysUpTime if not present already
        if not varBinds or varBinds[0][0] != sysUpTime:
            varBinds.insert(
                0, (v2c.ObjectIdentifier(sysUpTime), v2c.TimeTicks(0)))

        # Search for and reposition sysUpTime if it's elsewhere
        for idx, varBind in enumerate(varBinds[1:]):
            if varBind[0] == sysUpTime:
                varBinds[0] = varBind
                del varBinds[idx + 1]
                break

        if len(varBinds) < 2:
            raise error.PySnmpError('SNMP notification PDU requires '
                                    'SNMPv2-MIB::snmpTrapOID.0 to be present')

        # Search for and reposition snmpTrapOID if it's elsewhere
        for idx, varBind in enumerate(varBinds[2:]):
            if varBind[0] == snmpTrapOID:
                del varBinds[idx + 2]
                if varBinds[1][0] == snmpTrapOID:
                    varBinds[1] = varBind
                else:
                    varBinds.insert(1, varBind)
                break

        # Fail on missing snmpTrapOID
        if varBinds[1][0] != snmpTrapOID:
            raise error.PySnmpError('SNMP notification PDU requires '
                                    'SNMPv2-MIB::snmpTrapOID.0 to be present')

        return varBinds
コード例 #3
0
def _generic_trap_filter(domain, sock, pdu, **kwargs):
    snmpTrapOID = (1, 3, 6, 1, 6, 3, 1, 1, 4, 1, 0)
    if 'host' in kwargs and kwargs['host']:
        if sock[0] != kwargs['host']:
            return False

    for oid, val in v2c.apiPDU.getVarBindList(pdu):
        if 'oid' in kwargs and kwargs['oid']:
            if oid == snmpTrapOID:
                if val[0][0][2] != v2c.ObjectIdentifier(kwargs['oid']):
                    return False
    return True
コード例 #4
0
def getNextVarBinds(varBinds, origVarBinds=None):
    errorIndication = None
    idx = nonNulls = len(varBinds)
    rspVarBinds = []
    while idx:
        idx -= 1
        if varBinds[idx][1].tagSet in (rfc1905.NoSuchObject.tagSet,
                                       rfc1905.NoSuchInstance.tagSet,
                                       rfc1905.EndOfMibView.tagSet):
            nonNulls -= 1
        elif origVarBinds is not None:
            if v2c.ObjectIdentifier(origVarBinds[idx][0]).asTuple() >= varBinds[idx][0].asTuple():
                errorIndication = errind.oidNotIncreasing

        rspVarBinds.insert(0, (varBinds[idx][0], __null))

    if not nonNulls:
        rspVarBinds = []

    return errorIndication, rspVarBinds
コード例 #5
0
ファイル: oidfilter.py プロジェクト: sharty/snmpfwd
def processCommandRequest(pluginId, snmpEngine, pdu, trunkMsg, reqCtx):

    reqOids = []

    reqCtx['req-oids'] = reqOids
    reqCtx['req-pdu'] = pdu

    if pdu.tagSet in (v2c.GetRequestPDU.tagSet, v2c.SetRequestPDU.tagSet):

        allDenied = True

        deniedOids = []

        for varBindIdx, varBind in enumerate(v2c.apiPDU.getVarBindList(pdu)):

            oid, val = v2c.apiVarBind.getOIDVal(varBind)

            oid = tuple(oid)

            skip, aclIdx = findAcl(oid)

            # skipped to the next OID
            if skip != oid:
                aclIdx = None

            # OID went out of range
            if aclIdx is None:
                # report OIDs we are sending errors for
                if logDenials:
                    deniedOids.append(str(varBind[0]))
            else:
                allDenied = False

            reqOids.append((oid, varBindIdx, aclIdx))

        if logDenials and deniedOids:
            denialMsg = formatDenialMsg(pdu, trunkMsg)
            denialMsg += ' OIDs ' + ', '.join(deniedOids)
            denialMsg += ' denied'
            error(denialMsg)

        reqVarBinds = v2c.VarBindList()

        if allDenied:
            pdu = v2c.apiPDU.getResponse(pdu)

            for oid, _, _ in reqOids:
                varBind = v2c.VarBind()
                v2c.apiVarBind.setOIDVal(varBind, (oid, noSuchInstance))
                reqVarBinds.append(varBind)

            nextAction = status.RESPOND

        else:
            for oid, _, aclIdx in reqOids:
                if aclIdx is None:
                    continue
                varBind = v2c.VarBind()
                v2c.apiVarBind.setOIDVal(varBind, (oid, null))
                reqVarBinds.append(varBind)

            nextAction = status.NEXT

        v2c.apiPDU.setVarBindList(pdu, reqVarBinds)

        return nextAction, pdu

    elif pdu.tagSet == v2c.GetNextRequestPDU.tagSet:

        allDenied = True

        skippedOids = []

        for varBindIdx, varBind in enumerate(v2c.apiPDU.getVarBindList(pdu)):

            oid, val = v2c.apiVarBind.getOIDVal(varBind)

            oid = tuple(oid)

            skip, aclIdx = findAcl(oid, nextOid=True)

            if logDenials and oid != skip:
                skippedOids.append((oid, skip))

            oid = skip

            # OID went out of range
            if aclIdx is not None:
                allDenied = False

            reqOids.append((oid, varBindIdx, aclIdx))

        if logDenials and skippedOids:
            denialMsg = formatDenialMsg(pdu, trunkMsg)
            denialMsg += ' ' + ', '.join([
                '%s not in range skipping to %s' %
                (v2c.ObjectIdentifier(x[0]), v2c.ObjectIdentifier(x[1]))
                for x in skippedOids
            ])
            info(denialMsg)

        reqVarBinds = v2c.VarBindList()

        if allDenied:
            pdu = v2c.apiPDU.getResponse(pdu)

            for oid, _, _ in reqOids:
                varBind = v2c.VarBind()
                v2c.apiVarBind.setOIDVal(varBind, (oid, endOfMibView))
                reqVarBinds.append(varBind)

            nextAction = status.RESPOND

        else:
            for oid, _, aclIdx in reqOids:
                if aclIdx is None:
                    continue
                varBind = v2c.VarBind()
                v2c.apiVarBind.setOIDVal(varBind, (oid, null))
                reqVarBinds.append(varBind)

            nextAction = status.NEXT

        v2c.apiPDU.setVarBindList(pdu, reqVarBinds)

        return nextAction, pdu

    elif pdu.tagSet == v2c.GetBulkRequestPDU.tagSet:

        nonRepeaters = v2c.apiBulkPDU.getNonRepeaters(pdu)
        maxRepeaters = v2c.apiBulkPDU.getMaxRepetitions(pdu)

        nonRepOids = []
        linearizedOids = []
        repOids = []

        linearizedOidsMap = {}
        repeatersOidMap = {}

        reqCtx['linearized-oids-map'] = linearizedOidsMap
        reqCtx['repeaters-oids-map'] = repeatersOidMap

        reqCtx['non-repeaters'] = nonRepeaters

        allDenied = True

        skippedOids = []

        for varBindIdx, varBind in enumerate(
                v2c.apiBulkPDU.getVarBindList(pdu)):

            oid, val = v2c.apiVarBind.getOIDVal(varBind)

            oid = tuple(oid)

            skip, aclIdx = findAcl(oid, nextOid=True)

            if logDenials and oid != skip:
                skippedOids.append((oid, skip))

            oid = skip

            # original request var-binds
            reqOids.append((oid, varBindIdx, aclIdx))

            # OID went beyond all ranges
            if aclIdx is None:
                continue

            allDenied = False

            # original request non-repeaters
            if varBindIdx < nonRepeaters:
                nonRepOids.append((oid, varBindIdx, aclIdx))
                continue

            # original request repeaters
            skip, begin, end = oidsList[aclIdx]

            # move single-OID ranges from repeaters into non-repeaters
            startIdx = len(nonRepOids) + len(linearizedOids)
            endIdx = startIdx

            if begin == end:
                while endIdx - startIdx < maxRepeaters:
                    linearizedOids.append((oid, varBindIdx, aclIdx))
                    endIdx += 1
                    aclIdx += 1
                    if aclIdx >= len(endOids):
                        break
                    oid, begin, end = oidsList[aclIdx]
                    if begin != end:
                        break

                linearizedOidsMap[varBindIdx] = startIdx, endIdx

                debug(
                    '%s: repeating OID #%d (%s) converted into non-repeaters #%d..%d'
                    % (PLUGIN_NAME, varBindIdx, varBind[0], startIdx,
                       endIdx - 1))

                continue

            # proceed with original repeaters
            repeatersOidMap[varBindIdx] = len(repOids)

            repOids.append((oid, varBindIdx, aclIdx))

        if logDenials and skippedOids:
            denialMsg = formatDenialMsg(pdu, trunkMsg)
            denialMsg += ' ' + ', '.join([
                '%s not in range skipping to %s' %
                (v2c.ObjectIdentifier(x[0]), v2c.ObjectIdentifier(x[1]))
                for x in skippedOids
            ])
            info(denialMsg)

        # assemble new var-binds
        reqVarBinds = v2c.VarBindList()

        if allDenied:
            pdu = v2c.apiBulkPDU.getResponse(pdu)

            for oid, _, _ in reqOids:
                varBind = v2c.VarBind()
                v2c.apiVarBind.setOIDVal(varBind, (oid, endOfMibView))
                reqVarBinds.append(varBind)

            nextAction = status.RESPOND

        else:

            for varBindIdx in repeatersOidMap:
                repeatersOidMap[varBindIdx] += len(nonRepOids) + len(
                    linearizedOids)

            for oid, varBindIdx, aclIdx in nonRepOids + linearizedOids + repOids:
                if aclIdx is None:
                    continue

                varBind = v2c.VarBind()
                v2c.apiVarBind.setOIDVal(varBind, (oid, null))
                reqVarBinds.append(varBind)

            v2c.apiBulkPDU.setNonRepeaters(pdu,
                                           nonRepeaters + len(linearizedOids))

            nextAction = status.NEXT

        v2c.apiPDU.setVarBindList(pdu, reqVarBinds)

        return nextAction, pdu

    else:
        return status.NEXT, pdu
コード例 #6
0
ファイル: rfc2576.py プロジェクト: ithek/pysnmp
# PDU v1/v2c two-way proxy
from pysnmp.proto import rfc1905, rfc3411, error
from pysnmp.proto.api import v1, v2c
from pysnmp import debug

# 2.1.1

__v1ToV2ValueMap = {
    v1.Integer.tagSet: v2c.Integer32(),
    v1.OctetString.tagSet: v2c.OctetString(),
    v1.Null.tagSet: v2c.Null(),
    v1.ObjectIdentifier.tagSet: v2c.ObjectIdentifier(),
    v1.IpAddress.tagSet: v2c.IpAddress(),
    v1.Counter.tagSet: v2c.Counter32(),
    v1.Gauge.tagSet: v2c.Gauge32(),
    v1.TimeTicks.tagSet: v2c.TimeTicks(),
    v1.Opaque.tagSet: v2c.Opaque()
}

__v2ToV1ValueMap = {  # XXX do not re-create same-type items?
    v2c.Integer32.tagSet: v1.Integer(),
    v2c.OctetString.tagSet: v1.OctetString(),
    v2c.Null.tagSet: v1.Null(),
    v2c.ObjectIdentifier.tagSet: v1.ObjectIdentifier(),
    v2c.IpAddress.tagSet: v1.IpAddress(),
    v2c.Counter32.tagSet: v1.Counter(),
    v2c.Gauge32.tagSet: v1.Gauge(),
    v2c.TimeTicks.tagSet: v1.TimeTicks(),
    v2c.Opaque.tagSet: v1.Opaque()
}
コード例 #7
0
ファイル: rfc2576.py プロジェクト: ithek/pysnmp
def v1ToV2(v1Pdu, origV2Pdu=None):
    pduType = v1Pdu.tagSet
    v2Pdu = __v1ToV2PduMap[pduType].clone()

    debug.logger & debug.flagPrx and debug.logger(
        'v1ToV2: v1Pdu %s' % v1Pdu.prettyPrint())

    v2VarBinds = []

    # 3.1
    if pduType in rfc3411.notificationClassPDUs:
        # 3.1.1
        sysUpTime = v1.apiTrapPDU.getTimeStamp(v1Pdu)

        # 3.1.2
        genericTrap = v1.apiTrapPDU.getGenericTrap(v1Pdu)
        if genericTrap == 6:
            snmpTrapOIDParam = v1.apiTrapPDU.getEnterprise(v1Pdu) + (0,) + \
                               (int(v1.apiTrapPDU.getSpecificTrap(v1Pdu)),)

        # 3.1.3
        else:
            snmpTrapOIDParam = v2c.ObjectIdentifier(
                __v1ToV2TrapMap[genericTrap])

        # 3.1.4 (XXX snmpTrapCommunity.0 is missing here)
        v2VarBinds.append((v2c.apiTrapPDU.sysUpTime, sysUpTime))
        v2VarBinds.append((v2c.apiTrapPDU.snmpTrapOID, snmpTrapOIDParam))
        v2VarBinds.append((v2c.apiTrapPDU.snmpTrapAddress,
                           v1.apiTrapPDU.getAgentAddr(v1Pdu)))
        v2VarBinds.append(
            (v2c.apiTrapPDU.snmpTrapCommunity, v2c.OctetString("")))
        v2VarBinds.append((v2c.apiTrapPDU.snmpTrapEnterprise,
                           v1.apiTrapPDU.getEnterprise(v1Pdu)))

        varBinds = v1.apiTrapPDU.getVarBinds(v1Pdu)
    else:
        varBinds = v1.apiPDU.getVarBinds(v1Pdu)

    # Translate Var-Binds
    for oid, v1Val in varBinds:
        # 2.1.1.11
        if v1Val.tagSet == v1.NetworkAddress.tagSet:
            v1Val = v1Val.getComponent()
        v2VarBinds.append((oid, __v1ToV2ValueMap[v1Val.tagSet].clone(v1Val)))

    if pduType in rfc3411.responseClassPDUs:
        # 4.1.2.2.1&2
        errorStatus = int(v1.apiPDU.getErrorStatus(v1Pdu))
        errorIndex = int(v1.apiPDU.getErrorIndex(v1Pdu))
        if errorStatus == 2:  # noSuchName
            if origV2Pdu.tagSet == v2c.GetNextRequestPDU.tagSet:
                v2VarBinds[errorIndex - 1] = (v2VarBinds[errorIndex - 1][0],
                                              rfc1905.endOfMibView)
            else:
                v2VarBinds[errorIndex - 1] = (v2VarBinds[errorIndex - 1][0],
                                              rfc1905.noSuchObject)
        # one-to-one mapping
        v2c.apiPDU.setErrorStatus(v2Pdu, errorStatus)
        v2c.apiPDU.setErrorIndex(v2Pdu, errorIndex)

        # 4.1.2.1 --> no-op

    if pduType not in rfc3411.notificationClassPDUs:
        v2c.apiPDU.setRequestID(v2Pdu, int(v1.apiPDU.getRequestID(v1Pdu)))

    v2c.apiPDU.setVarBinds(v2Pdu, v2VarBinds)

    debug.logger & debug.flagPrx and debug.logger(
        'v1ToV2: v2Pdu %s' % v2Pdu.prettyPrint())

    return v2Pdu
コード例 #8
0
# *** SNMP engine configuration is complete by this line ***

# Create Notification Originator App instance.
ntfOrg = ntforg.NotificationOriginator()

# Build and submit notification message to dispatcher
ntfOrg.sendVarBinds(
    snmpEngine,
    # Notification targets
    'my-notification',  # notification targets
    None,
    '',  # contextEngineId, contextName
    # var-binds
    [
        # Uptime value with 12345
        (v2c.ObjectIdentifier('1.3.6.1.2.1.1.3.0'), v2c.TimeTicks(12345)),
        # trap OID: Generic Trap #6 (enterpriseSpecific)
        #           and Specific Trap 432
        (v2c.ObjectIdentifier('1.3.6.1.6.3.1.1.4.1.0'),
         v2c.ObjectIdentifier('1.3.6.1.4.1.20408.4.1.1.2.0.432')),
        # Agent Address with '127.0.0.1'
        (v2c.ObjectIdentifier('1.3.6.1.6.3.18.1.3.0'),
         v2c.IpAddress('127.0.0.1')),
        # Enterprise OID with 1.3.6.1.4.1.20408.4.1.1.2
        (v2c.ObjectIdentifier('1.3.6.1.6.3.1.1.4.3.0'),
         v2c.ObjectIdentifier('1.3.6.1.4.1.20408.4.1.1.2')),
        # managed object '1.3.6.1.2.1.1.1.0' = 'my system'
        (v2c.ObjectIdentifier('1.3.6.1.2.1.1.1.0'),
         v2c.OctetString('my system'))
    ])
コード例 #9
0
def SnmpwalkAsync(target_IP=None,
                  oid=None,
                  community='public',
                  walk_timeout=10,
                  mode='ipv4'):
    """Script to run in the remote device for snmp mib walk.

       This script can be copied to the remote device eg:wan
       and can be executed directly using python for snmp mib walk
       The walk can done for both ipv6 and ipv4

    :param target_IP: device IP for mib query
    :type target_IP: string
    :param oid: mib query OID
    :type oid: string
    :param community: community string for mib query, defaults to public
    :type community: string, optional
    :param walk_timeout: snmp walk timeout, defaults to 10
    :type walk_timeout: integer, optional
    :param mode: mib query mode, defaults to ipv4
    :type mode: string, optional
    :return: mib query output
    :rtype: string
    """
    # SNMP table header
    headVars = [v2c.ObjectIdentifier((oid))]

    # Build PDU
    reqPDU = v2c.GetBulkRequestPDU()
    v2c.apiBulkPDU.setDefaults(reqPDU)
    v2c.apiBulkPDU.setNonRepeaters(reqPDU, 0)
    v2c.apiBulkPDU.setMaxRepetitions(reqPDU, 25)
    v2c.apiBulkPDU.setVarBinds(reqPDU, [(x, v2c.null) for x in headVars])

    # Build message
    reqMsg = v2c.Message()
    v2c.apiMessage.setDefaults(reqMsg)
    v2c.apiMessage.setCommunity(reqMsg, community)
    v2c.apiMessage.setPDU(reqMsg, reqPDU)

    startedAt = time.time()
    output_list = []

    def cbTimerFun(timeNow):
        # Duration
        if timeNow - startedAt > walk_timeout:
            if walk_timeout != 0:
                raise Exception("Request timed out")
            else:
                if timeNow - startedAt > 30:
                    transportDispatcher.jobFinished(1)

    # noinspection PyUnusedLocal
    def cbRecvFun(transportDispatcher,
                  transportDomain,
                  transportAddress,
                  wholeMsg,
                  reqPDU=reqPDU,
                  headVars=headVars):
        while wholeMsg:
            rspMsg, wholeMsg = decoder.decode(wholeMsg, asn1Spec=v2c.Message())
            rspPDU = v2c.apiMessage.getPDU(rspMsg)

            # Match response to request
            if v2c.apiBulkPDU.getRequestID(
                    reqPDU) == v2c.apiBulkPDU.getRequestID(rspPDU):
                # Format var-binds table
                varBindTable = v2c.apiBulkPDU.getVarBindTable(reqPDU, rspPDU)

                # Check for SNMP errors reported
                errorStatus = v2c.apiBulkPDU.getErrorStatus(rspPDU)
                if errorStatus and errorStatus != 2:
                    errorIndex = v2c.apiBulkPDU.getErrorIndex(rspPDU)
                    print('%s at %s' %
                          (errorStatus.prettyPrint(), errorIndex
                           and varBindTable[int(errorIndex) - 1] or '?'))
                    transportDispatcher.jobFinished(1)
                    break

                # Report SNMP table
                for tableRow in varBindTable:
                    for name, val in tableRow:
                        # print mib data
                        print('from: %s, %s = %s' %
                              (transportAddress, name.prettyPrint(),
                               val.prettyPrint()))
                        output_list.append(
                            'from: %s, %s = %s\n' %
                            (transportAddress, name.prettyPrint(),
                             val.prettyPrint()))

                # Stop on EOM
                for oid, val in varBindTable[-1]:
                    if not isinstance(val, v2c.Null):
                        break
                    else:
                        transportDispatcher.jobFinished(1)

                # Generate request for next row
                v2c.apiBulkPDU.setVarBinds(reqPDU,
                                           [(x, v2c.null)
                                            for x, y in varBindTable[-1]])
                v2c.apiBulkPDU.setRequestID(reqPDU, v2c.getNextRequestID())
                transportDispatcher.sendMessage(encoder.encode(reqMsg),
                                                transportDomain,
                                                transportAddress)
        return wholeMsg

    transportDispatcher = AsyncoreDispatcher()
    transportDispatcher.registerRecvCbFun(cbRecvFun)
    transportDispatcher.registerTimerCbFun(cbTimerFun)
    if mode == 'ipv4':
        transportDispatcher.registerTransport(
            udp.domainName,
            udp.UdpSocketTransport().openClientMode())
        transportDispatcher.sendMessage(encoder.encode(reqMsg), udp.domainName,
                                        (target_IP, 161))
    else:
        transportDispatcher.registerTransport(
            udp6.domainName,
            udp6.Udp6SocketTransport().openClientMode())
        transportDispatcher.sendMessage(encoder.encode(reqMsg),
                                        udp6.domainName, (target_IP, 161))
    transportDispatcher.jobStarted(1)
    # Dispatcher will finish as job#1 counter reaches zero
    transportDispatcher.runDispatcher()
    transportDispatcher.closeDispatcher()

    if output_list != []:
        return output_list
    else:
        return
コード例 #10
0
ファイル: ntforg.py プロジェクト: zxx1819/pysnmp
    def sendVarBinds(self,
                     snmpEngine,
                     notificationTarget,
                     contextEngineId,
                     contextName,
                     varBinds=(),
                     cbFun=None,
                     cbCtx=None):
        debug.logger & debug.FLAG_APP and debug.logger(
            'sendVarBinds: notificationTarget %s, contextEngineId %s, '
            'contextName "%s", varBinds %s' %
            (notificationTarget, contextEngineId
             or '<default>', contextName, varBinds))

        mibBuilder = snmpEngine.msgAndPduDsp.mibInstrumController.mibBuilder

        if contextName:
            __SnmpAdminString, = mibBuilder.importSymbols(
                'SNMP-FRAMEWORK-MIB', 'SnmpAdminString')
            contextName = __SnmpAdminString(contextName)

        # 3.3
        notifyTag, notifyType = config.getNotificationInfo(
            snmpEngine, notificationTarget)

        notificationHandle = getNextHandle()

        debug.logger & debug.FLAG_APP and debug.logger(
            'sendVarBinds: notificationHandle %s, notifyTag %s, '
            'notifyType %s' % (notificationHandle, notifyTag, notifyType))

        varBinds = [(v2c.ObjectIdentifier(x), y) for x, y in varBinds]

        # 3.3.2 & 3.3.3
        snmpTrapOID, sysUpTime = mibBuilder.importSymbols(
            '__SNMPv2-MIB', 'snmpTrapOID', 'sysUpTime')

        snmpTrapOID = snmpTrapOID.getName()
        sysUpTime, uptime = sysUpTime.getName(), sysUpTime.getSyntax()

        # Add sysUpTime if not present already
        if not varBinds or varBinds[0][0] != sysUpTime:
            varBinds.insert(0,
                            (v2c.ObjectIdentifier(sysUpTime), uptime.clone()))

        # Search for and reposition sysUpTime if it's elsewhere
        for idx, varBind in enumerate(varBinds[1:]):
            if varBind[0] == sysUpTime:
                varBinds[0] = varBind
                del varBinds[idx + 1]
                break

        if len(varBinds) < 2:
            raise error.PySnmpError('SNMP notification PDU requires '
                                    'SNMPv2-MIB::snmpTrapOID.0 to be present')

        # Search for and reposition snmpTrapOID if it's elsewhere
        for idx, varBind in enumerate(varBinds[2:]):
            if varBind[0] == snmpTrapOID:
                del varBinds[idx + 2]
                if varBinds[1][0] == snmpTrapOID:
                    varBinds[1] = varBind

                else:
                    varBinds.insert(1, varBind)
                break

        if varBinds[1][0] != snmpTrapOID:
            raise error.PySnmpError('SNMP notification PDU requires '
                                    'SNMPv2-MIB::snmpTrapOID.0 to be present')

        sendRequestHandle = -1

        debug.logger & debug.FLAG_APP and debug.logger(
            'sendVarBinds: final varBinds %s' % (varBinds, ))

        for targetAddrName in config.getTargetNames(snmpEngine, notifyTag):
            (transportDomain, transportAddress, timeout, retryCount,
             params) = config.getTargetAddr(snmpEngine, targetAddrName)

            (messageProcessingModel, securityModel, securityName,
             securityLevel) = config.getTargetParams(snmpEngine, params)

            # 3.3.1 XXX
            # XXX filtering's yet to be implemented
            #             filterProfileName = config.getNotifyFilterProfile(params)

            #             (filterSubtree, filterMask,
            #              filterType) = config.getNotifyFilter(filterProfileName)

            debug.logger & debug.FLAG_APP and debug.logger(
                'sendVarBinds: notificationHandle %s, notifyTag %s yields: '
                'transportDomain %s, transportAddress %r, securityModel %s, '
                'securityName %s, securityLevel %s' %
                (notificationHandle, notifyTag, transportDomain,
                 transportAddress, securityModel, securityName, securityLevel))

            for varName, varVal in varBinds:
                if varName in (sysUpTime, snmpTrapOID):
                    continue

                try:
                    snmpEngine.accessControlModel[self.ACM_ID].isAccessAllowed(
                        snmpEngine, securityModel, securityName, securityLevel,
                        'notify', contextName, varName)

                    debug.logger & debug.FLAG_APP and debug.logger(
                        'sendVarBinds: ACL succeeded for OID %s securityName %s'
                        % (varName, securityName))

                except error.StatusInformation:
                    debug.logger & debug.FLAG_APP and debug.logger(
                        'sendVarBinds: ACL denied access for OID %s securityName %s,'
                        'dropping notification' % (varName, securityName))
                    return

            # 3.3.4
            if notifyType == 1:
                pdu = v2c.SNMPv2TrapPDU()

            elif notifyType == 2:
                pdu = v2c.InformRequestPDU()

            else:
                raise error.ProtocolError('Unknown notify-type %r', notifyType)

            v2c.apiPDU.setDefaults(pdu)
            v2c.apiPDU.setVarBinds(pdu, varBinds)

            # 3.3.5
            try:
                sendRequestHandle = self.sendPdu(
                    snmpEngine, targetAddrName, contextEngineId, contextName,
                    pdu, self.processResponseVarBinds,
                    (notificationHandle, cbFun, cbCtx))

            except error.StatusInformation as exc:
                statusInformation = exc

                debug.logger & debug.FLAG_APP and debug.logger(
                    'sendVarBinds: sendRequestHandle %s: sendPdu() failed '
                    'with %r' % (sendRequestHandle, statusInformation))

                if (notificationHandle not in self.__pendingNotifications or
                        not self.__pendingNotifications[notificationHandle]):

                    if notificationHandle in self.__pendingNotifications:
                        del self.__pendingNotifications[notificationHandle]

                    if cbFun:
                        cbFun(snmpEngine, notificationHandle,
                              statusInformation['errorIndication'], 0, 0, (),
                              cbCtx)

                return notificationHandle

            debug.logger & debug.FLAG_APP and debug.logger(
                'sendVarBinds: notificationHandle %s, sendRequestHandle %s, '
                'timeout %d' %
                (notificationHandle, sendRequestHandle, timeout))

            if notifyType == 2:
                if notificationHandle not in self.__pendingNotifications:
                    self.__pendingNotifications[notificationHandle] = set()
                self.__pendingNotifications[notificationHandle].add(
                    sendRequestHandle)

        debug.logger & debug.FLAG_APP and debug.logger(
            'sendVarBinds: notificationHandle %s, sendRequestHandle %s, '
            'notification(s) sent' % (notificationHandle, sendRequestHandle))

        return notificationHandle
コード例 #11
0
        # Delete duplication
        self.headVars = list(set(self.headVars))
        # Build PDU
        self.reqPDU = v2c.GetBulkRequestPDU()
        v2c.apiBulkPDU.setDefaults(self.reqPDU)
        v2c.apiBulkPDU.setNonRepeaters(self.reqPDU, 0)
        v2c.apiBulkPDU.setMaxRepetitions(self.reqPDU, self.max_repetitions)

        # Cut SNMP request if it is too long
        if len(self.headVars) >= 100:
            self.remaining_tablerow = set(self.headVars[99:])
            self.headVars = self.headVars[:99]

        v2c.apiBulkPDU.setVarBinds(self.reqPDU,
                                   [(v2c.ObjectIdentifier(tuple(int(i) for i in x.split("."))), v2c.null)
                                    for x in sorted(self.headVars)])

        # Build message
        self.reqMsg = v2c.Message()
        v2c.apiMessage.setDefaults(self.reqMsg)
        v2c.apiMessage.setCommunity(self.reqMsg, self.community)
        v2c.apiMessage.setPDU(self.reqMsg, self.reqPDU)
        # Save the time when snmp request start
        self.snmp_request_start_time = time.time()

        # Prepare SNMP Request
        transportDispatcher = AsynsockDispatcher()
        transportDispatcher.registerTransport(udp.domainName,
                                              udp.UdpSocketTransport().openClientMode())
コード例 #12
0
ファイル: oidfilter.py プロジェクト: sharty/snmpfwd
            for line in open(configFile).readlines():
                line = line.strip()

                if not line or line.startswith('#'):
                    continue

                try:
                    skip, begin, end = line.split()

                except ValueError:
                    raise SnmpfwdError('%s: bad configuration syntax: "%s"' %
                                       (PLUGIN_NAME, line))

                try:
                    skip = v2c.ObjectIdentifier(skip)
                    begin = v2c.ObjectIdentifier(begin)
                    end = v2c.ObjectIdentifier(end)

                except Exception:
                    raise SnmpfwdError('%s: malformed OID %s/%s/%s' %
                                       (PLUGIN_NAME, skip, begin, end))

                oidsList.append((skip, begin, end))

            oidsList.sort(key=lambda x: x[0])

            idx = 0
            while idx < len(oidsList):
                skip, begin, end = oidsList[idx]
                if skip >= begin:
コード例 #13
0
# Error/confirmation receiver
# noinspection PyUnusedLocal,PyUnusedLocal,PyUnusedLocal,PyUnusedLocal,PyUnusedLocal
def cbFun(snmpEngine, sendRequestHandle, errorIndication, errorStatus,
          errorIndex, varBinds, cbCtx):
    print('Notification %s, status - %s' %
          (sendRequestHandle, errorIndication and errorIndication
           or 'delivered'))


# Build and submit notification message to dispatcher
sendRequestHandle = ntfOrg.sendVarBinds(
    snmpEngine,
    'my-notification',  # notification targets
    None,
    '',  # contextEngineId, contextName
    # var-binds
    [
        # SNMPv2-SMI::snmpTrapOID.0 = SNMPv2-MIB::coldStart
        ((1, 3, 6, 1, 6, 3, 1, 1, 4, 1, 0),
         v2c.ObjectIdentifier((1, 3, 6, 1, 6, 3, 1, 1, 5, 1))),
        # additional var-binds: ( (oid, value), ... )
        ((1, 3, 6, 1, 2, 1, 1, 1, 0), v2c.OctetString('Example Notificator')),
        ((1, 3, 6, 1, 2, 1, 1, 5, 0), v2c.OctetString('Notificator Example'))
    ],
    cbFun)

print('Notification %s scheduled to be sent' % sendRequestHandle)

# Run I/O dispatcher which would send pending message and process response
snmpEngine.transportDispatcher.runDispatcher()
コード例 #14
0
ファイル: send-custom-pdu.py プロジェクト: nrolans/pysnmp
    snmpEngine, 'my-nms',
    udp.domainName, ('195.218.195.228', 162),
    'my-creds'
)

# *** SNMP engine configuration is complete by this line ***

# Create SNMP v2c TRAP PDU with defaults
trapPDU = v2c.TrapPDU()
v2c.apiTrapPDU.setDefaults(trapPDU)

# Set custom var-binds to TRAP PDU
v2c.apiTrapPDU.setVarBinds(
    trapPDU, [
        # sysUpTime
        (v2c.ObjectIdentifier('1.3.6.1.2.1.1.3.0'), v2c.TimeTicks(123)),
        # snmpTrapPDU
        ((1, 3, 6, 1, 6, 3, 1, 1, 4, 1, 0), v2c.ObjectIdentifier((1, 3, 6, 1, 6, 3, 1, 1, 5, 1)))
    ]
)

# Create Notification Originator App instance. 
ntfOrg = ntforg.NotificationOriginator()


# Error/confirmation receiver
# noinspection PyUnusedLocal,PyUnusedLocal,PyUnusedLocal,PyUnusedLocal,PyUnusedLocal
def cbFun(snmpEngine, sendRequestHandle, errorIndication,
          errorStatus, errorIndex, varBinds, cbCtx):
    print('Notification %s, status - %s' % (
        sendRequestHandle, errorIndication and errorIndication or 'delivered'
コード例 #15
0
ファイル: rfc2576.py プロジェクト: jordonTian/pysnmp
def v1ToV2(v1Pdu, origV2Pdu=None, snmpTrapCommunity=''):
    pduType = v1Pdu.tagSet
    v2Pdu = V1_TO_V2_PDU_MAP[pduType].clone()

    debug.logger & debug.FLAG_PRX and debug.logger(
        'v1ToV2: v1Pdu %s' % v1Pdu.prettyPrint())

    v2VarBinds = []

    # 3.1
    if pduType in rfc3411.NOTIFICATION_CLASS_PDUS:
        # 3.1.1
        sysUpTime = v1.apiTrapPDU.getTimeStamp(v1Pdu)

        # 3.1.2
        genericTrap = v1.apiTrapPDU.getGenericTrap(v1Pdu)
        if genericTrap == 6:
            snmpTrapOIDParam = (v1.apiTrapPDU.getEnterprise(v1Pdu) +
                                (0, int(v1.apiTrapPDU.getSpecificTrap(v1Pdu))))

        # 3.1.3
        else:
            snmpTrapOIDParam = v2c.ObjectIdentifier(V1_TO_V2_TRAP_MAP[genericTrap])

        # 3.1.4
        v2VarBinds.append(
            (v2c.apiTrapPDU.sysUpTime, sysUpTime))
        v2VarBinds.append(
            (v2c.apiTrapPDU.snmpTrapOID, snmpTrapOIDParam))
        v2VarBinds.append(
            (v2c.apiTrapPDU.snmpTrapAddress, v1.apiTrapPDU.getAgentAddr(v1Pdu)))
        v2VarBinds.append(
            (v2c.apiTrapPDU.snmpTrapCommunity, v2c.OctetString(snmpTrapCommunity)))
        v2VarBinds.append(
            (v2c.apiTrapPDU.snmpTrapEnterprise, v1.apiTrapPDU.getEnterprise(v1Pdu)))

        varBinds = v1.apiTrapPDU.getVarBinds(v1Pdu)

    else:
        varBinds = v1.apiPDU.getVarBinds(v1Pdu)

    # Translate Var-Binds
    for oid, v1Val in varBinds:
        # 2.1.1.11
        if v1Val.tagSet == v1.NetworkAddress.tagSet:
            v1Val = v1Val.getComponent()

        v2VarBinds.append(
            (oid, V1_TO_V2_VALUE_MAP[v1Val.tagSet].clone(v1Val)))

    if pduType in rfc3411.RESPONSE_CLASS_PDUS:
        # 4.1.2.2.1&2
        errorStatus = int(v1.apiPDU.getErrorStatus(v1Pdu))
        errorIndex = int(v1.apiPDU.getErrorIndex(v1Pdu, muteErrors=True))

        if errorStatus == 2:  # noSuchName
            if origV2Pdu.tagSet == v2c.GetNextRequestPDU.tagSet:
                v2VarBinds = [(o, rfc1905.endOfMibView) for o, v in v2VarBinds]

            else:
                v2VarBinds = [(o, rfc1905.noSuchObject) for o, v in v2VarBinds]

        # partial one-to-one mapping - 4.2.1
        v2c.apiPDU.setErrorStatus(v2Pdu, errorStatus)
        v2c.apiPDU.setErrorIndex(v2Pdu, errorIndex)

        # 4.1.2.1 --> no-op

    elif pduType in rfc3411.CONFIRMED_CLASS_PDUS:
        v2c.apiPDU.setErrorStatus(v2Pdu, 0)
        v2c.apiPDU.setErrorIndex(v2Pdu, 0)

    if pduType not in rfc3411.NOTIFICATION_CLASS_PDUS:
        v2c.apiPDU.setRequestID(v2Pdu, int(v1.apiPDU.getRequestID(v1Pdu)))

    v2c.apiPDU.setVarBinds(v2Pdu, v2VarBinds)

    debug.logger & debug.FLAG_PRX and debug.logger(
        'v1ToV2: v2Pdu %s' % v2Pdu.prettyPrint())

    return v2Pdu
コード例 #16
0
def sendTheTrap():
    uptime = getUptime()
    # Create SNMP engine instance with specific (and locally unique)
    # SnmpEngineId -- it must also be known to the receiving party
    # and configured at its VACM users table.
    snmpEngine = engine.SnmpEngine(snmpEngineID=v2c.OctetString(
        hexValue='0102030405060708'))

    # Add USM user
    config.addV3User(snmpEngine, userConfig['DEFAULT']['SNMPUSER'],
                     config.usmHMAC128SHA224AuthProtocol,
                     userConfig['DEFAULT']['SNMPAUTH'],
                     config.usmAesCfb192Protocol,
                     userConfig['DEFAULT']['SNMPPRIV'])

    config.addTargetParams(snmpEngine, userConfig['DEFAULT']['SNMPAUTH'],
                           userConfig['DEFAULT']['SNMPUSER'], 'authPriv')

    # Setup transport endpoint and bind it with security settings yielding
    # a target name
    config.addTransport(snmpEngine, udp.domainName,
                        udp.UdpSocketTransport().openClientMode())

    config.addTargetAddr(snmpEngine,
                         'my-nms',
                         udp.domainName,
                         (userConfig['DEFAULT']['SNMPMANAGERIP'],
                          int(userConfig['DEFAULT']['SNMPMANAGERPORT'])),
                         userConfig['DEFAULT']['SNMPAUTH'],
                         tagList='all-my-managers')

    # Specify what kind of notification should be sent (TRAP or INFORM),
    # to what targets (chosen by tag) and what filter should apply to
    # the set of targets (selected by tag)
    config.addNotificationTarget(snmpEngine, 'my-notification', 'my-filter',
                                 'all-my-managers', 'trap')

    # Allow NOTIFY access to Agent's MIB by this SNMP model (3), securityLevel
    # and SecurityName
    config.addContext(snmpEngine, '')
    config.addVacmUser(snmpEngine, 3, userConfig['DEFAULT']['SNMPUSER'],
                       'authPriv', (), (), (1, 3, 6), 'aContextName')

    # *** SNMP engine configuration is complete by this line ***

    # Create Notification Originator App instance.
    ntfOrg = ntforg.NotificationOriginator()

    # Build and submit notification message to dispatcher
    ntfOrg.sendVarBinds(
        snmpEngine,
        # Notification targets
        'my-notification',  # notification targets
        None,
        'aContextName',  # contextEngineId, contextName
        # var-binds
        [((1, 3, 6, 1, 2, 1, 1, 3, 0), v2c.OctetString(uptime)),
         ((1, 3, 6, 1, 6, 3, 1, 1, 4, 1, 0),
          v2c.ObjectIdentifier((1, 3, 6, 1, 6, 3, 1, 1, 5, 1))),
         ((1, 3, 6, 1, 2, 1, 1, 5, 0), v2c.OctetString(socket.getfqdn())),
         ((1, 3, 6, 1, 4, 1, 6876, 4, 50, 1, 2, 10, 0),
          v2c.OctetString('Application')),
         ((1, 3, 6, 1, 4, 1, 6876, 4, 50, 1, 2, 11, 0),
          v2c.OctetString('Performance')),
         ((1, 3, 6, 1, 4, 1, 6876, 4, 50, 1, 2, 12, 0),
          v2c.OctetString('critical')),
         ((1, 3, 6, 1, 4, 1, 6876, 4, 50, 1, 2, 19, 0),
          v2c.OctetString('health')),
         ((1, 3, 6, 1, 4, 1, 6876, 4, 50, 1, 2, 20, 0),
          v2c.OctetString('vROpsExternalMonitorService.py')),
         ((1, 3, 6, 1, 4, 1, 6876, 4, 50, 1, 2, 50, 0),
          v2c.OctetString(
              'vROps services are having issues, please check nodes'))])

    print('Notification is scheduled to be sent')

    # Run I/O dispatcher which would send pending message and process response
    snmpEngine.transportDispatcher.runDispatcher()
コード例 #17
0
    def sendNotification(self,
                         snmpEngine,
                         notificationTarget,
                         notificationName,
                         additionalVarBinds=(),
                         cbFun=None,
                         cbCtx=None,
                         contextName=null,
                         instanceIndex=None):
        debug.logger & debug.flagApp and debug.logger(
            'sendNotification: notificationTarget %s, notificationName %s, additionalVarBinds %s, contextName "%s", instanceIndex %s'
            % (notificationTarget, notificationName, additionalVarBinds,
               contextName, instanceIndex))

        if contextName:
            __SnmpAdminString, = snmpEngine.msgAndPduDsp.mibInstrumController.mibBuilder.importSymbols(
                'SNMP-FRAMEWORK-MIB', 'SnmpAdminString')
            contextName = __SnmpAdminString(contextName)

        # 3.3
        (notifyTag,
         notifyType) = config.getNotificationInfo(snmpEngine,
                                                  notificationTarget)

        metaSendPduHandle = getNextHandle()

        debug.logger & debug.flagApp and debug.logger(
            'sendNotification: metaSendPduHandle %s, notifyTag %s, notifyType %s'
            % (metaSendPduHandle, notifyTag, notifyType))

        contextMibInstrumCtl = self.snmpContext.getMibInstrum(contextName)

        additionalVarBinds = [(v2c.ObjectIdentifier(x), y)
                              for x, y in additionalVarBinds]

        for targetAddrName in config.getTargetNames(snmpEngine, notifyTag):
            (transportDomain, transportAddress, timeout, retryCount,
             params) = config.getTargetAddr(snmpEngine, targetAddrName)
            (messageProcessingModel, securityModel, securityName,
             securityLevel) = config.getTargetParams(snmpEngine, params)

            debug.logger & debug.flagApp and debug.logger(
                'sendNotification: metaSendPduHandle %s, notifyTag %s yields: transportDomain %s, transportAddress %r, securityModel %s, securityName %s, securityLevel %s'
                %
                (metaSendPduHandle, notifyTag, transportDomain,
                 transportAddress, securityModel, securityName, securityLevel))

            # 3.3.1 XXX
            # XXX filtering's yet to be implemented
            #             filterProfileName = config.getNotifyFilterProfile(params)

            #             ( filterSubtree,
            #               filterMask,
            #               filterType ) = config.getNotifyFilter(filterProfileName)

            varBinds = []

            # 3.3.2 & 3.3.3
            sysUpTime, = snmpEngine.msgAndPduDsp.mibInstrumController.mibBuilder.importSymbols(
                '__SNMPv2-MIB', 'sysUpTime')

            for varName, varVal in additionalVarBinds:
                if varName == sysUpTime.name:
                    varBinds.append((varName, varVal))
                    break
            if not varBinds:
                varBinds.append((sysUpTime.name,
                                 sysUpTime.syntax.clone()))  # for actual value

            snmpTrapOid, = snmpEngine.msgAndPduDsp.mibInstrumController.mibBuilder.importSymbols(
                '__SNMPv2-MIB', 'snmpTrapOID')
            if len(notificationName) == 2:  # ('MIB', 'symbol')
                notificationTypeObject, = contextMibInstrumCtl.mibBuilder.importSymbols(
                    *notificationName)
                varBinds.append(
                    (snmpTrapOid.name,
                     v2c.ObjectIdentifier(notificationTypeObject.name)))
                debug.logger & debug.flagApp and debug.logger(
                    'sendNotification: notification type object is %s' %
                    notificationTypeObject)
                for notificationObject in notificationTypeObject.getObjects():
                    mibNode, = contextMibInstrumCtl.mibBuilder.importSymbols(
                        *notificationObject)
                    if instanceIndex:
                        mibNode = mibNode.getNode(mibNode.name + instanceIndex)
                    else:
                        mibNode = mibNode.getNextNode(mibNode.name)
                    varBinds.append((mibNode.name, mibNode.syntax))
                    debug.logger & debug.flagApp and debug.logger(
                        'sendNotification: processed notification object %s, instance index %s, var-bind %s'
                        % (notificationObject, instanceIndex is None
                           and "<first>" or instanceIndex, mibNode))
            elif notificationName:  # numeric OID
                varBinds.append((snmpTrapOid.name,
                                 snmpTrapOid.syntax.clone(notificationName)))
            else:
                varBinds.append((snmpTrapOid.name, snmpTrapOid.syntax))

            for varName, varVal in additionalVarBinds:
                if varName in (sysUpTime.name, snmpTrapOid.name):
                    continue
                try:
                    snmpEngine.accessControlModel[self.acmID].isAccessAllowed(
                        snmpEngine, securityModel, securityName, securityLevel,
                        'notify', contextName, varName)
                except error.StatusInformation:
                    debug.logger & debug.flagApp and debug.logger(
                        'sendNotification: OID %s not allowed for %s, droppping notification'
                        % (varName, securityName))
                    return
                else:
                    varBinds.append((varName, varVal))

            # 3.3.4
            if notifyType == 1:
                pdu = v2c.SNMPv2TrapPDU()
            elif notifyType == 2:
                pdu = v2c.InformRequestPDU()
            else:
                raise RuntimeError()
            v2c.apiPDU.setDefaults(pdu)
            v2c.apiPDU.setVarBinds(pdu, varBinds)

            # User-side API assumes SMIv2
            if messageProcessingModel == 0:
                reqPDU = rfc2576.v2ToV1(pdu)
                pduVersion = 0
            else:
                reqPDU = pdu
                pduVersion = 1

            # 3.3.5
            if notifyType == 1:
                try:
                    snmpEngine.msgAndPduDsp.sendPdu(
                        snmpEngine, transportDomain, transportAddress,
                        messageProcessingModel, securityModel, securityName,
                        securityLevel, self.snmpContext.contextEngineId,
                        contextName, pduVersion, reqPDU, None)
                except error.StatusInformation:
                    statusInformation = sys.exc_info()[1]
                    debug.logger & debug.flagApp and debug.logger(
                        'sendReq: metaSendPduHandle %s: sendPdu() failed with %r'
                        % (metaSendPduHandle, statusInformation))
                    if metaSendPduHandle not in self.__pendingNotifications or \
                            not self.__pendingNotifications[metaSendPduHandle]:
                        if metaSendPduHandle in self.__pendingNotifications:
                            del self.__pendingNotifications[metaSendPduHandle]
                        self._handleResponse(
                            metaSendPduHandle,
                            statusInformation['errorIndication'], 0, 0, (),
                            cbFun, cbCtx)
                    return metaSendPduHandle
            else:
                # Convert timeout in seconds into timeout in timer ticks
                timeoutInTicks = float(
                    timeout
                ) / 100 / snmpEngine.transportDispatcher.getTimerResolution()

                # 3.3.6a
                try:
                    sendPduHandle = snmpEngine.msgAndPduDsp.sendPdu(
                        snmpEngine,
                        transportDomain,
                        transportAddress,
                        messageProcessingModel,
                        securityModel,
                        securityName,
                        securityLevel,
                        self.snmpContext.contextEngineId,
                        contextName,
                        pduVersion,
                        reqPDU,
                        1,  # expectResponse
                        timeoutInTicks,
                        self.processResponsePdu,
                        (cbFun, cbCtx))
                except error.StatusInformation:
                    statusInformation = sys.exc_info()[1]
                    debug.logger & debug.flagApp and debug.logger(
                        'sendReq: metaSendPduHandle %s: sendPdu() failed with %r'
                        % (metaSendPduHandle, statusInformation))
                    if metaSendPduHandle not in self.__pendingNotifications or \
                            not self.__pendingNotifications[metaSendPduHandle]:
                        if metaSendPduHandle in self.__pendingNotifications:
                            del self.__pendingNotifications[metaSendPduHandle]
                        self._handleResponse(
                            metaSendPduHandle,
                            statusInformation['errorIndication'], 0, 0, (),
                            cbFun, cbCtx)
                    return metaSendPduHandle

                debug.logger & debug.flagApp and debug.logger(
                    'sendNotification: metaSendPduHandle %s, sendPduHandle %s, timeout %d'
                    % (metaSendPduHandle, sendPduHandle, timeout))

                # 3.3.6b
                self.__pendingReqs[sendPduHandle] = (
                    transportDomain, transportAddress, messageProcessingModel,
                    securityModel, securityName, securityLevel,
                    self.snmpContext.contextEngineId, contextName, pdu,
                    timeout, retryCount, 1, metaSendPduHandle)

                if metaSendPduHandle not in self.__pendingNotifications:
                    self.__pendingNotifications[metaSendPduHandle] = 0
                self.__pendingNotifications[metaSendPduHandle] += 1

                snmpEngine.transportDispatcher.jobStarted(id(self))

        debug.logger & debug.flagApp and debug.logger(
            'sendNotification: metaSendPduHandle %s, notification(s) sent' %
            metaSendPduHandle)

        return metaSendPduHandle
コード例 #18
0
    def callback(self, transportDispatcher, transportDomain, transportAddress,
                 wholeMsg, reqPDU=None, headVars=None):
        """ Callback function called when SNMP answer arrives """
        aBP = v2c.apiBulkPDU
        # Get PDU
        if reqPDU:
            self.reqPDU = reqPDU
        # Get headVars (OID list)
        if headVars:
            self.headVars = headVars

        while wholeMsg:
            # Do some stuff to read SNMP anser
            self.rspMsg, wholeMsg = decoder.decode(wholeMsg,
                                                   asn1Spec=v2c.Message())
            self.rspPDU = v2c.apiMessage.getPDU(self.rspMsg)
            if aBP.getRequestID(self.reqPDU) == aBP.getRequestID(self.rspPDU):
                # Check for SNMP errors reported
                errorStatus = aBP.getErrorStatus(self.rspPDU)
                if errorStatus and errorStatus != 2:
                    logger.error('[SnmpBooster] SNMP Request error 2: %s' % str(errorStatus))
                    self.set_exit("SNMP Request error 2: " + str(errorStatus), rc=3)
                    return wholeMsg
                # Format var-binds table
                varBindTable = aBP.getVarBindTable(self.reqPDU, self.rspPDU)
                # Initialize mapping_instance dict
                mapping_instance = {}
                # Read datas from the anser
                for tableRow in varBindTable:
                    # TODO: MAYBE: Check if the current 'tableRow' is in the list of the
                    # need tables. If NOT, maybe we can jump the current 'tableRow' ?? (continue)

                    # Read all oid in the 'tableRow'
                    for oid, val in tableRow:
                        # Clean the oid
                        oid = "." + oid.prettyPrint()

                        # Check what kind of datas we have
                        if oid in self.oids_waiting_values:
                            # Standard datas
                            # Get value and save it in the result dict
                            self.results_oid_dict[oid] = str(val)
                        elif any([oid.startswith(m_oid + ".") for m_oid in self.mapping_oids]):
                            # Mapping datas
                            # TODO: Need more detail
                            for m_oid in self.mapping_oids:
                                if oid.startswith(m_oid + "."):
                                    instance = oid.replace(m_oid + ".", "")
                                    val = re.sub("[,:/ ]", "_", str(val))
                                    mapping_instance[val] = instance
                        elif oid in self.limit_oids:
                            # get limits => What is a limit ????????????
                            try:
                                self.results_limits_dict[oid] = float(val)
                            except ValueError:
                                logger.error('[SnmpBooster] Bad limit for '
                                             'oid: %s - Skipping' % str(oid))
                        else:
                            # The current oid is not needed
                            pass

                # IF the mapping is done, we can look for OID values
                if self.mapping_done:
                    # Get all OIDS that we want datas
                    oids = set(self.oids_waiting_values.keys() + self.limit_oids.keys())
                    # Get all OIDS that we have datas
                    results_oids = set(self.results_oid_dict.keys() +
                                       self.results_limits_dict.keys())
                    # Get all OIDS which have not datas YET
                    self.remaining_oids = oids - results_oids


                    # We have to determinate which OIDs we need to ask,
                    # to get the datas for our wanted OIDs...
                    tableRow = []
                    for oid in self.remaining_oids:
                        # For all current OIDs, we need to get the previous OID
                        # But if in the current OID is last number is 0
                        # We get the parent table
                        if int(oid.rsplit(".", 1)[1]) - 1 >= 0:
                            # Get previous oid here
                            tableRow.append(oid[1:].rsplit(".", 1)[0] +
                                            "." +
                                            str(int(oid[1:].rsplit(".", 1)[1]) - 1))
                        else:
                            # Get parent table here
                            tableRow.append(oid[1:].rsplit(".", 1)[0])

                    # We need to get more OIDs (the request ask more than 100 oids)
                    # - From the __init__ function
                    #   => We didn't query all needed oids YET
                    # - From "oids != results_oids"
                    #   => Some OIDs doesn't have value, so probably the table
                    #      that we queried is long (more than 100 children)
                    if len(self.remaining_tablerow) > 0:
                        # SNMP BULK is limited to 100 OIDs in same request
                        if len(self.remaining_tablerow) >= 100:
                            oids_to_check = [self.remaining_tablerow.pop() for x in xrange(99)]
                        else:
                            oids_to_check = self.remaining_tablerow
                            self.remaining_tablerow = set()
                        # Prepare request to get nest OIDs
                        aBP.setVarBinds(self.reqPDU,
                                        [(x, v2c.null) for x in oids_to_check])
                        aBP.setRequestID(self.reqPDU, v2c.getNextRequestID())
                        transportDispatcher.sendMessage(encoder.encode(self.reqMsg),
                                                        transportDomain,
                                                        transportAddress)
                        # Count the number of requests done for one host/frequency couple
                        self.nb_next_requests = self.nb_next_requests + 1
                        return wholeMsg

                    # Some oids doesn't have any value (oids != results_oids)
                    # We make a new request to get this values
                    if oids != results_oids and self.nb_next_requests < 5:
                        # SNMP BULK is limited to 100 OIDs in same request
                        if len(tableRow) >= 100:
                            # Add missing oid to self.remaining_tablerow
                            # This oids will be checked in a few requests
                            # Here : "if len(self.remaining_tablerow) > 0:"
                            self.remaining_tablerow.update(set(tableRow[99:]))
                            tableRow = tableRow[:99]

                        aBP.setVarBinds(self.reqPDU,
                                        [(v2c.ObjectIdentifier(x), v2c.null) for x in tableRow])
                        aBP.setRequestID(self.reqPDU, v2c.getNextRequestID())
                        transportDispatcher.sendMessage(encoder.encode(self.reqMsg),
                                                        transportDomain,
                                                        transportAddress)
                        self.nb_next_requests = self.nb_next_requests + 1
                        return wholeMsg

                # LOCKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKK
                try:
                    # Get OID from memcache
                    self.obj = self.memcached.get(self.obj_key)
                except ValueError, e:
                    logger.error('[SnmpBooster] Memcached error while getting: `%s' % self.obj_key)
                    self.set_exit("Memcached error: `%s'"
                                  % self.memcached.get(self.obj_key),
                                  3, transportDispatcher)
                    return wholeMsg

                self.obj.frequences[self.check_interval].old_check_time = copy.copy(self.obj.frequences[self.check_interval].check_time)
                self.obj.frequences[self.check_interval].check_time = self.start_time

                # We have to do the mapping instance
                if not self.mapping_done:
                    # TODO: need more documentation
                    self.obj.instances = mapping_instance

                    self.obj.map_instances(self.check_interval)
                    s = self.obj.frequences[self.check_interval].services[self.serv_key]

                    self.obj.frequences[self.check_interval].checking = False
                    self.memcached.set(self.obj_key, self.obj, time=604800)
                    if s.instance.startswith("map("):
                        result_oids_mapping = set([".%s" % str(o).rsplit(".", 1)[0]
                                                   for t in varBindTable for o, _ in t])
                        if not result_oids_mapping.intersection(set(self.mapping_oids.keys())):
                            s.instance = "NOTFOUND"
                            self.obj.frequences[self.check_interval].checking = False
                            self.memcached.set(self.obj_key, self.obj, time=604800)
                            logger.info("[SnmpBooster] - Instance mapping not found. "
                                        "Please check your config")
                            self.set_exit("%s: Instance mapping not found. "
                                          "Please check your config" % s.instance_name,
                                          3,
                                          transportDispatcher)
                            # Stop if oid not in mappping oidS
                            return

                        # Mapping not finished
                        aBP.setVarBinds(self.reqPDU,
                                        [(x, v2c.null) for x, y in varBindTable[-1]])
                        aBP.setRequestID(self.reqPDU, v2c.getNextRequestID())
                        transportDispatcher.sendMessage(encoder.encode(self.reqMsg),
                                                        transportDomain,
                                                        transportAddress)
                        return wholeMsg

                    logger.info("[SnmpBooster] - Instance mapping completed. "
                                "Expect results at next check")
                    self.set_exit("Instance mapping completed. "
                                  "Expect results at next check",
                                  3,
                                  transportDispatcher)
                    return

                # set Limits
                if not self.limits_done:
                    self.obj.set_limits(self.check_interval,
                                        self.results_limits_dict)
                    self.memcached.set(self.obj_key,
                                       self.obj,
                                       time=604800)

                # Save values
                self.oids_to_check = self.obj.get_oids_by_frequence(self.check_interval)
                for oid, value in self.results_oid_dict.items():
                    if value != None:
                        self.oids_to_check[oid].raw_value = str(value)
                    else:
                        self.oids_to_check[oid].raw_value = None

                # save data
                self.obj.frequences[self.check_interval].checking = False
                self.memcached.set(self.obj_key, self.obj, time=604800)

                # UNLOCKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKK

                if time.time() - self.snmp_request_start_time > self.timeout:
                    self.set_exit("SNMP Request timed out",
                                  3,
                                  transportDispatcher)
                #return wholeMsg

                self.snmp_request_start_time = time.time()
コード例 #19
0
    def _setup(self, q):
        """Setup a new agent in a separate process.

        The port the agent is listening too will be returned using the
        provided queue.
        """
        port = random.randrange(22000, 22989)
        snmpEngine = engine.SnmpEngine()
        if self.ipv6:
            config.addSocketTransport(
                snmpEngine, udp6.domainName,
                udp6.Udp6Transport().openServerMode(('::1', port)))
        else:
            config.addSocketTransport(
                snmpEngine, udp.domainName,
                udp.UdpTransport().openServerMode(('127.0.0.1', port)))
        # Community is public and MIB is writable
        config.addV1System(snmpEngine, 'read-write', 'public')
        config.addVacmUser(snmpEngine, 1, 'read-write', 'noAuthNoPriv',
                           (1, 3, 6), (1, 3, 6))
        config.addVacmUser(snmpEngine, 2, 'read-write', 'noAuthNoPriv',
                           (1, 3, 6), (1, 3, 6))
        config.addV3User(snmpEngine, 'read-write',
                         config.usmHMACMD5AuthProtocol, 'authpass',
                         config.usmAesCfb128Protocol, 'privpass')
        config.addVacmUser(snmpEngine, 3, 'read-write', 'authPriv', (1, 3, 6),
                           (1, 3, 6))

        # Build MIB
        def stringToOid(string):
            return [ord(x) for x in string]

        def flatten(*args):
            result = []
            for el in args:
                if isinstance(el, (list, tuple)):
                    for sub in el:
                        result.append(sub)
                else:
                    result.append(el)
            return tuple(result)

        snmpContext = context.SnmpContext(snmpEngine)
        mibBuilder = snmpContext.getMibInstrum().getMibBuilder()
        (MibTable, MibTableRow, MibTableColumn,
         MibScalar, MibScalarInstance) = mibBuilder.importSymbols(
             'SNMPv2-SMI', 'MibTable', 'MibTableRow', 'MibTableColumn',
             'MibScalar', 'MibScalarInstance')
        mibBuilder.exportSymbols(
            '__MY_SNMPv2_MIB',
            # SNMPv2-MIB::sysDescr
            MibScalar((1, 3, 6, 1, 2, 1, 1, 1), v2c.OctetString()),
            MibScalarInstance((1, 3, 6, 1, 2, 1, 1, 1), (0, ),
                              v2c.OctetString("Snimpy Test Agent")))
        mibBuilder.exportSymbols(
            '__MY_IF_MIB',
            # IF-MIB::ifNumber
            MibScalar((1, 3, 6, 1, 2, 1, 2, 1), v2c.Integer()),
            MibScalarInstance((1, 3, 6, 1, 2, 1, 2, 1), (0, ), v2c.Integer(3)),
            # IF-MIB::ifTable
            MibTable((1, 3, 6, 1, 2, 1, 2, 2)),
            MibTableRow((1, 3, 6, 1, 2, 1, 2, 2, 1)).setIndexNames(
                (0, '__MY_IF_MIB', 'ifIndex')),
            # IF-MIB::ifIndex
            MibScalarInstance((1, 3, 6, 1, 2, 1, 2, 2, 1, 1), (1, ),
                              v2c.Integer(1)),
            MibScalarInstance((1, 3, 6, 1, 2, 1, 2, 2, 1, 1), (2, ),
                              v2c.Integer(2)),
            MibScalarInstance((1, 3, 6, 1, 2, 1, 2, 2, 1, 1), (3, ),
                              v2c.Integer(3)),
            # IF-MIB::ifDescr
            MibTableColumn((1, 3, 6, 1, 2, 1, 2, 2, 1, 2), v2c.OctetString()),
            MibScalarInstance((1, 3, 6, 1, 2, 1, 2, 2, 1, 2), (1, ),
                              v2c.OctetString("lo")),
            MibScalarInstance((1, 3, 6, 1, 2, 1, 2, 2, 1, 2), (2, ),
                              v2c.OctetString("eth0")),
            MibScalarInstance((1, 3, 6, 1, 2, 1, 2, 2, 1, 2), (3, ),
                              v2c.OctetString("eth1")),
            # IF-MIB::ifType
            MibTableColumn((1, 3, 6, 1, 2, 1, 2, 2, 1, 3), v2c.Integer()),
            MibScalarInstance((1, 3, 6, 1, 2, 1, 2, 2, 1, 3), (1, ),
                              v2c.Integer(24)),
            MibScalarInstance((1, 3, 6, 1, 2, 1, 2, 2, 1, 3), (2, ),
                              v2c.Integer(6)),
            MibScalarInstance((1, 3, 6, 1, 2, 1, 2, 2, 1, 3), (3, ),
                              v2c.Integer(6)),
            # IF-MIB::ifIndex
            ifIndex=MibTableColumn((1, 3, 6, 1, 2, 1, 2, 2, 1, 1),
                                   v2c.Integer()))
        mibBuilder.exportSymbols(
            '__MY_SNIMPY-MIB',
            # SNIMPY-MIB::snimpyIpAddress
            MibScalar((1, 3, 6, 1, 2, 1, 45121, 1, 1),
                      v2c.OctetString()).setMaxAccess("readwrite"),
            MibScalarInstance((1, 3, 6, 1, 2, 1, 45121, 1, 1), (0, ),
                              v2c.OctetString("AAAA")),
            # SNIMPY-MIB::snimpyString
            MibScalar((1, 3, 6, 1, 2, 1, 45121, 1, 2),
                      v2c.OctetString()).setMaxAccess("readwrite"),
            MibScalarInstance((1, 3, 6, 1, 2, 1, 45121, 1, 2), (0, ),
                              v2c.OctetString("bye")),
            # SNIMPY-MIB::snimpyInteger
            MibScalar((1, 3, 6, 1, 2, 1, 45121, 1, 3),
                      v2c.Integer()).setMaxAccess("readwrite"),
            MibScalarInstance((1, 3, 6, 1, 2, 1, 45121, 1, 3), (0, ),
                              v2c.Integer(19)),
            # SNIMPY-MIB::snimpyEnum
            MibScalar((1, 3, 6, 1, 2, 1, 45121, 1, 4),
                      v2c.Integer()).setMaxAccess("readwrite"),
            MibScalarInstance((1, 3, 6, 1, 2, 1, 45121, 1, 4), (0, ),
                              v2c.Integer(2)),
            # SNIMPY-MIB::snimpyObjectId
            MibScalar((1, 3, 6, 1, 2, 1, 45121, 1, 5),
                      v2c.ObjectIdentifier()).setMaxAccess("readwrite"),
            MibScalarInstance((1, 3, 6, 1, 2, 1, 45121, 1, 5), (0, ),
                              v2c.ObjectIdentifier((1, 3, 6, 4454, 0, 0))),
            # SNIMPY-MIB::snimpyBoolean
            MibScalar((1, 3, 6, 1, 2, 1, 45121, 1, 6),
                      v2c.Integer()).setMaxAccess("readwrite"),
            MibScalarInstance((1, 3, 6, 1, 2, 1, 45121, 1, 6), (0, ),
                              v2c.Integer(1)),
            # SNIMPY-MIB::snimpyCounter
            MibScalar((1, 3, 6, 1, 2, 1, 45121, 1, 7),
                      v2c.Counter32()).setMaxAccess("readwrite"),
            MibScalarInstance((1, 3, 6, 1, 2, 1, 45121, 1, 7), (0, ),
                              v2c.Counter32(47)),
            # SNIMPY-MIB::snimpyGauge
            MibScalar((1, 3, 6, 1, 2, 1, 45121, 1, 8),
                      v2c.Gauge32()).setMaxAccess("readwrite"),
            MibScalarInstance((1, 3, 6, 1, 2, 1, 45121, 1, 8), (0, ),
                              v2c.Gauge32(18)),
            # SNIMPY-MIB::snimpyTimeticks
            MibScalar((1, 3, 6, 1, 2, 1, 45121, 1, 9),
                      v2c.TimeTicks()).setMaxAccess("readwrite"),
            MibScalarInstance((1, 3, 6, 1, 2, 1, 45121, 1, 9), (0, ),
                              v2c.TimeTicks(12111100)),
            # SNIMPY-MIB::snimpyCounter64
            MibScalar((1, 3, 6, 1, 2, 1, 45121, 1, 10),
                      v2c.Counter64()).setMaxAccess("readwrite"),
            MibScalarInstance((1, 3, 6, 1, 2, 1, 45121, 1, 10), (0, ),
                              v2c.Counter64(2**48 + 3)),
            # SNIMPY-MIB::snimpyBits
            MibScalar((1, 3, 6, 1, 2, 1, 45121, 1, 11),
                      v2c.OctetString()).setMaxAccess("readwrite"),
            MibScalarInstance((1, 3, 6, 1, 2, 1, 45121, 1, 11), (0, ),
                              v2c.OctetString(b"\xa0")),
            # SNIMPY-MIB::snimpyMacAddress
            MibScalar((1, 3, 6, 1, 2, 1, 45121, 1, 15),
                      v2c.OctetString()).setMaxAccess("readwrite"),
            MibScalarInstance((1, 3, 6, 1, 2, 1, 45121, 1, 15), (0, ),
                              v2c.OctetString(b"\x11\x12\x13\x14\x15\x16")),
            # SNIMPY-MIB::snimpyMacAddressInvalid
            MibScalar((1, 3, 6, 1, 2, 1, 45121, 1, 16),
                      v2c.OctetString()).setMaxAccess("readwrite"),
            MibScalarInstance((1, 3, 6, 1, 2, 1, 45121, 1, 16), (0, ),
                              v2c.OctetString(b"\xf1\x12\x13\x14\x15\x16")),

            # SNIMPY-MIB::snimpyIndexTable
            MibTable((1, 3, 6, 1, 2, 1, 45121, 2, 3)),
            MibTableRow((1, 3, 6, 1, 2, 1, 45121, 2, 3, 1)).setIndexNames(
                (0, "__MY_SNIMPY-MIB", "snimpyIndexVarLen"),
                (0, "__MY_SNIMPY-MIB", "snimpyIndexOidVarLen"),
                (0, "__MY_SNIMPY-MIB", "snimpyIndexFixedLen"),
                (1, "__MY_SNIMPY-MIB", "snimpyIndexImplied")),
            # SNIMPY-MIB::snimpyIndexInt
            MibScalarInstance((1, 3, 6, 1, 2, 1, 45121, 2, 3, 1, 6),
                              flatten(4, stringToOid('row1'), 3, 1, 2, 3,
                                      stringToOid('alpha5'),
                                      stringToOid('end of row1')),
                              v2c.Integer(4571)),
            MibScalarInstance((1, 3, 6, 1, 2, 1, 45121, 2, 3, 1, 6),
                              flatten(4, stringToOid('row2'), 4, 1, 0, 2, 3,
                                      stringToOid('beta32'),
                                      stringToOid('end of row2')),
                              v2c.Integer(78741)),
            MibScalarInstance((1, 3, 6, 1, 2, 1, 45121, 2, 3, 1, 6),
                              flatten(4, stringToOid('row3'), 4, 120, 1, 2, 3,
                                      stringToOid('gamma7'),
                                      stringToOid('end of row3')),
                              v2c.Integer(4110)),

            # SNIMPY-MIB::snimpyInvalidTable
            MibTable((1, 3, 6, 1, 2, 1, 45121, 2, 5)),
            MibTableRow((1, 3, 6, 1, 2, 1, 45121, 2, 5, 1)).setIndexNames(
                (0, "__MY_SNIMPY-MIB", "snimpyInvalidIndex")),
            # SNIMPY-MIB::snimpyInvalidDescr
            MibScalarInstance((1, 3, 6, 1, 2, 1, 45121, 2, 5, 1, 2), (1, ),
                              v2c.OctetString(b"Hello")),
            MibScalarInstance((1, 3, 6, 1, 2, 1, 45121, 2, 5, 1, 2), (2, ),
                              v2c.OctetString(b"\xf1\x12\x13\x14\x15\x16")),

            # Indexes
            snimpyIndexVarLen=MibTableColumn(
                (1, 3, 6, 1, 2, 1, 45121, 2, 3, 1, 1),
                v2c.OctetString()).setMaxAccess("noaccess"),
            snimpyIndexIntIndex=MibTableColumn(
                (1, 3, 6, 1, 2, 1, 45121, 2, 3, 1, 2),
                v2c.Integer()).setMaxAccess("noaccess"),
            snimpyIndexOidVarLen=MibTableColumn(
                (1, 3, 6, 1, 2, 1, 45121, 2, 3, 1, 3),
                v2c.ObjectIdentifier()).setMaxAccess("noaccess"),
            snimpyIndexFixedLen=MibTableColumn(
                (1, 3, 6, 1, 2, 1, 45121, 2, 3, 1, 4),
                v2c.OctetString().setFixedLength(6)).setMaxAccess("noaccess"),
            snimpyIndexImplied=MibTableColumn(
                (1, 3, 6, 1, 2, 1, 45121, 2, 3, 1, 5),
                v2c.OctetString()).setMaxAccess("noaccess"),
            snimpyIndexInt=MibTableColumn(
                (1, 3, 6, 1, 2, 1, 45121, 2, 3, 1, 6),
                v2c.Integer()).setMaxAccess("readwrite"),
            snimpyInvalidIndex=MibTableColumn(
                (1, 3, 6, 1, 2, 1, 45121, 2, 5, 1, 1),
                v2c.Integer()).setMaxAccess("noaccess"),
            snimpyInvalidDescr=MibTableColumn(
                (1, 3, 6, 1, 2, 1, 45121, 2, 5, 1, 2),
                v2c.OctetString()).setMaxAccess("readwrite"))
        # Start agent
        cmdrsp.GetCommandResponder(snmpEngine, snmpContext)
        cmdrsp.SetCommandResponder(snmpEngine, snmpContext)
        cmdrsp.NextCommandResponder(snmpEngine, snmpContext)
        cmdrsp.BulkCommandResponder(snmpEngine, snmpContext)
        q.put(port)
        snmpEngine.transportDispatcher.jobStarted(1)
        snmpEngine.transportDispatcher.runDispatcher()
コード例 #20
0
ファイル: oidfilter.py プロジェクト: sharty/snmpfwd
def processCommandResponse(pluginId, snmpEngine, pdu, trunkMsg, reqCtx):
    if pdu.tagSet != v2c.GetResponsePDU.tagSet:
        return status.NEXT, pdu

    try:
        reqPdu = reqCtx['req-pdu']
        reqOids = reqCtx['req-oids']

    except KeyError:
        return status.NEXT, pdu

    if reqPdu.tagSet in (v2c.GetRequestPDU.tagSet, v2c.SetRequestPDU.tagSet,
                         v2c.GetNextRequestPDU.tagSet):

        nextCmd = reqPdu.tagSet == v2c.GetNextRequestPDU.tagSet

        rspVarBinds = v2c.apiPDU.getVarBindList(pdu)

        terminatedOids = []
        mutedOids = []

        rspVarBindIdx = 0

        varBinds = v2c.VarBindList()

        for oid, reqVarBindIdx, aclIdx in reqOids:

            if aclIdx is None:
                varBind = v2c.VarBind()

                if nextCmd:
                    v2c.apiVarBind.setOIDVal(varBind, (oid, endOfMibView))
                else:
                    v2c.apiVarBind.setOIDVal(varBind, (oid, noSuchInstance))

            else:
                try:
                    varBind = rspVarBinds[rspVarBindIdx]

                except IndexError:
                    error('%s: missing response OID #%s' %
                          (PLUGIN_NAME, rspVarBindIdx))
                    return status.DROP, pdu

                rspVarBindIdx += 1

                overrideLeakingOid(varBind, aclIdx, mutedOids, terminatedOids)

            varBinds.append(varBind)

        if logDenials and (terminatedOids or mutedOids):
            denialMsg = formatDenialMsg(pdu, trunkMsg)
            if terminatedOids:
                denialMsg += ' ' + 'OID(s) %s replaced with %s and reported as <end-of-mib>' % (
                    ','.join([
                        str(v2c.ObjectIdentifier(x[0])) for x in terminatedOids
                    ]), ','.join([
                        str(v2c.ObjectIdentifier(x[1])) for x in terminatedOids
                    ]))
            if mutedOids:
                denialMsg += ' ' + 'OID(s) %s replaced with %s and reported as <nil>' % (
                    ','.join(
                        [str(v2c.ObjectIdentifier(x[0]))
                         for x in mutedOids]), ','.
                    join([str(v2c.ObjectIdentifier(x[1])) for x in mutedOids]))
            info(denialMsg)

        v2c.apiPDU.setVarBindList(pdu, varBinds)

        return status.NEXT, pdu

    elif reqPdu.tagSet == v2c.GetBulkRequestPDU.tagSet:

        linearizedOidsMap = reqCtx['linearized-oids-map']
        if linearizedOidsMap:
            linearizedColumnDepth = max(
                [x[1] - x[0] for x in linearizedOidsMap.values()])
        else:
            linearizedColumnDepth = 0

        repeatersOidsMap = reqCtx['repeaters-oids-map']

        origNonRepeaters = int(reqCtx['non-repeaters'])
        nonRepeaters = int(v2c.apiBulkPDU.getNonRepeaters(reqPdu))

        reqVarBinds = v2c.apiBulkPDU.getVarBindList(reqPdu)
        rspVarBinds = v2c.apiBulkPDU.getVarBindList(pdu)

        maxColumns = len(reqVarBinds) - nonRepeaters

        if maxColumns:
            columnDepth = (len(rspVarBinds) - nonRepeaters) // maxColumns

        else:
            columnDepth = 0

        if columnDepth < 0:
            error('%s: malformed GETBULK response table' % PLUGIN_NAME)
            return status.DROP, pdu

        maxColumnDepth = max(columnDepth, linearizedColumnDepth)

        nonRepVarBinds = []
        repVarBindTable = []

        terminatedOids = []
        mutedOids = []

        try:

            # Walk over original request var-binds
            for oid, reqVarBindIdx, aclIdx in reqOids:

                # copy over original non-repeaters
                if reqVarBindIdx < origNonRepeaters:
                    # locally terminated var-binds
                    if aclIdx is None:
                        varBind = v2c.VarBind()
                        v2c.apiVarBind.setOIDVal(varBind, (oid, endOfMibView))

                    else:
                        varBind = rspVarBinds[reqVarBindIdx]

                        overrideLeakingOid(varBind, aclIdx, mutedOids,
                                           terminatedOids)

                    nonRepVarBinds.append(varBind)

                    continue

                # process linearized OIDs
                elif reqVarBindIdx in linearizedOidsMap:
                    startIdx, endIdx = linearizedOidsMap[reqVarBindIdx]

                    override = oid

                    repVarBindTable.append([])

                    # move non-repeaters into repeaters as individual columns
                    for rspVarBindIdx in range(startIdx, endIdx):

                        if rspVarBindIdx - startIdx < maxColumnDepth:
                            varBind = rspVarBinds[rspVarBindIdx]

                            override = overrideLeakingOid(
                                varBind, aclIdx, mutedOids, terminatedOids)

                            repVarBindTable[-1].append(varBind)

                            # this assumes that aclIdx grows with endIdx
                            aclIdx += 1

                        else:
                            break

                    # pad insufficient rows
                    insufficientRows = maxColumnDepth - (endIdx - startIdx)

                    while insufficientRows:
                        varBind = v2c.VarBind()
                        v2c.apiVarBind.setOIDVal(varBind, (override, null))
                        repVarBindTable[-1].append(varBind)
                        insufficientRows -= 1

                # copy over original repeaters into individual columns
                elif reqVarBindIdx in repeatersOidsMap:
                    override = oid

                    repVarBindTable.append([])

                    startIdx = repeatersOidsMap[reqVarBindIdx]

                    for row in range(maxColumnDepth):

                        if aclIdx is not None and row < columnDepth:
                            rspVarBindIdx = startIdx + maxColumns * row

                            varBind = rspVarBinds[rspVarBindIdx]

                            override = overrideLeakingOid(
                                varBind, aclIdx, mutedOids, terminatedOids)

                        else:
                            varBind = v2c.VarBind()
                            v2c.apiVarBind.setOIDVal(varBind, (override, null))

                        repVarBindTable[-1].append(varBind)

                else:
                    error('%s: malformed GETBULK state information!' %
                          PLUGIN_NAME)
                    return status.DROP, pdu

        except IndexError:
            error('%s: short GETBULK response PDU' % PLUGIN_NAME)
            return status.DROP, pdu

        if logDenials and (terminatedOids or mutedOids):
            denialMsg = formatDenialMsg(pdu, trunkMsg)
            if terminatedOids:
                denialMsg += ' ' + 'OID(s) %s replaced with %s and reported as <end-of-mib>' % (
                    ','.join([
                        str(v2c.ObjectIdentifier(x[0])) for x in terminatedOids
                    ]), ','.join([
                        str(v2c.ObjectIdentifier(x[1])) for x in terminatedOids
                    ]))
            if mutedOids:
                denialMsg += ' ' + 'OID(s) %s replaced with %s and reported as <nil>' % (
                    ','.join(
                        [str(v2c.ObjectIdentifier(x[0]))
                         for x in mutedOids]), ','.
                    join([str(v2c.ObjectIdentifier(x[1])) for x in mutedOids]))
            info(denialMsg)

        varBinds = v2c.VarBindList()

        for varBind in nonRepVarBinds:
            varBinds.append(varBind)

        for row in range(maxColumnDepth):
            for repVarBinds in repVarBindTable:
                varBinds.append(repVarBinds[row])

        v2c.apiBulkPDU.setVarBindList(pdu, varBinds)

        return status.NEXT, pdu

    else:
        return status.NEXT, pdu
コード例 #21
0
    def sendVarBinds(self,
                     snmpEngine,
                     notificationTarget,
                     contextEngineId,
                     contextName,
                     varBinds=(),
                     cbFun=None,
                     cbCtx=None):
        debug.logger & debug.flagApp and debug.logger('sendVarBinds: notificationTarget %s, contextEngineId %s, contextName "%s", varBinds %s' % (notificationTarget, contextEngineId or '<default>', contextName, varBinds))

        if contextName:
            __SnmpAdminString, = snmpEngine.msgAndPduDsp.mibInstrumController.mibBuilder.importSymbols('SNMP-FRAMEWORK-MIB', 'SnmpAdminString')
            contextName = __SnmpAdminString(contextName)
 
        # 3.3
        ( notifyTag,
          notifyType ) = config.getNotificationInfo(
                snmpEngine, notificationTarget
            )

        notificationHandle = getNextHandle()

        debug.logger & debug.flagApp and debug.logger('sendVarBinds: notificationHandle %s, notifyTag %s, notifyType %s' % (notificationHandle, notifyTag, notifyType))

        varBinds = [  (v2c.ObjectIdentifier(x),y) for x,y in varBinds ]

        # 3.3.2 & 3.3.3
        snmpTrapOID, sysUpTime = snmpEngine.msgAndPduDsp.mibInstrumController.mibBuilder.importSymbols('__SNMPv2-MIB', 'snmpTrapOID', 'sysUpTime')

        for idx in range(len(varBinds)):
            if idx and varBinds[idx][0] == sysUpTime.getName():
                if varBinds[0][0] == sysUpTime.getName():
                    varBinds[0] = varBinds[idx]
                else:
                    varBinds.insert(0, varBinds[idx])
                    del varBinds[idx]

            if varBinds[0][0] != sysUpTime.getName():
                varBinds.insert(0, (v2c.ObjectIdentifier(sysUpTime.getName()),
                                    sysUpTime.getSyntax().clone()))

        if len(varBinds) < 2 or varBinds[1][0] != snmpTrapOID.getName():
            varBinds.insert(1, (v2c.ObjectIdentifier(snmpTrapOID.getName()),
                                snmpTrapOID.getSyntax()))

        debug.logger & debug.flagApp and debug.logger('sendVarBinds: final varBinds %s' % (varBinds,))

        for targetAddrName in config.getTargetNames(snmpEngine, notifyTag):
            ( transportDomain,
              transportAddress,
              timeout,
              retryCount,
              params ) = config.getTargetAddr(snmpEngine, targetAddrName)
            ( messageProcessingModel,
              securityModel,
              securityName,
              securityLevel ) = config.getTargetParams(snmpEngine, params)

            # 3.3.1 XXX
# XXX filtering's yet to be implemented
#             filterProfileName = config.getNotifyFilterProfile(params)

#             ( filterSubtree,
#               filterMask,
#               filterType ) = config.getNotifyFilter(filterProfileName)

            debug.logger & debug.flagApp and debug.logger('sendVarBinds: notificationHandle %s, notifyTag %s yields: transportDomain %s, transportAddress %r, securityModel %s, securityName %s, securityLevel %s' % (notificationHandle, notifyTag, transportDomain, transportAddress, securityModel, securityName, securityLevel))

            for varName, varVal in varBinds:
                if varName in (sysUpTime.name, snmpTrapOID.name):
                    continue
                try:
                    snmpEngine.accessControlModel[self.acmID].isAccessAllowed(
                        snmpEngine, securityModel, securityName,
                        securityLevel, 'notify', contextName, varName
                        )

                    debug.logger & debug.flagApp and debug.logger('sendVarBinds: ACL succeeded for OID %s securityName %s' % (varName, securityName))

                except error.StatusInformation:
                    debug.logger & debug.flagApp and debug.logger('sendVarBinds: ACL denied access for OID %s securityName %s, droppping notification' % (varName, securityName))
                    return

            # 3.3.4
            if notifyType == 1:
                pdu = v2c.SNMPv2TrapPDU()
            elif notifyType == 2:
                pdu = v2c.InformRequestPDU()
            else:
                raise error.ProtocolError('Unknown notify-type %r', notifyType)
            
            v2c.apiPDU.setDefaults(pdu)
            v2c.apiPDU.setVarBinds(pdu, varBinds)

            # 3.3.5
            try:
                sendRequestHandle = self.sendPdu(snmpEngine,
                                                 targetAddrName,
                                                 contextEngineId,
                                                 contextName,
                                                 pdu,
                                                 self.processResponseVarBinds,
                                                 (notificationHandle, 
                                                  cbFun, cbCtx))
                
            except error.StatusInformation:
                statusInformation = sys.exc_info()[1]
                debug.logger & debug.flagApp and debug.logger('sendVarBinds: sendRequestHandle %s: sendPdu() failed with %r' % (sendRequestHandle, statusInformation))
                if notificationHandle not in self.__pendingNotifications or \
                       not self.__pendingNotifications[notificationHandle]:
                    if notificationHandle in self.__pendingNotifications:
                        del self.__pendingNotifications[notificationHandle]
                    cbFun(snmpEngine,
                          notificationHandle,
                          statusInformation['errorIndication'],
                          0, 0, (), cbCtx)
                return notificationHandle

            debug.logger & debug.flagApp and debug.logger('sendVarBinds: notificationHandle %s, sendRequestHandle %s, timeout %d' % (notificationHandle, sendRequestHandle, timeout))

            if notifyType == 2:
                if notificationHandle not in self.__pendingNotifications:
                    self.__pendingNotifications[notificationHandle] = set()
                self.__pendingNotifications[notificationHandle].add(sendRequestHandle)

        debug.logger & debug.flagApp and debug.logger('sendVarBinds: notificationHandle %s, sendRequestHandle %s, notification(s) sent' % (notificationHandle, sendRequestHandle))

        return notificationHandle
コード例 #22
0
* for OID in tuple form
* with non-repeaters=0 and max-repeaters=25

This script performs similar to the following Net-SNMP command:

| $ snmpbulkwalk -v2c -c public -ObentU -Cn0 -Cr25 demo.snmplabs.com 1.3.6

"""#
from pysnmp.carrier.asyncore.dispatch import AsyncoreDispatcher
from pysnmp.carrier.asyncore.dgram import udp
from pyasn1.codec.ber import encoder, decoder
from pysnmp.proto.api import v2c
from time import time

# SNMP table header
headVars = [v2c.ObjectIdentifier((1, 3, 6))]

# Build PDU
reqPDU = v2c.GetBulkRequestPDU()
v2c.apiBulkPDU.setDefaults(reqPDU)
v2c.apiBulkPDU.setNonRepeaters(reqPDU, 0)
v2c.apiBulkPDU.setMaxRepetitions(reqPDU, 25)
v2c.apiBulkPDU.setVarBinds(reqPDU, [(x, v2c.null) for x in headVars])

# Build message
reqMsg = v2c.Message()
v2c.apiMessage.setDefaults(reqMsg)
v2c.apiMessage.setCommunity(reqMsg, 'public')
v2c.apiMessage.setPDU(reqMsg, reqPDU)

startedAt = time()