diff -r 4c0f7929ee33 -r fec1d60c0594 src/sim/root.cc --- a/src/sim/root.cc Tue Jan 18 01:27:04 2011 -0800 +++ b/src/sim/root.cc Tue Jan 18 04:18:40 2011 -0800 @@ -1,5 +1,6 @@ /* * Copyright (c) 2002-2005 The Regents of The University of Michigan + * Copyright (c) 2011 Advanced Micro Devices * All rights reserved. * * Redistribution and use in source and binary forms, with or without @@ -27,17 +28,51 @@ * * Authors: Nathan Binkert * Steve Reinhardt + * Gabe Black */ #include "base/misc.hh" -#include "params/Root.hh" -#include "sim/sim_object.hh" +#include "sim/root.hh" -// Dummy Object -struct Root : public SimObject +Root *Root::_root = NULL; + +void +Root::timeSync() { - Root(RootParams *params) : SimObject(params) {} -}; + Time cur_time, diff; + + do { + cur_time.setTimer(); + diff = cur_time - lastTime; + Time remainder = period() - diff; + if (diff < period() && remainder > _spinThreshold) { + DPRINTF(TimeSync, "Sleeping to sync with real time.\n"); + // Sleep until the end of the period, or until a signal. + sleep(remainder); + // Refresh the current time. + cur_time.setTimer(); + } + } while (diff < period()); + lastTime = cur_time; + schedule(&syncEvent, curTick() + _periodTick); +} + +void +Root::enable(bool en) +{ + if (en == _enabled) + return; + _enabled = en; + if (_enabled) { + // Get event going. + Tick periods = ((curTick() + _periodTick - 1) / _periodTick); + Tick nextPeriod = periods * _periodTick; + schedule(&syncEvent, nextPeriod); + } else { + // Stop event. + deschedule(&syncEvent); + } +} Root * RootParams::create() diff -r 4c0f7929ee33 -r fec1d60c0594 src/sim/Root.py --- a/src/sim/Root.py Tue Jan 18 01:27:04 2011 -0800 +++ b/src/sim/Root.py Tue Jan 18 04:18:40 2011 -0800 @@ -57,4 +57,9 @@ return 'root' type = 'Root' - dummy = Param.Int(0, "We don't support objects without params") + + # Time syncing prevents the simulation from running faster than real time. + time_sync_enable = Param.Bool(False, "whether time syncing is enabled") + time_sync_period = Param.Clock("100ms", "how often to sync with real time") + time_sync_spin_threshold = \ + Param.Clock("100us", "when less than this much time is left, spin") diff -r 4c0f7929ee33 -r fec1d60c0594 src/sim/SConscript --- a/src/sim/SConscript Tue Jan 18 01:27:04 2011 -0800 +++ b/src/sim/SConscript Tue Jan 18 04:18:40 2011 -0800 @@ -73,6 +73,7 @@ TraceFlag('Loader') TraceFlag('Stack') TraceFlag('SyscallVerbose') +TraceFlag('TimeSync') TraceFlag('TLB') TraceFlag('Thread') TraceFlag('Timer') diff -r 4c0f7929ee33 -r fec1d60c0594 src/sim/root.hh --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/src/sim/root.hh Tue Jan 18 04:18:40 2011 -0800 @@ -0,0 +1,106 @@ +/* + * Copyright (c) 2011 Advanced Micro Devices + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are + * met: redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer; + * redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution; + * neither the name of the copyright holders nor the names of its + * contributors may be used to endorse or promote products derived from + * this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + * + * Authors: Gabe Black + */ + +#ifndef __SIM_ROOT_HH__ +#define __SIM_ROOT_HH__ + +#include "base/time.hh" +#include "params/Root.hh" +#include "sim/core.hh" +#include "sim/eventq.hh" +#include "sim/sim_object.hh" + +class Root : public SimObject +{ + private: + static Root *_root; + + protected: + bool _enabled; + Time _period; + Tick _periodTick; + Time _spinThreshold; + + Time lastTime; + + void timeSync(); + EventWrapper syncEvent; + friend class EventWrapper; + + public: + static Root * + root() + { + assert(_root); + return _root; + } + + public: + + bool enabled() const { return _enabled; } + const Time period() const { return _period; } + const Time spinThreshold() const { return _spinThreshold; } + + void enable(bool en); + + void + period(long ns) + { + bool en = enabled(); + _period = ns; + _periodTick = _period * SimClock::Int::ns; + enable(en); + } + + void + spinThreshold(long ns) + { + bool en = enabled(); + _spinThreshold = ns; + enable(en); + } + + Root(RootParams *p) : SimObject(p), _enabled(false), + _periodTick(p->time_sync_period), syncEvent(this) + { + uint64_t nsecs = p->time_sync_period / SimClock::Int::ns; + _period.set(nsecs / Time::NSEC_PER_SEC, nsecs % Time::NSEC_PER_SEC); + nsecs = p->time_sync_spin_threshold / SimClock::Int::ns; + _spinThreshold.set(nsecs / Time::NSEC_PER_SEC, + nsecs % Time::NSEC_PER_SEC); + + assert(_root == NULL); + _root = this; + lastTime.setTimer(); + enable(p->time_sync_enable); + } +}; + +#endif diff -r 4c0f7929ee33 -r fec1d60c0594 configs/example/fs.py --- a/configs/example/fs.py Tue Jan 18 01:27:04 2011 -0800 +++ b/configs/example/fs.py Tue Jan 18 04:18:40 2011 -0800 @@ -65,6 +65,10 @@ parser = optparse.OptionParser() +# Simulation options +parser.add_option("--timesync", action="store_true", + help="Prevent simulated time from getting ahead of real time") + # System options parser.add_option("--kernel", action="store", type="string") parser.add_option("--script", action="store", type="string") @@ -187,4 +191,7 @@ print "Error I don't know how to create more than 2 systems." sys.exit(1) +if options.timesync: + root.time_sync_enable = True + Simulation.run(options, root, test_sys, FutureClass)