'attrs': {
'address' :
{'help' : 'ipv4 or ipv6 addresses',
- 'validvals' : [IPv4Network, IPv6Network],
+ 'validvals' : ['<ipv4/prefixlen>', '<ipv6/prefixlen>'],
'multiline' : True,
'example' : ['address 10.0.12.3/24',
'address 2000:1000:1000:1000:3::5/128']},
'netmask' :
{'help': 'netmask',
- 'validvals' : [IPv4Address, ],
+ 'validvals' : ['<ipv4>', ],
'example' : ['netmask 255.255.255.0'],
'compat' : True},
'broadcast' :
{'help': 'broadcast address',
- 'validvals' : [IPv4Address, ],
+ 'validvals' : ['<ipv4>', ],
'example' : ['broadcast 10.0.1.255']},
'scope' :
{'help': 'scope',
'preferred-lifetime 10']},
'gateway' :
{'help': 'default gateway',
- 'validvals' : [IPv4Address, IPv6Address],
+ 'validvals' : ['<ipv4>', '<ipv6>'],
'example' : ['gateway 255.255.255.0']},
'mtu' :
{ 'help': 'interface mtu',
'clagd-vxlan-anycast-ip' :
{ 'help' : 'Anycast local IP address for ' +
'dual connected VxLANs',
- 'validvals' : [IPv4Address, ],
+ 'validvals' : ['<ipv4>', ],
'example' : ['clagd-vxlan-anycast-ip 36.0.0.11']}}}
def __init__(self, *args, **kargs):
'every mac ip address-virtual line',
'attrs' : {
'address-virtual' :
- { 'help' : 'bridge router virtual mac and ip',
- 'validvals' : [('<mac>', IPv4Network), ],
+ { 'help' : 'bridge router virtual mac and ips',
+ 'validvals' : ['<mac-ipaddr/prefixlen-list>',],
'example' : ['address-virtual 00:11:22:33:44:01 11.0.1.1/24 11.0.1.2/24']}
}}
'bond-ad-sys-mac-addr':
{'help' : '802.3ad system mac address',
'default' : '00:00:00:00:00:00',
+ 'validvals': ['<mac>', ],
'example' : ['bond-ad-sys-mac-addr 00:00:00:00:00:00'],
'deprecated' : True,
'new-attribute' : 'bond-ad-actor-system'},
'bond-ad-actor-system':
{'help' : '802.3ad system mac address',
'default' : '00:00:00:00:00:00',
+ 'validvals': ['<mac>', ],
'example' : ['bond-ad-actor-system 00:00:00:00:00:00'],},
'bond-lacp-bypass-allow':
{'help' : 'allow lacp bypass',
{'help' : 'bond slaves',
'required' : True,
'multivalue' : True,
+ 'validvals': ['<interface-list>'],
'example' : ['bond-slaves swp1 swp2',
'bond-slaves glob swp1-2',
'bond-slaves regex (swp[1|2)']}}}
ifname=ifaceobj.name,
attr=attrname)
if attrval:
- msg = ('%s: invalid value %s for attr %s.'
- %(ifaceobj.name, attrval, attrname))
- optiondict = self.get_mod_attr(attrname)
- if not optiondict:
- return None
- validvals = optiondict.get('validvals')
- if validvals and attrval not in validvals:
- raise Exception(msg + ' Valid values are %s' %str(validvals))
- validrange = optiondict.get('validrange')
- if validrange:
- if (int(attrval) < int(validrange[0]) or
- int(attrval) > int(validrange[1])):
- raise Exception(msg + ' Valid range is [%s,%s]'
- %(validrange[0], validrange[1]))
if attrname == 'bond-mode':
attrval = bond._get_readable_bond_mode(attrval)
if attrval == '802.3ad':
{'help' : 'bridge ports',
'multivalue' : True,
'required' : True,
+ 'validvals': ['<interface-list>'],
'example' : ['bridge-ports swp1.100 swp2.100 swp3.100',
'bridge-ports glob swp1-3.100',
'bridge-ports regex (swp[1|2|3].100)']},
'default' : '20'},
'bridge-pathcosts' :
{ 'help' : 'bridge set port path costs',
+ 'validvals': ['<interface-range-list>'],
'validrange' : ['0', '65535'],
'example' : ['under the bridge: bridge-pathcosts swp1=100 swp2=100',
'under the port (recommended): bridge-pathcosts 100'],
'default' : '100'},
'bridge-portprios' :
{ 'help' : 'bridge port prios',
+ 'validvals': ['<interface-range-list>'],
'validrange' : ['0', '65535'],
'example' : ['under the bridge: bridge-portprios swp1=32 swp2=32',
'under the port (recommended): bridge-portprios 32'],
'example' : ['bridge-mcqv4src 100=172.16.100.1 101=172.16.101.1']},
'bridge-portmcrouter' :
{ 'help' : 'set port multicast routers',
- 'validvals' : ['yes', 'no', '0', '1'],
+ 'validvals' : ['<interface-yes-no-0-1-list>'],
'default' : 'yes',
'example' : ['under the bridge: bridge-portmcrouter swp1=yes swp2=yes',
'under the port (recommended): bridge-portmcrouter yes']},
'bridge-portmcfl' :
{ 'help' : 'port multicast fast leave.',
+ 'validvals': ['<interface-range-list>'],
'validrange' : ['0', '65535'],
'default' : '0',
'example' : ['under the bridge: bridge-portmcfl swp1=0 swp2=0',
'regex or \"all\" on bridge_ports,' +
'as it wouldnt work.',
'default' : '0',
+ 'validvals': ['<number-interface-list>'],
'example' : ['bridge-waitport 4 swp1 swp2']},
'bridge-maxwait' :
{ 'help' : 'forces to time seconds the maximum time ' +
'If specified under the bridge the ports ' +
'inherit it unless overridden by a ' +
'bridge-vids attribute under the port',
+ 'validvals': ['<number-range-list>'],
'example' : ['bridge-vids 4000',
'bridge-vids 2000 2200-3000']},
'bridge-pvid' :
'bridge-igmp-querier-src' :
{ 'help' : 'bridge igmp querier src. Must be ' +
'specified under the vlan interface',
- 'validvals' : [IPv4Address, ],
+ 'validvals' : ['<ipv4>', ],
'example' : ['bridge-igmp-querier-src 172.16.101.1']}}}
def __init__(self, *args, **kargs):
'new-attribute': 'bridge-ports'},
'mstpctl-stp' :
{'help': 'bridge stp yes/no',
- 'validvals' : ['yes', 'no'],
+ 'validvals' : ['yes', 'no', 'on', 'off'],
'compat' : True,
'default' : 'no',
'deprecated': True,
'example' : ['mstpctl-forcevers rstp']},
'mstpctl-portpathcost' :
{ 'help' : 'bridge port path cost',
+ 'validvals': ['<interface-range-list>'],
'validrange' : ['0', '65535'],
'default' : '0',
'jsonAttr' : 'adminExtPortCost',
{ 'help' : 'bridge port p2p detection mode',
'default' : 'auto',
'jsonAttr' : 'adminPointToPoint',
- 'validvals' : ['yes', 'no', 'auto'],
+ 'validvals' : ['<interface-yes-no-auto-list>'],
'required' : False,
'example' : ['under the bridge: mstpctl-portp2p swp1=yes swp2=no',
'under the port (recommended): mstpctl-portp2p yes']},
'enable/disable port ability to take root role of the port',
'default' : 'no',
'jsonAttr' : 'restrictedRole',
- 'validvals' : ['yes', 'no'],
+ 'validvals' : ['<interface-yes-no-list>'],
'required' : False,
'example' : ['under the bridge: mstpctl-portrestrrole swp1=yes swp2=no',
'under the port (recommended): mstpctl-portrestrrole yes']},
'enable/disable port ability to propagate received topology change notification of the port',
'default' : 'no',
'jsonAttr' : 'restrictedTcn',
- 'validvals' : ['yes', 'no'],
+ 'validvals' : ['<interface-yes-no-list>'],
'required' : False,
'example' : ['under the bridge: mstpctl-portrestrtcn swp1=yes swp2=no',
'under the port (recommended): mstpctl-portrestrtcn yes']},
'enable/disable bpduguard',
'default' : 'no',
'jsonAttr' : 'bpduGuardPort',
- 'validvals' : ['yes', 'no'],
+ 'validvals' : ['<interface-yes-no-list>'],
'required' : False,
'example' : ['under the bridge: mstpctl-bpduguard swp1=yes swp2=no',
'under the port (recommended): mstpctl-bpduguard yes']},
{ 'help' :
'port priority for MSTI instance',
'default' : '128',
+ 'validvals': ['<interface-range-list>'],
'validrange' : ['0', '240'],
'required' : False,
'example' : ['under the bridge: mstpctl-treeportprio swp1=128 swp2=128',
'example' : ['mstpctl-hello 2']},
'mstpctl-portnetwork' :
{ 'help' : 'enable/disable bridge assurance capability for a port',
- 'validvals' : ['yes', 'no'],
+ 'validvals' : ['<interface-yes-no-list>'],
'default' : 'no',
'jsonAttr' : 'networkPort',
'required' : False,
'under the port (recommended): mstpctl-portnetwork yes']},
'mstpctl-portadminedge' :
{ 'help' : 'enable/disable initial edge state of the port',
- 'validvals' : ['yes', 'no'],
+ 'validvals' : ['<interface-yes-no-list>'],
'default' : 'no',
'jsonAttr' : 'adminEdgePort',
'required' : False,
'under the port (recommended): mstpctl-portadminedge yes']},
'mstpctl-portautoedge' :
{ 'help' : 'enable/disable auto transition to/from edge state of the port',
- 'validvals' : ['yes', 'no'],
+ 'validvals' : ['<interface-yes-no-list>'],
'default' : 'yes',
'jsonAttr' : 'autoEdgePort',
'required' : False,
{ 'help' : 'enable/disable bpdu filter on a port. ' +
'syntax varies when defined under a bridge ' +
'vs under a port',
- 'validvals' : ['yes', 'no'],
+ 'validvals' : ['<interface-yes-no-list>'],
'jsonAttr' : 'bpduFilterPort',
'default' : 'no',
'required' : False,
'attrs' : {
'vlan-raw-device' :
{'help' : 'vlan raw device',
- 'validvals' : ['<interface>' ,]},
+ 'validvals': ['<interface>']},
'vlan-id' :
{'help' : 'vlan id',
'validrange' : ['0', '4096']}}}
'creating a vrf device. ' +
'Table id is either \'auto\' or '+
'\'valid routing table id\'',
+ 'validvals': ['<auto>', '<number>'],
'example': ['vrf-table auto', 'vrf-table 1001']},
'vrf':
{'help' : 'vrf the interface is part of.',
+ 'validvals': ['<text>'],
'example': ['vrf blue']}}}
iproute2_vrf_filename = '/etc/iproute2/rt_tables.d/ifupdown2_vrf_map.conf'
'example' : ['vrrp-priority 20']},
'vrrp-virtual-ip' :
{'help': 'set vrrp virtual ip',
- 'validvals' : [IPv4Address, ],
+ 'validvals' : ['<ipv4>', ],
'example' : ['vrrp-virtual-ip 10.0.1.254']}}}
def __init__(self, *args, **kargs):
'example': ['vxlan-id 100']},
'vxlan-local-tunnelip' :
{'help' : 'vxlan local tunnel ip',
- 'validvals' : [IPv4Address, ],
+ 'validvals' : ['<ipv4>', '<ipv6>'],
'example': ['vxlan-local-tunnelip 172.16.20.103']},
'vxlan-svcnodeip' :
{'help' : 'vxlan id',
- 'validvals' : [IPv4Address, ],
+ 'validvals' : ['<ipv4>', '<ipv6>'],
'example': ['vxlan-svcnodeip 172.16.22.125']},
'vxlan-remoteip' :
{'help' : 'vxlan remote ip',
- 'validvals' : [IPv4Address, ],
+ 'validvals' : ['<ipv4>', '<ipv6>'],
'example': ['vxlan-remoteip 172.16.22.127']},
'vxlan-learning' :
{'help' : 'vxlan learning yes/no',
from exceptions import *
from sets import Set
+from ipaddr import IPNetwork, IPv4Network, IPv6Network, IPAddress, IPv4Address, IPv6Address
+
"""
.. module:: ifupdownmain
:synopsis: main module for ifupdown package
# This makes config available to addon modules
ifupdownConfig.config = self.config
+ self.validate_keywords = {
+ '<mac>': self._keyword_mac,
+ '<text>': self._keyword_text,
+ '<ipv4>': self._keyword_ipv4,
+ '<ipv6>': self._keyword_ipv6,
+ '<auto>': self._keyword_auto,
+ '<ipaddr>': self._keyword_ipaddr,
+ '<number>': self._keyword_number,
+ '<interface>': self._keyword_interface,
+ '<ipv4-vrf-text>': self._keyword_ipv4_vrf_text,
+ '<number-ipv4-list>': self._keyword_number_ipv4_list,
+ '<interface-list>': self._keyword_interface_list,
+ '<ipv4/prefixlen>': self._keyword_ipv4_prefixlen,
+ '<ipv6/prefixlen>': self._keyword_ipv6_prefixlen,
+ '<ipaddr/prefixlen>': self._keyword_ipaddr_prefixlen,
+ '<number-range-list>': self._keyword_number_range_list,
+ '<interface-range-list>': self._keyword_interface_range_list,
+ '<mac-ipaddr/prefixlen-list>': self._keyword_mac_ipaddr_prefixlen_list,
+ '<number-interface-list>': self._keyword_number_interface_list,
+ '<interface-yes-no-list>': self._keyword_interface_yes_no_list,
+ '<interface-yes-no-0-1-list>': self._keyword_interface_yes_no_0_1_list,
+ '<interface-yes-no-auto-list>': self._keyword_interface_yes_no_auto_list,
+ }
+
def link_master_slave_ignore_error(self, errorstr):
# If link master slave flag is set,
# there may be cases where the lowerdev may not be
ifaceobj.flags |= ifaceobj.OLDEST_SIBLING
self.ifaceobjdict[ifaceobj.name].append(ifaceobj)
+ def _keyword_text(self, value, validrange=None):
+ return isinstance(value, str) and len(value) > 0
+
+ def _keyword_mac(self, value, validrange=None):
+ if value.strip().startswith('ether'):
+ value = value.strip()[6:]
+ return re.match('[0-9a-f]{1,2}([-:])[0-9a-f]{1,2}(\\1[0-9a-f]{1,2}){4}$',
+ value.lower())
+
+ def _keyword_check_list(self, _list, obj, limit=None):
+ try:
+ if limit and limit > 0:
+ for i in xrange(0, limit):
+ obj(_list[i])
+ return len(_list) == limit
+ else:
+ for elem in _list:
+ obj(elem)
+ return True
+ except Exception as e:
+ self.logger.debug('keyword: check list: %s' % str(e))
+ return False
+
+ def _keyword_ipv4(self, value, validrange=None):
+ return self._keyword_check_list(value.split(), IPv4Address, limit=1)
+
+ def _keyword_ipv4_prefixlen(self, value, validrange=None):
+ return self._keyword_check_list(value.split(), IPv4Network, limit=1)
+
+ def _keyword_ipv6(self, value, validrange=None):
+ return self._keyword_check_list(value.split(), IPv6Address, limit=1)
+
+ def _keyword_ipv6_prefixlen(self, value, validrange=None):
+ return self._keyword_check_list(value.split(), IPv6Network, limit=1)
+
+ def _keyword_ipaddr(self, value, validrange=None):
+ return self._keyword_check_list(value.split(), IPAddress, limit=1)
+
+ def _keyword_ipaddr_prefixlen(self, value, validrange=None):
+ return self._keyword_check_list(value.split(), IPNetwork, limit=1)
+
+ def _keyword_mac_ipaddr_prefixlen_list(self, value, validrange=None):
+ """
+ <mac> <ipaddr> [<ipaddr> ...]
+ ex: address-virtual 00:11:22:33:44:01 11.0.1.1/24 11.0.1.2/24
+ """
+ try:
+ res = value.split()
+ if len(res) < 2:
+ return False
+ if not self._keyword_mac(res[0]):
+ return False
+ for ip in res[1:]:
+ if not self._keyword_ipaddr_prefixlen(ip):
+ return False
+ return True
+ except Exception as e:
+ self.logger.debug('keyword: mac ipaddr prefixlen: %s' % str(e))
+ return False
+
+ def _keyword_number_ipv4_list(self, value, validrange=None):
+ """
+ <number>=<ipv4> [<number>=<ipv4> ...]
+ ex: bridge-mcqv4src 100=172.16.100.1 101=172.16.101.1
+ """
+ try:
+ elements = value.split(' ')
+ if not elements:
+ return False
+ for elem in elements:
+ v = elem.split('=')
+ int(v[0])
+ IPv4Address(v[1])
+ return True
+ except Exception as e:
+ self.logger.debug('keyword: number ipv4: %s' % str(e))
+ return False
+
+ def _keyword_interface(self, ifacename, validrange=None):
+ return self.get_ifaceobjs(ifacename)
+
+ def _keyword_ipv4_vrf_text(self, value, validrange=None):
+ """
+ <ipv4> "vrf" <text>
+ ex: clagd-backup-ip 10.10.10.42 vrf blue
+ """
+ values = value.split()
+ size = len(values)
+
+ if size > 3 or size < 1:
+ return False
+ try:
+ IPv4Address(values[0])
+ if size > 1:
+ if values[1] != 'vrf':
+ return False
+ if size > 2:
+ if not self._keyword_text(values[2]):
+ return False
+ return True
+ except Exception as e:
+ self.logger.debug('keyword: ipv4 vrf text: %s' % str(e))
+ return False
+
+ def _keyword_interface_list_with_value(self, value, validvals):
+ values = value.split()
+ try:
+ if len(values) == 1:
+ if values[0] in validvals:
+ return True
+ for v in values:
+ iface_value = v.split('=')
+ size = len(iface_value)
+ if size != 2:
+ if iface_value[0] == 'glob' or iface_value[0] == 'regex':
+ continue
+ return False
+ if not iface_value[1] in validvals:
+ return False
+ return True
+ except Exception as e:
+ self.logger.debug('keyword: interface list with value: %s' % str(e))
+ return False
+
+ def _keyword_interface_yes_no_list(self, value, validrange=None):
+ """
+ <yes|no> | ( <interface>=<yes|no> [<interface>=<yes|no> ...] )
+ ex: mstpctl-portrestrrole swp1=yes swp2=no
+ """
+ return self._keyword_interface_list_with_value(value, ['yes', 'no'])
+
+ def _keyword_interface_yes_no_auto_list(self, value, validrange=None):
+ """
+ <yes|no|auto> |
+ ( <interface>=<yes|no|auto> [<interface>=<yes|no|auto> ...] )
+ ex: mstpctl-portp2p swp1=yes swp2=no swp3=auto
+ """
+ return self._keyword_interface_list_with_value(value,
+ ['yes', 'no', 'auto'])
+
+ def _keyword_interface_yes_no_0_1_list(self, value, validrange=None):
+ """
+ <yes|no|0|1> |
+ ( <interface>=<yes|no|0|1> [<interface>=<yes|no|0|1> ...] )
+ ex: bridge-portmcrouter swp1=yes swp2=yes swp3=1
+ """
+ return self._keyword_interface_list_with_value(value,
+ ['yes', 'no', '1', '0'])
+
+ def _keyword_interface_range_list(self, value, validrange):
+ """
+ <number> | ( <interface>=<number> [ <interface>=number> ...] )
+ ex: mstpctl-portpathcost swp1=0 swp2=1
+ """
+ values = value.split()
+ try:
+ if len(values) == 1:
+ try:
+ n = int(values[0])
+ if n < int(validrange[0]) or n > int(
+ validrange[1]):
+ raise invalidValueError('value of out range "%s":'
+ ' valid attribute range: %s'
+ % (values[0],
+ '-'.join(validrange)))
+ return True
+ except invalidValueError as e:
+ raise e
+ except Exception as e:
+ self.logger.debug('keyword: interface range list: %s'
+ % str(e))
+ return False
+ for v in values:
+ iface_value = v.split('=')
+ size = len(iface_value)
+ if size != 2:
+ return False
+ number = int(iface_value[1])
+ if number < int(validrange[0]) or number > int(
+ validrange[1]):
+ raise invalidValueError(
+ 'value of out range "%s" for iface "%s":'
+ ' valid attribute range: %s'
+ % (iface_value[1],
+ iface_value[0],
+ '-'.join(validrange)))
+ return True
+ except invalidValueError as e:
+ raise e
+ except Exception as e:
+ self.logger.debug('keyword: interface range list: %s' % str(e))
+ return False
+
+ def _keyword_interface_list(self, value, validrange=None):
+ """
+ [glob|regex] <interface> [ [glob|regex] <interface> ...]
+ ex: bridge-ports swp1 swp2 glob swp3-5.100 regex (swp[6|7|8].100)
+ """
+ interface_list = value.split()
+ size = len(interface_list)
+ i = 0
+ while i < size:
+ if interface_list[i] == 'glob' or interface_list[i] == 'regex':
+ i += 1
+ else:
+ if not self._keyword_interface(interface_list[i]):
+ return False
+ i += 1
+ return True
+
+ def _keyword_number_range_list(self, value, validrange=None):
+ """
+ <number> [<number>-<number>]
+ ex: bridge-vids 42 100-200
+ """
+ number_list = value.split()
+ try:
+ i = 0
+ while i < len(number_list):
+ if '-' in number_list[i]:
+ range = number_list[i].split('-')
+ a = int(range[0])
+ b = int(range[1])
+ if a > b:
+ return False
+ else:
+ int(number_list[i])
+ i += 1
+ return True
+ except Exception as e:
+ self.logger.debug('keyword: number range list: %s' % str(e))
+ return False
+
+ def _keyword_number_interface_list(self, value, validrange=None):
+ """
+ <number> <interface> [<interface>... [<number> <interface> ... ]]
+ bridge-waitport 42 swp1 swp2 swp3 9 swp4
+ """
+ interface_list = value.split()
+ if not interface_list:
+ return False
+ try:
+ int(interface_list[0])
+ prev = True
+ for elem in interface_list[1:]:
+ try:
+ int(elem)
+ if prev:
+ return False
+ prev = True
+ except:
+ prev = False
+ return not prev
+ except Exception as e:
+ self.logger.debug('keyword: number interface list: %s' % str(e))
+ return False
+
+ def _keyword_auto(self, value, validrange=None):
+ return value == 'auto'
+
+ def _keyword_number(self, value, validrange=None):
+ try:
+ int(value)
+ return True
+ except Exception as e:
+ self.logger.debug('keyword: number: %s' % str(e))
+ return False
+
+ def _is_keyword(self, value):
+ if isinstance(value, tuple):
+ return True
+ keyword_found = value in self.validate_keywords
+ if value.startswith('<') and value.endswith('>') and not keyword_found:
+ raise Exception('%s: invalid keyword, please make sure to use'
+ ' a valid keyword see `ifquery -s`' % value)
+ return keyword_found
+
+ def _check_validvals_value(self, attrname, value, validvals, validrange):
+ if validvals and value not in validvals:
+ is_valid = False
+ for keyword in validvals:
+ if self._is_keyword(keyword):
+ if validrange:
+ if self.validate_keywords[keyword](value, validrange):
+ return {'result': True}
+ else:
+ if self.validate_keywords[keyword](value):
+ return {'result': True}
+ if not is_valid:
+ return {
+ 'result': False,
+ 'message': 'invalid value "%s": valid attribute values: %s'
+ % (value, validvals)
+ }
+ elif validrange:
+ if len(validrange) != 2:
+ raise Exception('%s: invalid range in addon configuration'
+ % '-'.join(validrange))
+ _value = int(value)
+ if _value < int(validrange[0]) or _value > int(validrange[1]):
+ return {
+ 'result': False,
+ 'message': 'value of out range "%s": '
+ 'valid attribute range: %s'
+ % (value, '-'.join(validrange))
+ }
+ return {'result': True}
+
+ def _check_validvals(self, ifacename, module_name, attrs):
+ ifaceobj = self.get_ifaceobjs(ifacename)
+ if not ifaceobj:
+ return
+ success = True
+ for attrname, attrvalue in ifaceobj[0].config.items():
+ try:
+ attrname_dict = attrs.get(attrname, {})
+ validvals = attrname_dict.get('validvals', [])
+ validrange = attrname_dict.get('validrange', [])
+ for value in attrvalue:
+ res = self._check_validvals_value(attrname,
+ value,
+ validvals,
+ validrange)
+ if not res['result']:
+ self.logger.warn('%s: %s: %s' %
+ (ifacename, attrname, res['message']))
+ success = False
+ except Exception as e:
+ self.logger.warn('addon \'%s\': %s: %s' % (module_name,
+ attrname,
+ str(e)))
+ success = False
+ return success
+
def _module_syntax_check(self, filtered_ifacenames):
+ result = True
for ifacename in filtered_ifacenames:
for module in self.modules.values():
try:
- if hasattr(module, 'syntax_check') \
- and callable(module.syntax_check):
- module.syntax_check(self.get_ifaceobjs(ifacename))
+ if hasattr(module, '_modinfo'):
+ if not self._check_validvals(ifacename,
+ module.__class__.__name__,
+ module._modinfo.get('attrs', {})):
+ result = False
+ if hasattr(module, 'syntax_check') and callable(module.syntax_check):
+ if not module.syntax_check(self.get_ifaceobjs(ifacename)):
+ result = False
except Exception, e:
- pass #self.logger.warn('%s: %s' % (ifacename, str(e)))
+ self.logger.warn('%s: %s' % (ifacename, str(e)))
+ result = False
+ return result
def _iface_configattr_syntax_checker(self, attrname, attrval):
for m, mdict in self.module_attrs.items():
# return here because we want to make sure most
# errors above are caught and reported.
if syntaxcheck:
- self._module_syntax_check(filtered_ifacenames)
+ if not self._module_syntax_check(filtered_ifacenames):
+ raise Exception()
if not iface_read_ret:
raise Exception()
elif self._any_iface_errors(filtered_ifacenames):
# return here because we want to make sure most
# errors above are caught and reported.
if syntaxcheck:
- self._module_syntax_check(interfaces_to_up)
+ if not self._module_syntax_check(interfaces_to_up):
+ raise Exception()
if not iface_read_ret:
raise Exception()
elif self._any_iface_errors(interfaces_to_up):
# return here because we want to make sure most
# errors above are caught and reported.
if syntaxcheck:
- self._module_syntax_check(new_filtered_ifacenames)
+ if not self._module_syntax_check(new_filtered_ifacenames):
+ raise Exception()
if not iface_read_ret:
raise Exception()
elif self._any_iface_errors(new_filtered_ifacenames):