DirectoryMemory.cc revision 11108
16145SN/A/* 26145SN/A * Copyright (c) 1999-2008 Mark D. Hill and David A. Wood 36145SN/A * All rights reserved. 46145SN/A * 56145SN/A * Redistribution and use in source and binary forms, with or without 66145SN/A * modification, are permitted provided that the following conditions are 76145SN/A * met: redistributions of source code must retain the above copyright 86145SN/A * notice, this list of conditions and the following disclaimer; 96145SN/A * redistributions in binary form must reproduce the above copyright 106145SN/A * notice, this list of conditions and the following disclaimer in the 116145SN/A * documentation and/or other materials provided with the distribution; 126145SN/A * neither the name of the copyright holders nor the names of its 136145SN/A * contributors may be used to endorse or promote products derived from 146145SN/A * this software without specific prior written permission. 156145SN/A * 166145SN/A * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 176145SN/A * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 186145SN/A * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 196145SN/A * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 206145SN/A * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 216145SN/A * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 226145SN/A * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 236145SN/A * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 246145SN/A * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 256145SN/A * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 266145SN/A * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 276145SN/A */ 286145SN/A 297056SN/A#include "base/intmath.hh" 308232SN/A#include "debug/RubyCache.hh" 319104SN/A#include "debug/RubyStats.hh" 327039SN/A#include "mem/ruby/slicc_interface/RubySlicc_Util.hh" 3310301Snilay@cs.wisc.edu#include "mem/ruby/structures/DirectoryMemory.hh" 3411108Sdavid.hashe@amd.com#include "mem/ruby/system/RubySystem.hh" 356145SN/A 367055SN/Ausing namespace std; 377055SN/A 386285SN/Aint DirectoryMemory::m_num_directories = 0; 396285SN/Aint DirectoryMemory::m_num_directories_bits = 0; 407027SN/Aint DirectoryMemory::m_numa_high_bit = 0; 416285SN/A 426876SN/ADirectoryMemory::DirectoryMemory(const Params *p) 436876SN/A : SimObject(p) 446145SN/A{ 456876SN/A m_version = p->version; 466903SN/A m_size_bytes = p->size; 477056SN/A m_size_bits = floorLog2(m_size_bytes); 487025SN/A m_num_entries = 0; 497027SN/A m_numa_high_bit = p->numa_high_bit; 506285SN/A} 516285SN/A 527039SN/Avoid 537039SN/ADirectoryMemory::init() 546285SN/A{ 557039SN/A m_num_entries = m_size_bytes / RubySystem::getBlockSizeBytes(); 5610520Snilay@cs.wisc.edu m_entries = new AbstractEntry*[m_num_entries]; 5710520Snilay@cs.wisc.edu for (int i = 0; i < m_num_entries; i++) 5810520Snilay@cs.wisc.edu m_entries[i] = NULL; 596285SN/A 607039SN/A m_num_directories++; 6110004SN/A m_num_directories_bits = ceilLog2(m_num_directories); 627027SN/A 637039SN/A if (m_numa_high_bit == 0) { 647563SN/A m_numa_high_bit = RubySystem::getMemorySizeBits() - 1; 657039SN/A } 667039SN/A assert(m_numa_high_bit != 0); 676145SN/A} 686145SN/A 696145SN/ADirectoryMemory::~DirectoryMemory() 706145SN/A{ 717039SN/A // free up all the directory entries 7211025Snilay@cs.wisc.edu for (uint64_t i = 0; i < m_num_entries; i++) { 7310520Snilay@cs.wisc.edu if (m_entries[i] != NULL) { 7410520Snilay@cs.wisc.edu delete m_entries[i]; 757039SN/A } 767039SN/A } 7710520Snilay@cs.wisc.edu delete [] m_entries; 786285SN/A} 796145SN/A 8011025Snilay@cs.wisc.eduuint64_t 8111025Snilay@cs.wisc.eduDirectoryMemory::mapAddressToDirectoryVersion(Addr address) 826285SN/A{ 837039SN/A if (m_num_directories_bits == 0) 847039SN/A return 0; 857039SN/A 8611025Snilay@cs.wisc.edu uint64_t ret = bitSelect(address, 8711025Snilay@cs.wisc.edu m_numa_high_bit - m_num_directories_bits + 1, 8811025Snilay@cs.wisc.edu m_numa_high_bit); 897039SN/A return ret; 906145SN/A} 916145SN/A 927039SN/Abool 9311025Snilay@cs.wisc.eduDirectoryMemory::isPresent(Addr address) 946145SN/A{ 957039SN/A bool ret = (mapAddressToDirectoryVersion(address) == m_version); 967039SN/A return ret; 976145SN/A} 986145SN/A 9911025Snilay@cs.wisc.eduuint64_t 10011025Snilay@cs.wisc.eduDirectoryMemory::mapAddressToLocalIdx(Addr address) 1016161SN/A{ 10211025Snilay@cs.wisc.edu uint64_t ret; 1037563SN/A if (m_num_directories_bits > 0) { 10411025Snilay@cs.wisc.edu ret = bitRemove(address, m_numa_high_bit - m_num_directories_bits + 1, 10511025Snilay@cs.wisc.edu m_numa_high_bit); 1067563SN/A } else { 10711025Snilay@cs.wisc.edu ret = address; 1087563SN/A } 1097563SN/A 1107563SN/A return ret >> (RubySystem::getBlockSizeBits()); 1116161SN/A} 1126161SN/A 1138644SN/AAbstractEntry* 11411025Snilay@cs.wisc.eduDirectoryMemory::lookup(Addr address) 1156145SN/A{ 1167039SN/A assert(isPresent(address)); 1178644SN/A DPRINTF(RubyCache, "Looking up address: %s\n", address); 1188644SN/A 11910520Snilay@cs.wisc.edu uint64_t idx = mapAddressToLocalIdx(address); 12010520Snilay@cs.wisc.edu assert(idx < m_num_entries); 12110520Snilay@cs.wisc.edu return m_entries[idx]; 1228644SN/A} 1238644SN/A 1248644SN/AAbstractEntry* 12511025Snilay@cs.wisc.eduDirectoryMemory::allocate(Addr address, AbstractEntry *entry) 1268644SN/A{ 1278644SN/A assert(isPresent(address)); 12811025Snilay@cs.wisc.edu uint64_t idx; 1298436SN/A DPRINTF(RubyCache, "Looking up address: %s\n", address); 1307025SN/A 13110520Snilay@cs.wisc.edu idx = mapAddressToLocalIdx(address); 13210520Snilay@cs.wisc.edu assert(idx < m_num_entries); 13310520Snilay@cs.wisc.edu entry->changePermission(AccessPermission_Read_Only); 13410520Snilay@cs.wisc.edu m_entries[idx] = entry; 1356145SN/A 1368644SN/A return entry; 1376145SN/A} 1386145SN/A 1397039SN/Avoid 1407039SN/ADirectoryMemory::print(ostream& out) const 1417039SN/A{ 1427039SN/A} 1437039SN/A 1447039SN/Avoid 1459104SN/ADirectoryMemory::recordRequestType(DirectoryRequestType requestType) { 1469104SN/A DPRINTF(RubyStats, "Recorded statistic: %s\n", 1479104SN/A DirectoryRequestType_to_string(requestType)); 1489104SN/A} 1499104SN/A 1506876SN/ADirectoryMemory * 1516876SN/ARubyDirectoryMemoryParams::create() 1526876SN/A{ 1536876SN/A return new DirectoryMemory(this); 1546876SN/A} 155