Mesh_XY.py revision 13774
15647Sgblack@eecs.umich.edu# Copyright (c) 2010 Advanced Micro Devices, Inc.
29544Sandreas.hansson@arm.com#               2016 Georgia Institute of Technology
38922Swilliam.wang@arm.com# All rights reserved.
48922Swilliam.wang@arm.com#
58922Swilliam.wang@arm.com# Redistribution and use in source and binary forms, with or without
68922Swilliam.wang@arm.com# modification, are permitted provided that the following conditions are
78922Swilliam.wang@arm.com# met: redistributions of source code must retain the above copyright
88922Swilliam.wang@arm.com# notice, this list of conditions and the following disclaimer;
98922Swilliam.wang@arm.com# redistributions in binary form must reproduce the above copyright
108922Swilliam.wang@arm.com# notice, this list of conditions and the following disclaimer in the
118922Swilliam.wang@arm.com# documentation and/or other materials provided with the distribution;
128922Swilliam.wang@arm.com# neither the name of the copyright holders nor the names of its
138922Swilliam.wang@arm.com# contributors may be used to endorse or promote products derived from
145647Sgblack@eecs.umich.edu# this software without specific prior written permission.
155647Sgblack@eecs.umich.edu#
165647Sgblack@eecs.umich.edu# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
177087Snate@binkert.org# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
187087Snate@binkert.org# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
197087Snate@binkert.org# A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
207087Snate@binkert.org# OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
217087Snate@binkert.org# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
227087Snate@binkert.org# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
237087Snate@binkert.org# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
247087Snate@binkert.org# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
255647Sgblack@eecs.umich.edu# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
267087Snate@binkert.org# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
277087Snate@binkert.org#
287087Snate@binkert.org# Authors: Brad Beckmann
297087Snate@binkert.org#          Tushar Krishna
307087Snate@binkert.org
317087Snate@binkert.orgfrom __future__ import print_function
327087Snate@binkert.orgfrom __future__ import absolute_import
337087Snate@binkert.org
345647Sgblack@eecs.umich.edufrom m5.params import *
357087Snate@binkert.orgfrom m5.objects import *
365647Sgblack@eecs.umich.edu
375647Sgblack@eecs.umich.edufrom .BaseTopology import SimpleTopology
385647Sgblack@eecs.umich.edu
395647Sgblack@eecs.umich.edu# Creates a generic Mesh assuming an equal number of cache
405647Sgblack@eecs.umich.edu# and directory controllers.
415647Sgblack@eecs.umich.edu# XY routing is enforced (using link weights)
425647Sgblack@eecs.umich.edu# to guarantee deadlock freedom.
435647Sgblack@eecs.umich.edu
445647Sgblack@eecs.umich.educlass Mesh_XY(SimpleTopology):
455647Sgblack@eecs.umich.edu    description='Mesh_XY'
465647Sgblack@eecs.umich.edu
475647Sgblack@eecs.umich.edu    def __init__(self, controllers):
485647Sgblack@eecs.umich.edu        self.nodes = controllers
495647Sgblack@eecs.umich.edu
505647Sgblack@eecs.umich.edu    # Makes a generic mesh
515647Sgblack@eecs.umich.edu    # assuming an equal number of cache and directory cntrls
5211793Sbrandon.potter@amd.com
5311793Sbrandon.potter@amd.com    def makeTopology(self, options, network, IntLink, ExtLink, Router):
5410474Sandreas.hansson@arm.com        nodes = self.nodes
5510474Sandreas.hansson@arm.com
5611793Sbrandon.potter@amd.com        num_routers = options.num_cpus
578229Snate@binkert.org        num_rows = options.mesh_rows
585647Sgblack@eecs.umich.edu
598232Snate@binkert.org        # default values for link latency and router latency.
606137Sgblack@eecs.umich.edu        # Can be over-ridden on a per link/router basis
616137Sgblack@eecs.umich.edu        link_latency = options.link_latency # used by simple and garnet
626137Sgblack@eecs.umich.edu        router_latency = options.router_latency # only used by garnet
635654Sgblack@eecs.umich.edu
6411793Sbrandon.potter@amd.com
656046Sgblack@eecs.umich.edu        # There must be an evenly divisible number of cntrls to routers
665647Sgblack@eecs.umich.edu        # Also, obviously the number or rows must be <= the number of routers
675648Sgblack@eecs.umich.edu        cntrls_per_router, remainder = divmod(len(nodes), num_routers)
685648Sgblack@eecs.umich.edu        assert(num_rows > 0 and num_rows <= num_routers)
695647Sgblack@eecs.umich.edu        num_columns = int(num_routers / num_rows)
705647Sgblack@eecs.umich.edu        assert(num_columns * num_rows == num_routers)
715647Sgblack@eecs.umich.edu
725647Sgblack@eecs.umich.edu        # Create the routers in the mesh
735647Sgblack@eecs.umich.edu        routers = [Router(router_id=i, latency = router_latency) \
745647Sgblack@eecs.umich.edu            for i in range(num_routers)]
755647Sgblack@eecs.umich.edu        network.routers = routers
765647Sgblack@eecs.umich.edu
775647Sgblack@eecs.umich.edu        # link counter to set unique link ids
785648Sgblack@eecs.umich.edu        link_count = 0
795647Sgblack@eecs.umich.edu
805648Sgblack@eecs.umich.edu        # Add all but the remainder nodes to the list of nodes to be uniformly
815648Sgblack@eecs.umich.edu        # distributed across the network.
825648Sgblack@eecs.umich.edu        network_nodes = []
835648Sgblack@eecs.umich.edu        remainder_nodes = []
845648Sgblack@eecs.umich.edu        for node_index in range(len(nodes)):
855648Sgblack@eecs.umich.edu            if node_index < (len(nodes) - remainder):
865648Sgblack@eecs.umich.edu                network_nodes.append(nodes[node_index])
875648Sgblack@eecs.umich.edu            else:
885648Sgblack@eecs.umich.edu                remainder_nodes.append(nodes[node_index])
895648Sgblack@eecs.umich.edu
905648Sgblack@eecs.umich.edu        # Connect each node to the appropriate router
915648Sgblack@eecs.umich.edu        ext_links = []
925648Sgblack@eecs.umich.edu        for (i, n) in enumerate(network_nodes):
935648Sgblack@eecs.umich.edu            cntrl_level, router_id = divmod(i, num_routers)
945648Sgblack@eecs.umich.edu            assert(cntrl_level < cntrls_per_router)
955648Sgblack@eecs.umich.edu            ext_links.append(ExtLink(link_id=link_count, ext_node=n,
965648Sgblack@eecs.umich.edu                                    int_node=routers[router_id],
975648Sgblack@eecs.umich.edu                                    latency = link_latency))
985648Sgblack@eecs.umich.edu            link_count += 1
995648Sgblack@eecs.umich.edu
1005648Sgblack@eecs.umich.edu        # Connect the remainding nodes to router 0.  These should only be
1015648Sgblack@eecs.umich.edu        # DMA nodes.
1025648Sgblack@eecs.umich.edu        for (i, node) in enumerate(remainder_nodes):
1035648Sgblack@eecs.umich.edu            assert(node.type == 'DMA_Controller')
1045648Sgblack@eecs.umich.edu            assert(i < remainder)
1055648Sgblack@eecs.umich.edu            ext_links.append(ExtLink(link_id=link_count, ext_node=node,
1065648Sgblack@eecs.umich.edu                                    int_node=routers[0],
1075648Sgblack@eecs.umich.edu                                    latency = link_latency))
1085648Sgblack@eecs.umich.edu            link_count += 1
1095648Sgblack@eecs.umich.edu
1105648Sgblack@eecs.umich.edu        network.ext_links = ext_links
1115648Sgblack@eecs.umich.edu
1125648Sgblack@eecs.umich.edu        # Create the mesh links.
1135648Sgblack@eecs.umich.edu        int_links = []
1145648Sgblack@eecs.umich.edu
1155648Sgblack@eecs.umich.edu        # East output to West input links (weight = 1)
1165648Sgblack@eecs.umich.edu        for row in range(num_rows):
1175648Sgblack@eecs.umich.edu            for col in range(num_columns):
1185648Sgblack@eecs.umich.edu                if (col + 1 < num_columns):
1195648Sgblack@eecs.umich.edu                    east_out = col + (row * num_columns)
1205648Sgblack@eecs.umich.edu                    west_in = (col + 1) + (row * num_columns)
1215648Sgblack@eecs.umich.edu                    int_links.append(IntLink(link_id=link_count,
1225648Sgblack@eecs.umich.edu                                             src_node=routers[east_out],
12311479Sbaz21@cam.ac.uk                                             dst_node=routers[west_in],
1245648Sgblack@eecs.umich.edu                                             src_outport="East",
1255648Sgblack@eecs.umich.edu                                             dst_inport="West",
1265648Sgblack@eecs.umich.edu                                             latency = link_latency,
1275648Sgblack@eecs.umich.edu                                             weight=1))
1285648Sgblack@eecs.umich.edu                    link_count += 1
1295648Sgblack@eecs.umich.edu
1305648Sgblack@eecs.umich.edu        # West output to East input links (weight = 1)
1315648Sgblack@eecs.umich.edu        for row in range(num_rows):
1325648Sgblack@eecs.umich.edu            for col in range(num_columns):
13311479Sbaz21@cam.ac.uk                if (col + 1 < num_columns):
1345648Sgblack@eecs.umich.edu                    east_in = col + (row * num_columns)
1355648Sgblack@eecs.umich.edu                    west_out = (col + 1) + (row * num_columns)
1365648Sgblack@eecs.umich.edu                    int_links.append(IntLink(link_id=link_count,
1375648Sgblack@eecs.umich.edu                                             src_node=routers[west_out],
1385648Sgblack@eecs.umich.edu                                             dst_node=routers[east_in],
1395648Sgblack@eecs.umich.edu                                             src_outport="West",
1405648Sgblack@eecs.umich.edu                                             dst_inport="East",
1415648Sgblack@eecs.umich.edu                                             latency = link_latency,
1425648Sgblack@eecs.umich.edu                                             weight=1))
14311479Sbaz21@cam.ac.uk                    link_count += 1
1445648Sgblack@eecs.umich.edu
1455648Sgblack@eecs.umich.edu        # North output to South input links (weight = 2)
1465648Sgblack@eecs.umich.edu        for col in range(num_columns):
1475648Sgblack@eecs.umich.edu            for row in range(num_rows):
1485648Sgblack@eecs.umich.edu                if (row + 1 < num_rows):
1495648Sgblack@eecs.umich.edu                    north_out = col + (row * num_columns)
1505648Sgblack@eecs.umich.edu                    south_in = col + ((row + 1) * num_columns)
1515648Sgblack@eecs.umich.edu                    int_links.append(IntLink(link_id=link_count,
1525648Sgblack@eecs.umich.edu                                             src_node=routers[north_out],
1535648Sgblack@eecs.umich.edu                                             dst_node=routers[south_in],
1545648Sgblack@eecs.umich.edu                                             src_outport="North",
1555648Sgblack@eecs.umich.edu                                             dst_inport="South",
1565648Sgblack@eecs.umich.edu                                             latency = link_latency,
1575648Sgblack@eecs.umich.edu                                             weight=2))
1585648Sgblack@eecs.umich.edu                    link_count += 1
1595648Sgblack@eecs.umich.edu
1605648Sgblack@eecs.umich.edu        # South output to North input links (weight = 2)
1615648Sgblack@eecs.umich.edu        for col in range(num_columns):
1625648Sgblack@eecs.umich.edu            for row in range(num_rows):
1635648Sgblack@eecs.umich.edu                if (row + 1 < num_rows):
1645648Sgblack@eecs.umich.edu                    north_in = col + (row * num_columns)
1655648Sgblack@eecs.umich.edu                    south_out = col + ((row + 1) * num_columns)
1665648Sgblack@eecs.umich.edu                    int_links.append(IntLink(link_id=link_count,
1675648Sgblack@eecs.umich.edu                                             src_node=routers[south_out],
1685648Sgblack@eecs.umich.edu                                             dst_node=routers[north_in],
1695648Sgblack@eecs.umich.edu                                             src_outport="South",
1705648Sgblack@eecs.umich.edu                                             dst_inport="North",
1715648Sgblack@eecs.umich.edu                                             latency = link_latency,
1725648Sgblack@eecs.umich.edu                                             weight=2))
1735648Sgblack@eecs.umich.edu                    link_count += 1
1745648Sgblack@eecs.umich.edu
1755648Sgblack@eecs.umich.edu
1765648Sgblack@eecs.umich.edu        network.int_links = int_links
1775648Sgblack@eecs.umich.edu