Mesh_westfirst.py revision 13731
12391SN/A# Copyright (c) 2010 Advanced Micro Devices, Inc. 28931Sandreas.hansson@arm.com# 2016 Georgia Institute of Technology 38931Sandreas.hansson@arm.com# All rights reserved. 48931Sandreas.hansson@arm.com# 58931Sandreas.hansson@arm.com# Redistribution and use in source and binary forms, with or without 68931Sandreas.hansson@arm.com# modification, are permitted provided that the following conditions are 78931Sandreas.hansson@arm.com# met: redistributions of source code must retain the above copyright 88931Sandreas.hansson@arm.com# notice, this list of conditions and the following disclaimer; 98931Sandreas.hansson@arm.com# redistributions in binary form must reproduce the above copyright 108931Sandreas.hansson@arm.com# notice, this list of conditions and the following disclaimer in the 118931Sandreas.hansson@arm.com# documentation and/or other materials provided with the distribution; 128931Sandreas.hansson@arm.com# neither the name of the copyright holders nor the names of its 138931Sandreas.hansson@arm.com# contributors may be used to endorse or promote products derived from 142391SN/A# this software without specific prior written permission. 152391SN/A# 162391SN/A# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 172391SN/A# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 182391SN/A# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 192391SN/A# A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 202391SN/A# OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 212391SN/A# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 222391SN/A# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 232391SN/A# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 242391SN/A# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 252391SN/A# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 262391SN/A# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 272391SN/A# 282391SN/A# Authors: Brad Beckmann 292391SN/A# Tushar Krishna 302391SN/A 312391SN/Afrom m5.params import * 322391SN/Afrom m5.objects import * 332391SN/A 342391SN/Afrom BaseTopology import SimpleTopology 352391SN/A 362391SN/A# Creates a generic Mesh assuming an equal number of cache 372391SN/A# and directory controllers. 382391SN/A# West-first routing is enforced (using link weights) 392665SN/A# to guarantee deadlock freedom. 402665SN/A# The network randomly chooses between links with the same 418931Sandreas.hansson@arm.com# weight for messages within unordered virtual networks. 422391SN/A# Within ordered virtual networks, a fixed link direction 432391SN/A# is always chosen based on which appears first inside the 448931Sandreas.hansson@arm.com# routing table. 458931Sandreas.hansson@arm.com 468931Sandreas.hansson@arm.comclass Mesh_westfirst(SimpleTopology): 472391SN/A description='Mesh_westfirst' 482391SN/A 498931Sandreas.hansson@arm.com def __init__(self, controllers): 508931Sandreas.hansson@arm.com self.nodes = controllers 512391SN/A 522462SN/A # Makes a generic mesh 538931Sandreas.hansson@arm.com # assuming an equal number of cache and directory cntrls 548719SN/A 552462SN/A def makeTopology(self, options, network, IntLink, ExtLink, Router): 569053Sdam.sunwoo@arm.com nodes = self.nodes 579053Sdam.sunwoo@arm.com 589053Sdam.sunwoo@arm.com num_routers = options.num_cpus 598931Sandreas.hansson@arm.com num_rows = options.mesh_rows 609293Sandreas.hansson@arm.com 619293Sandreas.hansson@arm.com # default values for link latency and router latency. 629293Sandreas.hansson@arm.com # Can be over-ridden on a per link/router basis 639293Sandreas.hansson@arm.com link_latency = options.link_latency # used by simple and garnet 649293Sandreas.hansson@arm.com router_latency = options.router_latency # only used by garnet 659293Sandreas.hansson@arm.com 669293Sandreas.hansson@arm.com # There must be an evenly divisible number of cntrls to routers 679293Sandreas.hansson@arm.com # Also, obviously the number or rows must be <= the number of routers 689293Sandreas.hansson@arm.com cntrls_per_router, remainder = divmod(len(nodes), num_routers) 699293Sandreas.hansson@arm.com assert(num_rows > 0 and num_rows <= num_routers) 709293Sandreas.hansson@arm.com num_columns = int(num_routers / num_rows) 719293Sandreas.hansson@arm.com assert(num_columns * num_rows == num_routers) 729293Sandreas.hansson@arm.com 739293Sandreas.hansson@arm.com # Create the routers in the mesh 749293Sandreas.hansson@arm.com routers = [Router(router_id=i, latency=router_latency) \ 759293Sandreas.hansson@arm.com for i in range(num_routers)] 769293Sandreas.hansson@arm.com network.routers = routers 7711005Sandreas.sandberg@arm.com 789293Sandreas.hansson@arm.com # link counter to set unique link ids 799293Sandreas.hansson@arm.com link_count = 0 809293Sandreas.hansson@arm.com 819293Sandreas.hansson@arm.com # Add all but the remainder nodes to the list of nodes to be uniformly 829293Sandreas.hansson@arm.com # distributed across the network. 839293Sandreas.hansson@arm.com network_nodes = [] 849293Sandreas.hansson@arm.com remainder_nodes = [] 859293Sandreas.hansson@arm.com for node_index in range(len(nodes)): 869293Sandreas.hansson@arm.com if node_index < (len(nodes) - remainder): 879293Sandreas.hansson@arm.com network_nodes.append(nodes[node_index]) 889293Sandreas.hansson@arm.com else: 899293Sandreas.hansson@arm.com remainder_nodes.append(nodes[node_index]) 909293Sandreas.hansson@arm.com 919293Sandreas.hansson@arm.com # Connect each node to the appropriate router 929293Sandreas.hansson@arm.com ext_links = [] 939293Sandreas.hansson@arm.com for (i, n) in enumerate(network_nodes): 949293Sandreas.hansson@arm.com cntrl_level, router_id = divmod(i, num_routers) 959293Sandreas.hansson@arm.com assert(cntrl_level < cntrls_per_router) 969293Sandreas.hansson@arm.com ext_links.append(ExtLink(link_id=link_count, ext_node=n, 978931Sandreas.hansson@arm.com int_node=routers[router_id], 988931Sandreas.hansson@arm.com latency = link_latency)) 998931Sandreas.hansson@arm.com link_count += 1 1008931Sandreas.hansson@arm.com 1018931Sandreas.hansson@arm.com # Connect the remainding nodes to router 0. These should only be 1028931Sandreas.hansson@arm.com # DMA nodes. 1038931Sandreas.hansson@arm.com for (i, node) in enumerate(remainder_nodes): 1042391SN/A assert(node.type == 'DMA_Controller') 1056107SN/A assert(i < remainder) 1066107SN/A ext_links.append(ExtLink(link_id=link_count, ext_node=node, 1078931Sandreas.hansson@arm.com int_node=routers[0], 1089235Sandreas.hansson@arm.com latency = link_latency)) 1092413SN/A link_count += 1 1108931Sandreas.hansson@arm.com 1118931Sandreas.hansson@arm.com network.ext_links = ext_links 1122413SN/A 1138931Sandreas.hansson@arm.com # Create the mesh links. 1148931Sandreas.hansson@arm.com int_links = [] 1152413SN/A 1168931Sandreas.hansson@arm.com # East output to West input links (weight = 2) 1178931Sandreas.hansson@arm.com for row in range(num_rows): 1183170SN/A for col in range(num_columns): 1193170SN/A if (col + 1 < num_columns): 1203170SN/A east_out = col + (row * num_columns) 1213170SN/A west_in = (col + 1) + (row * num_columns) 1223170SN/A int_links.append(IntLink(link_id=link_count, 1233170SN/A src_node=routers[east_out], 1243170SN/A dst_node=routers[west_in], 1254626SN/A latency = link_latency, 1263170SN/A weight=2)) 1273170SN/A link_count += 1 1283170SN/A 1293170SN/A # West output to East input links (weight = 1) 1304626SN/A for row in range(num_rows): 1313170SN/A for col in range(num_columns): 1323170SN/A if (col + 1 < num_columns): 1333170SN/A east_in = col + (row * num_columns) 1343170SN/A west_out = (col + 1) + (row * num_columns) 1353170SN/A int_links.append(IntLink(link_id=link_count, 1363170SN/A src_node=routers[west_out], 1373170SN/A dst_node=routers[east_in], 1383170SN/A latency = link_latency, 1394626SN/A weight=1)) 1404626SN/A link_count += 1 1413170SN/A 1423170SN/A 1436102SN/A # North output to South input links (weight = 2) 1446102SN/A for col in range(num_columns): 1454040SN/A for row in range(num_rows): 1463170SN/A if (row + 1 < num_rows): 1476102SN/A north_out = col + (row * num_columns) 1483170SN/A south_in = col + ((row + 1) * num_columns) 1493170SN/A int_links.append(IntLink(link_id=link_count, 1504626SN/A src_node=routers[north_out], 1513170SN/A dst_node=routers[south_in], 1523170SN/A latency = link_latency, 1533170SN/A weight=2)) 1548719SN/A link_count += 1 1559053Sdam.sunwoo@arm.com 1568719SN/A # South output to North input links (weight = 2) 1579053Sdam.sunwoo@arm.com for col in range(num_columns): 1588719SN/A for row in range(num_rows): 1599053Sdam.sunwoo@arm.com if (row + 1 < num_rows): 1608719SN/A north_in = col + (row * num_columns) 1619053Sdam.sunwoo@arm.com south_out = col + ((row + 1) * num_columns) 1628719SN/A int_links.append(IntLink(link_id=link_count, 1639053Sdam.sunwoo@arm.com src_node=routers[south_out], 1648719SN/A dst_node=routers[north_in], 1659053Sdam.sunwoo@arm.com latency = link_latency, 1668719SN/A weight=2)) 1678719SN/A link_count += 1 1688719SN/A 1698719SN/A 1708719SN/A network.int_links = int_links 1718719SN/A