class ConfClass(object):
class Interceptor(object):
class ProgPath(ConfClass):
class ConfigFieldList:
class Emphasize(ConfigFieldList):
class Resolve(ConfigFieldList):
class Num2Layer:
class LayersList(List[Type['scapy.packet.Packet']]):
class CommandsList(List[Callable[..., Any]]):
class CacheInstance(Dict[str, Any], object):
class NetCache:
class Conf(ConfClass):
    def configure(self, cnf):
    def __repr__(self):
    def __str__(self):
    def __init__(self,
                 name,  # type: str
                 default,  # type: Any
                 hook,  # type: Callable[..., Any]
                 args=None,  # type: Optional[List[Any]]
                 kargs=None  # type: Optional[Dict[str, Any]]
                 ):
    def __get__(self, obj, typ=None):
    def set_from_hook(obj, name, val):
    def __set__(self, obj, val):
def _readonly(name):
    def __init__(self):
    def _is_field(f):
    def _recalc_layer_list(self):
    def add(self, *flds):
    def remove(self, *flds):
    def __contains__(self, elt):
    def __repr__(self):
    def __init__(self):
    def register(self, num, layer):
    def register_num2layer(self, num, layer):
    def register_layer2num(self, num, layer):
    def __getitem__(self, item):
    def __contains__(self, item):
    def get(self,
            item,  # type: Union[int, Type[Packet]]
            default=None,  # type: Optional[Type[Packet]]
            ):
    def __repr__(self):
    def __init__(self):
    def __repr__(self):
    def register(self, layer):
    def layers(self):
    def filter(self, items):
    def unfilter(self):
    def __repr__(self):
    def register(self, cmd):
def lsc():
    def __init__(self, name="noname", timeout=None):
    def flush(self):
    def __getitem__(self, item):
    def get(self, item, default=None):
    def __setitem__(self, item, v):
    def update(self,  # type: ignore
               other,  # type: Any
               **kwargs  # type: Any
               ):
    def iteritems(self):
    def iterkeys(self):
    def __iter__(self):
    def itervalues(self):
    def items(self):
    def keys(self):
    def values(self):
    def __len__(self):
    def summary(self):
    def __repr__(self):
    def copy(self):
    def __init__(self):
    def add_cache(self, cache):
    def new_cache(self, name, timeout=None):
    def __delattr__(self, attr):
    def update(self, other):
    def flush(self):
    def __repr__(self):
def _version_checker(module, minver):
def isCryptographyValid():
def isCryptographyAdvanced():
def isPyPy():
def _prompt_changer(attr, val, old):
def _set_conf_sockets():
def _socket_changer(attr, val, old):
def _loglevel_changer(attr, val, old):
def _iface_changer(attr, val, old):
    def __getattribute__(self, attr):
def crypto_validator(func):
    def func_in(*args, **kwargs):
def scapy_delete_temp_files(): def raw(x):
    # type: (Union[Packet]) -> bytes
    """
    Builds a packet and returns its bytes representation.
    This function is and will always be cross-version compatible
    """
    if hasattr(x, "__bytes__"):
        return x.__bytes__()
    return bytes(x) def orb(x):
    # type: (Union[int, str, bytes]) -> int
    """Return ord(x) when not already an int."""
    if isinstance(x, int):
        return x
    return ord(x) class NoPayload(Packet):
    def __new__(cls, *args, **kargs):
        # type: (Type[Packet], *Any, **Any) -> Packet
        singl = cls.__dict__.get("__singl__")
        if singl is None:
            cls.__singl__ = singl = Packet.__new__(cls)
            Packet.__init__(singl)
        return singl

    def __init__(self, *args, **kargs):
        # type: (*Any, **Any) -> None
        pass

    def dissection_done(self, pkt):
        # type: (Packet) -> None
        pass

    def add_payload(self, payload):
        # type: (Union[Packet, bytes]) -> NoReturn
        raise Scapy_Exception("Can't add payload to NoPayload instance")

    def remove_payload(self):
        # type: () -> None
        pass

    def add_underlayer(self, underlayer):
        # type: (Any) -> None
        pass

    def remove_underlayer(self, other):
        # type: (Packet) -> None
        pass

    def copy(self):
        # type: () -> NoPayload
        return self

    def clear_cache(self):
        # type: () -> None
        pass

    def __repr__(self):
        # type: () -> str
        return ""

    def __str__(self):
        # type: () -> str
        return ""

    def __bytes__(self):
        # type: () -> bytes
        return b""

    def __nonzero__(self):
        # type: () -> bool
        return False
    __bool__ = __nonzero__

    def do_build(self):
        # type: () -> bytes
        return b""

    def build(self):
        # type: () -> bytes
        return b""

    def build_padding(self):
        # type: () -> bytes
        return b""

    def build_done(self, p):
        # type: (bytes) -> bytes
        return p

    def build_ps(self, internal=0):
        # type: (int) -> Tuple[bytes, List[Any]]
        return b"", []

    def getfieldval(self, attr):
        # type: (str) -> NoReturn
        raise AttributeError(attr)

    def getfield_and_val(self, attr):
        # type: (str) -> NoReturn
        raise AttributeError(attr)

    def setfieldval(self, attr, val):
        # type: (str, Any) -> NoReturn
        raise AttributeError(attr)

    def delfieldval(self, attr):
        # type: (str) -> NoReturn
        raise AttributeError(attr)

    def hide_defaults(self):
        # type: () -> None
        pass

    def __iter__(self):
        # type: () -> Iterator[Packet]
        return iter([])

    def __eq__(self, other):
        # type: (Any) -> bool
        if isinstance(other, NoPayload):
            return True
        return False

    def hashret(self):
        # type: () -> bytes
        return b""

    def answers(self, other):
        # type: (NoPayload) -> bool
        return isinstance(other, (NoPayload, conf.padding_layer))  # noqa: E501

    def haslayer(self, cls, _subclass=None):
        # type: (Union[Type[Packet], str], Optional[bool]) -> int
        return 0

    def getlayer(self,
                 cls,  # type: Union[int, Type[Packet], str]
                 nb=1,  # type: int
                 _track=None,  # type: Optional[List[int]]
                 _subclass=None,  # type: Optional[bool]
                 **flt  # type: Any
                 ):
        # type: (...) -> Optional[Packet]
        if _track is not None:
            _track.append(nb)
        return None

    def fragment(self, *args, **kargs):
        # type: (*Any, **Any) -> List[Packet]
        raise Scapy_Exception("cannot fragment this packet")

    def show(self, dump=False, indent=3, lvl="", label_lvl=""):
        # type: (bool, int, str, str) -> None
        pass

    def sprintf(self, fmt, relax=1):
        # type: (str, int) -> str
        if relax:
            return "??"
        else:
            raise Scapy_Exception("Format not found [%s]" % fmt)

    def _do_summary(self):
        # type: () -> Tuple[int, str, List[Any]]
        return 0, "", []

    def layers(self):
        # type: () -> List[Type[Packet]]
        return []

    def lastlayer(self, layer=None):
        # type: (Optional[Packet]) -> Packet
        return layer or self

    def command(self):
        # type: () -> str
        return ""

    def route(self):
        # type: () -> Tuple[None, None, None]
        return (None, None, None) class IPTools(object):
class _IPOption_HDR(Packet):
class IPOption(Packet):
class IPOption_EOL(IPOption):
class IPOption_NOP(IPOption):
class IPOption_Security(IPOption):
class IPOption_RR(IPOption):
class IPOption_LSRR(IPOption_RR):
class IPOption_SSRR(IPOption_RR):
class IPOption_Stream_Id(IPOption):
class IPOption_MTU_Probe(IPOption):
class IPOption_MTU_Reply(IPOption_MTU_Probe):
class IPOption_Traceroute(IPOption):
class IPOption_Timestamp(IPOption):
class IPOption_Address_Extension(IPOption):
class IPOption_Router_Alert(IPOption):
class IPOption_SDBM(IPOption):
class RandTCPOptions(VolatileValue):
class TCPOptionsField(StrField):
class ICMPTimeStampField(IntField):
class DestIPField(IPField, DestField):
class IP(Packet, IPTools):
class TCP(Packet):
class UDP(Packet):
class ICMP(Packet):
class IPerror(IP):
class TCPerror(TCP):
class UDPerror(UDP):
class ICMPerror(ICMP):
class TracerouteResult(SndRcvList):
        class IPsphere(vpython.sphere):
class TCP_client(Automaton):
class ICMPEcho_am(AnsweringMachine):
    def whois(self):
    def _ttl(self):
    def ottl(self):
    def hops(self):
    def extract_padding(self, p):
    def register_variant(cls):
    def dispatch_hook(cls, pkt=None, *args, **kargs):
    def get_current_router(self):
    def post_build(self, p, pay):
    def __init__(self, size=None):
    def _fix(self):
    def __bytes__(self):
    def getfield(self, pkt, s):
    def m2i(self, pkt, x):
    def i2h(self, pkt, x):
    def i2m(self, pkt, x):
    def randval(self):
    def i2repr(self, pkt, val):
    def any2i(self, pkt, val):
    def __init__(self, name, default):
    def i2m(self, pkt, x):
    def i2h(self, pkt, x):
    def post_build(self, p, pay):
    def extract_padding(self, s):
    def route(self):
    def hashret(self):
    def answers(self, other):
    def mysummary(self):
    def fragment(self, fragsize=1480):
def in4_chksum(proto, u, p):
    def post_build(self, p, pay):
    def hashret(self):
    def answers(self, other):
    def mysummary(self):
    def post_build(self, p, pay):
    def extract_padding(self, s):
    def hashret(self):
    def answers(self, other):
    def mysummary(self):
    def post_build(self, p, pay):
    def hashret(self):
    def answers(self, other):
    def guess_payload_class(self, payload):
    def mysummary(self):
    def answers(self, other):
    def mysummary(self):
    def answers(self, other):
    def mysummary(self):
    def answers(self, other):
    def mysummary(self):
    def answers(self, other):
    def mysummary(self):
def inet_register_l3(l2, l3):
def fragment(pkt, fragsize=1480):
def overlap_frag(p, overlap, fragsize=8, overlap_fragsize=None):
def _defrag_list(lst, defrag, missfrag):
def _defrag_logic(plist, complete=False):
def defrag(plist):
def defragment(plist):
def _packetlist_timeskew_graph(self, ip, **kargs):
    def _wrap_data(ts_tuple, wrap_seconds=2000):
    def __init__(self, res=None, name="Traceroute", stats=None):
    def show(self):
    def get_trace(self):
    def trace3D(self, join=True):
    def trace3D_notebook(self):
            def __init__(self, ip, **kargs):
            def fullinfos(self):
            def unfull(self):
            def setlabel(self, txt, visible=None):
            def check_double_click(self):
            def action(self):
        def mouse_click(ev):
    def world_trace(self):
    def make_graph(self, ASres=None, padding=0):
    def graph(self, ASres=conf.AS_resolver, padding=0, **kargs):
def traceroute(target, dport=80, minttl=1, maxttl=30, sport=RandShort(), l4=None, filter=None, timeout=2, verbose=None, **kargs):  # noqa: E501
def traceroute_map(ips, **kargs):
    def parse_args(self, ip, port, *args, **kargs):
    def _transmit_packet(self, pkt):
    def master_filter(self, pkt):
    def START(self):
    def SYN_SENT(self):
    def ESTABLISHED(self):
    def LAST_ACK(self):
    def CLOSED(self):
    def STOP(self):
    def STOP_SENT_FIN_ACK(self):
    def connect(self):
    def send_syn(self):
    def synack_received(self, pkt):
    def send_ack_of_synack(self, pkt):
    def incoming_data_received(self, pkt):
    def receive_data(self, pkt):
    def outgoing_data_received(self, fd):
    def send_data(self, d):
    def reset_received(self, pkt):
    def fin_received(self, pkt):
    def send_finack(self, pkt):
    def ack_of_fin_received(self, pkt):
    def stop_requested(self):
    def stop_send_finack(self):
    def stop_fin_received(self, pkt):
    def stop_send_ack(self, pkt):
    def syn_ack_timeout(self):
    def stop_ack_timeout(self):
def report_ports(target, ports):
def IPID_count(lst, funcID=lambda x: x[1].id, funcpres=lambda x: x[1].summary()):  # noqa: E501
def fragleak(target, sport=123, dport=123, timeout=0.2, onlyasc=0, count=None):
def fragleak2(target, timeout=0.4, onlyasc=0, count=None):
    def is_request(self, req):
    def print_reply(self, req, reply):
    def make_reply(self, req):
        X = ct % wrap_seconds
        Y = ((ct - first_creation_time) - ((rt - first_replied_timestamp) / 1000.0))  # noqa: E501 class HTTP(Packet):
    name = "HTTP 1"
    fields_desc = []
    show_indent = 0

    @classmethod
    def dispatch_hook(cls, _pkt=None, *args, **kargs):
        if _pkt and len(_pkt) >= 9:
            from scapy.contrib.http2 import _HTTP2_types, H2Frame
            # To detect a valid HTTP2, we check that the type is correct
            # that the Reserved bit is set and length makes sense.
            while _pkt:
                if len(_pkt) < 9:
                    # Invalid total length
                    return cls
                if ord(_pkt[3:4]) not in _HTTP2_types:
                    # Invalid type
                    return cls
                length = struct.unpack("!I", b"\0" + _pkt[:3])[0] + 9
                if length > len(_pkt):
                    # Invalid length
                    return cls
                sid = struct.unpack("!I", _pkt[5:9])[0]
                if sid >> 31 != 0:
                    # Invalid Reserved bit
                    return cls
                _pkt = _pkt[length:]
            return H2Frame
        return cls

    # tcp_reassemble is used by TCPSession in session.py
    @classmethod
    def tcp_reassemble(cls, data, metadata):
        detect_end = metadata.get("detect_end", None)
        is_unknown = metadata.get("detect_unknown", True)
        if not detect_end or is_unknown:
            metadata["detect_unknown"] = False
            http_packet = HTTP(data)
            # Detect packing method
            if not isinstance(http_packet.payload, _HTTPContent):
                return http_packet
            length = http_packet.Content_Length
            if length is not None:
                # The packet provides a Content-Length attribute: let's
                # use it. When the total size of the frags is high enough,
                # we have the packet
                length = int(length)
                # Subtract the length of the "HTTP*" layer
                if http_packet.payload.payload or length == 0:
                    http_length = len(data) - len(http_packet.payload.payload)
                    detect_end = lambda dat: len(dat) - http_length >= length
                else:
                    # The HTTP layer isn't fully received.
                    detect_end = lambda dat: False
                    metadata["detect_unknown"] = True
            else:
                # It's not Content-Length based. It could be chunked
                encodings = http_packet[HTTP].payload._get_encodings()
                chunked = ("chunked" in encodings)
                is_response = isinstance(http_packet.payload, HTTPResponse)
                if chunked:
                    detect_end = lambda dat: dat.endswith(b"0\r\n\r\n")
                # HTTP Requests that do not have any content,
                # end with a double CRLF
                elif isinstance(http_packet.payload, HTTPRequest):
                    detect_end = lambda dat: dat.endswith(b"\r\n\r\n")
                    # In case we are handling a HTTP Request,
                    # we want to continue assessing the data,
                    # to handle requests with a body (POST)
                    metadata["detect_unknown"] = True
                elif is_response and http_packet.Status_Code == b"101":
                    # If it's an upgrade response, it may also hold a
                    # different protocol data.
                    # make sure all headers are present
                    detect_end = lambda dat: dat.find(b"\r\n\r\n")
                else:
                    # If neither Content-Length nor chunked is specified,
                    # it means it's the TCP packet that contains the data,
                    # or that the information hasn't been given yet.
                    detect_end = lambda dat: metadata.get("tcp_end", False)
                    metadata["detect_unknown"] = True
            metadata["detect_end"] = detect_end
            if detect_end(data):
                return http_packet
        else:
            if detect_end(data):
                http_packet = HTTP(data)
                return http_packet

    def guess_payload_class(self, payload):
        """Decides if the payload is an HTTP Request or Response, or
        something else.
        """
        try:
            prog = re.compile(
                br"^(?:OPTIONS|GET|HEAD|POST|PUT|DELETE|TRACE|CONNECT) "
                br"(?:.+?) "
                br"HTTP/\d\.\d$"
            )
            crlfIndex = payload.index(b"\r\n")
            req = payload[:crlfIndex]
            result = prog.match(req)
            if result:
                return HTTPRequest
            else:
                prog = re.compile(br"^HTTP/\d\.\d \d\d\d .*$")
                result = prog.match(req)
                if result:
                    return HTTPResponse
        except ValueError:
            # Anything that isn't HTTP but on port 80
            pass
        return Raw class HTTPRequest(_HTTPContent):
    name = "HTTP Request"
    fields_desc = [
        # First line
        _HTTPHeaderField("Method", "GET"),
        _HTTPHeaderField("Path", "/"),
        _HTTPHeaderField("Http-Version", "HTTP/1.1"),
        # Headers
    ] + (
        _generate_headers(
            GENERAL_HEADERS,
            REQUEST_HEADERS,
            COMMON_UNSTANDARD_GENERAL_HEADERS,
            COMMON_UNSTANDARD_REQUEST_HEADERS
        )
    ) + [
        _HTTPHeaderField("Unknown-Headers", None),
    ]

    def do_dissect(self, s):
        """From the HTTP packet string, populate the scapy object"""
        first_line, body = _dissect_headers(self, s)
        try:
            Method, Path, HTTPVersion = re.split(br"\s+", first_line, 2)
            self.setfieldval('Method', Method)
            self.setfieldval('Path', Path)
            self.setfieldval('Http_Version', HTTPVersion)
        except ValueError:
            pass
        if body:
            self.raw_packet_cache = s[:-len(body)]
        else:
            self.raw_packet_cache = s
        return body

    def mysummary(self):
        return self.sprintf(
            "%HTTPRequest.Method% %HTTPRequest.Path% "
            "%HTTPRequest.Http_Version%"
        ) class HTTPResponse(_HTTPContent):
    name = "HTTP Response"
    fields_desc = [
        # First line
        _HTTPHeaderField("Http-Version", "HTTP/1.1"),
        _HTTPHeaderField("Status-Code", "200"),
        _HTTPHeaderField("Reason-Phrase", "OK"),
        # Headers
    ] + (
        _generate_headers(
            GENERAL_HEADERS,
            RESPONSE_HEADERS,
            COMMON_UNSTANDARD_GENERAL_HEADERS,
            COMMON_UNSTANDARD_RESPONSE_HEADERS
        )
    ) + [
        _HTTPHeaderField("Unknown-Headers", None),
    ]

    def answers(self, other):
        return HTTPRequest in other

    def do_dissect(self, s):
        ''' From the HTTP packet string, populate the scapy object '''
        first_line, body = _dissect_headers(self, s)
        try:
            HTTPVersion, Status, Reason = re.split(br"\s+", first_line, 2)
            self.setfieldval('Http_Version', HTTPVersion)
            self.setfieldval('Status_Code', Status)
            self.setfieldval('Reason_Phrase', Reason)
        except ValueError:
            pass
        if body:
            self.raw_packet_cache = s[:-len(body)]
        else:
            self.raw_packet_cache = s
        return body

    def mysummary(self):
        return self.sprintf(
            "%HTTPResponse.Http_Version% %HTTPResponse.Status_Code% "
            "%HTTPResponse.Reason_Phrase%"
        ) class IPv6(_IPv6GuessPayload, Packet, IPTools):
    name = "IPv6"
    fields_desc = [BitField("version", 6, 4),
                   BitField("tc", 0, 8),
                   BitField("fl", 0, 20),
                   ShortField("plen", None),
                   ByteEnumField("nh", 59, ipv6nh),
                   ByteField("hlim", 64),
                   SourceIP6Field("src", "dst"),  # dst is for src @ selection
                   DestIP6Field("dst", "::1")]

    def route(self):
        """Used to select the L2 address"""
        dst = self.dst
        if isinstance(dst, Gen):
            dst = next(iter(dst))
        return conf.route6.route(dst)

    def mysummary(self):
        return "%s > %s (%i)" % (self.src, self.dst, self.nh)

    def post_build(self, p, pay):
        p += pay
        if self.plen is None:
            tmp_len = len(p) - 40
            p = p[:4] + struct.pack("!H", tmp_len) + p[6:]
        return p

    def extract_padding(self, data):
        """Extract the IPv6 payload"""

        if self.plen == 0 and self.nh == 0 and len(data) >= 8:
            # Extract Hop-by-Hop extension length
            hbh_len = orb(data[1])
            hbh_len = 8 + hbh_len * 8

            # Extract length from the Jumbogram option
            # Note: the following algorithm take advantage of the Jumbo option
            #        mandatory alignment (4n + 2, RFC2675 Section 2)
            jumbo_len = None
            idx = 0
            offset = 4 * idx + 2
            while offset <= len(data):
                opt_type = orb(data[offset])
                if opt_type == 0xc2:  # Jumbo option
                    jumbo_len = struct.unpack("I", data[offset + 2:offset + 2 + 4])[0]  # noqa: E501
                    break
                offset = 4 * idx + 2
                idx += 1

            if jumbo_len is None:
                log_runtime.info("Scapy did not find a Jumbo option")
                jumbo_len = 0

            tmp_len = hbh_len + jumbo_len
        else:
            tmp_len = self.plen

        return data[:tmp_len], data[tmp_len:]

    def hashret(self):
        if self.nh == 58 and isinstance(self.payload, _ICMPv6):
            if self.payload.type < 128:
                return self.payload.payload.hashret()
            elif (self.payload.type in [133, 134, 135, 136, 144, 145]):
                return struct.pack("B", self.nh) + self.payload.hashret()

        if not conf.checkIPinIP and self.nh in [4, 41]:  # IP, IPv6
            return self.payload.hashret()

        nh = self.nh
        sd = self.dst
        ss = self.src
        if self.nh == 43 and isinstance(self.payload, IPv6ExtHdrRouting):
            # With routing header, the destination is the last
            # address of the IPv6 list if segleft > 0
            nh = self.payload.nh
            try:
                sd = self.addresses[-1]
            except IndexError:
                sd = '::1'
            # TODO: big bug with ICMPv6 error messages as the destination of IPerror6  # noqa: E501
            #       could be anything from the original list ...
            if 1:
                sd = inet_pton(socket.AF_INET6, sd)
                for a in self.addresses:
                    a = inet_pton(socket.AF_INET6, a)
                    sd = strxor(sd, a)
                sd = inet_ntop(socket.AF_INET6, sd)

        if self.nh == 43 and isinstance(self.payload, IPv6ExtHdrSegmentRouting):  # noqa: E501
            # With segment routing header (rh == 4), the destination is
            # the first address of the IPv6 addresses list
            try:
                sd = self.addresses[0]
            except IndexError:
                sd = self.dst

        if self.nh == 44 and isinstance(self.payload, IPv6ExtHdrFragment):
            nh = self.payload.nh

        if self.nh == 0 and isinstance(self.payload, IPv6ExtHdrHopByHop):
            nh = self.payload.nh

        if self.nh == 60 and isinstance(self.payload, IPv6ExtHdrDestOpt):
            foundhao = None
            for o in self.payload.options:
                if isinstance(o, HAO):
                    foundhao = o
            if foundhao:
                nh = self.payload.nh  # XXX what if another extension follows ?
                ss = foundhao.hoa

        if conf.checkIPsrc and conf.checkIPaddr and not in6_ismaddr(sd):
            sd = inet_pton(socket.AF_INET6, sd)
            ss = inet_pton(socket.AF_INET6, ss)
            return strxor(sd, ss) + struct.pack("B", nh) + self.payload.hashret()  # noqa: E501
        else:
            return struct.pack("B", nh) + self.payload.hashret()

    def answers(self, other):
        if not conf.checkIPinIP:  # skip IP in IP and IPv6 in IP
            if self.nh in [4, 41]:
                return self.payload.answers(other)
            if isinstance(other, IPv6) and other.nh in [4, 41]:
                return self.answers(other.payload)
            if isinstance(other, IP) and other.proto in [4, 41]:
                return self.answers(other.payload)
        if not isinstance(other, IPv6):  # self is reply, other is request
            return False
        if conf.checkIPaddr:
            # ss = inet_pton(socket.AF_INET6, self.src)
            sd = inet_pton(socket.AF_INET6, self.dst)
            os = inet_pton(socket.AF_INET6, other.src)
            od = inet_pton(socket.AF_INET6, other.dst)
            # request was sent to a multicast address (other.dst)
            # Check reply destination addr matches request source addr (i.e
            # sd == os) except when reply is multicasted too
            # XXX test mcast scope matching ?
            if in6_ismaddr(other.dst):
                if in6_ismaddr(self.dst):
                    if ((od == sd) or
                            (in6_isaddrllallnodes(self.dst) and in6_isaddrllallservers(other.dst))):  # noqa: E501
                        return self.payload.answers(other.payload)
                    return False
                if (os == sd):
                    return self.payload.answers(other.payload)
                return False
            elif (sd != os):  # or ss != od): <- removed for ICMP errors
                return False
        if self.nh == 58 and isinstance(self.payload, _ICMPv6) and self.payload.type < 128:  # noqa: E501
            # ICMPv6 Error message -> generated by IPv6 packet
            # Note : at the moment, we jump the ICMPv6 specific class
            # to call answers() method of erroneous packet (over
            # initial packet). There can be cases where an ICMPv6 error
            # class could implement a specific answers method that perform
            # a specific task. Currently, don't see any use ...
            return self.payload.payload.answers(other)
        elif other.nh == 0 and isinstance(other.payload, IPv6ExtHdrHopByHop):
            return self.payload.answers(other.payload)
        elif other.nh == 44 and isinstance(other.payload, IPv6ExtHdrFragment):
            return self.payload.answers(other.payload.payload)
        elif other.nh == 43 and isinstance(other.payload, IPv6ExtHdrRouting):
            return self.payload.answers(other.payload.payload)  # Buggy if self.payload is a IPv6ExtHdrRouting  # noqa: E501
        elif other.nh == 43 and isinstance(other.payload, IPv6ExtHdrSegmentRouting):  # noqa: E501
            return self.payload.answers(other.payload.payload)  # Buggy if self.payload is a IPv6ExtHdrRouting  # noqa: E501
        elif other.nh == 60 and isinstance(other.payload, IPv6ExtHdrDestOpt):
            return self.payload.payload.answers(other.payload.payload)
        elif self.nh == 60 and isinstance(self.payload, IPv6ExtHdrDestOpt):  # BU in reply to BRR, for instance  # noqa: E501
            return self.payload.payload.answers(other.payload)
        else:
            if (self.nh != other.nh):
                return False
            return self.payload.answers(other.payload) class RandByte(RandNum):
    def __init__(self):
        # type: () -> None
        RandNum.__init__(self, 0, 2**8 - 1) class RandShort(RandNum):
    def __init__(self):
        # type: () -> None
        RandNum.__init__(self, 0, 2**16 - 1) class RandString(_RandString[bytes]):
    _DEFAULT_CHARS = (string.ascii_uppercase + string.ascii_lowercase +
                      string.digits).encode("utf-8")

    def __init__(self, size=None, chars=_DEFAULT_CHARS):
        # type: (Optional[Union[int, RandNum]], bytes) -> None
        if size is None:
            size = RandNumExpo(0.01)
        self.size = size
        self.chars = chars

    def _command_args(self):
        # type: () -> str
        ret = ""
        if isinstance(self.size, VolatileValue):
            if self.size.lambd != 0.01 or self.size.base != 0:
                ret += "size=%r" % self.size.command()
        else:
            ret += "size=%r" % self.size

        if self.chars != self._DEFAULT_CHARS:
            ret += ", chars=%r" % self.chars
        return ret

    def _fix(self):
        # type: () -> bytes
        s = b""
        for _ in range(int(self.size)):
            rdm_chr = random.choice(self.chars)
            s += rdm_chr if isinstance(rdm_chr, str) else chb(rdm_chr)
        return s
import re
import struct
import random
from scapy.data import KnowledgeBase, select_path
from scapy.config import conf
from scapy.compat import raw, orb
from scapy.packet import NoPayload
from scapy.layers.inet import IP, TCP, TCPOptions
from scapy.layers.http import HTTP, HTTPRequest, HTTPResponse
from scapy.layers.inet6 import IPv6
from scapy.volatile import RandByte, RandShort, RandString
from scapy.error import warning
from scapy.modules.six import integer_types, string_types
from scapy.modules.six.moves import range
        olayout = ""
        optlen = (tcp.dataofs << 2) - 20
        x = raw(tcp)[-optlen:]  # raw bytes of TCP options
        while x:
            onum = orb(x[0])
            if onum == 0:
                x = x[1:]
                olayout += "eol+%i," % len(x)
                if x.strip(b"\x00"):  # non-zero past EOL
                    addq("opt+")
                break
            if onum == 1:
                x = x[1:]
                olayout += "nop,"
                continue
            try:
                olen = orb(x[1])
            except IndexError:  # no room for length field
                addq("bad")
                break
            oval = x[2:olen]
            if onum in tcp_options_p0f:
                ofmt = TCPOptions[0][onum][1]
                olayout += "%s," % tcp_options_p0f[onum]
                optsize = 2 + struct.calcsize(ofmt) if ofmt else 2  # total len
                if len(x) < optsize:  # option would end past end of header
                    addq("bad")
                    break

                if onum == 5:
                    if olen < 10 or olen > 34:  # SACK length out of range
                        addq("bad")
                        break
                else:
                    if olen != optsize:  # length field doesn't fit option type
                        addq("bad")
                        break
                    if ofmt:
                        oval = struct.unpack(ofmt, oval)
                        if len(oval) == 1:
                            oval = oval[0]
                    if onum == 2:
                        mss = oval
                    elif onum == 3:
                        wscale = oval
                        if wscale > 14:
                            addq("exws")
                    elif onum == 8:
                        ts1 = oval[0]
                        if not ts1:
                            addq("ts1-")
                        if oval[1] and (tcp.flags.S and not tcp.flags.A):
                            addq("ts2+")
            else:  # Unknown option, presumably with specified size
                if olen < 2 or olen > 40 or olen > len(x):
                    addq("bad")
                    break
            x = x[olen:]
        olayout = olayout[:-1]

        return cls(olayout, quirks, ip_opt_len, ip_ver, ttl, mss, win, None, wscale, pay_class, ts1)  # noqa: E501

    @classmethod
    def from_raw_sig(cls, sig_line):
        """
        Parses a TCP sig line and returns a tuple consisting of a
        TCP_Signature object and bad_ttl as bool
        """
        ver, ttl, olen, mss, wsize, olayout, quirks, pclass = lparse(sig_line, 8)  # noqa: E501
        wsize, _, scale = wsize.partition(",")

        ip_ver = -1 if ver == "*" else int(ver)
        ttl, bad_ttl = (int(ttl[:-1]), True) if ttl[-1] == "-" else (int(ttl), False)  # noqa: E501
        ip_opt_len = int(olen)
        mss = -1 if mss == "*" else int(mss)
        if wsize == "*":
            win, win_type = (0, WIN_TYPE_ANY)
        elif wsize[:3] == "mss":
            win, win_type = (int(wsize[4:]), WIN_TYPE_MSS)
        elif wsize[0] == "%":
            win, win_type = (int(wsize[1:]), WIN_TYPE_MOD)
        elif wsize[:3] == "mtu":
            win, win_type = (int(wsize[4:]), WIN_TYPE_MTU)
        else:
            win, win_type = (int(wsize), WIN_TYPE_NORMAL)
        wscale = -1 if scale == "*" else int(scale)
        if quirks:
            quirks = frozenset(q for q in quirks.split(","))
        else:
            quirks = frozenset()
        pay_class = -1 if pclass == "*" else int(pclass == "+")

        sig = cls(olayout, quirks, ip_opt_len, ip_ver, ttl, mss, win, win_type, wscale, pay_class, None)  # noqa: E501
        return sig, bad_ttl

    def __str__(self):
        quirks = ",".join(q for q in self.quirks)
        fmt = "%i:%i+%i:%i:%i:%i,%i:%s:%s:%i"
        s = fmt % (self.ip_ver, self.ttl, guess_dist(self.ttl),
                   self.ip_opt_len, self.mss, self.win, self.wscale,
                   self.olayout, quirks, self.pay_class)
        return s


class HTTP_Signature(object):
    __slots__ = ["http_ver", "hdr", "hdr_set", "habsent", "sw"]

    def __init__(self, http_ver, hdr, hdr_set, habsent, sw):
        self.http_ver = http_ver
        self.hdr = hdr
        self.hdr_set = hdr_set
        self.habsent = habsent  # None for packet signatures
        self.sw = sw

    @classmethod
    def from_packet(cls, pkt):
        """
        Receives an HTTP packet (assuming it's valid), and returns
        a HTTP_Signature object
        """

        http_payload = raw(pkt[TCP].payload)