1 #! /usr/bin/env python3
3 # Copyright (c) 2006-2022. The SimGrid Team. All rights reserved.
5 # This program is free software; you can redistribute it and/or modify it
6 # under the terms of the license (GNU LGPL) which comes with this package.
9 # This script takes as input a C++ platform file, compiles it, then dumps the
10 # routing graph as a CSV and generates an SVG image.
11 # The layout should be alright for any platform file, but the colors are very
12 # ad-hoc for file supernode.cpp : do not hesitate to adapt this script to your needs.
17 import matplotlib as mpl
18 import matplotlib.pyplot as plt
21 from palettable.colorbrewer.qualitative import Set1_9
22 colors = Set1_9.hex_colors
24 print('Warning: could not import palettable, will use a default palette.')
30 subprocess.run(cmd.split(), capture_output=True, check=True)
33 def compile_platform(platform_cpp):
34 platform_so = platform_cpp.replace('.cpp', '.so')
35 cmd = f'g++ -g -fPIC -shared -o {platform_so} {platform_cpp} -lsimgrid'
40 def dump_csv(platform_so):
41 platform_csv = platform_so.replace('.so', '.csv')
42 cmd = f'graphicator {platform_so} {platform_csv}'
47 def load_graph(platform_csv):
48 edges = pandas.read_csv(platform_csv)
50 G.add_edges_from([e for _, e in edges.drop_duplicates().iterrows()])
51 print(f'Loaded a graph with {len(G)} vertices with {len(G.edges)} edges')
55 def plot_graph(graph, label=False, groups=[]):
56 # First, we compute the graph layout, i.e. the position of the nodes.
57 # The neato algorithm from graphviz is nicer, but this is an extra-dependency.
58 # The spring_layout is also not too bad.
60 pos = nx.nx_agraph.graphviz_layout(graph, 'neato')
62 print('Warning: could not import pygraphviz, will use another layout algorithm.')
63 pos = nx.spring_layout(graph, k=0.5, iterations=1000, seed=42)
64 plt.figure(figsize=(20, 15))
66 all_nodes = set(graph)
67 # We then iterate on all the specified groups, to plot each of them in the right color.
68 # Note that the order of the groups is important here, as we are looking at substrings in the node names.
69 for i, grp in enumerate(groups):
70 nodes = {u for u in all_nodes if grp in u}
72 nx.draw_networkx_nodes(graph, pos, nodelist=nodes, node_size=50, node_color=colors[i], label=grp.replace('_', ''))
73 nx.draw_networkx_nodes(graph, pos, nodelist=all_nodes, node_size=50, node_color=colors[-1], label='unknown')
74 # Finally we draw the edges, the (optional) labels, and the legend.
75 nx.draw_networkx_edges(graph, pos, alpha=0.3)
77 nx.draw_networkx_labels(graph, pos)
78 plt.legend(scatterpoints = 1)
81 def generate_svg(platform_csv):
82 graph = load_graph(platform_csv)
83 plot_graph(graph, label=False, groups=['router', 'link', 'cpu', '_node', 'supernode', 'cluster'])
84 img = platform_csv.replace('.csv', '.svg')
86 print(f'Generated file {img}')
89 if __name__ == '__main__':
90 if len(sys.argv) != 2:
91 sys.exit(f'Syntax: {sys.argv[0]} platform.cpp')
92 platform_cpp = sys.argv[1]
93 platform_so = compile_platform(platform_cpp)
94 platform_csv = dump_csv(platform_so)
95 generate_svg(platform_csv)