mirror of
				https://github.com/CumulusNetworks/ifupdown2.git
				synced 2024-05-06 15:54:50 +00:00 
			
		
		
		
	the tree)
Ticket: CM-7765
Reviewed By: CCR-3621
Testing Done: tested interface dependencies with auto and non-auto
interfaces
This commit fixes a change in behaviour introduced by "460906d0552d" ("skip adding
filtered or blacklisted interfaces in the dependency graph") that
skipped non-auto (or blacklisted) interfaces.
Turns out we have files out there that do have non-auto
dependents. This patch makes sure blacklisted interfaces who are
dependents of other interfaces are always picked up.
		
	
		
			
				
	
	
		
			95 lines
		
	
	
		
			2.7 KiB
		
	
	
	
		
			Python
		
	
	
	
	
	
			
		
		
	
	
			95 lines
		
	
	
		
			2.7 KiB
		
	
	
	
		
			Python
		
	
	
	
	
	
| #!/usr/bin/python
 | |
| #
 | |
| # Copyright 2014 Cumulus Networks, Inc. All rights reserved.
 | |
| # Author: Roopa Prabhu, roopa@cumulusnetworks.com
 | |
| #
 | |
| # graph --
 | |
| #    graph helper module for ifupdown
 | |
| #
 | |
| 
 | |
| import logging
 | |
| import copy
 | |
| from collections import deque
 | |
| try:
 | |
|     from gvgen import *
 | |
| except ImportError, e:
 | |
|     pass
 | |
| 
 | |
| class graph():
 | |
|     """ graph functions to sort and print interface graph """
 | |
| 
 | |
|     def __init__(self):
 | |
|         self.logger = logging.getLogger('ifupdown.' +
 | |
|                     self.__class__.__name__)
 | |
| 
 | |
|     @classmethod
 | |
|     def topological_sort_graphs_all(cls, dependency_graphs, indegrees_arg):
 | |
|         """ runs topological sort on interface list passed as dependency graph
 | |
| 
 | |
|         Args:
 | |
|             **dependency_graphs** (dict): dependency graph with dependency
 | |
|                                           lists for interfaces 
 | |
| 
 | |
|             **indegrees_arg** (dict): indegrees array for all interfaces
 | |
|         """
 | |
|         S = []
 | |
|         Q = deque()
 | |
| 
 | |
|         indegrees = copy.deepcopy(indegrees_arg)
 | |
|         for ifname,indegree in indegrees.items():
 | |
|             if indegree == 0:
 | |
|                 Q.append(ifname)
 | |
| 
 | |
|         while len(Q):
 | |
|             # initialize queue
 | |
|             x = Q.popleft()
 | |
| 
 | |
|             # Get dependents of x
 | |
|             dlist = dependency_graphs.get(x)
 | |
|             if not dlist:
 | |
|                 S.append(x)
 | |
|                 continue
 | |
| 
 | |
|             for y in dlist:
 | |
|                 try:
 | |
|                     indegrees[y] = indegrees.get(y) - 1
 | |
|                 except:
 | |
|                     self.logger.debug('topological_sort_graphs_all: did not find %s' %y)
 | |
|                     indegrees[y] = 0
 | |
|                     pass
 | |
|                 if indegrees.get(y) == 0:
 | |
|                     Q.append(y)
 | |
| 
 | |
|             S.append(x)
 | |
| 
 | |
|         for ifname,indegree in indegrees.items():
 | |
|             if indegree != 0:
 | |
|                 raise Exception('cycle found involving iface %s' %ifname +
 | |
|                                 ' (indegree %d)' %indegree)
 | |
| 
 | |
|         return S
 | |
| 
 | |
|     @classmethod
 | |
|     def generate_dots(cls, dependency_graph, indegrees):
 | |
|         """ spits out interface dependency graph in dot format
 | |
| 
 | |
|         Args:
 | |
|             **dependency_graphs** (dict): dependency graph with dependency
 | |
|                                           lists for interfaces 
 | |
| 
 | |
|             **indegrees_arg** (dict): indegrees array for all interfaces
 | |
|         """
 | |
| 
 | |
|         gvgraph = GvGen()
 | |
|         graphnodes = {}
 | |
|         for v in dependency_graph.keys():
 | |
|             graphnodes[v] = gvgraph.newItem(v)
 | |
| 
 | |
|         for i, v in graphnodes.items():
 | |
|             dlist = dependency_graph.get(i, [])
 | |
|             if not dlist:
 | |
|                 continue
 | |
|             for d in dlist:
 | |
|                 gvgraph.newLink(v, graphnodes.get(d))
 | |
|         gvgraph.dot()
 |