1
2
3
4
5
6
7
8
9
10
11
12
13
14 __doc__="""IpInterface
15
16 IpInterface is a collection of devices and subsystems that make
17 up a business function
18 """
19
20 import re
21 import copy
22 import logging
23 log = logging.getLogger("zen.IpInterface")
24
25 from Globals import DTMLFile
26 from Globals import InitializeClass
27 from Acquisition import aq_base
28 from App.Dialogs import MessageDialog
29 from AccessControl import ClassSecurityInfo
30 from zope.event import notify
31 from zope.container.contained import ObjectMovedEvent
32
33 from Products.ZenRelations.RelSchema import *
34
35 from Products.ZenUtils.Utils import localIpCheck, localInterfaceCheck
36 from Products.ZenUtils.IpUtil import *
37
38 from ConfmonPropManager import ConfmonPropManager
39 from OSComponent import OSComponent
40 from Products.ZenModel.Exceptions import *
41 from Products.ZenModel.Linkable import Layer2Linkable
42
43 from Products.ZenModel.ZenossSecurity import *
44
57
58 addIpInterface = DTMLFile('dtml/addIpInterface',globals())
59
60
62 """
63 IpInterface object
64 """
65
66 portal_type = meta_type = 'IpInterface'
67
68 manage_editIpInterfaceForm = DTMLFile('dtml/manageEditIpInterface',
69 globals())
70
71
72
73
74
75 ifindex = '0'
76 interfaceName = ''
77 macaddress = ""
78 type = ""
79 description = ""
80 mtu = 0
81 speed = 0
82 adminStatus = 0
83 operStatus = 0
84 duplex = 0
85 _ipAddresses = []
86
87
88 _properties = OSComponent._properties + (
89 {'id':'ips', 'type':'lines', 'mode':'w', 'setter':'setIpAddresses'},
90 {'id':'interfaceName', 'type':'string', 'mode':'w'},
91 {'id':'ifindex', 'type':'string', 'mode':'w'},
92 {'id':'macaddress', 'type':'string', 'mode':'w'},
93 {'id':'type', 'type':'string', 'mode':'w'},
94 {'id':'description', 'type':'string', 'mode':'w'},
95 {'id':'mtu', 'type':'int', 'mode':'w'},
96 {'id':'speed', 'type':'long', 'mode':'w'},
97 {'id':'adminStatus', 'type':'int', 'mode':'w'},
98 {'id':'operStatus', 'type':'int', 'mode':'w'},
99 {'id':'duplex', 'type':'int', 'mode':'w'},
100 )
101
102 _relations = OSComponent._relations + (
103 ("os", ToOne(ToManyCont,"Products.ZenModel.OperatingSystem","interfaces")),
104 ("ipaddresses", ToMany(ToOne,"Products.ZenModel.IpAddress","interface")),
105 ("iproutes", ToMany(ToOne,"Products.ZenModel.IpRouteEntry","interface")),
106 )
107
108 zNoPropertiesCopy = ('ips','macaddress')
109
110 localipcheck = re.compile(r'^127.|^0.|^::1$|^fe80:').search
111 localintcheck = re.compile(r'^lo0').search
112
113 defaultIgnoreTypes = ('Other', 'softwareLoopback', 'CATV MAC Layer')
114
115 factory_type_information = (
116 {
117 'id' : 'IpInterface',
118 'meta_type' : 'IpInterface',
119 'description' : """Arbitrary device grouping class""",
120 'icon' : 'IpInterface_icon.gif',
121 'product' : 'ZenModel',
122 'factory' : 'manage_addIpInterface',
123 'immediate_view' : 'viewIpInterface',
124 'actions' :
125 (
126 { 'id' : 'status'
127 , 'name' : 'Status'
128 , 'action' : 'viewIpInterface'
129 , 'permissions' : (ZEN_VIEW,)
130 },
131 { 'id' : 'events'
132 , 'name' : 'Events'
133 , 'action' : 'viewEvents'
134 , 'permissions' : (ZEN_VIEW, )
135 },
136 { 'id' : 'perfConf'
137 , 'name' : 'Template'
138 , 'action' : 'objTemplates'
139 , 'permissions' : ("Change Device", )
140 },
141 )
142 },
143 )
144
145 security = ClassSecurityInfo()
146
153
154
155 security.declareProtected('View', 'viewName')
157 """
158 Use the unmagled interface name for display
159 """
160 return self.interfaceName.rstrip('\x00')
161 name = primarySortKey = viewName
162
164 """
165 Override from PerpertyManager to handle checks and ip creation
166 """
167 self._wrapperCheck(value)
168 if id == 'ips':
169 self.setIpAddresses(value)
170 else:
171 setattr(self,id,value)
172 if id == 'macaddress':
173 self.index_object()
174
184
194
204
216
217
219 """
220 Allow access to ipAddresses via the ips attribute
221 """
222 if name == 'ips':
223 return self.getIpAddresses()
224 else:
225 raise AttributeError( name )
226
227
228 - def _prepIp(self, ip, netmask=24):
229 """
230 Split ips in the format 1.1.1.1/24 into ip and netmask.
231 Default netmask is 24.
232 """
233 iparray = ip.split("/")
234 if len(iparray) > 1:
235 ip = iparray[0]
236 checkip(ip)
237 netmask = maskToBits(iparray[1])
238 return ip, netmask
239
240
242 """
243 Add an ip to the ipaddresses relationship on this interface.
244 """
245 networks = self.device().getNetworkRoot()
246 ip, netmask = self._prepIp(ip, netmask)
247
248 ipobj = networks.findIp(ip)
249 if ipobj:
250 dev = ipobj.device()
251 if dev and dev != self.device():
252 log.warn("Adding IP Address %s to %s found it on device %s",
253 ip, self.getId(), dev.getId())
254 self.ipaddresses.addRelation(ipobj)
255
256 else:
257 ipobj = networks.createIp(ip, netmask)
258 self.ipaddresses.addRelation(ipobj)
259 ipobj.index_object()
260 os = self.os()
261 notify(ObjectMovedEvent(self, os, self.id, os, self.id))
262
263
264
274
275
277 """
278 If no IPs are sent remove all in the relation
279 """
280 if not ips:
281 self.removeRelation('ipaddresses')
282 return True
283
284
321
322
332
333
342
343
352
353
362
363
365 """
366 Return the first real IP address object or None if none are found.
367 """
368 if len(self.ipaddresses()):
369 return self.ipaddresses()[0]
370
371
373 """
374 Return a list of the ip objects on this interface.
375 """
376 retval=[]
377 for ip in self.ipaddresses.objectValuesAll():
378 retval.append(ip)
379 for ip in self._ipAddresses:
380 retval.append(ip)
381 return retval
382
383
385 """
386 Return list of ip addresses as strings in the form 1.1.1.1/24.
387 """
388 return map(str, self.getIpAddressObjs())
389
390
397
398
400 """
401 Return the network name for the first ip on this interface.
402 """
403 net = self.getNetwork()
404 if net: return net.getNetworkName()
405 return ""
406
407
422
423
425 """
426 Return a list of network links for each ip in this interface.
427 """
428 addrs = self.ipaddresses() + self._ipAddresses
429 if addrs:
430 links = []
431 for addr in addrs:
432 if hasattr(aq_base(addr), 'network'):
433 if self.checkRemotePerm('View', addr.network()):
434 links.append(addr.network.getPrimaryLink())
435 else:
436 links.append(addr.network.getRelatedId())
437 else:
438 links.append("")
439 return "<br/>".join(links)
440 else:
441 return ""
442
443
444 security.declareProtected('View', 'getInterfaceName')
452
453
454 security.declareProtected('View', 'getInterfaceMacaddress')
456 """
457 Return the mac address of this interface.
458 """
459 return self.macaddress
460
461
463 """
464 Return the interface type as the target type name.
465 """
466 return self.prepId(self.type or "Unknown")
467
468
470 """
471 Return a list containing the appropriate RRDTemplate for this
472 IpInterface. If none is found then the list will be empty.
473
474 Order of preference if the interface supports 64bit counters.
475 1. <type>_64
476 2. ethernetCsmacd_64
477 3. <type>
478 4. ethernetCsmacd
479
480 Order of preference if the interface doesn't support 64bit counters.
481 1. <type>
482 2. ethernetCsmacd
483 """
484 templateName = self.getRRDTemplateName()
485
486 order = ['ethernetCsmacd']
487 if templateName.endswith('_64'):
488 order.insert(0, 'ethernetCsmacd_64')
489 if templateName not in order:
490 order.insert(0, templateName)
491 order.insert(2, templateName[:-3])
492 else:
493 if templateName not in order:
494 order.insert(0, templateName)
495
496 for name in order:
497 template = self.getRRDTemplateByName(name)
498 if template:
499 return [template]
500
501 return []
502
503
505 """
506 Ignore interface that are administratively down.
507 """
508
509
510 return self.adminStatus > 1 or self.monitor == False
511
512
514 """
515 Get the current administrative state of the interface. Prefer real-time
516 value over modeled value.
517 """
518 s = self.cacheRRDValue('ifAdminStatus', None)
519 if s is None: s = self.adminStatus
520 return s
521
522
524 """
525 Return the current administrative state of the interface converted to
526 its string version.
527 """
528 return {1: 'Up', 2: 'Down', 3: 'Testing'}.get(
529 self.getAdminStatus(), 'Unknown')
530
531
533 """
534 Get the current operational state of the interface. Prefer real-time
535 value over modeled value.
536 """
537 s = self.cacheRRDValue('ifOperStatus', None)
538 if s is None: s = self.operStatus
539 return s
540
541
543 """
544 Return the current operational state of the interface converted to
545 its string version.
546 """
547 return {
548 1: 'Up', 2: 'Down', 3: 'Testing', 5: 'Dormant', 6: 'Not Present',
549 7: 'Lower Layer Down'}.get(
550 self.getOperStatus(), 'Unknown')
551
552
554 """
555 Return the status number for this interface.
556 """
557
558 if self.snmpIgnore():
559 return -1
560
561 return super(IpInterface, self).getStatus()
562
563
565 """
566 Return a string that expresses self.speed in reasonable units.
567 """
568 if not self.speed:
569 return 'Unknown'
570 speed = self.speed
571 for unit in ('bps', 'Kbps', 'Mbps', 'Gbps'):
572 if speed < 1000: break
573 speed /= 1000.0
574 return "%.3f%s" % (speed, unit)
575
577 """
578 The device id, for indexing purposes.
579 """
580 d = self.device()
581 if d: return d.getPrimaryId()
582 else: return None
583
585 """
586 The interface id, for indexing purposes.
587 """
588 return self.getPrimaryId()
589
591 """
592 pass
593 """
594 return 'None'
595
597 """
598 Return a string that expresses self.duplex into human readable format.
599 """
600
601 if self.duplex == 2:
602 return 'halfDuplex'
603 elif self.duplex == 3:
604 return 'fullDuplex'
605 return 'unknown'
606
607 InitializeClass(IpInterface)
608
613