def SrcDstSelector(src, dst): """A selector that matches packets between the specified IP addresses.""" srcver = csocket.AddressVersion(src) dstver = csocket.AddressVersion(dst) if srcver != dstver: raise ValueError("Cross-address family selector specified: %s -> %s" % (src, dst)) prefixlen = net_test.AddressLengthBits(srcver) family = net_test.GetAddressFamily(srcver) return XfrmSelector(saddr=PaddedAddress(src), daddr=PaddedAddress(dst), prefixlen_s=prefixlen, prefixlen_d=prefixlen, family=family)
def AddAddress(self, address, prefixlen, ifindex): """Adds a statically-configured IP address to an interface. The address is created with flags IFA_F_PERMANENT, and, if IPv6, IFA_F_NODAD. The requested scope is RT_SCOPE_UNIVERSE, but at least for IPv6, is instead determined by the kernel. In order to avoid races (see comments in _WaitForAddress above), when configuring IPv6 addresses, the method blocks until it receives an RTM_NEWADDR from the kernel confirming that the address has been added. If the address does not appear within 100ms, AssertionError is thrown. Args: address: A string, the IP address to configure. prefixlen: The prefix length passed to the kernel. If not /32 for IPv4 or /128 for IPv6, the kernel creates an implicit directly-connected route. ifindex: The interface index to add the address to. Raises: AssertionError: An IPv6 address was requested, and it did not appear within the timeout. """ version = csocket.AddressVersion(address) flags = IFA_F_PERMANENT if version == 6: flags |= IFA_F_NODAD sock = self._OpenNetlinkSocket(netlink.NETLINK_ROUTE, groups=RTMGRP_IPV6_IFADDR) self._Address(version, RTM_NEWADDR, address, prefixlen, flags, RT_SCOPE_UNIVERSE, ifindex) if version == 6: self._WaitForAddress(sock, address, ifindex)
def GetRoutes(self, dest, oif, mark, uid, iif=None): version = csocket.AddressVersion(dest) prefixlen = {4: 32, 6: 128}[version] self._Route(version, RTPROT_STATIC, RTM_GETROUTE, 0, dest, prefixlen, None, oif, mark, uid, iif=iif) data = self._Recv() # The response will either be an error or a list of routes. if netlink.NLMsgHdr(data).type == netlink.NLMSG_ERROR: self._ParseAck(data) routes = self._GetMsgList(RTMsg, data, False) return routes
def ExpectProbe(self, is_unicast, addr): version = csocket.AddressVersion(addr) if version == 6: llsrc = self.MyMacAddress(self.netid) if is_unicast: src = self.MyLinkLocalAddress(self.netid) dst = addr else: solicited = inet_pton(AF_INET6, addr) last3bytes = tuple([ord(b) for b in solicited[-3:]]) dst = "ff02::1:ff%02x:%02x%02x" % last3bytes src = self.MyAddress(6, self.netid) expected = (scapy.IPv6(src=src, dst=dst) / scapy.ICMPv6ND_NS(tgt=addr) / scapy.ICMPv6NDOptSrcLLAddr(lladdr=llsrc)) msg = "%s probe" % ("Unicast" if is_unicast else "Multicast") self.ExpectPacketOn(self.netid, msg, expected) else: raise NotImplementedError
def ReceiveUnicastAdvertisement(self, addr, mac, srcaddr=None, dstaddr=None, S=1, O=0, R=1): version = csocket.AddressVersion(addr) if srcaddr is None: srcaddr = addr if dstaddr is None: dstaddr = self.MyLinkLocalAddress(self.netid) if version == 6: packet = (scapy.Ether(src=mac, dst=self.MyMacAddress(self.netid)) / scapy.IPv6(src=srcaddr, dst=dstaddr) / scapy.ICMPv6ND_NA(tgt=addr, S=S, O=O, R=R) / scapy.ICMPv6NDOptDstLLAddr(lladdr=mac)) self.ReceiveEtherPacketOn(self.netid, packet) else: raise NotImplementedError
def DelAddress(self, address, prefixlen, ifindex): self._Address(csocket.AddressVersion(address), RTM_DELADDR, address, prefixlen, 0, 0, ifindex)
def GetNeighbour(self, addr, ifindex): version = csocket.AddressVersion(addr) for msg, args in self.iproute.DumpNeighbours(version, ifindex): if args["NDA_DST"] == addr: return msg, args