TimerTable.cc revision 6467
12SN/A
21762SN/A/*
32SN/A * Copyright (c) 1999-2008 Mark D. Hill and David A. Wood
42SN/A * All rights reserved.
52SN/A *
62SN/A * Redistribution and use in source and binary forms, with or without
72SN/A * modification, are permitted provided that the following conditions are
82SN/A * met: redistributions of source code must retain the above copyright
92SN/A * notice, this list of conditions and the following disclaimer;
102SN/A * redistributions in binary form must reproduce the above copyright
112SN/A * notice, this list of conditions and the following disclaimer in the
122SN/A * documentation and/or other materials provided with the distribution;
132SN/A * neither the name of the copyright holders nor the names of its
142SN/A * contributors may be used to endorse or promote products derived from
152SN/A * this software without specific prior written permission.
162SN/A *
172SN/A * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
182SN/A * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
192SN/A * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
202SN/A * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
212SN/A * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
222SN/A * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
232SN/A * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
242SN/A * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
252SN/A * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
262SN/A * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
272665SN/A * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
282665SN/A */
292SN/A
302SN/A/*
311722SN/A * $Id$
325480Snate@binkert.org */
332SN/A
342SN/A#include "mem/ruby/common/Global.hh"
355480Snate@binkert.org#include "mem/ruby/system/TimerTable.hh"
365480Snate@binkert.org#include "mem/ruby/eventqueue/RubyEventQueue.hh"
372SN/A
386216Snate@binkert.orgTimerTable::TimerTable()
393534SN/A{
40545SN/A  m_consumer_ptr  = NULL;
415480Snate@binkert.org  m_next_valid = false;
42843SN/A  m_next_address = Address(0);
432SN/A  m_next_time = 0;
442SN/A}
455478SN/A
462158SN/A
472SN/Abool TimerTable::isReady() const
482SN/A{
491722SN/A  if (m_map.size() == 0) {
502SN/A    return false;
512SN/A  }
525480Snate@binkert.org
532SN/A  if (!m_next_valid) {
542SN/A    updateNext();
552SN/A  }
562SN/A  assert(m_next_valid);
572SN/A  return (g_eventQueue_ptr->getTime() >= m_next_time);
582SN/A}
592SN/A
602SN/Aconst Address& TimerTable::readyAddress() const
612SN/A{
622SN/A  assert(isReady());
632SN/A
642SN/A  if (!m_next_valid) {
652SN/A    updateNext();
662SN/A  }
672SN/A  assert(m_next_valid);
682SN/A  return m_next_address;
692SN/A}
702SN/A
712SN/Avoid TimerTable::set(const Address& address, Time relative_latency)
722SN/A{
732SN/A  assert(address == line_address(address));
745480Snate@binkert.org  assert(relative_latency > 0);
752SN/A  assert(m_map.exist(address) == false);
762SN/A  Time ready_time = g_eventQueue_ptr->getTime() + relative_latency;
7710905Sandreas.sandberg@arm.com  m_map.add(address, ready_time);
781804SN/A  assert(m_consumer_ptr != NULL);
7910905Sandreas.sandberg@arm.com  g_eventQueue_ptr->scheduleEventAbsolute(m_consumer_ptr, ready_time);
8010905Sandreas.sandberg@arm.com  m_next_valid = false;
811804SN/A
821804SN/A  // Don't always recalculate the next ready address
83934SN/A  if (ready_time <= m_next_time) {
841804SN/A    m_next_valid = false;
851310SN/A  }
86934SN/A}
872SN/A
882SN/Avoid TimerTable::unset(const Address& address)
892SN/A{
902SN/A  assert(address == line_address(address));
912SN/A  assert(m_map.exist(address) == true);
925478SN/A  m_map.remove(address);
932SN/A
941634SN/A  // Don't always recalculate the next ready address
952158SN/A  if (address == m_next_address) {
961634SN/A    m_next_valid = false;
971634SN/A  }
981634SN/A}
991634SN/A
1002512SN/Avoid TimerTable::print(ostream& out) const
1015480Snate@binkert.org{
1025480Snate@binkert.org}
1034762SN/A
1044762SN/A
1054762SN/Avoid TimerTable::updateNext() const
1062512SN/A{
1074762SN/A  if (m_map.size() == 0) {
1084762SN/A    assert(m_next_valid == false);
1092SN/A    return;
1101806SN/A  }
1111634SN/A
1122SN/A  Vector<Address> addresses = m_map.keys();
1132SN/A  m_next_address = addresses[0];
1142SN/A  m_next_time = m_map.lookup(m_next_address);
1153349SN/A
1163349SN/A  // Search for the minimum time
1172SN/A  int size = addresses.size();
1182SN/A  for (int i=1; i<size; i++) {
1192SN/A    Address maybe_next_address = addresses[i];
1202SN/A    Time maybe_next_time = m_map.lookup(maybe_next_address);
12110905Sandreas.sandberg@arm.com    if (maybe_next_time < m_next_time) {
12210905Sandreas.sandberg@arm.com      m_next_time = maybe_next_time;
1232SN/A      m_next_address= maybe_next_address;
1242SN/A    }
1255480Snate@binkert.org  }
126  m_next_valid = true;
127}
128