X-Git-Url: https://git.libre-soc.org/?a=blobdiff_plain;f=configs%2Fcommon%2FSimulation.py;h=08e700d87f04c6c4ddc3ae72def50ceed997797e;hb=02a56d8d01ff4969f73740197309885e8ebdc527;hp=374ff3fc2521598a38a00da9ad09c545fd6bd2ee;hpb=51d8c59ef8bddb1078d2f010c143ae9471c60c2d;p=gem5.git diff --git a/configs/common/Simulation.py b/configs/common/Simulation.py index 374ff3fc2..08e700d87 100644 --- a/configs/common/Simulation.py +++ b/configs/common/Simulation.py @@ -1,4 +1,4 @@ -# Copyright (c) 2006 The Regents of The University of Michigan +# Copyright (c) 2006-2008 The Regents of The University of Michigan # All rights reserved. # # Redistribution and use in source and binary forms, with or without @@ -37,20 +37,23 @@ def setCPUClass(options): atomic = False if options.timing: - TmpClass = TimingSimpleCPU + class TmpClass(TimingSimpleCPU): pass elif options.detailed: - TmpClass = DerivO3CPU + if not options.caches: + print "O3 CPU must be used with caches" + sys.exit(1) + class TmpClass(DerivO3CPU): pass else: - TmpClass = AtomicSimpleCPU + class TmpClass(AtomicSimpleCPU): pass atomic = True CPUClass = None test_mem_mode = 'atomic' if not atomic: - if options.checkpoint_restore: + if options.checkpoint_restore != None or options.fast_forward: CPUClass = TmpClass - TmpClass = AtomicSimpleCPU + class TmpClass(AtomicSimpleCPU): pass else: test_mem_mode = 'timing' @@ -61,7 +64,7 @@ def run(options, root, testsys, cpu_class): if options.maxtick: maxtick = options.maxtick elif options.maxtime: - simtime = int(options.maxtime * root.clock.value) + simtime = m5.ticks.seconds(simtime) print "simulating for: ", simtime maxtick = simtime else: @@ -69,9 +72,17 @@ def run(options, root, testsys, cpu_class): if options.checkpoint_dir: cptdir = options.checkpoint_dir + elif m5.options.outdir: + cptdir = m5.options.outdir else: cptdir = getcwd() + if options.fast_forward and options.checkpoint_restore != None: + m5.panic("Error: Can't specify both --fast-forward and --checkpoint-restore") + + if options.standard_switch and not options.caches: + m5.panic("Error: Must specify --caches when using --standard-switch") + np = options.num_cpus max_checkpoints = options.max_checkpoints switch_cpus = None @@ -81,12 +92,17 @@ def run(options, root, testsys, cpu_class): for i in xrange(np)] for i in xrange(np): + if options.fast_forward: + testsys.cpu[i].max_insts_any_thread = int(options.fast_forward) switch_cpus[i].system = testsys if not m5.build_env['FULL_SYSTEM']: switch_cpus[i].workload = testsys.cpu[i].workload switch_cpus[i].clock = testsys.cpu[0].clock + # simulation period + if options.max_inst: + switch_cpus[i].max_insts_any_thread = options.max_inst - root.switch_cpus = switch_cpus + testsys.switch_cpus = switch_cpus switch_cpu_list = [(testsys.cpu[i], switch_cpus[i]) for i in xrange(np)] if options.standard_switch: @@ -104,106 +120,237 @@ def run(options, root, testsys, cpu_class): switch_cpus[i].clock = testsys.cpu[0].clock switch_cpus_1[i].clock = testsys.cpu[0].clock + # if restoring, make atomic cpu simulate only a few instructions + if options.checkpoint_restore != None: + testsys.cpu[i].max_insts_any_thread = 1 + # Fast forward to specified location if we are not restoring + elif options.fast_forward: + testsys.cpu[i].max_insts_any_thread = int(options.fast_forward) + # Fast forward to a simpoint (warning: time consuming) + elif options.simpoint: + if testsys.cpu[i].workload[0].simpoint == None: + m5.panic('simpoint not found') + testsys.cpu[i].max_insts_any_thread = \ + testsys.cpu[i].workload[0].simpoint + # No distance specified, just switch + else: + testsys.cpu[i].max_insts_any_thread = 1 + + # warmup period + if options.warmup_insts: + switch_cpus[i].max_insts_any_thread = options.warmup_insts + + # simulation period + if options.max_inst: + switch_cpus_1[i].max_insts_any_thread = options.max_inst + if not options.caches: # O3 CPU must have a cache to work. switch_cpus_1[i].addPrivateSplitL1Caches(L1Cache(size = '32kB'), L1Cache(size = '64kB')) switch_cpus_1[i].connectMemPorts(testsys.membus) - testsys.switch_cpus = switch_cpus testsys.switch_cpus_1 = switch_cpus_1 switch_cpu_list = [(testsys.cpu[i], switch_cpus[i]) for i in xrange(np)] switch_cpu_list1 = [(switch_cpus[i], switch_cpus_1[i]) for i in xrange(np)] + # set the checkpoint in the cpu before m5.instantiate is called + if options.take_checkpoints != None and \ + (options.simpoint or options.at_instruction): + offset = int(options.take_checkpoints) + # Set an instruction break point + if options.simpoint: + for i in xrange(np): + if testsys.cpu[i].workload[0].simpoint == None: + m5.panic('no simpoint for testsys.cpu[%d].workload[0]' % i) + checkpoint_inst = int(testsys.cpu[i].workload[0].simpoint) + offset + testsys.cpu[i].max_insts_any_thread = checkpoint_inst + # used for output below + options.take_checkpoints = checkpoint_inst + else: + options.take_checkpoints = offset + # Set all test cpus with the right number of instructions + # for the upcoming simulation + for i in xrange(np): + testsys.cpu[i].max_insts_any_thread = offset + m5.instantiate(root) - if options.checkpoint_restore: - from os.path import isdir + if options.checkpoint_restore != None: + from os.path import isdir, exists from os import listdir import re if not isdir(cptdir): m5.panic("checkpoint dir %s does not exist!" % cptdir) - dirs = listdir(cptdir) - expr = re.compile('cpt.([0-9]*)') - cpts = [] - for dir in dirs: - match = expr.match(dir) - if match: - cpts.append(match.group(1)) + if options.at_instruction: + checkpoint_dir = joinpath(cptdir, "cpt.%s.%s" % \ + (options.bench, options.checkpoint_restore)) + if not exists(checkpoint_dir): + m5.panic("Unable to find checkpoint directory %s" % \ + checkpoint_dir) + + print "Restoring checkpoint ..." + m5.restoreCheckpoint(root, checkpoint_dir) + print "Done." + elif options.simpoint: + # assume workload 0 has the simpoint + if testsys.cpu[0].workload[0].simpoint == None: + m5.panic('Unable to find simpoint') + + options.checkpoint_restore += \ + int(testsys.cpu[0].workload[0].simpoint) + + checkpoint_dir = joinpath(cptdir, "cpt.%s.%d" % \ + (options.bench, options.checkpoint_restore)) + if not exists(checkpoint_dir): + m5.panic("Unable to find checkpoint directory %s.%s" % \ + (options.bench, options.checkpoint_restore)) + + print "Restoring checkpoint ..." + m5.restoreCheckpoint(root,checkpoint_dir) + print "Done." + else: + dirs = listdir(cptdir) + expr = re.compile('cpt\.([0-9]*)') + cpts = [] + for dir in dirs: + match = expr.match(dir) + if match: + cpts.append(match.group(1)) + + cpts.sort(lambda a,b: cmp(long(a), long(b))) - cpts.sort(lambda a,b: cmp(long(a), long(b))) + cpt_num = options.checkpoint_restore - cpt_num = options.checkpoint_restore + if cpt_num > len(cpts): + m5.panic('Checkpoint %d not found' % cpt_num) - if cpt_num > len(cpts): - m5.panic('Checkpoint %d not found' % cpt_num) + ## Adjust max tick based on our starting tick + maxtick = maxtick - int(cpts[cpt_num - 1]) - m5.restoreCheckpoint(root, - joinpath(cptdir, "cpt.%s" % cpts[cpt_num - 1])) + ## Restore the checkpoint + m5.restoreCheckpoint(root, + joinpath(cptdir, "cpt.%s" % cpts[cpt_num - 1])) if options.standard_switch or cpu_class: - exit_event = m5.simulate(10000) + if options.standard_switch: + print "Switch at instruction count:%s" % \ + str(testsys.cpu[0].max_insts_any_thread) + exit_event = m5.simulate() + elif cpu_class and options.fast_forward: + print "Switch at instruction count:%s" % \ + str(testsys.cpu[0].max_insts_any_thread) + exit_event = m5.simulate() + else: + print "Switch at curTick count:%s" % str(10000) + exit_event = m5.simulate(10000) + print "Switched CPUS @ cycle = %s" % (m5.curTick()) - ## when you change to Timing (or Atomic), you halt the system given - ## as argument. When you are finished with the system changes - ## (including switchCpus), you must resume the system manually. - ## You DON'T need to resume after just switching CPUs if you haven't - ## changed anything on the system level. + # when you change to Timing (or Atomic), you halt the system + # given as argument. When you are finished with the system + # changes (including switchCpus), you must resume the system + # manually. You DON'T need to resume after just switching + # CPUs if you haven't changed anything on the system level. m5.changeToTiming(testsys) m5.switchCpus(switch_cpu_list) m5.resume(testsys) if options.standard_switch: - exit_event = m5.simulate(options.warmup) + print "Switch at instruction count:%d" % \ + (testsys.switch_cpus[0].max_insts_any_thread) + + #warmup instruction count may have already been set + if options.warmup_insts: + exit_event = m5.simulate() + else: + exit_event = m5.simulate(options.warmup) + print "Switching CPUS @ cycle = %s" % (m5.curTick()) + print "Simulation ends instruction count:%d" % \ + (testsys.switch_cpus_1[0].max_insts_any_thread) + m5.drain(testsys) m5.switchCpus(switch_cpu_list1) + m5.resume(testsys) num_checkpoints = 0 exit_cause = '' - ## Checkpoints being taken via the command line at and at subsequent - ## periods of . Checkpoint instructions received from the benchmark running - ## are ignored and skipped in favor of command line checkpoint instructions. - if options.take_checkpoints: - [when, period] = options.take_checkpoints.split(",", 1) - when = int(when) - period = int(period) - - exit_event = m5.simulate(when) - while exit_event.getCause() == "checkpoint": - exit_event = m5.simulate(when - m5.curTick()) - - if exit_event.getCause() == "simulate() limit reached": - m5.checkpoint(root, joinpath(cptdir, "cpt.%d")) - num_checkpoints += 1 - - sim_ticks = when - exit_cause = "maximum %d checkpoints dropped" % max_checkpoints - while num_checkpoints < max_checkpoints: - if (sim_ticks + period) > maxtick: - exit_event = m5.simulate(maxtick - sim_ticks) - exit_cause = exit_event.getCause() - break - else: - exit_event = m5.simulate(period) - sim_ticks += period - while exit_event.getCause() == "checkpoint": - exit_event = m5.simulate(sim_ticks - m5.curTick()) - if exit_event.getCause() == "simulate() limit reached": - m5.checkpoint(root, joinpath(cptdir, "cpt.%d")) - num_checkpoints += 1 - - else: #no checkpoints being taken via this script + # Checkpoints being taken via the command line at and at + # subsequent periods of . Checkpoint instructions + # received from the benchmark running are ignored and skipped in + # favor of command line checkpoint instructions. + if options.take_checkpoints != None : + if options.at_instruction or options.simpoint: + checkpoint_inst = int(options.take_checkpoints) + + # maintain correct offset if we restored from some instruction + if options.checkpoint_restore != None: + checkpoint_inst += options.checkpoint_restore + + print "Creating checkpoint at inst:%d" % (checkpoint_inst) + exit_event = m5.simulate() + print "exit cause = %s" % (exit_event.getCause()) + + # skip checkpoint instructions should they exist + while exit_event.getCause() == "checkpoint": + exit_event = m5.simulate() + + if exit_event.getCause() == \ + "a thread reached the max instruction count": + m5.checkpoint(root, joinpath(cptdir, "cpt.%s.%d" % \ + (options.bench, checkpoint_inst))) + print "Checkpoint written." + num_checkpoints += 1 + + if exit_event.getCause() == "user interrupt received": + exit_cause = exit_event.getCause(); + else: + when, period = options.take_checkpoints.split(",", 1) + when = int(when) + period = int(period) + + exit_event = m5.simulate(when) + while exit_event.getCause() == "checkpoint": + exit_event = m5.simulate(when - m5.curTick()) + + if exit_event.getCause() == "simulate() limit reached": + m5.checkpoint(root, joinpath(cptdir, "cpt.%d")) + num_checkpoints += 1 + + sim_ticks = when + exit_cause = "maximum %d checkpoints dropped" % max_checkpoints + while num_checkpoints < max_checkpoints and \ + exit_event.getCause() == "simulate() limit reached": + if (sim_ticks + period) > maxtick: + exit_event = m5.simulate(maxtick - sim_ticks) + exit_cause = exit_event.getCause() + break + else: + exit_event = m5.simulate(period) + sim_ticks += period + while exit_event.getCause() == "checkpoint": + exit_event = m5.simulate(sim_ticks - m5.curTick()) + if exit_event.getCause() == "simulate() limit reached": + m5.checkpoint(root, joinpath(cptdir, "cpt.%d")) + num_checkpoints += 1 + + if exit_event.getCause() != "simulate() limit reached": + exit_cause = exit_event.getCause(); + + else: # no checkpoints being taken via this script + if options.fast_forward: + m5.stats.reset() + print "**** REAL SIMULATION ****" exit_event = m5.simulate(maxtick) while exit_event.getCause() == "checkpoint": m5.checkpoint(root, joinpath(cptdir, "cpt.%d")) num_checkpoints += 1 if num_checkpoints == max_checkpoints: - exit_cause = "maximum %d checkpoints dropped" % max_checkpoints + exit_cause = "maximum %d checkpoints dropped" % max_checkpoints break exit_event = m5.simulate(maxtick - m5.curTick())