Пример #1
0
 def i2m(self, pkt, p):
     """
     Update the context with information from the built packet.
     If no type was given at the record layer, we try to infer it.
     """
     cur = b""
     if isinstance(p, _GenericTLSSessionInheritance):
         if pkt.type is None:
             if isinstance(p, TLSChangeCipherSpec):
                 pkt.type = 20
             elif isinstance(p, TLSAlert):
                 pkt.type = 21
             elif isinstance(p, _TLSHandshake):
                 pkt.type = 22
             elif isinstance(p, TLSApplicationData):
                 pkt.type = 23
         p.tls_session = pkt.tls_session
         if not pkt.tls_session.frozen:
             cur = p.raw_stateful()
             p.post_build_tls_session_update(cur)
         else:
             cur = raw(p)
     else:
         pkt.type = 23
         cur = raw(p)
     return cur
Пример #2
0
 def verifyCert(self, cert):
     """ Verifies either a Cert or an X509_Cert. """
     tbsCert = cert.tbsCertificate
     sigAlg = tbsCert.signature
     h = hash_by_oid[sigAlg.algorithm.val]
     sigVal = raw(cert.signatureValue)
     return self.verify(raw(tbsCert), sigVal, h=h, t='pkcs')
Пример #3
0
    def import_from_asn1pkt(self, cert):
        error_msg = "Unable to import certificate"

        self.x509Cert = cert

        tbsCert = cert.tbsCertificate
        self.tbsCertificate = tbsCert

        if tbsCert.version:
            self.version = tbsCert.version.val + 1
        else:
            self.version = 1
        self.serial = tbsCert.serialNumber.val
        self.sigAlg = tbsCert.signature.algorithm.oidname
        self.issuer = tbsCert.get_issuer()
        self.issuer_str = tbsCert.get_issuer_str()
        self.issuer_hash = hash(self.issuer_str)
        self.subject = tbsCert.get_subject()
        self.subject_str = tbsCert.get_subject_str()
        self.subject_hash = hash(self.subject_str)
        self.authorityKeyID = None

        self.notBefore_str = tbsCert.validity.not_before.pretty_time
        notBefore = tbsCert.validity.not_before.val
        if notBefore[-1] == "Z":
            notBefore = notBefore[:-1]
        try:
            self.notBefore = time.strptime(notBefore, "%y%m%d%H%M%S")
        except Exception:
            raise Exception(error_msg)
        self.notBefore_str_simple = time.strftime("%x", self.notBefore)

        self.notAfter_str = tbsCert.validity.not_after.pretty_time
        notAfter = tbsCert.validity.not_after.val
        if notAfter[-1] == "Z":
            notAfter = notAfter[:-1]
        try:
            self.notAfter = time.strptime(notAfter, "%y%m%d%H%M%S")
        except Exception:
            raise Exception(error_msg)
        self.notAfter_str_simple = time.strftime("%x", self.notAfter)

        self.pubKey = PubKey(raw(tbsCert.subjectPublicKeyInfo))

        if tbsCert.extensions:
            for extn in tbsCert.extensions:
                if extn.extnID.oidname == "basicConstraints":
                    self.cA = False
                    if extn.extnValue.cA:
                        self.cA = not (extn.extnValue.cA.val == 0)
                elif extn.extnID.oidname == "keyUsage":
                    self.keyUsage = extn.extnValue.get_keyUsage()
                elif extn.extnID.oidname == "extKeyUsage":
                    self.extKeyUsage = extn.extnValue.get_extendedKeyUsage()
                elif extn.extnID.oidname == "authorityKeyIdentifier":
                    self.authorityKeyID = extn.extnValue.keyIdentifier.val

        self.signatureValue = raw(cert.signatureValue)
        self.signatureLen = len(self.signatureValue)
Пример #4
0
    def post_build(self, pkt, pay):
        """
        need to set the length of the whole PDU manually
        to avoid any bit fiddling use a dummy class to build the layer content

        also add padding if frame is < 64 bytes

        Note: padding only handles Ether/n*Dot1Q/EtherCat
              (no special mumbo jumbo)

        :param pkt: raw string containing the current layer
        :param pay: raw string containing the payload
        :return: <new current layer> + payload
        """

        class _EtherCatLengthCalc(Packet):
            """
            dummy class used to generate str representation easily
            """
            fields_desc = [
                LEBitField('length', None, 11),
                LEBitField('_reserved', 0, 1),
                LEBitField('type', 0, 4),
            ]

        payload_len = len(pay)

        # length field is 11 bit
        if payload_len > 2047:
            raise ValueError('payload size {} exceeds maximum length {} '
                             'of EtherCat message.'.format(payload_len, 2047))

        self.length = payload_len

        vlan_headers_total_size = 0
        upper_layer = self.underlayer

        # add size occupied by VLAN tags
        while upper_layer and isinstance(upper_layer, Dot1Q):
            vlan_headers_total_size += 4
            upper_layer = upper_layer.underlayer

        if not isinstance(upper_layer, Ether):
            raise Exception('missing Ether layer')

        pad_len = EtherCat.ETHER_FRAME_MIN_LEN - (EtherCat.ETHER_HEADER_LEN +
                                                  vlan_headers_total_size +
                                                  EtherCat.ETHERCAT_HEADER_LEN +  # noqa: E501
                                                  payload_len +
                                                  EtherCat.ETHER_FSC_LEN)

        if pad_len > 0:
            pad = Padding()
            pad.load = b'\x00' * pad_len

            return raw(_EtherCatLengthCalc(length=self.length,
                                           type=self.type)) + pay + raw(pad)
        return raw(_EtherCatLengthCalc(length=self.length,
                                       type=self.type)) + pay
Пример #5
0
    def _encrypt_esp(self, pkt, seq_num=None, iv=None):

        if iv is None:
            iv = self.crypt_algo.generate_iv()
        else:
            if len(iv) != self.crypt_algo.iv_size:
                raise TypeError('iv length must be %s' % self.crypt_algo.iv_size)

        esp = _ESPPlain(spi=self.spi, seq=seq_num or self.seq_num, iv=iv)

        if self.tunnel_header:
            tunnel = self.tunnel_header.copy()

            if tunnel.version == 4:
                del tunnel.proto
                del tunnel.len
                del tunnel.chksum
            else:
                del tunnel.nh
                del tunnel.plen

            pkt = tunnel.__class__(raw(tunnel / pkt))

        ip_header, nh, payload = split_for_transport(pkt, socket.IPPROTO_ESP)
        esp.data = payload
        esp.nh = nh

        esp = self.crypt_algo.pad(esp)
        esp = self.crypt_algo.encrypt(self, esp, self.crypt_key)

        self.auth_algo.sign(esp, self.auth_key)

        if self.nat_t_header:
            nat_t_header = self.nat_t_header.copy()
            nat_t_header.chksum = 0
            del nat_t_header.len
            if ip_header.version == 4:
                del ip_header.proto
            else:
                del ip_header.nh
            ip_header /= nat_t_header

        if ip_header.version == 4:
            ip_header.len = len(ip_header) + len(esp)
            del ip_header.chksum
            ip_header = ip_header.__class__(raw(ip_header))
        else:
            ip_header.plen = len(ip_header.payload) + len(esp)

        # sequence number must always change, unless specified by the user
        if seq_num is None:
            self.seq_num += 1

        return ip_header / esp
Пример #6
0
 def i2m(self, pkt, p):
     cur = b""
     if isinstance(p, _GenericTLSSessionInheritance):
         p.tls_session = pkt.tls_session
         if not pkt.tls_session.frozen:
             cur = p.raw_stateful()
             p.post_build_tls_session_update(cur)
         else:
             cur = raw(p)
     else:
         cur = raw(p)
     return cur
Пример #7
0
    def _encrypt_ah(self, pkt, seq_num=None):

        ah = AH(spi=self.spi, seq=seq_num or self.seq_num,
                icv = b"\x00" * self.auth_algo.icv_size)

        if self.tunnel_header:
            tunnel = self.tunnel_header.copy()

            if tunnel.version == 4:
                del tunnel.proto
                del tunnel.len
                del tunnel.chksum
            else:
                del tunnel.nh
                del tunnel.plen

            pkt = tunnel.__class__(raw(tunnel / pkt))

        ip_header, nh, payload = split_for_transport(pkt, socket.IPPROTO_AH)
        ah.nh = nh

        if ip_header.version == 6 and len(ah) % 8 != 0:
            # For IPv6, the total length of the header must be a multiple of
            # 8-octet units.
            ah.padding = b"\x00" * (-len(ah) % 8)
        elif len(ah) % 4 != 0:
            # For IPv4, the total length of the header must be a multiple of
            # 4-octet units.
            ah.padding = b"\x00" * (-len(ah) % 4)

        # RFC 4302 - Section 2.2. Payload Length
        # This 8-bit field specifies the length of AH in 32-bit words (4-byte
        # units), minus "2".
        ah.payloadlen = len(ah) // 4 - 2

        if ip_header.version == 4:
            ip_header.len = len(ip_header) + len(ah) + len(payload)
            del ip_header.chksum
            ip_header = ip_header.__class__(raw(ip_header))
        else:
            ip_header.plen = len(ip_header.payload) + len(ah) + len(payload)

        signed_pkt = self.auth_algo.sign(ip_header / ah / payload, self.auth_key)

        # sequence number must always change, unless specified by the user
        if seq_num is None:
            self.seq_num += 1

        return signed_pkt
Пример #8
0
    def parse_args(self, server="127.0.0.1", dport=4433, server_name=None,
                   mycert=None, mykey=None,
                   client_hello=None, version=None,
                   data=None,
                   **kargs):

        super(TLSClientAutomaton, self).parse_args(mycert=mycert,
                                                   mykey=mykey,
                                                   **kargs)
        tmp = socket.getaddrinfo(server, dport)
        self.remote_name = None
        try:
            if ':' in server:
                inet_pton(socket.AF_INET6, server)
            else:
                inet_pton(socket.AF_INET, server)
        except Exception:
            self.remote_name = socket.getfqdn(server)
            if self.remote_name != server:
                tmp = socket.getaddrinfo(self.remote_name, dport)

        if server_name:
            self.remote_name = server_name
        self.remote_family = tmp[0][0]
        self.remote_ip = tmp[0][4][0]
        self.remote_port = dport
        self.local_ip = None
        self.local_port = None
        self.socket = None

        self.client_hello = client_hello
        self.advertised_tls_version = None
        if version:
            v = _tls_version_options.get(version, None)
            if not v:
                self.vprint("Unrecognized TLS version option.")
            else:
                self.advertised_tls_version = v

        self.linebreak = False
        if isinstance(data, bytes):
            self.data_to_send = [data]
        elif isinstance(data, six.string_types):
            self.data_to_send = [raw(data)]
        elif isinstance(data, list):
            self.data_to_send = list(raw(d) for d in reversed(data))
        else:
            self.data_to_send = []
Пример #9
0
    def _decrypt_ah(self, pkt, verify=True):

        if verify:
            self.check_spi(pkt)
            self.auth_algo.verify(pkt, self.auth_key)

        ah = pkt[AH]
        payload = ah.payload
        payload.remove_underlayer(None)  # useless argument...

        if self.tunnel_header:
            return payload
        else:
            ip_header = pkt

            if ip_header.version == 4:
                ip_header.proto = ah.nh
                del ip_header.chksum
                ip_header.remove_payload()
                ip_header.len = len(ip_header) + len(payload)
                # recompute checksum
                ip_header = ip_header.__class__(raw(ip_header))
            else:
                ah.underlayer.nh = ah.nh
                ah.underlayer.remove_payload()
                ip_header.plen = len(ip_header.payload) + len(payload)

            # reassemble the ip_header with the AH payload
            return ip_header / payload
Пример #10
0
 def send(self, x):
     try:
         sx = raw(x)
         x.sent_time = time.time()
         self.outs.sendto(sx, (x.dst, 0))
     except socket.error as msg:
         log_runtime.error(msg)
Пример #11
0
    def send_wpa_enc(self, data, iv, seqnum, dest, mic_key,
                     key_idx=0, additionnal_flag=["from-DS"],
                     encrypt_key=None):
        """Send an encrypted packet with content @data, using IV @iv,
        sequence number @seqnum, MIC key @mic_key
        """

        if encrypt_key is None:
            encrypt_key = self.tk

        rep = RadioTap()
        rep /= Dot11(
            addr1=dest,
            addr2=self.mac,
            addr3=self.mac,
            FCfield="+".join(['wep'] + additionnal_flag),
            SC=(next(self.seq_num) << 4),
            subtype=0,
            type="Data",
        )

        # Assume packet is send by our AP -> use self.mac as source

        # Encapsule in TKIP with MIC Michael and ICV
        data_to_enc = build_MIC_ICV(raw(data), mic_key, self.mac, dest)

        # Header TKIP + payload
        rep /= Raw(build_TKIP_payload(data_to_enc, iv, self.mac, encrypt_key))

        self.send(rep)
        return rep
Пример #12
0
def sixlowpan_fragment(packet, datagram_tag=1):
    """Split a packet into different links to transmit as 6lowpan packets.
        Usage example:
          >>> ipv6 = ..... (very big packet)
          >>> pkts = sixlowpan_fragment(ipv6, datagram_tag=0x17)
          >>> send = [Dot15d4()/Dot15d4Data()/x for x in pkts]
          >>> wireshark(send)
    """
    if not packet.haslayer(IPv6):
        raise Exception("SixLoWPAN only fragments IPv6 packets !")

    str_packet = raw(packet[IPv6])

    if len(str_packet) <= MAX_SIZE:
        return [packet]

    def chunks(l, n):
        return [l[i:i + n] for i in range(0, len(l), n)]

    new_packet = chunks(str_packet, MAX_SIZE)

    new_packet[0] = LoWPANFragmentationFirst(datagramTag=datagram_tag, datagramSize=len(str_packet)) / new_packet[0]  # noqa: E501
    i = 1
    while i < len(new_packet):
        new_packet[i] = LoWPANFragmentationSubsequent(datagramTag=datagram_tag, datagramSize=len(str_packet), datagramOffset=MAX_SIZE // 8 * i) / new_packet[i]  # noqa: E501
        i += 1

    return new_packet
Пример #13
0
 def send(self, x):
     data = raw(x)
     if self.cls not in x:
         raise Scapy_Exception("L3WinSocket can only send IP/IPv6 packets !"
                               " Install Npcap/Winpcap to send more")
     dst_ip = str(x[self.cls].dst)
     self.outs.sendto(data, (dst_ip, 0))
Пример #14
0
 def post_build(self, p, pay):
     if self.properties == []:
         p += raw(OFPQTNone())
     if self.len is None:
         l = len(p) + len(pay)
         p = p[:4] + struct.pack("!H", l) + p[6:]
     return p + pay
Пример #15
0
 def i2m(self, pkt, x):
     if x is None:
         s = b""
     else:
         s = raw(x)
     return BER_tagging_enc(s, implicit_tag=self.implicit_tag,
                            explicit_tag=self.explicit_tag)
Пример #16
0
def _tls_P_hash(secret, seed, req_len, hm):
    """
    Provides the implementation of P_hash function defined in
    section 5 of RFC 4346 (and section 5 of RFC 5246). Two
    parameters have been added (hm and req_len):

    - secret : the key to be used. If RFC 4868 is to be believed,
               the length must match hm.key_len. Actually,
               python hmac takes care of formatting every key.
    - seed : the seed to be used.
    - req_len : the length of data to be generated by iterating
               the specific HMAC function (hm). This prevents
               multiple calls to the function.
    - hm : the hmac function class to use for iteration (either
           Hmac_MD5 or Hmac_SHA1 in TLS <= 1.1 or
           Hmac_SHA256 or Hmac_SHA384 in TLS 1.2)
    """
    hash_len = hm.hash_alg.hash_len
    n = (req_len + hash_len - 1) // hash_len

    res = b""
    a = hm(secret).digest(seed)  # A(1)

    while n > 0:
        res += hm(secret).digest(a + raw(seed))
        a = hm(secret).digest(a)
        n -= 1

    return res[:req_len]
Пример #17
0
    def self_build(self, field_pos_list=None):
        """ Implements the swap-bytes functionality when building

        this is based on a copy of the Packet.self_build default method.
        The goal is to affect only the CAN layer data and keep
        under layers (e.g LinuxCooked) unchanged
        """
        if self.raw_packet_cache is not None:
            for fname, fval in six.iteritems(self.raw_packet_cache_fields):
                if self.getfieldval(fname) != fval:
                    self.raw_packet_cache = None
                    self.raw_packet_cache_fields = None
                    break
            if self.raw_packet_cache is not None:
                if conf.contribs['CAN']['swap-bytes']:
                    return CAN.inv_endianness(self.raw_packet_cache)
                return self.raw_packet_cache
        p = b""
        for f in self.fields_desc:
            val = self.getfieldval(f.name)
            if isinstance(val, RawVal):
                sval = raw(val)
                p += sval
                if field_pos_list is not None:
                    field_pos_list.append((f.name,
                                           sval.encode('string_escape'),
                                           len(p), len(sval)))
            else:
                p = f.addfield(self, p, val)
        if conf.contribs['CAN']['swap-bytes']:
            return CAN.inv_endianness(p)
        return p
Пример #18
0
 def build(self, pkt):
     val = getattr(pkt, self.name)
     if isinstance(val, ASN1_Object) and val.tag == ASN1_Class_UNIVERSAL.RAW:  # noqa: E501
         s = val
     elif val is None:
         s = b""
     else:
         s = b"".join(raw(i) for i in val)
     return self.i2m(pkt, s)
Пример #19
0
 def i2m(self, pkt, x):
     if x is None:
         s = b""
     else:
         s = raw(x)
         if hash(type(x)) in self.pktchoices:
             imp, exp = self.pktchoices[hash(type(x))]
             s = BER_tagging_enc(s, implicit_tag=imp,
                                 explicit_tag=exp)
     return BER_tagging_enc(s, explicit_tag=self.explicit_tag)
Пример #20
0
    def __call__(cls, key_path=None):
        """
        key_path may be the path to either:
            _an RSAPrivateKey_OpenSSL (as generated by openssl);
            _an ECDSAPrivateKey_OpenSSL (as generated by openssl);
            _an RSAPrivateKey;
            _an ECDSAPrivateKey.
        """
        if key_path is None:
            obj = type.__call__(cls)
            if cls is PrivKey:
                cls = PrivKeyECDSA
            obj.__class__ = cls
            obj.frmt = "original"
            obj.fill_and_store()
            return obj

        obj = _PKIObjMaker.__call__(cls, key_path, _MAX_KEY_SIZE)
        multiPEM = False
        try:
            privkey = RSAPrivateKey_OpenSSL(obj.der)
            privkey = privkey.privateKey
            obj.__class__ = PrivKeyRSA
            marker = b"PRIVATE KEY"
        except Exception:
            try:
                privkey = ECDSAPrivateKey_OpenSSL(obj.der)
                privkey = privkey.privateKey
                obj.__class__ = PrivKeyECDSA
                marker = b"EC PRIVATE KEY"
                multiPEM = True
            except Exception:
                try:
                    privkey = RSAPrivateKey(obj.der)
                    obj.__class__ = PrivKeyRSA
                    marker = b"RSA PRIVATE KEY"
                except Exception:
                    try:
                        privkey = ECDSAPrivateKey(obj.der)
                        obj.__class__ = PrivKeyECDSA
                        marker = b"EC PRIVATE KEY"
                    except Exception:
                        raise Exception("Unable to import private key")
        try:
            obj.import_from_asn1pkt(privkey)
        except ImportError:
            pass

        if obj.frmt == "DER":
            if multiPEM:
                # this does not restore the EC PARAMETERS header
                obj.pem = der2pem(raw(privkey), marker)
            else:
                obj.pem = der2pem(obj.der, marker)
        return obj
Пример #21
0
 def sign(self, M, t="pkcs", h="sha256", mgf=None, L=None):
     M = raw(M)
     mgf = mgf or padding.MGF1
     h = _get_hash(h)
     pad = _get_padding(t, mgf, h, L)
     try:
         return self.key.sign(M, pad, h)
     except UnsupportedAlgorithm:
         if t != "pkcs" and h != "md5-sha1":
             raise UnsupportedAlgorithm("RSA signature with %s" % h)
         return self._legacy_sign_md5_sha1(M)
Пример #22
0
 def send(self, x):
     try:
         return SuperSocket.send(self, x)
     except socket.error as msg:
         if msg.errno == 22 and len(x) < conf.min_pkt_size:
             padding = b"\x00" * (conf.min_pkt_size - len(x))
             if isinstance(x, Packet):
                 return SuperSocket.send(self, x / Padding(load=padding))
             else:
                 return SuperSocket.send(self, raw(x) + padding)
         raise
Пример #23
0
 def enc(cls, oid):
     oid = raw(oid)
     if oid:
         lst = [int(x) for x in oid.strip(b".").split(b".")]
     else:
         lst = list()
     if len(lst) >= 2:
         lst[1] += 40 * lst[0]
         del(lst[0])
     s = b"".join(BER_num_enc(k) for k in lst)
     return chb(hash(cls.tag)) + BER_len_enc(len(s)) + s
Пример #24
0
 def send(self, x):
     # Makes send detects when it should add Loopback(), Dot11... instead of Ether()  # noqa: E501
     ll = self.ins.datalink()
     if ll in conf.l2types:
         cls = conf.l2types[ll]
     else:
         cls = conf.default_l2
         warning("Unable to guess datalink type (interface=%s linktype=%i). Using %s", self.iface, ll, cls.name)  # noqa: E501
     sx = raw(cls() / x)
     if hasattr(x, "sent_time"):
         x.sent_time = time.time()
     return self.ins.send(sx)
Пример #25
0
 def enc(cls, s):
     # /!\ this is DER encoding (bit strings are only zero-bit padded)
     s = raw(s)
     if len(s) % 8 == 0:
         unused_bits = 0
     else:
         unused_bits = 8 - len(s) % 8
         s += b"0" * unused_bits
     s = b"".join(chb(int(b"".join(chb(y) for y in x), 2))
                  for x in zip(*[iter(s)] * 8))
     s = chb(unused_bits) + s
     return chb(hash(cls.tag)) + BER_len_enc(len(s)) + s
Пример #26
0
def sixlowpan_defragment(packet_list):
    results = {}
    for p in packet_list:
        cls = None
        if LoWPANFragmentationFirst in p:
            cls = LoWPANFragmentationFirst
        elif LoWPANFragmentationSubsequent in p:
            cls = LoWPANFragmentationSubsequent
        if cls:
            tag = p[cls].datagramTag
            results[tag] = results.get(tag, b"") + raw(p[cls][LoWPAN_IPHC].payload)  # noqa: E501
    return {tag: IPv6(x) for tag, x in results.items()}
Пример #27
0
 def decap(self, orig_pkt):
     """decapsulate a MACsec frame"""
     if orig_pkt.name != Ether().name or orig_pkt.payload.name != MACsec().name:  # noqa: E501
         raise TypeError('cannot decapsulate MACsec packet, must be Ethernet/MACsec')  # noqa: E501
     packet = copy.deepcopy(orig_pkt)
     prev_layer = packet[MACsec].underlayer
     prev_layer.type = packet[MACsec].type
     next_layer = packet[MACsec].payload
     del prev_layer.payload
     if prev_layer.name == Ether().name:
         return Ether(raw(prev_layer / next_layer))
     return prev_layer / next_layer
Пример #28
0
def sixlowpan_defragment(packet_list):
    results = {}
    for p in packet_list:
        cls = None
        if LoWPANFragmentationFirst in p:
            cls = LoWPANFragmentationFirst
        elif LoWPANFragmentationSubsequent in p:
            cls = LoWPANFragmentationSubsequent
        if cls:
            tag = p[cls].datagramTag
            results[tag] = results.get(tag, b"") + raw(
                p[cls][LoWPAN_IPHC].payload)
    return {tag: IPv6(x) for tag, x in results.items()}
Пример #29
0
def nmap_udppacket_sig(snd, rcv):
    res = {}
    if rcv is None:
        res["Resp"] = "N"
    else:
        res["DF"] = "Y" if rcv.flags.DF else "N"
        res["TOS"] = "%X" % rcv.tos
        res["IPLEN"] = "%X" % rcv.len
        res["RIPTL"] = "%X" % rcv.payload.payload.len
        res["RID"] = "E" if snd.id == rcv[IPerror].id else "F"
        res["RIPCK"] = "E" if snd.chksum == rcv[IPerror].chksum else (
            "0" if rcv[IPerror].chksum == 0 else "F"
        )
        res["UCK"] = "E" if snd.payload.chksum == rcv[UDPerror].chksum else (
            "0" if rcv[UDPerror].chksum == 0 else "F"
        )
        res["ULEN"] = "%X" % rcv[UDPerror].len
        res["DAT"] = "E" if (
            isinstance(rcv[UDPerror].payload, NoPayload) or
            raw(rcv[UDPerror].payload) == raw(snd[UDP].payload)
        ) else "F"
    return res
 def _process_packet(self, pkt):
     """Process each packet: matches the TCP seq/ack numbers
     to follow the TCP streams, and orders the fragments.
     """
     from scapy.layers.inet import IP, TCP
     if TCP not in pkt:
         return pkt
     pay = pkt[TCP].payload
     if isinstance(pay, (NoPayload, conf.padding_layer)):
         return pkt
     new_data = raw(pay)
     # Match packets by a uniqute TCP identifier
     seq = pkt[TCP].seq
     ident = pkt.sprintf(self.fmt)
     data, metadata = self.tcp_frags[ident]
     # Let's guess which class is going to be used
     if "pay_class" not in metadata:
         pay_class = pay.__class__
         if not hasattr(pay_class, "tcp_reassemble"):
             # Cannot tcp-reassemble
             return pkt
         metadata["pay_class"] = pay_class
     else:
         pay_class = metadata["pay_class"]
     # Get a relative sequence number for a storage purpose
     relative_seq = metadata.get("relative_seq", None)
     if not relative_seq:
         relative_seq = metadata["relative_seq"] = seq - 1
     seq = seq - relative_seq
     # Add the data to the buffer
     # Note that this take care of retransmission packets.
     data.append(new_data, seq)
     # Check TCP FIN or TCP RESET
     if pkt[TCP].flags.F or pkt[TCP].flags.R or pkt[TCP].flags.P:
         metadata["tcp_end"] = True
     # XXX TODO: check that no empty space is missing in the buffer.
     # XXX Currently, if a TCP fragment was missing, we won't notice it.
     packet = None
     if data.full():
         # Reassemble using all previous packets
         packet = pay_class.tcp_reassemble(bytes(data), metadata)
     # Stack the result on top of the previous frames
     if packet:
         data.clear()
         del self.tcp_frags[ident]
         pay.underlayer.remove_payload()
         if IP in pkt:
             pkt[IP].len = None
             pkt[IP].chksum = None
         return pkt / packet
Пример #31
0
 def decap(self, orig_pkt):
     """decapsulate a MACsec frame"""
     if not isinstance(orig_pkt, Ether) or \
             not isinstance(orig_pkt.payload, MACsec):
         raise TypeError(
             'cannot decapsulate MACsec packet, must be Ethernet/MACsec')
     packet = copy.deepcopy(orig_pkt)
     prev_layer = packet[MACsec].underlayer
     prev_layer.type = packet[MACsec].type
     next_layer = packet[MACsec].payload
     del prev_layer.payload
     if prev_layer.name == Ether().name:
         return Ether(raw(prev_layer / next_layer))
     return prev_layer / next_layer
Пример #32
0
 def send(self, x):
     # Makes send detects when it should add Loopback(), Dot11... instead of Ether()  # noqa: E501
     ll = self.ins.datalink()
     if ll in conf.l2types:
         cls = conf.l2types[ll]
     else:
         cls = conf.default_l2
         warning(
             "Unable to guess datalink type (interface=%s linktype=%i). Using %s",
             self.iface, ll, cls.name)  # noqa: E501
     sx = raw(cls() / x)
     if hasattr(x, "sent_time"):
         x.sent_time = time.time()
     return self.ins.send(sx)
Пример #33
0
 def i2m(self, pkt, i):
     if i is None:
         return b""
     if isinstance(pkt, _GenericTLSSessionInheritance):
         if not pkt.tls_session.frozen:
             s = b""
             for ext in i:
                 if isinstance(ext, _GenericTLSSessionInheritance):
                     ext.tls_session = pkt.tls_session
                     s += ext.raw_stateful()
                 else:
                     s += raw(ext)
             return s
     return b"".join(map(raw, i))
Пример #34
0
def prepare_packed_data(radius_packet, packed_req_authenticator):
    """
    Pack RADIUS data prior computing the authentication MAC
    """

    packed_hdr = struct.pack("!B", radius_packet.code)
    packed_hdr += struct.pack("!B", radius_packet.id)
    packed_hdr += struct.pack("!H", radius_packet.len)

    packed_attrs = b''
    for attr in radius_packet.attributes:
        packed_attrs += raw(attr)

    return packed_hdr + packed_req_authenticator + packed_attrs
 def is_request(self, pkt):
     if not isinstance(pkt, Dot11):
         return 0
     if not pkt.FCfield & 1:
         return 0
     if not pkt.haslayer(TCP):
         return 0
     tcp = pkt.getlayer(TCP)
     pay = raw(tcp.payload)
     if not self.ptrn.match(pay):
         return 0
     if self.iptrn.match(pay) is True:
         return 0
     return True
Пример #36
0
 def split_pkt(pkt, assoclen, icvlen=0):
     """
     split the packet into associated data, plaintext or ciphertext, and
     optional ICV
     """
     data = raw(pkt)
     assoc = data[:assoclen]
     if icvlen:
         icv = data[-icvlen:]
         enc = data[assoclen:-icvlen]
     else:
         icv = b''
         enc = data[assoclen:]
     return assoc, enc, icv
Пример #37
0
 def test_0603_bofpacket_addpayload_automatic(self):
     """Test that we can dynamically bind payloads.
     ScapyBasicOtterPacket 1 and 3 are not bound in Scapy implementation.
     """
     bof_pkt = BOFPacket(scapy_pkt=ScapyBasicOtterPacket1())
     bof_pkt.append(ScapyBasicOtterPacket3(), autobind=True)
     self.assertEqual(bof_pkt.scapy_pkt.payload.get_field("basic_otter_3_1").name,
                      "basic_otter_3_1")
     self.assertEqual(bof_pkt.scapy_pkt.getlayer("ScapyBasicOtterPacket3").get_field("basic_otter_3_1").name,
                      "basic_otter_3_1")
     self.assertEqual(bytes(bof_pkt), bytes(ScapyBasicOtterPacket1())
                      + bytes(ScapyBasicOtterPacket3()))
     # effectively tests for "logical" payload binding (in addition to the correct frame bytes)
     self.assertEqual(bof_pkt.scapy_pkt.__class__(raw(bof_pkt.scapy_pkt)).payload.name, "basic_otter_packet_3")
Пример #38
0
def prepare_packed_data(radius_packet, packed_req_authenticator):
    """
    Pack RADIUS data prior computing the authentication MAC
    """

    packed_hdr = struct.pack("!B", radius_packet.code)
    packed_hdr += struct.pack("!B", radius_packet.id)
    packed_hdr += struct.pack("!H", radius_packet.len)

    packed_attrs = b''
    for attr in radius_packet.attributes:
        packed_attrs += raw(attr)

    return packed_hdr + packed_req_authenticator + packed_attrs
Пример #39
0
 def split_pkt(pkt, assoclen, icvlen=0):
     """
     split the packet into associated data, plaintext or ciphertext, and
     optional ICV
     """
     data = raw(pkt)
     assoc = data[:assoclen]
     if icvlen:
         icv = data[-icvlen:]
         enc = data[assoclen:-icvlen]
     else:
         icv = b''
         enc = data[assoclen:]
     return assoc, enc, icv
Пример #40
0
    def i2m(self, pkt, x):
        if isinstance(x, str):
            return x
        s = b""
        for o in x:
            if isinstance(o, tuple) and len(o) >= 2:
                name = o[0]
                lval = o[1:]

                if isinstance(name, int):
                    onum, oval = name, b"".join(lval)
                elif name in DHCPRevOptions:
                    onum, f = DHCPRevOptions[name]
                    if f is not None:
                        lval = (f.addfield(pkt, b"", f.any2i(pkt, val))
                                for val in lval)  # noqa: E501
                    else:
                        lval = (raw(x) for x in lval)
                    oval = b"".join(lval)
                else:
                    warning("Unknown field option %s", name)
                    continue

                s += chb(onum)
                s += chb(len(oval))
                s += oval

            elif (isinstance(o, str) and o in DHCPRevOptions
                  and DHCPRevOptions[o][1] is None):
                s += chb(DHCPRevOptions[o][0])
            elif isinstance(o, int):
                s += chb(o) + b"\0"
            elif isinstance(o, (str, bytes)):
                s += raw(o)
            else:
                warning("Malformed option %s", o)
        return s
Пример #41
0
def split_for_transport(orig_pkt, transport_proto):
    """
    Split an IP(v6) packet in the correct location to insert an ESP or AH
    header.

    @param orig_pkt: the packet to split. Must be an IP or IPv6 packet
    @param transport_proto: the IPsec protocol number that will be inserted
                            at the split position.
    @return: a tuple (header, nh, payload) where nh is the protocol number of
             payload.
    """
    # force resolution of default fields to avoid padding errors
    header = orig_pkt.__class__(raw(orig_pkt))
    next_hdr = header.payload
    nh = None

    if header.version == 4:
        nh = header.proto
        header.proto = transport_proto
        header.remove_payload()
        del header.chksum
        del header.len

        return header, nh, next_hdr
    else:
        found_rt_hdr = False
        prev = header

        # Since the RFC 4302 is vague about where the ESP/AH headers should be
        # inserted in IPv6, I chose to follow the linux implementation.
        while isinstance(
                next_hdr,
            (IPv6ExtHdrHopByHop, IPv6ExtHdrRouting, IPv6ExtHdrDestOpt)):
            if isinstance(next_hdr, IPv6ExtHdrHopByHop):
                pass
            if isinstance(next_hdr, IPv6ExtHdrRouting):
                found_rt_hdr = True
            elif isinstance(next_hdr, IPv6ExtHdrDestOpt) and found_rt_hdr:
                break

            prev = next_hdr
            next_hdr = next_hdr.payload

        nh = prev.nh
        prev.nh = transport_proto
        prev.remove_payload()
        del header.plen

        return header, nh, next_hdr
Пример #42
0
    def sign(self, pkt, key):
        """
        Sign an IPsec (ESP or AH) packet with this algo.

        @param pkt:    a packet that contains a valid encrypted ESP or AH layer
        @param key:    the authentication key, a byte string

        @return: the signed packet
        """
        if not self.mac:
            return pkt

        mac = self.new_mac(key)

        if pkt.haslayer(ESP):
            mac.update(raw(pkt[ESP]))
            pkt[ESP].data += mac.finalize()[:self.icv_size]

        elif pkt.haslayer(AH):
            clone = zero_mutable_fields(pkt.copy(), sending=True)
            mac.update(raw(clone))
            pkt[AH].icv = mac.finalize()[:self.icv_size]

        return pkt
Пример #43
0
 def decap(self, orig_pkt):
     """decapsulate a MACsec frame"""
     if orig_pkt.name != Ether().name or orig_pkt.payload.name != MACsec(
     ).name:  # noqa: E501
         raise TypeError(
             'cannot decapsulate MACsec packet, must be Ethernet/MACsec'
         )  # noqa: E501
     packet = copy.deepcopy(orig_pkt)
     prev_layer = packet[MACsec].underlayer
     prev_layer.type = packet[MACsec].type
     next_layer = packet[MACsec].payload
     del prev_layer.payload
     if prev_layer.name == Ether().name:
         return Ether(raw(prev_layer / next_layer))
     return prev_layer / next_layer
Пример #44
0
    def send(self, x):
        # type: (Packet) -> int
        try:
            x.sent_time = time.time()
        except AttributeError:
            pass

        # need to change the byte order of the first four bytes,
        # required by the underlying Linux SocketCAN frame format
        bs = raw(x)
        if not conf.contribs['CAN']['swap-bytes']:
            bs = bs + b'\x00' * (CAN_MTU - len(bs))
            bs = struct.pack("<I12s", *struct.unpack(">I12s", bs))

        return super(NativeCANSocket, self).send(bs)  # type: ignore
Пример #45
0
 def test_0605_bofpacket_addpayload_automatic_guess(self):
     """Test dynamic payload binding when specific conditions are used
      via guess_payload in Scapy implementation"""
     bof_pkt = BOFPacket(scapy_pkt=ScapyOtterGuessPayloadPacket1())
     bof_pkt.append(ScapyBasicOtterPacket3(), autobind=True)
     self.assertEqual(bof_pkt.scapy_pkt.payload.get_field("basic_otter_3_1").name,
                      "basic_otter_3_1")
     self.assertEqual(
         bof_pkt.scapy_pkt.getlayer("ScapyBasicOtterPacket3").get_field("basic_otter_3_1").name,
         "basic_otter_3_1")
     self.assertEqual(bytes(bof_pkt), bytes(ScapyOtterGuessPayloadPacket1())
                      + bytes(ScapyBasicOtterPacket3()))
     # effectively tests for "logical" payload binding (in addition to the correct frame bytes)
     self.assertEqual(bof_pkt.scapy_pkt.__class__(raw(bof_pkt.scapy_pkt)).payload.name,
                      "basic_otter_packet_3")
Пример #46
0
 def verify(self, M, S, t="pkcs", h="sha256", mgf=None, L=None):
     M = raw(M)
     mgf = mgf or padding.MGF1
     h = _get_hash(h)
     pad = _get_padding(t, mgf, h, L)
     try:
         try:
             self.pubkey.verify(S, M, pad, h)
         except UnsupportedAlgorithm:
             if t != "pkcs" and h != "md5-sha1":
                 raise UnsupportedAlgorithm("RSA verification with %s" % h)
             self._legacy_verify_md5_sha1(M, S)
         return True
     except InvalidSignature:
         return False
Пример #47
0
    def send_assoc_response(self, pkt):

        # Get RSN info
        temp_pkt = pkt[Dot11Elt::{"ID": 48}].copy()
        temp_pkt.remove_payload()
        self.RSN = raw(temp_pkt)
        # Avoid 802.11w, etc. (deactivate RSN capabilities)
        self.RSN = self.RSN[:-2] + "\x00\x00"

        rep = RadioTap()
        rep /= Dot11(addr1=self.client, addr2=self.mac, addr3=self.mac)
        rep /= Dot11AssoResp()
        rep /= Dot11EltRates(rates=[130, 132, 139, 150, 12, 18, 24, 36])

        self.send(rep)
Пример #48
0
 def send(self, x):
     iff = x.route()[0]
     if iff is None:
         iff = conf.iface
     sdto = (iff, self.type)
     self.outs.bind(sdto)
     sn = self.outs.getsockname()
     ll = lambda x: x
     if type(x) in conf.l3types:
         sdto = (iff, conf.l3types[type(x)])
     if sn[3] in conf.l2types:
         ll = lambda x: conf.l2types[sn[3]]() / x
     sx = raw(ll(x))
     x.sent_time = time.time()
     try:
         self.outs.sendto(sx, sdto)
     except socket.error as msg:
         if msg.errno == 22 and len(sx) < conf.min_pkt_size:
             self.outs.send(sx + b"\x00" * (conf.min_pkt_size - len(sx)))
         elif conf.auto_fragment and msg.errno == 90:
             for p in x.fragment():
                 self.outs.sendto(raw(ll(p)), sdto)
         else:
             raise
Пример #49
0
    def send_assoc_response(self, pkt):

        # Get RSN info
        temp_pkt = pkt[Dot11Elt::{"ID": 48}].copy()
        temp_pkt.remove_payload()
        self.RSN = raw(temp_pkt)
        # Avoid 802.11w, etc. (deactivate RSN capabilities)
        self.RSN = self.RSN[:-2] + "\x00\x00"

        rep = RadioTap()
        rep /= Dot11(addr1=self.client, addr2=self.mac, addr3=self.mac)
        rep /= Dot11AssoResp()
        rep /= Dot11Elt(ID="Rates", info='\x82\x84\x8b\x96\x0c\x12\x18$')

        self.send(rep)
Пример #50
0
 def __init__(self,
              name,  # type: str
              default,  # type: Optional[ASN1_Packet]
              cls,  # type: Type[ASN1_Packet]
              context=None,  # type: Optional[Any]
              implicit_tag=None,  # type: Optional[int]
              explicit_tag=None,  # type: Optional[int]
              ):
     # type: (...) -> None
     self.cls = cls
     super(ASN1F_BIT_STRING_ENCAPS, self).__init__(
         name, default and raw(default), context=context,
         implicit_tag=implicit_tag,
         explicit_tag=explicit_tag
     )
Пример #51
0
 def send(self, x):
     # type: (Packet) -> int
     try:
         sx = raw(x)
         if self.outs:
             x.sent_time = time.time()
             return self.outs.sendto(sx, (x.dst, 0))
     except AttributeError:
         raise ValueError(
             "Missing 'dst' attribute in the first layer to be "
             "sent using a native L3 socket ! (make sure you passed the "
             "IP layer)")
     except socket.error as msg:
         log_runtime.error(msg)
     return 0
Пример #52
0
def _legacy_pkcs1_v1_5_encode_md5_sha1(M, emLen):
    """
    Legacy method for PKCS1 v1.5 encoding with MD5-SHA1 hash.
    """
    M = raw(M)
    md5_hash = hashes.Hash(_get_hash("md5"), backend=default_backend())
    md5_hash.update(M)
    sha1_hash = hashes.Hash(_get_hash("sha1"), backend=default_backend())
    sha1_hash.update(M)
    H = md5_hash.finalize() + sha1_hash.finalize()
    if emLen < 36 + 11:
        warning("pkcs_emsa_pkcs1_v1_5_encode: "
                "intended encoded message length too short")
        return None
    PS = b'\xff' * (emLen - 36 - 3)
    return b'\x00' + b'\x01' + PS + b'\x00' + H
Пример #53
0
def assert_redirect_to_real_server_ipv6(test, real_server_ip, packet_in,
                                        result):
    test.assertEqual(BPF.XDP_TX, result.retval)
    # client -> virtual server
    # become
    # client -> given real server
    expected = packet_in.copy()
    expected[Ether].dst = packet_in[Ether].src
    expected[Ether].src = packet_in[Ether].dst
    expected[IPv6].dst = real_server_ip
    expected[IPv6].hlim = packet_in[IPv6].hlim - 1
    # force checksum calculation
    del expected[UDP].chksum
    expected = Ether(raw(expected))

    test.assertEqual(expected, result.packet)
Пример #54
0
    def send(self, data, address: tuple = None) -> int:
        """Converts BOF and Scapy frames to bytes to send.
        Relies on ``TCP`` class to send data.

        :param data: Data to send as ``ModbusPacket``, Scapy ``Packet``, string
                     or bytes. Will be converted to bytes anyway.
        :param address: Address to send ``data`` to, with format ``(ip, port)``.
                        If address is not specified, uses the address given to
                        `` connect``.
        :returns: The number of bytes sent, as an integer.
        """
        if isinstance(data, ModbusPacket):
            data = bytes(data)
        elif isinstance(data, Packet):
            data = raw(data)
        return super().send(data, address)
Пример #55
0
 def test_0604_bofpacket_addpayload_automatic_layer(self):
     """Test that we can bind payloads with another layer than the 1st one.
     (This was a bug because we were not binding with the last)
     Here, Packet 2 is bound to 1, but Packet 2 is not bound to 3 by default.
     """
     bof_pkt1 = BOFPacket(scapy_pkt=ScapyBasicOtterPacket1() / ScapyBasicOtterPacket2())
     bof_pkt1.append(ScapyBasicOtterPacket3(), autobind=True)
     self.assertEqual(bof_pkt1.scapy_pkt.payload.payload.get_field("basic_otter_3_1").name,
                      "basic_otter_3_1")
     self.assertEqual(bof_pkt1.scapy_pkt.getlayer("ScapyBasicOtterPacket3").get_field("basic_otter_3_1").name,
                      "basic_otter_3_1")
     self.assertEqual(bytes(bof_pkt1), bytes(ScapyBasicOtterPacket1())
                      + bytes(ScapyBasicOtterPacket2())
                      + bytes(ScapyBasicOtterPacket3()))
     # effectively tests for "logical" payload binding (in addition to the correct frame bytes)
     self.assertEqual(bof_pkt1.scapy_pkt.__class__(raw(bof_pkt1.scapy_pkt)).payload.payload.name,
                      "basic_otter_packet_3")
Пример #56
0
    def _decrypt_esp(self, pkt, verify=True, esn_en=None, esn=None):

        encrypted = pkt[ESP]

        if verify:
            self.check_spi(pkt)
            self.auth_algo.verify(encrypted, self.auth_key)

        esp = self.crypt_algo.decrypt(self,
                                      encrypted,
                                      self.crypt_key,
                                      self.crypt_algo.icv_size
                                      or self.auth_algo.icv_size,
                                      esn_en=esn_en or self.esn_en,
                                      esn=esn or self.esn)

        if self.tunnel_header:
            # drop the tunnel header and return the payload untouched

            pkt.remove_payload()
            if pkt.version == 4:
                pkt.proto = esp.nh
            else:
                pkt.nh = esp.nh
            cls = pkt.guess_payload_class(esp.data)

            return cls(esp.data)
        else:
            ip_header = pkt

            if ip_header.version == 4:
                ip_header.proto = esp.nh
                del ip_header.chksum
                ip_header.remove_payload()
                ip_header.len = len(ip_header) + len(esp.data)
                # recompute checksum
                ip_header = ip_header.__class__(raw(ip_header))
            else:
                encrypted.underlayer.nh = esp.nh
                encrypted.underlayer.remove_payload()
                ip_header.plen = len(ip_header.payload) + len(esp.data)

            cls = ip_header.guess_payload_class(esp.data)

            # reassemble the ip_header with the ESP payload
            return ip_header / cls(esp.data)
Пример #57
0
 def addfield(self, pkt, s, val):
     """Add an internal value to a string"""
     if self.length_of(pkt) == 8:
         return s + struct.pack(self.fmt[0] + "B", val)
     if self.length_of(pkt) == 16:
         return s + struct.pack(self.fmt[0] + "H", val)
     if self.length_of(pkt) == 32:
         return s + struct.pack(self.fmt[0] + "2H", val)  # TODO: fix!
     if self.length_of(pkt) == 48:
         return s + struct.pack(self.fmt[0] + "3H", val)  # TODO: fix!
     elif self.length_of(pkt) == 64:
         return s + struct.pack(self.fmt[0] + "Q", val)
     elif self.length_of(pkt) == 128:
         # TODO: FIX THE PACKING!!
         return s + struct.pack(self.fmt[0] + "16s", raw(val))
     else:
         return s
Пример #58
0
 def post_dissect(self, data):
     if not self.underlayer or not hasattr(self.underlayer, "_ipv6"):
         return data
     if self.guess_payload_class(data) != IPv6:
         return data
     # Underlayer is LoWPAN_IPHC
     packet = self.underlayer._ipv6
     try:
         ipv6_hdr = next(
             x for x in self.exts if isinstance(x, LoWPAN_NHC_IPv6Ext)
         )
     except StopIteration:
         ipv6_hdr = None
     if ipv6_hdr:
         # XXX todo: implement: append the IPv6 extension
         # packet = packet / ipv6extension
         pass
     try:
         udp_hdr = next(
             x for x in self.exts if isinstance(x, LoWPAN_NHC_UDP)
         )
     except StopIteration:
         udp_hdr = None
     if udp_hdr:
         packet.nh = 0x11  # UDP
         udp = UDP()
         # https://tools.ietf.org/html/rfc6282#section-4.3.3
         if udp_hdr.C == 0:
             udp.chksum = udp_hdr.udpChecksum
         if udp_hdr.P == 0:
             udp.sport = udp_hdr.udpSourcePort
             udp.dport = udp_hdr.udpDestPort
         elif udp_hdr.P == 1:
             udp.sport = udp_hdr.udpSourcePort
             udp.dport = 0xF000 + udp_hdr.udpDestPort
         elif udp_hdr.P == 2:
             udp.sport = 0xF000 + udp_hdr.udpSourcePort
             udp.dport = udp_hdr.udpDestPort
         elif udp_hdr.P == 3:
             udp.sport = 0xF0B0 + udp_hdr.udpSourcePort
             udp.dport = 0xF0B0 + udp_hdr.udpDestPort
         packet.lastlayer().add_payload(udp / data)
     else:
         packet.lastlayer().add_payload(data)
     data = raw(packet)
     return Packet.post_dissect(self, data)
Пример #59
0
 def _legacy_sign_md5_sha1(self, M):
     M = raw(M)
     k = self._modulusLen // 8
     EM = _legacy_pkcs1_v1_5_encode_md5_sha1(M, k)
     if EM is None:
         warning("Key._rsassa_pkcs1_v1_5_sign(): unable to encode")
         return None
     m = pkcs_os2ip(EM)
     n = self._modulus
     if isinstance(m, int) and six.PY2:
         m = long(m)  # noqa: F821
     if (six.PY2 and not isinstance(m, long)) or m > n - 1:  # noqa: F821
         warning("Key._rsaep() expects a long between 0 and n-1")
         return None
     privExp = self.key.private_numbers().d
     s = pow(m, privExp, n)
     return pkcs_i2osp(s, k)
Пример #60
0
 def make_reply(self, p):
     ip = p.getlayer(IP)
     tcp = p.getlayer(TCP)
     pay = raw(tcp.payload)
     del(p.payload.payload.payload)
     p.FCfield = "from-DS"
     p.addr1, p.addr2 = p.addr2, p.addr1
     p /= IP(src=ip.dst, dst=ip.src)
     p /= TCP(sport=tcp.dport, dport=tcp.sport,
              seq=tcp.ack, ack=tcp.seq + len(pay),
              flags="PA")
     q = p.copy()
     p /= self.replace
     q.ID += 1
     q.getlayer(TCP).flags = "RA"
     q.getlayer(TCP).seq += len(self.replace)
     return [p, q]