1*4dc78e53SAndroid Build Coastguard Worker# 2*4dc78e53SAndroid Build Coastguard Worker# Copyright (c) 2011 Thomas Graf <[email protected]> 3*4dc78e53SAndroid Build Coastguard Worker# 4*4dc78e53SAndroid Build Coastguard Worker 5*4dc78e53SAndroid Build Coastguard Worker"""Module providing access to network links 6*4dc78e53SAndroid Build Coastguard Worker 7*4dc78e53SAndroid Build Coastguard WorkerThis module provides an interface to view configured network links, 8*4dc78e53SAndroid Build Coastguard Workermodify them and to add and delete virtual network links. 9*4dc78e53SAndroid Build Coastguard Worker 10*4dc78e53SAndroid Build Coastguard WorkerThe following is a basic example: 11*4dc78e53SAndroid Build Coastguard Worker import netlink.core as netlink 12*4dc78e53SAndroid Build Coastguard Worker import netlink.route.link as link 13*4dc78e53SAndroid Build Coastguard Worker 14*4dc78e53SAndroid Build Coastguard Worker sock = netlink.Socket() 15*4dc78e53SAndroid Build Coastguard Worker sock.connect(netlink.NETLINK_ROUTE) 16*4dc78e53SAndroid Build Coastguard Worker 17*4dc78e53SAndroid Build Coastguard Worker cache = link.LinkCache() # create new empty link cache 18*4dc78e53SAndroid Build Coastguard Worker cache.refill(sock) # fill cache with all configured links 19*4dc78e53SAndroid Build Coastguard Worker eth0 = cache['eth0'] # lookup link "eth0" 20*4dc78e53SAndroid Build Coastguard Worker print eth0 # print basic configuration 21*4dc78e53SAndroid Build Coastguard Worker 22*4dc78e53SAndroid Build Coastguard WorkerThe module contains the following public classes: 23*4dc78e53SAndroid Build Coastguard Worker 24*4dc78e53SAndroid Build Coastguard Worker - Link -- Represents a network link. Instances can be created directly 25*4dc78e53SAndroid Build Coastguard Worker via the constructor (empty link objects) or via the refill() 26*4dc78e53SAndroid Build Coastguard Worker method of a LinkCache. 27*4dc78e53SAndroid Build Coastguard Worker - LinkCache -- Derived from netlink.Cache, holds any number of 28*4dc78e53SAndroid Build Coastguard Worker network links (Link instances). Main purpose is to keep 29*4dc78e53SAndroid Build Coastguard Worker a local list of all network links configured in the 30*4dc78e53SAndroid Build Coastguard Worker kernel. 31*4dc78e53SAndroid Build Coastguard Worker 32*4dc78e53SAndroid Build Coastguard WorkerThe following public functions exist: 33*4dc78e53SAndroid Build Coastguard Worker - get_from_kernel(socket, name) 34*4dc78e53SAndroid Build Coastguard Worker 35*4dc78e53SAndroid Build Coastguard Worker""" 36*4dc78e53SAndroid Build Coastguard Worker 37*4dc78e53SAndroid Build Coastguard Workerfrom __future__ import absolute_import 38*4dc78e53SAndroid Build Coastguard Worker 39*4dc78e53SAndroid Build Coastguard Worker__version__ = "0.1" 40*4dc78e53SAndroid Build Coastguard Worker__all__ = [ 41*4dc78e53SAndroid Build Coastguard Worker "LinkCache", 42*4dc78e53SAndroid Build Coastguard Worker "Link", 43*4dc78e53SAndroid Build Coastguard Worker] 44*4dc78e53SAndroid Build Coastguard Worker 45*4dc78e53SAndroid Build Coastguard Workerimport socket 46*4dc78e53SAndroid Build Coastguard Workerfrom .. import core as netlink 47*4dc78e53SAndroid Build Coastguard Workerfrom .. import capi as core_capi 48*4dc78e53SAndroid Build Coastguard Workerfrom . import capi as capi 49*4dc78e53SAndroid Build Coastguard Workerfrom .links import inet as inet 50*4dc78e53SAndroid Build Coastguard Workerfrom .. import util as util 51*4dc78e53SAndroid Build Coastguard Worker 52*4dc78e53SAndroid Build Coastguard Worker# Link statistics definitions 53*4dc78e53SAndroid Build Coastguard WorkerRX_PACKETS = 0 54*4dc78e53SAndroid Build Coastguard WorkerTX_PACKETS = 1 55*4dc78e53SAndroid Build Coastguard WorkerRX_BYTES = 2 56*4dc78e53SAndroid Build Coastguard WorkerTX_BYTES = 3 57*4dc78e53SAndroid Build Coastguard WorkerRX_ERRORS = 4 58*4dc78e53SAndroid Build Coastguard WorkerTX_ERRORS = 5 59*4dc78e53SAndroid Build Coastguard WorkerRX_DROPPED = 6 60*4dc78e53SAndroid Build Coastguard WorkerTX_DROPPED = 7 61*4dc78e53SAndroid Build Coastguard WorkerRX_COMPRESSED = 8 62*4dc78e53SAndroid Build Coastguard WorkerTX_COMPRESSED = 9 63*4dc78e53SAndroid Build Coastguard WorkerRX_FIFO_ERR = 10 64*4dc78e53SAndroid Build Coastguard WorkerTX_FIFO_ERR = 11 65*4dc78e53SAndroid Build Coastguard WorkerRX_LEN_ERR = 12 66*4dc78e53SAndroid Build Coastguard WorkerRX_OVER_ERR = 13 67*4dc78e53SAndroid Build Coastguard WorkerRX_CRC_ERR = 14 68*4dc78e53SAndroid Build Coastguard WorkerRX_FRAME_ERR = 15 69*4dc78e53SAndroid Build Coastguard WorkerRX_MISSED_ERR = 16 70*4dc78e53SAndroid Build Coastguard WorkerTX_ABORT_ERR = 17 71*4dc78e53SAndroid Build Coastguard WorkerTX_CARRIER_ERR = 18 72*4dc78e53SAndroid Build Coastguard WorkerTX_HBEAT_ERR = 19 73*4dc78e53SAndroid Build Coastguard WorkerTX_WIN_ERR = 20 74*4dc78e53SAndroid Build Coastguard WorkerCOLLISIONS = 21 75*4dc78e53SAndroid Build Coastguard WorkerMULTICAST = 22 76*4dc78e53SAndroid Build Coastguard WorkerIP6_INPKTS = 23 77*4dc78e53SAndroid Build Coastguard WorkerIP6_INHDRERRORS = 24 78*4dc78e53SAndroid Build Coastguard WorkerIP6_INTOOBIGERRORS = 25 79*4dc78e53SAndroid Build Coastguard WorkerIP6_INNOROUTES = 26 80*4dc78e53SAndroid Build Coastguard WorkerIP6_INADDRERRORS = 27 81*4dc78e53SAndroid Build Coastguard WorkerIP6_INUNKNOWNPROTOS = 28 82*4dc78e53SAndroid Build Coastguard WorkerIP6_INTRUNCATEDPKTS = 29 83*4dc78e53SAndroid Build Coastguard WorkerIP6_INDISCARDS = 30 84*4dc78e53SAndroid Build Coastguard WorkerIP6_INDELIVERS = 31 85*4dc78e53SAndroid Build Coastguard WorkerIP6_OUTFORWDATAGRAMS = 32 86*4dc78e53SAndroid Build Coastguard WorkerIP6_OUTPKTS = 33 87*4dc78e53SAndroid Build Coastguard WorkerIP6_OUTDISCARDS = 34 88*4dc78e53SAndroid Build Coastguard WorkerIP6_OUTNOROUTES = 35 89*4dc78e53SAndroid Build Coastguard WorkerIP6_REASMTIMEOUT = 36 90*4dc78e53SAndroid Build Coastguard WorkerIP6_REASMREQDS = 37 91*4dc78e53SAndroid Build Coastguard WorkerIP6_REASMOKS = 38 92*4dc78e53SAndroid Build Coastguard WorkerIP6_REASMFAILS = 39 93*4dc78e53SAndroid Build Coastguard WorkerIP6_FRAGOKS = 40 94*4dc78e53SAndroid Build Coastguard WorkerIP6_FRAGFAILS = 41 95*4dc78e53SAndroid Build Coastguard WorkerIP6_FRAGCREATES = 42 96*4dc78e53SAndroid Build Coastguard WorkerIP6_INMCASTPKTS = 43 97*4dc78e53SAndroid Build Coastguard WorkerIP6_OUTMCASTPKTS = 44 98*4dc78e53SAndroid Build Coastguard WorkerIP6_INBCASTPKTS = 45 99*4dc78e53SAndroid Build Coastguard WorkerIP6_OUTBCASTPKTS = 46 100*4dc78e53SAndroid Build Coastguard WorkerIP6_INOCTETS = 47 101*4dc78e53SAndroid Build Coastguard WorkerIP6_OUTOCTETS = 48 102*4dc78e53SAndroid Build Coastguard WorkerIP6_INMCASTOCTETS = 49 103*4dc78e53SAndroid Build Coastguard WorkerIP6_OUTMCASTOCTETS = 50 104*4dc78e53SAndroid Build Coastguard WorkerIP6_INBCASTOCTETS = 51 105*4dc78e53SAndroid Build Coastguard WorkerIP6_OUTBCASTOCTETS = 52 106*4dc78e53SAndroid Build Coastguard WorkerICMP6_INMSGS = 53 107*4dc78e53SAndroid Build Coastguard WorkerICMP6_INERRORS = 54 108*4dc78e53SAndroid Build Coastguard WorkerICMP6_OUTMSGS = 55 109*4dc78e53SAndroid Build Coastguard WorkerICMP6_OUTERRORS = 56 110*4dc78e53SAndroid Build Coastguard Worker 111*4dc78e53SAndroid Build Coastguard Worker 112*4dc78e53SAndroid Build Coastguard Workerclass LinkCache(netlink.Cache): 113*4dc78e53SAndroid Build Coastguard Worker """Cache of network links""" 114*4dc78e53SAndroid Build Coastguard Worker 115*4dc78e53SAndroid Build Coastguard Worker def __init__(self, family=socket.AF_UNSPEC, cache=None): 116*4dc78e53SAndroid Build Coastguard Worker if not cache: 117*4dc78e53SAndroid Build Coastguard Worker cache = self._alloc_cache_name("route/link") 118*4dc78e53SAndroid Build Coastguard Worker 119*4dc78e53SAndroid Build Coastguard Worker self._info_module = None 120*4dc78e53SAndroid Build Coastguard Worker self._protocol = netlink.NETLINK_ROUTE 121*4dc78e53SAndroid Build Coastguard Worker self._nl_cache = cache 122*4dc78e53SAndroid Build Coastguard Worker self._set_arg1(family) 123*4dc78e53SAndroid Build Coastguard Worker 124*4dc78e53SAndroid Build Coastguard Worker def __getitem__(self, key): 125*4dc78e53SAndroid Build Coastguard Worker if type(key) is int: 126*4dc78e53SAndroid Build Coastguard Worker link = capi.rtnl_link_get(self._nl_cache, key) 127*4dc78e53SAndroid Build Coastguard Worker else: 128*4dc78e53SAndroid Build Coastguard Worker link = capi.rtnl_link_get_by_name(self._nl_cache, key) 129*4dc78e53SAndroid Build Coastguard Worker 130*4dc78e53SAndroid Build Coastguard Worker if link is None: 131*4dc78e53SAndroid Build Coastguard Worker raise KeyError() 132*4dc78e53SAndroid Build Coastguard Worker else: 133*4dc78e53SAndroid Build Coastguard Worker return Link.from_capi(link) 134*4dc78e53SAndroid Build Coastguard Worker 135*4dc78e53SAndroid Build Coastguard Worker @staticmethod 136*4dc78e53SAndroid Build Coastguard Worker def _new_object(obj): 137*4dc78e53SAndroid Build Coastguard Worker return Link(obj) 138*4dc78e53SAndroid Build Coastguard Worker 139*4dc78e53SAndroid Build Coastguard Worker def _new_cache(self, cache): 140*4dc78e53SAndroid Build Coastguard Worker return LinkCache(family=self.arg1, cache=cache) 141*4dc78e53SAndroid Build Coastguard Worker 142*4dc78e53SAndroid Build Coastguard Worker 143*4dc78e53SAndroid Build Coastguard Workerclass Link(netlink.Object): 144*4dc78e53SAndroid Build Coastguard Worker """Network link""" 145*4dc78e53SAndroid Build Coastguard Worker 146*4dc78e53SAndroid Build Coastguard Worker def __init__(self, obj=None): 147*4dc78e53SAndroid Build Coastguard Worker netlink.Object.__init__(self, "route/link", "link", obj) 148*4dc78e53SAndroid Build Coastguard Worker self._rtnl_link = self._obj2type(self._nl_object) 149*4dc78e53SAndroid Build Coastguard Worker 150*4dc78e53SAndroid Build Coastguard Worker if self.type: 151*4dc78e53SAndroid Build Coastguard Worker self._module_lookup("netlink.route.links." + self.type) 152*4dc78e53SAndroid Build Coastguard Worker 153*4dc78e53SAndroid Build Coastguard Worker self.inet = inet.InetLink(self) 154*4dc78e53SAndroid Build Coastguard Worker self.af = {"inet": self.inet} 155*4dc78e53SAndroid Build Coastguard Worker 156*4dc78e53SAndroid Build Coastguard Worker def __enter__(self): 157*4dc78e53SAndroid Build Coastguard Worker return self 158*4dc78e53SAndroid Build Coastguard Worker 159*4dc78e53SAndroid Build Coastguard Worker def __exit__(self, exc_type, exc_value, tb): 160*4dc78e53SAndroid Build Coastguard Worker if exc_type is None: 161*4dc78e53SAndroid Build Coastguard Worker self.change() 162*4dc78e53SAndroid Build Coastguard Worker else: 163*4dc78e53SAndroid Build Coastguard Worker return False 164*4dc78e53SAndroid Build Coastguard Worker 165*4dc78e53SAndroid Build Coastguard Worker @classmethod 166*4dc78e53SAndroid Build Coastguard Worker def from_capi(cls, obj): 167*4dc78e53SAndroid Build Coastguard Worker return cls(capi.link2obj(obj)) 168*4dc78e53SAndroid Build Coastguard Worker 169*4dc78e53SAndroid Build Coastguard Worker @staticmethod 170*4dc78e53SAndroid Build Coastguard Worker def _obj2type(obj): 171*4dc78e53SAndroid Build Coastguard Worker return capi.obj2link(obj) 172*4dc78e53SAndroid Build Coastguard Worker 173*4dc78e53SAndroid Build Coastguard Worker def __cmp__(self, other): 174*4dc78e53SAndroid Build Coastguard Worker return self.ifindex - other.ifindex 175*4dc78e53SAndroid Build Coastguard Worker 176*4dc78e53SAndroid Build Coastguard Worker @staticmethod 177*4dc78e53SAndroid Build Coastguard Worker def _new_instance(obj): 178*4dc78e53SAndroid Build Coastguard Worker if not obj: 179*4dc78e53SAndroid Build Coastguard Worker raise ValueError() 180*4dc78e53SAndroid Build Coastguard Worker 181*4dc78e53SAndroid Build Coastguard Worker return Link(obj) 182*4dc78e53SAndroid Build Coastguard Worker 183*4dc78e53SAndroid Build Coastguard Worker @property 184*4dc78e53SAndroid Build Coastguard Worker @netlink.nlattr(type=int, immutable=True, fmt=util.num) 185*4dc78e53SAndroid Build Coastguard Worker def ifindex(self): 186*4dc78e53SAndroid Build Coastguard Worker """interface index""" 187*4dc78e53SAndroid Build Coastguard Worker return capi.rtnl_link_get_ifindex(self._rtnl_link) 188*4dc78e53SAndroid Build Coastguard Worker 189*4dc78e53SAndroid Build Coastguard Worker @ifindex.setter 190*4dc78e53SAndroid Build Coastguard Worker def ifindex(self, value): 191*4dc78e53SAndroid Build Coastguard Worker capi.rtnl_link_set_ifindex(self._rtnl_link, int(value)) 192*4dc78e53SAndroid Build Coastguard Worker 193*4dc78e53SAndroid Build Coastguard Worker # ifindex is immutable but we assume that if _orig does not 194*4dc78e53SAndroid Build Coastguard Worker # have an ifindex specified, it was meant to be given here 195*4dc78e53SAndroid Build Coastguard Worker if capi.rtnl_link_get_ifindex(self._orig) == 0: 196*4dc78e53SAndroid Build Coastguard Worker capi.rtnl_link_set_ifindex(self._orig, int(value)) 197*4dc78e53SAndroid Build Coastguard Worker 198*4dc78e53SAndroid Build Coastguard Worker @property 199*4dc78e53SAndroid Build Coastguard Worker @netlink.nlattr(type=str, fmt=util.bold) 200*4dc78e53SAndroid Build Coastguard Worker def name(self): 201*4dc78e53SAndroid Build Coastguard Worker """Name of link""" 202*4dc78e53SAndroid Build Coastguard Worker return capi.rtnl_link_get_name(self._rtnl_link) 203*4dc78e53SAndroid Build Coastguard Worker 204*4dc78e53SAndroid Build Coastguard Worker @name.setter 205*4dc78e53SAndroid Build Coastguard Worker def name(self, value): 206*4dc78e53SAndroid Build Coastguard Worker capi.rtnl_link_set_name(self._rtnl_link, value) 207*4dc78e53SAndroid Build Coastguard Worker 208*4dc78e53SAndroid Build Coastguard Worker # name is the secondary identifier, if _orig does not have 209*4dc78e53SAndroid Build Coastguard Worker # the name specified yet, assume it was meant to be specified 210*4dc78e53SAndroid Build Coastguard Worker # here. ifindex will always take priority, therefore if ifindex 211*4dc78e53SAndroid Build Coastguard Worker # is specified as well, this will be ignored automatically. 212*4dc78e53SAndroid Build Coastguard Worker if capi.rtnl_link_get_name(self._orig) is None: 213*4dc78e53SAndroid Build Coastguard Worker capi.rtnl_link_set_name(self._orig, value) 214*4dc78e53SAndroid Build Coastguard Worker 215*4dc78e53SAndroid Build Coastguard Worker @property 216*4dc78e53SAndroid Build Coastguard Worker @netlink.nlattr(type=str, fmt=util.string) 217*4dc78e53SAndroid Build Coastguard Worker def flags(self): 218*4dc78e53SAndroid Build Coastguard Worker """Flags 219*4dc78e53SAndroid Build Coastguard Worker Setting this property will *Not* reset flags to value you supply in 220*4dc78e53SAndroid Build Coastguard Worker Examples: 221*4dc78e53SAndroid Build Coastguard Worker link.flags = '+xxx' # add xxx flag 222*4dc78e53SAndroid Build Coastguard Worker link.flags = 'xxx' # exactly the same 223*4dc78e53SAndroid Build Coastguard Worker link.flags = '-xxx' # remove xxx flag 224*4dc78e53SAndroid Build Coastguard Worker link.flags = [ '+xxx', '-yyy' ] # list operation 225*4dc78e53SAndroid Build Coastguard Worker """ 226*4dc78e53SAndroid Build Coastguard Worker flags = capi.rtnl_link_get_flags(self._rtnl_link) 227*4dc78e53SAndroid Build Coastguard Worker return capi.rtnl_link_flags2str(flags, 256)[0].split(",") 228*4dc78e53SAndroid Build Coastguard Worker 229*4dc78e53SAndroid Build Coastguard Worker def _set_flag(self, flag): 230*4dc78e53SAndroid Build Coastguard Worker if flag.startswith("-"): 231*4dc78e53SAndroid Build Coastguard Worker i = capi.rtnl_link_str2flags(flag[1:]) 232*4dc78e53SAndroid Build Coastguard Worker capi.rtnl_link_unset_flags(self._rtnl_link, i) 233*4dc78e53SAndroid Build Coastguard Worker elif flag.startswith("+"): 234*4dc78e53SAndroid Build Coastguard Worker i = capi.rtnl_link_str2flags(flag[1:]) 235*4dc78e53SAndroid Build Coastguard Worker capi.rtnl_link_set_flags(self._rtnl_link, i) 236*4dc78e53SAndroid Build Coastguard Worker else: 237*4dc78e53SAndroid Build Coastguard Worker i = capi.rtnl_link_str2flags(flag) 238*4dc78e53SAndroid Build Coastguard Worker capi.rtnl_link_set_flags(self._rtnl_link, i) 239*4dc78e53SAndroid Build Coastguard Worker 240*4dc78e53SAndroid Build Coastguard Worker @flags.setter 241*4dc78e53SAndroid Build Coastguard Worker def flags(self, value): 242*4dc78e53SAndroid Build Coastguard Worker if not (type(value) is str): 243*4dc78e53SAndroid Build Coastguard Worker for flag in value: 244*4dc78e53SAndroid Build Coastguard Worker self._set_flag(flag) 245*4dc78e53SAndroid Build Coastguard Worker else: 246*4dc78e53SAndroid Build Coastguard Worker self._set_flag(value) 247*4dc78e53SAndroid Build Coastguard Worker 248*4dc78e53SAndroid Build Coastguard Worker @property 249*4dc78e53SAndroid Build Coastguard Worker @netlink.nlattr(type=int, fmt=util.num) 250*4dc78e53SAndroid Build Coastguard Worker def mtu(self): 251*4dc78e53SAndroid Build Coastguard Worker """Maximum Transmission Unit""" 252*4dc78e53SAndroid Build Coastguard Worker return capi.rtnl_link_get_mtu(self._rtnl_link) 253*4dc78e53SAndroid Build Coastguard Worker 254*4dc78e53SAndroid Build Coastguard Worker @mtu.setter 255*4dc78e53SAndroid Build Coastguard Worker def mtu(self, value): 256*4dc78e53SAndroid Build Coastguard Worker capi.rtnl_link_set_mtu(self._rtnl_link, int(value)) 257*4dc78e53SAndroid Build Coastguard Worker 258*4dc78e53SAndroid Build Coastguard Worker @property 259*4dc78e53SAndroid Build Coastguard Worker @netlink.nlattr(type=int, immutable=True, fmt=util.num) 260*4dc78e53SAndroid Build Coastguard Worker def family(self): 261*4dc78e53SAndroid Build Coastguard Worker """Address family""" 262*4dc78e53SAndroid Build Coastguard Worker return capi.rtnl_link_get_family(self._rtnl_link) 263*4dc78e53SAndroid Build Coastguard Worker 264*4dc78e53SAndroid Build Coastguard Worker @family.setter 265*4dc78e53SAndroid Build Coastguard Worker def family(self, value): 266*4dc78e53SAndroid Build Coastguard Worker capi.rtnl_link_set_family(self._rtnl_link, value) 267*4dc78e53SAndroid Build Coastguard Worker 268*4dc78e53SAndroid Build Coastguard Worker @property 269*4dc78e53SAndroid Build Coastguard Worker @netlink.nlattr(type=str, fmt=util.addr) 270*4dc78e53SAndroid Build Coastguard Worker def address(self): 271*4dc78e53SAndroid Build Coastguard Worker """Hardware address (MAC address)""" 272*4dc78e53SAndroid Build Coastguard Worker a = capi.rtnl_link_get_addr(self._rtnl_link) 273*4dc78e53SAndroid Build Coastguard Worker return netlink.AbstractAddress(a) 274*4dc78e53SAndroid Build Coastguard Worker 275*4dc78e53SAndroid Build Coastguard Worker @address.setter 276*4dc78e53SAndroid Build Coastguard Worker def address(self, value): 277*4dc78e53SAndroid Build Coastguard Worker capi.rtnl_link_set_addr(self._rtnl_link, value._addr) 278*4dc78e53SAndroid Build Coastguard Worker 279*4dc78e53SAndroid Build Coastguard Worker @property 280*4dc78e53SAndroid Build Coastguard Worker @netlink.nlattr(type=str, fmt=util.addr) 281*4dc78e53SAndroid Build Coastguard Worker def broadcast(self): 282*4dc78e53SAndroid Build Coastguard Worker """Hardware broadcast address""" 283*4dc78e53SAndroid Build Coastguard Worker a = capi.rtnl_link_get_broadcast(self._rtnl_link) 284*4dc78e53SAndroid Build Coastguard Worker return netlink.AbstractAddress(a) 285*4dc78e53SAndroid Build Coastguard Worker 286*4dc78e53SAndroid Build Coastguard Worker @broadcast.setter 287*4dc78e53SAndroid Build Coastguard Worker def broadcast(self, value): 288*4dc78e53SAndroid Build Coastguard Worker capi.rtnl_link_set_broadcast(self._rtnl_link, value._addr) 289*4dc78e53SAndroid Build Coastguard Worker 290*4dc78e53SAndroid Build Coastguard Worker @property 291*4dc78e53SAndroid Build Coastguard Worker @netlink.nlattr(type=str, immutable=True, fmt=util.string) 292*4dc78e53SAndroid Build Coastguard Worker def qdisc(self): 293*4dc78e53SAndroid Build Coastguard Worker """Name of qdisc (cannot be changed)""" 294*4dc78e53SAndroid Build Coastguard Worker return capi.rtnl_link_get_qdisc(self._rtnl_link) 295*4dc78e53SAndroid Build Coastguard Worker 296*4dc78e53SAndroid Build Coastguard Worker @qdisc.setter 297*4dc78e53SAndroid Build Coastguard Worker def qdisc(self, value): 298*4dc78e53SAndroid Build Coastguard Worker capi.rtnl_link_set_qdisc(self._rtnl_link, value) 299*4dc78e53SAndroid Build Coastguard Worker 300*4dc78e53SAndroid Build Coastguard Worker @property 301*4dc78e53SAndroid Build Coastguard Worker @netlink.nlattr(type=int, fmt=util.num) 302*4dc78e53SAndroid Build Coastguard Worker def txqlen(self): 303*4dc78e53SAndroid Build Coastguard Worker """Length of transmit queue""" 304*4dc78e53SAndroid Build Coastguard Worker return capi.rtnl_link_get_txqlen(self._rtnl_link) 305*4dc78e53SAndroid Build Coastguard Worker 306*4dc78e53SAndroid Build Coastguard Worker @txqlen.setter 307*4dc78e53SAndroid Build Coastguard Worker def txqlen(self, value): 308*4dc78e53SAndroid Build Coastguard Worker capi.rtnl_link_set_txqlen(self._rtnl_link, int(value)) 309*4dc78e53SAndroid Build Coastguard Worker 310*4dc78e53SAndroid Build Coastguard Worker @property 311*4dc78e53SAndroid Build Coastguard Worker @netlink.nlattr(type=str, immutable=True, fmt=util.string) 312*4dc78e53SAndroid Build Coastguard Worker def arptype(self): 313*4dc78e53SAndroid Build Coastguard Worker """Type of link (cannot be changed)""" 314*4dc78e53SAndroid Build Coastguard Worker type_ = capi.rtnl_link_get_arptype(self._rtnl_link) 315*4dc78e53SAndroid Build Coastguard Worker return core_capi.nl_llproto2str(type_, 64)[0] 316*4dc78e53SAndroid Build Coastguard Worker 317*4dc78e53SAndroid Build Coastguard Worker @arptype.setter 318*4dc78e53SAndroid Build Coastguard Worker def arptype(self, value): 319*4dc78e53SAndroid Build Coastguard Worker i = core_capi.nl_str2llproto(value) 320*4dc78e53SAndroid Build Coastguard Worker capi.rtnl_link_set_arptype(self._rtnl_link, i) 321*4dc78e53SAndroid Build Coastguard Worker 322*4dc78e53SAndroid Build Coastguard Worker @property 323*4dc78e53SAndroid Build Coastguard Worker @netlink.nlattr(type=str, immutable=True, fmt=util.string, title="state") 324*4dc78e53SAndroid Build Coastguard Worker def operstate(self): 325*4dc78e53SAndroid Build Coastguard Worker """Operational status""" 326*4dc78e53SAndroid Build Coastguard Worker operstate = capi.rtnl_link_get_operstate(self._rtnl_link) 327*4dc78e53SAndroid Build Coastguard Worker return capi.rtnl_link_operstate2str(operstate, 32)[0] 328*4dc78e53SAndroid Build Coastguard Worker 329*4dc78e53SAndroid Build Coastguard Worker @operstate.setter 330*4dc78e53SAndroid Build Coastguard Worker def operstate(self, value): 331*4dc78e53SAndroid Build Coastguard Worker i = capi.rtnl_link_str2operstate(value) 332*4dc78e53SAndroid Build Coastguard Worker capi.rtnl_link_set_operstate(self._rtnl_link, i) 333*4dc78e53SAndroid Build Coastguard Worker 334*4dc78e53SAndroid Build Coastguard Worker @property 335*4dc78e53SAndroid Build Coastguard Worker @netlink.nlattr(type=str, immutable=True, fmt=util.string) 336*4dc78e53SAndroid Build Coastguard Worker def mode(self): 337*4dc78e53SAndroid Build Coastguard Worker """Link mode""" 338*4dc78e53SAndroid Build Coastguard Worker mode = capi.rtnl_link_get_linkmode(self._rtnl_link) 339*4dc78e53SAndroid Build Coastguard Worker return capi.rtnl_link_mode2str(mode, 32)[0] 340*4dc78e53SAndroid Build Coastguard Worker 341*4dc78e53SAndroid Build Coastguard Worker @mode.setter 342*4dc78e53SAndroid Build Coastguard Worker def mode(self, value): 343*4dc78e53SAndroid Build Coastguard Worker i = capi.rtnl_link_str2mode(value) 344*4dc78e53SAndroid Build Coastguard Worker capi.rtnl_link_set_linkmode(self._rtnl_link, i) 345*4dc78e53SAndroid Build Coastguard Worker 346*4dc78e53SAndroid Build Coastguard Worker @property 347*4dc78e53SAndroid Build Coastguard Worker @netlink.nlattr(type=str, fmt=util.string) 348*4dc78e53SAndroid Build Coastguard Worker def alias(self): 349*4dc78e53SAndroid Build Coastguard Worker """Interface alias (SNMP)""" 350*4dc78e53SAndroid Build Coastguard Worker return capi.rtnl_link_get_ifalias(self._rtnl_link) 351*4dc78e53SAndroid Build Coastguard Worker 352*4dc78e53SAndroid Build Coastguard Worker @alias.setter 353*4dc78e53SAndroid Build Coastguard Worker def alias(self, value): 354*4dc78e53SAndroid Build Coastguard Worker capi.rtnl_link_set_ifalias(self._rtnl_link, value) 355*4dc78e53SAndroid Build Coastguard Worker 356*4dc78e53SAndroid Build Coastguard Worker @property 357*4dc78e53SAndroid Build Coastguard Worker @netlink.nlattr(type=str, fmt=util.string) 358*4dc78e53SAndroid Build Coastguard Worker def type(self): 359*4dc78e53SAndroid Build Coastguard Worker """Link type""" 360*4dc78e53SAndroid Build Coastguard Worker return capi.rtnl_link_get_type(self._rtnl_link) 361*4dc78e53SAndroid Build Coastguard Worker 362*4dc78e53SAndroid Build Coastguard Worker @type.setter 363*4dc78e53SAndroid Build Coastguard Worker def type(self, value): 364*4dc78e53SAndroid Build Coastguard Worker if capi.rtnl_link_set_type(self._rtnl_link, value) < 0: 365*4dc78e53SAndroid Build Coastguard Worker raise NameError("unknown info type") 366*4dc78e53SAndroid Build Coastguard Worker 367*4dc78e53SAndroid Build Coastguard Worker self._module_lookup("netlink.route.links." + value) 368*4dc78e53SAndroid Build Coastguard Worker 369*4dc78e53SAndroid Build Coastguard Worker def get_stat(self, stat): 370*4dc78e53SAndroid Build Coastguard Worker """Retrieve statistical information""" 371*4dc78e53SAndroid Build Coastguard Worker if type(stat) is str: 372*4dc78e53SAndroid Build Coastguard Worker stat = capi.rtnl_link_str2stat(stat) 373*4dc78e53SAndroid Build Coastguard Worker if stat < 0: 374*4dc78e53SAndroid Build Coastguard Worker raise NameError("unknown name of statistic") 375*4dc78e53SAndroid Build Coastguard Worker 376*4dc78e53SAndroid Build Coastguard Worker return capi.rtnl_link_get_stat(self._rtnl_link, stat) 377*4dc78e53SAndroid Build Coastguard Worker 378*4dc78e53SAndroid Build Coastguard Worker def enslave(self, slave, sock=None): 379*4dc78e53SAndroid Build Coastguard Worker if not sock: 380*4dc78e53SAndroid Build Coastguard Worker sock = netlink.lookup_socket(netlink.NETLINK_ROUTE) 381*4dc78e53SAndroid Build Coastguard Worker 382*4dc78e53SAndroid Build Coastguard Worker return capi.rtnl_link_enslave(sock._sock, self._rtnl_link, slave._rtnl_link) 383*4dc78e53SAndroid Build Coastguard Worker 384*4dc78e53SAndroid Build Coastguard Worker def release(self, slave, sock=None): 385*4dc78e53SAndroid Build Coastguard Worker if not sock: 386*4dc78e53SAndroid Build Coastguard Worker sock = netlink.lookup_socket(netlink.NETLINK_ROUTE) 387*4dc78e53SAndroid Build Coastguard Worker 388*4dc78e53SAndroid Build Coastguard Worker return capi.rtnl_link_release(sock._sock, self._rtnl_link, slave._rtnl_link) 389*4dc78e53SAndroid Build Coastguard Worker 390*4dc78e53SAndroid Build Coastguard Worker def add(self, sock=None, flags=None): 391*4dc78e53SAndroid Build Coastguard Worker if not sock: 392*4dc78e53SAndroid Build Coastguard Worker sock = netlink.lookup_socket(netlink.NETLINK_ROUTE) 393*4dc78e53SAndroid Build Coastguard Worker 394*4dc78e53SAndroid Build Coastguard Worker if not flags: 395*4dc78e53SAndroid Build Coastguard Worker flags = netlink.NLM_F_CREATE 396*4dc78e53SAndroid Build Coastguard Worker 397*4dc78e53SAndroid Build Coastguard Worker ret = capi.rtnl_link_add(sock._sock, self._rtnl_link, flags) 398*4dc78e53SAndroid Build Coastguard Worker if ret < 0: 399*4dc78e53SAndroid Build Coastguard Worker raise netlink.KernelError(ret) 400*4dc78e53SAndroid Build Coastguard Worker 401*4dc78e53SAndroid Build Coastguard Worker def change(self, sock=None, flags=0): 402*4dc78e53SAndroid Build Coastguard Worker """Commit changes made to the link object""" 403*4dc78e53SAndroid Build Coastguard Worker if sock is None: 404*4dc78e53SAndroid Build Coastguard Worker sock = netlink.lookup_socket(netlink.NETLINK_ROUTE) 405*4dc78e53SAndroid Build Coastguard Worker 406*4dc78e53SAndroid Build Coastguard Worker if not self._orig: 407*4dc78e53SAndroid Build Coastguard Worker raise netlink.NetlinkError("Original link not available") 408*4dc78e53SAndroid Build Coastguard Worker ret = capi.rtnl_link_change(sock._sock, self._orig, self._rtnl_link, flags) 409*4dc78e53SAndroid Build Coastguard Worker if ret < 0: 410*4dc78e53SAndroid Build Coastguard Worker raise netlink.KernelError(ret) 411*4dc78e53SAndroid Build Coastguard Worker 412*4dc78e53SAndroid Build Coastguard Worker def delete(self, sock=None): 413*4dc78e53SAndroid Build Coastguard Worker """Attempt to delete this link in the kernel""" 414*4dc78e53SAndroid Build Coastguard Worker if sock is None: 415*4dc78e53SAndroid Build Coastguard Worker sock = netlink.lookup_socket(netlink.NETLINK_ROUTE) 416*4dc78e53SAndroid Build Coastguard Worker 417*4dc78e53SAndroid Build Coastguard Worker ret = capi.rtnl_link_delete(sock._sock, self._rtnl_link) 418*4dc78e53SAndroid Build Coastguard Worker if ret < 0: 419*4dc78e53SAndroid Build Coastguard Worker raise netlink.KernelError(ret) 420*4dc78e53SAndroid Build Coastguard Worker 421*4dc78e53SAndroid Build Coastguard Worker ################################################################### 422*4dc78e53SAndroid Build Coastguard Worker # private properties 423*4dc78e53SAndroid Build Coastguard Worker # 424*4dc78e53SAndroid Build Coastguard Worker # Used for formatting output. USE AT OWN RISK 425*4dc78e53SAndroid Build Coastguard Worker @property 426*4dc78e53SAndroid Build Coastguard Worker def _state(self): 427*4dc78e53SAndroid Build Coastguard Worker if "up" in self.flags: 428*4dc78e53SAndroid Build Coastguard Worker buf = util.good("up") 429*4dc78e53SAndroid Build Coastguard Worker if "lowerup" not in self.flags: 430*4dc78e53SAndroid Build Coastguard Worker buf += " " + util.bad("no-carrier") 431*4dc78e53SAndroid Build Coastguard Worker else: 432*4dc78e53SAndroid Build Coastguard Worker buf = util.bad("down") 433*4dc78e53SAndroid Build Coastguard Worker return buf 434*4dc78e53SAndroid Build Coastguard Worker 435*4dc78e53SAndroid Build Coastguard Worker @property 436*4dc78e53SAndroid Build Coastguard Worker def _brief(self): 437*4dc78e53SAndroid Build Coastguard Worker return self._module_brief() + self._foreach_af("brief") 438*4dc78e53SAndroid Build Coastguard Worker 439*4dc78e53SAndroid Build Coastguard Worker @property 440*4dc78e53SAndroid Build Coastguard Worker def _flags(self): 441*4dc78e53SAndroid Build Coastguard Worker ignore = [ 442*4dc78e53SAndroid Build Coastguard Worker "up", 443*4dc78e53SAndroid Build Coastguard Worker "running", 444*4dc78e53SAndroid Build Coastguard Worker "lowerup", 445*4dc78e53SAndroid Build Coastguard Worker ] 446*4dc78e53SAndroid Build Coastguard Worker return ",".join([flag for flag in self.flags if flag not in ignore]) 447*4dc78e53SAndroid Build Coastguard Worker 448*4dc78e53SAndroid Build Coastguard Worker def _foreach_af(self, name, args=None): 449*4dc78e53SAndroid Build Coastguard Worker buf = "" 450*4dc78e53SAndroid Build Coastguard Worker for af in self.af: 451*4dc78e53SAndroid Build Coastguard Worker try: 452*4dc78e53SAndroid Build Coastguard Worker func = getattr(self.af[af], name) 453*4dc78e53SAndroid Build Coastguard Worker s = str(func(args)) 454*4dc78e53SAndroid Build Coastguard Worker if len(s) > 0: 455*4dc78e53SAndroid Build Coastguard Worker buf += " " + s 456*4dc78e53SAndroid Build Coastguard Worker except AttributeError: 457*4dc78e53SAndroid Build Coastguard Worker pass 458*4dc78e53SAndroid Build Coastguard Worker return buf 459*4dc78e53SAndroid Build Coastguard Worker 460*4dc78e53SAndroid Build Coastguard Worker def format(self, details=False, stats=False, indent=""): 461*4dc78e53SAndroid Build Coastguard Worker """Return link as formatted text""" 462*4dc78e53SAndroid Build Coastguard Worker fmt = util.MyFormatter(self, indent) 463*4dc78e53SAndroid Build Coastguard Worker 464*4dc78e53SAndroid Build Coastguard Worker buf = fmt.format( 465*4dc78e53SAndroid Build Coastguard Worker "{a|ifindex} {a|name} {a|arptype} {a|address} " 466*4dc78e53SAndroid Build Coastguard Worker "{a|_state} <{a|_flags}> {a|_brief}" 467*4dc78e53SAndroid Build Coastguard Worker ) 468*4dc78e53SAndroid Build Coastguard Worker 469*4dc78e53SAndroid Build Coastguard Worker if details: 470*4dc78e53SAndroid Build Coastguard Worker buf += fmt.nl("\t{t|mtu} {t|txqlen} {t|weight} " "{t|qdisc} {t|operstate}") 471*4dc78e53SAndroid Build Coastguard Worker buf += fmt.nl("\t{t|broadcast} {t|alias}") 472*4dc78e53SAndroid Build Coastguard Worker 473*4dc78e53SAndroid Build Coastguard Worker buf += self._foreach_af("details", fmt) 474*4dc78e53SAndroid Build Coastguard Worker 475*4dc78e53SAndroid Build Coastguard Worker if stats: 476*4dc78e53SAndroid Build Coastguard Worker lst = [ 477*4dc78e53SAndroid Build Coastguard Worker ["Packets", RX_PACKETS, TX_PACKETS], 478*4dc78e53SAndroid Build Coastguard Worker ["Bytes", RX_BYTES, TX_BYTES], 479*4dc78e53SAndroid Build Coastguard Worker ["Errors", RX_ERRORS, TX_ERRORS], 480*4dc78e53SAndroid Build Coastguard Worker ["Dropped", RX_DROPPED, TX_DROPPED], 481*4dc78e53SAndroid Build Coastguard Worker ["Compressed", RX_COMPRESSED, TX_COMPRESSED], 482*4dc78e53SAndroid Build Coastguard Worker ["FIFO Errors", RX_FIFO_ERR, TX_FIFO_ERR], 483*4dc78e53SAndroid Build Coastguard Worker ["Length Errors", RX_LEN_ERR, None], 484*4dc78e53SAndroid Build Coastguard Worker ["Over Errors", RX_OVER_ERR, None], 485*4dc78e53SAndroid Build Coastguard Worker ["CRC Errors", RX_CRC_ERR, None], 486*4dc78e53SAndroid Build Coastguard Worker ["Frame Errors", RX_FRAME_ERR, None], 487*4dc78e53SAndroid Build Coastguard Worker ["Missed Errors", RX_MISSED_ERR, None], 488*4dc78e53SAndroid Build Coastguard Worker ["Abort Errors", None, TX_ABORT_ERR], 489*4dc78e53SAndroid Build Coastguard Worker ["Carrier Errors", None, TX_CARRIER_ERR], 490*4dc78e53SAndroid Build Coastguard Worker ["Heartbeat Errors", None, TX_HBEAT_ERR], 491*4dc78e53SAndroid Build Coastguard Worker ["Window Errors", None, TX_WIN_ERR], 492*4dc78e53SAndroid Build Coastguard Worker ["Collisions", None, COLLISIONS], 493*4dc78e53SAndroid Build Coastguard Worker ["Multicast", None, MULTICAST], 494*4dc78e53SAndroid Build Coastguard Worker ["", None, None], 495*4dc78e53SAndroid Build Coastguard Worker ["Ipv6:", None, None], 496*4dc78e53SAndroid Build Coastguard Worker ["Packets", IP6_INPKTS, IP6_OUTPKTS], 497*4dc78e53SAndroid Build Coastguard Worker ["Bytes", IP6_INOCTETS, IP6_OUTOCTETS], 498*4dc78e53SAndroid Build Coastguard Worker ["Discards", IP6_INDISCARDS, IP6_OUTDISCARDS], 499*4dc78e53SAndroid Build Coastguard Worker ["Multicast Packets", IP6_INMCASTPKTS, IP6_OUTMCASTPKTS], 500*4dc78e53SAndroid Build Coastguard Worker ["Multicast Bytes", IP6_INMCASTOCTETS, IP6_OUTMCASTOCTETS], 501*4dc78e53SAndroid Build Coastguard Worker ["Broadcast Packets", IP6_INBCASTPKTS, IP6_OUTBCASTPKTS], 502*4dc78e53SAndroid Build Coastguard Worker ["Broadcast Bytes", IP6_INBCASTOCTETS, IP6_OUTBCASTOCTETS], 503*4dc78e53SAndroid Build Coastguard Worker ["Delivers", IP6_INDELIVERS, None], 504*4dc78e53SAndroid Build Coastguard Worker ["Forwarded", None, IP6_OUTFORWDATAGRAMS], 505*4dc78e53SAndroid Build Coastguard Worker ["No Routes", IP6_INNOROUTES, IP6_OUTNOROUTES], 506*4dc78e53SAndroid Build Coastguard Worker ["Header Errors", IP6_INHDRERRORS, None], 507*4dc78e53SAndroid Build Coastguard Worker ["Too Big Errors", IP6_INTOOBIGERRORS, None], 508*4dc78e53SAndroid Build Coastguard Worker ["Address Errors", IP6_INADDRERRORS, None], 509*4dc78e53SAndroid Build Coastguard Worker ["Unknown Protocol", IP6_INUNKNOWNPROTOS, None], 510*4dc78e53SAndroid Build Coastguard Worker ["Truncated Packets", IP6_INTRUNCATEDPKTS, None], 511*4dc78e53SAndroid Build Coastguard Worker ["Reasm Timeouts", IP6_REASMTIMEOUT, None], 512*4dc78e53SAndroid Build Coastguard Worker ["Reasm Requests", IP6_REASMREQDS, None], 513*4dc78e53SAndroid Build Coastguard Worker ["Reasm Failures", IP6_REASMFAILS, None], 514*4dc78e53SAndroid Build Coastguard Worker ["Reasm OK", IP6_REASMOKS, None], 515*4dc78e53SAndroid Build Coastguard Worker ["Frag Created", None, IP6_FRAGCREATES], 516*4dc78e53SAndroid Build Coastguard Worker ["Frag Failures", None, IP6_FRAGFAILS], 517*4dc78e53SAndroid Build Coastguard Worker ["Frag OK", None, IP6_FRAGOKS], 518*4dc78e53SAndroid Build Coastguard Worker ["", None, None], 519*4dc78e53SAndroid Build Coastguard Worker ["ICMPv6:", None, None], 520*4dc78e53SAndroid Build Coastguard Worker ["Messages", ICMP6_INMSGS, ICMP6_OUTMSGS], 521*4dc78e53SAndroid Build Coastguard Worker ["Errors", ICMP6_INERRORS, ICMP6_OUTERRORS], 522*4dc78e53SAndroid Build Coastguard Worker ] 523*4dc78e53SAndroid Build Coastguard Worker 524*4dc78e53SAndroid Build Coastguard Worker buf += "\n\t%s%s%s%s\n" % ( 525*4dc78e53SAndroid Build Coastguard Worker 33 * " ", 526*4dc78e53SAndroid Build Coastguard Worker util.title("RX"), 527*4dc78e53SAndroid Build Coastguard Worker 15 * " ", 528*4dc78e53SAndroid Build Coastguard Worker util.title("TX"), 529*4dc78e53SAndroid Build Coastguard Worker ) 530*4dc78e53SAndroid Build Coastguard Worker 531*4dc78e53SAndroid Build Coastguard Worker for row in lst: 532*4dc78e53SAndroid Build Coastguard Worker row[0] = util.kw(row[0]) 533*4dc78e53SAndroid Build Coastguard Worker row[1] = self.get_stat(row[1]) if row[1] else "" 534*4dc78e53SAndroid Build Coastguard Worker row[2] = self.get_stat(row[2]) if row[2] else "" 535*4dc78e53SAndroid Build Coastguard Worker buf += "\t{0[0]:27} {0[1]:>16} {0[2]:>16}\n".format(row) 536*4dc78e53SAndroid Build Coastguard Worker 537*4dc78e53SAndroid Build Coastguard Worker buf += self._foreach_af("stats") 538*4dc78e53SAndroid Build Coastguard Worker 539*4dc78e53SAndroid Build Coastguard Worker return buf 540*4dc78e53SAndroid Build Coastguard Worker 541*4dc78e53SAndroid Build Coastguard Worker 542*4dc78e53SAndroid Build Coastguard Workerdef get(name, sock=None): 543*4dc78e53SAndroid Build Coastguard Worker """Lookup Link object directly from kernel""" 544*4dc78e53SAndroid Build Coastguard Worker if not name: 545*4dc78e53SAndroid Build Coastguard Worker raise ValueError() 546*4dc78e53SAndroid Build Coastguard Worker 547*4dc78e53SAndroid Build Coastguard Worker if not sock: 548*4dc78e53SAndroid Build Coastguard Worker sock = netlink.lookup_socket(netlink.NETLINK_ROUTE) 549*4dc78e53SAndroid Build Coastguard Worker 550*4dc78e53SAndroid Build Coastguard Worker link = capi.get_from_kernel(sock._sock, 0, name) 551*4dc78e53SAndroid Build Coastguard Worker if not link: 552*4dc78e53SAndroid Build Coastguard Worker return None 553*4dc78e53SAndroid Build Coastguard Worker 554*4dc78e53SAndroid Build Coastguard Worker return Link.from_capi(link) 555*4dc78e53SAndroid Build Coastguard Worker 556*4dc78e53SAndroid Build Coastguard Worker 557*4dc78e53SAndroid Build Coastguard Worker_link_cache = LinkCache() 558*4dc78e53SAndroid Build Coastguard Worker 559*4dc78e53SAndroid Build Coastguard Worker 560*4dc78e53SAndroid Build Coastguard Workerdef resolve(name): 561*4dc78e53SAndroid Build Coastguard Worker _link_cache.refill() 562*4dc78e53SAndroid Build Coastguard Worker return _link_cache[name] 563