1 # Copyright (c) 2006 The Regents of The University of Michigan
4 # Redistribution and use in source and binary forms, with or without
5 # modification, are permitted provided that the following conditions are
6 # met: redistributions of source code must retain the above copyright
7 # notice, this list of conditions and the following disclaimer;
8 # redistributions in binary form must reproduce the above copyright
9 # notice, this list of conditions and the following disclaimer in the
10 # documentation and/or other materials provided with the distribution;
11 # neither the name of the copyright holders nor the names of its
12 # contributors may be used to endorse or promote products derived from
13 # this software without specific prior written permission.
15 # THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
16 # "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
17 # LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
18 # A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
19 # OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
20 # SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
21 # LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
22 # DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
23 # THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 # (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
25 # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 # Authors: Ron Dreslinski
34 from m5
.objects
import *
35 import os
, optparse
, sys
36 m5
.AddToPath('../common')
38 # --------------------
39 # Define Command Line Options
40 # ====================
42 parser
= optparse
.OptionParser()
44 parser
.add_option("-d", "--detailed", action
="store_true")
45 parser
.add_option("-t", "--timing", action
="store_true")
46 parser
.add_option("-m", "--maxtick", type="int")
47 parser
.add_option("-c", "--numclusters",
48 help="Number of clusters", type="int")
49 parser
.add_option("-n", "--numcpus",
50 help="Number of cpus in total", type="int")
51 parser
.add_option("-f", "--frequency",
53 help="Frequency of each CPU")
54 parser
.add_option("-p", "--protocol",
56 help="The coherence protocol to use for the L1'a (i.e. MOESI, MOSI)")
57 parser
.add_option("--l1size",
59 parser
.add_option("--l1latency",
61 parser
.add_option("--l2size",
63 parser
.add_option("--l2latency",
65 parser
.add_option("--rootdir",
66 help="ROot directory of Splash2",
67 default
="/dist/splash2/codes/")
68 parser
.add_option("-b", "--benchmark",
69 help="Splash 2 benchmark to run")
71 (options
, args
) = parser
.parse_args()
74 print "Error: script doesn't take any positional arguments"
77 # --------------------
78 # Define Splash2 Benchmarks
79 # ====================
80 class Cholesky(LiveProcess
):
81 executable
= options
.rootdir
+ '/kernels/cholesky/CHOLESKY'
82 cmd
= 'CHOLESKY -p' + str(options
.numcpus
) + ' '\
83 + options
.rootdir
+ '/kernels/cholesky/inputs/tk23.O'
85 class FFT(LiveProcess
):
86 executable
= options
.rootdir
+ 'kernels/fft/FFT'
87 cmd
= 'FFT -p' + str(options
.numcpus
) + ' -m18'
89 class LU_contig(LiveProcess
):
90 executable
= options
.rootdir
+ 'kernels/lu/contiguous_blocks/LU'
91 cmd
= 'LU -p' + str(options
.numcpus
)
93 class LU_noncontig(LiveProcess
):
94 executable
= options
.rootdir
+ 'kernels/lu/non_contiguous_blocks/LU'
95 cmd
= 'LU -p' + str(options
.numcpus
)
97 class Radix(LiveProcess
):
98 executable
= options
.rootdir
+ 'kernels/radix/RADIX'
99 cmd
= 'RADIX -n524288 -p' + str(options
.numcpus
)
101 class Barnes(LiveProcess
):
102 executable
= options
.rootdir
+ 'apps/barnes/BARNES'
104 input = options
.rootdir
+ 'apps/barnes/input.p' + str(options
.numcpus
)
106 class FMM(LiveProcess
):
107 executable
= options
.rootdir
+ 'apps/fmm/FMM'
109 input = options
.rootdir
+ 'apps/fmm/inputs/input.2048.p' + str(options
.numcpus
)
111 class Ocean_contig(LiveProcess
):
112 executable
= options
.rootdir
+ 'apps/ocean/contiguous_partitions/OCEAN'
113 cmd
= 'OCEAN -p' + str(options
.numcpus
)
115 class Ocean_noncontig(LiveProcess
):
116 executable
= options
.rootdir
+ 'apps/ocean/non_contiguous_partitions/OCEAN'
117 cmd
= 'OCEAN -p' + str(options
.numcpus
)
119 class Raytrace(LiveProcess
):
120 executable
= options
.rootdir
+ 'apps/raytrace/RAYTRACE'
121 cmd
= 'RAYTRACE -p' + str(options
.numcpus
) + ' ' \
122 + options
.rootdir
+ 'apps/raytrace/inputs/teapot.env'
124 class Water_nsquared(LiveProcess
):
125 executable
= options
.rootdir
+ 'apps/water-nsquared/WATER-NSQUARED'
126 cmd
= 'WATER-NSQUARED'
127 input = options
.rootdir
+ 'apps/water-nsquared/input.p' + str(options
.numcpus
)
129 class Water_spatial(LiveProcess
):
130 executable
= options
.rootdir
+ 'apps/water-spatial/WATER-SPATIAL'
131 cmd
= 'WATER-SPATIAL'
132 input = options
.rootdir
+ 'apps/water-spatial/input.p' + str(options
.numcpus
)
135 # --------------------
136 # Base L1 Cache Definition
137 # ====================
140 latency
= options
.l1latency
144 protocol
= CoherenceProtocol(protocol
=options
.protocol
)
146 # ----------------------
147 # Base L2 Cache Definition
148 # ----------------------
152 latency
= options
.l2latency
157 # ----------------------
158 # Define the clusters with their cpus
159 # ----------------------
163 cpusPerCluster
= options
.numcpus
/options
.numclusters
165 busFrequency
= Frequency(options
.frequency
)
166 busFrequency
*= cpusPerCluster
172 clusters
= [ Cluster() for i
in xrange(options
.numclusters
)]
173 for j
in xrange(options
.numclusters
):
175 for cluster
in clusters
:
176 cluster
.clusterbus
= Bus(clock
=busFrequency
)
177 all_l1buses
+= [cluster
.clusterbus
]
178 cluster
.cpus
= [TimingSimpleCPU(cpu_id
= i
+ cluster
.id,
179 clock
=options
.frequency
)
180 for i
in xrange(cpusPerCluster
)]
181 all_cpus
+= cluster
.cpus
182 cluster
.l1
= L1(size
=options
.l1size
, assoc
= 4)
183 all_l1s
+= [cluster
.l1
]
184 elif options
.detailed
:
185 clusters
= [ Cluster() for i
in xrange(options
.numclusters
)]
186 for j
in xrange(options
.numclusters
):
188 for cluster
in clusters
:
189 cluster
.clusterbus
= Bus(clock
=busFrequency
)
190 all_l1buses
+= [cluster
.clusterbus
]
191 cluster
.cpus
= [DerivO3CPU(cpu_id
= i
+ cluster
.id,
192 clock
=options
.frequency
)
193 for i
in xrange(cpusPerCluster
)]
194 all_cpus
+= cluster
.cpus
195 cluster
.l1
= L1(size
=options
.l1size
, assoc
= 4)
196 all_l1s
+= [cluster
.l1
]
198 clusters
= [ Cluster() for i
in xrange(options
.numclusters
)]
199 for j
in xrange(options
.numclusters
):
201 for cluster
in clusters
:
202 cluster
.clusterbus
= Bus(clock
=busFrequency
)
203 all_l1buses
+= [cluster
.clusterbus
]
204 cluster
.cpus
= [AtomicSimpleCPU(cpu_id
= i
+ cluster
.id,
205 clock
=options
.frequency
)
206 for i
in xrange(cpusPerCluster
)]
207 all_cpus
+= cluster
.cpus
208 cluster
.l1
= L1(size
=options
.l1size
, assoc
= 4)
209 all_l1s
+= [cluster
.l1
]
211 # ----------------------
212 # Create a system, and add system wide objects
213 # ----------------------
214 system
= System(cpu
= all_cpus
, l1_
= all_l1s
, l1bus_
= all_l1buses
, physmem
= PhysicalMemory(),
215 membus
= Bus(clock
= busFrequency
))
217 system
.toL2bus
= Bus(clock
= busFrequency
)
218 system
.l2
= L2(size
= options
.l2size
, assoc
= 8)
220 # ----------------------
221 # Connect the L2 cache and memory together
222 # ----------------------
224 system
.physmem
.port
= system
.membus
.port
225 system
.l2
.cpu_side
= system
.toL2bus
.port
226 system
.l2
.mem_side
= system
.membus
.port
228 # ----------------------
229 # Connect the L2 cache and clusters together
230 # ----------------------
231 for cluster
in clusters
:
232 cluster
.l1
.cpu_side
= cluster
.clusterbus
.port
233 cluster
.l1
.mem_side
= system
.toL2bus
.port
234 for cpu
in cluster
.cpus
:
235 cpu
.icache_port
= cluster
.clusterbus
.port
236 cpu
.dcache_port
= cluster
.clusterbus
.port
239 # ----------------------
241 # ----------------------
243 root
= Root(system
= system
)
245 # --------------------
246 # Pick the correct Splash2 Benchmarks
247 # ====================
248 if options
.benchmark
== 'Cholesky':
249 root
.workload
= Cholesky()
250 elif options
.benchmark
== 'FFT':
251 root
.workload
= FFT()
252 elif options
.benchmark
== 'LUContig':
253 root
.workload
= LU_contig()
254 elif options
.benchmark
== 'LUNoncontig':
255 root
.workload
= LU_noncontig()
256 elif options
.benchmark
== 'Radix':
257 root
.workload
= Radix()
258 elif options
.benchmark
== 'Barnes':
259 root
.workload
= Barnes()
260 elif options
.benchmark
== 'FMM':
261 root
.workload
= FMM()
262 elif options
.benchmark
== 'OceanContig':
263 root
.workload
= Ocean_contig()
264 elif options
.benchmark
== 'OceanNoncontig':
265 root
.workload
= Ocean_noncontig()
266 elif options
.benchmark
== 'Raytrace':
267 root
.workload
= Raytrace()
268 elif options
.benchmark
== 'WaterNSquared':
269 root
.workload
= Water_nsquared()
270 elif options
.benchmark
== 'WaterSpatial':
271 root
.workload
= Water_spatial()
273 panic("The --benchmark environment variable was set to something" \
274 +" improper.\nUse Cholesky, FFT, LUContig, LUNoncontig, Radix" \
275 +", Barnes, FMM, OceanContig,\nOceanNoncontig, Raytrace," \
276 +" WaterNSquared, or WaterSpatial\n")
278 # --------------------
279 # Assign the workload to the cpus
280 # ====================
282 for cluster
in clusters
:
283 for cpu
in cluster
.cpus
:
284 cpu
.workload
= root
.workload
286 # ----------------------
288 # ----------------------
290 if options
.timing
or options
.detailed
:
291 root
.system
.mem_mode
= 'timing'
293 # instantiate configuration
296 # simulate until program terminates
298 exit_event
= m5
.simulate(options
.maxtick
)
300 exit_event
= m5
.simulate(m5
.MaxTick
)
302 print 'Exiting @ tick', m5
.curTick(), 'because', exit_event
.getCause()