diff --git a/scapy/asn1/asn1.py b/scapy/asn1/asn1.py index 0df885ad911c921e36457682b245cbba73d51d13..c8c42f72d40ffe74382809d30bdf1f7a630b3549 100644 --- a/scapy/asn1/asn1.py +++ b/scapy/asn1/asn1.py @@ -159,6 +159,7 @@ class ASN1_Class_UNIVERSAL(ASN1_Class): UNIVERSAL_STRING = 28 CHAR_STRING = 29 BMP_STRING = 30 + IPADDRESS = 0x40 COUNTER32 = 0x41 TIME_TICKS = 0x43 @@ -239,6 +240,9 @@ class ASN1_NUMERIC_STRING(ASN1_STRING): class ASN1_VIDEOTEX_STRING(ASN1_STRING): tag = ASN1_Class_UNIVERSAL.VIDEOTEX_STRING +class ASN1_IPADDRESS(ASN1_STRING): + tag = ASN1_Class_UNIVERSAL.IPADDRESS + class ASN1_UTC_TIME(ASN1_STRING): tag = ASN1_Class_UNIVERSAL.UTC_TIME diff --git a/scapy/asn1/ber.py b/scapy/asn1/ber.py index a74aa6c94b0ee7963159c7ebabfda09d5018dd7f..b567eababda33203f641e15330b6ea6f6912a0e8 100644 --- a/scapy/asn1/ber.py +++ b/scapy/asn1/ber.py @@ -4,7 +4,7 @@ ## This program is published under a GPLv2 license from scapy.error import warning -from asn1 import ASN1_Decoding_Error,ASN1_BadTag_Decoding_Error,ASN1_Codecs,ASN1_Class_UNIVERSAL,ASN1_Error,ASN1_DECODING_ERROR,ASN1_BADTAG +from asn1 import ASN1_Decoding_Error,ASN1_Encoding_Error,ASN1_BadTag_Decoding_Error,ASN1_Codecs,ASN1_Class_UNIVERSAL,ASN1_Error,ASN1_DECODING_ERROR,ASN1_BADTAG ################## ## BER encoding ## @@ -18,6 +18,20 @@ from asn1 import ASN1_Decoding_Error,ASN1_BadTag_Decoding_Error,ASN1_Codecs,ASN1 class BER_Exception(Exception): pass +class BER_Encoding_Error(ASN1_Encoding_Error): + def __init__(self, msg, encoded=None, remaining=None): + Exception.__init__(self, msg) + self.remaining = remaining + self.encoded = encoded + def __str__(self): + s = Exception.__str__(self) + if isinstance(self.encoded, BERcodec_Object): + s+="\n### Already encoded ###\n%s" % self.encoded.strshow() + else: + s+="\n### Already encoded ###\n%r" % self.encoded + s+="\n### Remaining ###\n%r" % self.remaining + return s + class BER_Decoding_Error(ASN1_Decoding_Error): def __init__(self, msg, decoded=None, remaining=None): Exception.__init__(self, msg) @@ -239,6 +253,26 @@ class BERcodec_T61_STRING (BERcodec_STRING): class BERcodec_IA5_STRING(BERcodec_STRING): tag = ASN1_Class_UNIVERSAL.IA5_STRING +class BERcodec_IPADDRESS(BERcodec_STRING): + tag = ASN1_Class_UNIVERSAL.IPADDRESS + + @classmethod + def enc(cls, ipaddr_ascii): + try: + s = inet_aton(ipaddr_ascii) + except Exception: + raise BER_Encoding_Error("IPv4 address could not be encoded") + return chr(cls.tag)+BER_len_enc(len(s))+s + + @classmethod + def do_dec(cls, s, context=None, safe=False): + l,s,t = cls.check_type_check_len(s) + try: + ipaddr_ascii = inet_ntoa(s) + except Exception: + raise BER_Decoding_Error("IP address could not be decoded", decoded=obj) + return cls.asn1_object(ipaddr_ascii), t + class BERcodec_UTC_TIME(BERcodec_STRING): tag = ASN1_Class_UNIVERSAL.UTC_TIME diff --git a/scapy/asn1fields.py b/scapy/asn1fields.py index 3f564cbd91f414ff754d854ded0b36f04e9189f3..7351dad4b14464d6b6726c610d116a4d2b513afd 100644 --- a/scapy/asn1fields.py +++ b/scapy/asn1fields.py @@ -160,6 +160,12 @@ class ASN1F_PRINTABLE_STRING(ASN1F_STRING): class ASN1F_BIT_STRING(ASN1F_STRING): ASN1_tag = ASN1_Class_UNIVERSAL.BIT_STRING + +class ASN1F_IPADDRESS(ASN1F_STRING): + ASN1_tag = ASN1_Class_UNIVERSAL.IPADDRESS + +class ASN1F_TIME_TICKS(ASN1F_INTEGER): + ASN1_tag = ASN1_Class_UNIVERSAL.TIME_TICKS class ASN1F_UTC_TIME(ASN1F_STRING): ASN1_tag = ASN1_Class_UNIVERSAL.UTC_TIME diff --git a/scapy/layers/snmp.py b/scapy/layers/snmp.py index a3474472361b5b8719423ead52134a8f6fff355a..0681825c1ae9613cdf9da1746bcf7704eb15f9e5 100644 --- a/scapy/layers/snmp.py +++ b/scapy/layers/snmp.py @@ -179,12 +179,11 @@ class SNMPset(ASN1_Packet): class SNMPtrapv1(ASN1_Packet): ASN1_codec = ASN1_Codecs.BER - ASN1_root = ASN1F_SNMP_PDU_TRAPv1( ASN1F_INTEGER("id",0), - ASN1F_OID("enterprise", "1.3"), - ASN1F_STRING("agent_addr",""), + ASN1_root = ASN1F_SNMP_PDU_TRAPv1( ASN1F_OID("enterprise", "1.3"), + ASN1F_IPADDRESS("agent_addr","0.0.0.0"), ASN1F_enum_INTEGER("generic_trap", 0, SNMP_trap_types), ASN1F_INTEGER("specific_trap", 0), - ASN1F_INTEGER("time_stamp", IntAutoTime()), + ASN1F_TIME_TICKS("time_stamp", IntAutoTime()), ASN1F_SEQUENCE_OF("varbindlist", [], SNMPvarbind) ) @@ -231,6 +230,9 @@ class SNMP(ASN1_Packet): bind_layers( UDP, SNMP, sport=161) bind_layers( UDP, SNMP, dport=161) +bind_layers( UDP, SNMP, sport=162) +bind_layers( UDP, SNMP, dport=162) + def snmpwalk(dst, oid="1", community="public"): try: while 1: