interconnect_slave_impl.hh

00001 
00002 #include <iostream>
00003 #include <vector>
00004 
00005 #include "interconnect.hh"
00006 #include "interconnect_slave.hh"
00007 
00008 using namespace std;
00009 
00010 template<class MemType>
00011 InterconnectSlave<MemType>::InterconnectSlave(const string &name,
00012                                               Interconnect* interconnect,
00013                                               MemType* cache,
00014                                               HierParams *hier)
00015     : InterconnectInterface(interconnect, name, hier)
00016 {
00017     thisCache = cache;
00018 
00019     interfaceID = thisInterconnect->registerInterface(this,
00020                                                       true,
00021                                                       cache->getProcessorID());
00022     thisCache->setInterfaceID(interfaceID);
00023     
00024     if(trace_on) cout << "InterconnectSlave with id " << interfaceID 
00025                       << " created\n";
00026 
00027 }
00028 
00029 template<class MemType>
00030 MemAccessResult
00031 InterconnectSlave<MemType>::access(MemReqPtr &req){
00032 
00033     bool already_satisfied = req->isSatisfied();
00034     if (already_satisfied && !req->cmd.isDirectoryMessage()) {
00035         warn("Request is allready satisfied (InterconnectSlave: access())");
00036         return BA_NO_RESULT;
00037     }
00038     
00039     if (this->inRange(req->paddr)) {
00040         assert(!blocked);
00041 
00042         if(trace_on) cout << "TRACE: SLAVE_ACCESS from id " 
00043                           << req->fromInterfaceID << " addr " << req->paddr 
00044                           << " at " << curTick << "\n";
00045         
00046         thisCache->access(req);
00047 
00048         assert(!this->isBlocked() || thisCache->isBlocked());
00049 
00050         if (this->isBlocked()) {
00051             //Out of MSHRS, now we block
00052             return BA_BLOCKED; 
00053         } else {
00054             // This transaction went through ok
00055             return BA_SUCCESS;
00056         }
00057     }
00058 
00059     return BA_NO_RESULT;
00060 }
00061 
00062 template<class MemType>
00063 void
00064 InterconnectSlave<MemType>::respond(MemReqPtr &req, Tick time){
00065     
00066     if (!req->cmd.isNoResponse()) {
00067         if(trace_on) cout << "TRACE: SLAVE_RESPONSE " << req->cmd.toString() 
00068                           << " from id " << req->fromInterfaceID 
00069                           << " addr " << req->paddr 
00070                           << " at " << curTick << "\n";
00071         
00072         // handle directory requests
00073         if(req->toProcessorID != -1){
00074             // the sender interface recieves slave responses
00075             req->fromInterfaceID = 
00076                     thisInterconnect->getInterconnectID(req->toProcessorID);
00077             assert(req->fromInterfaceID != -1);
00078         }
00079         
00080         responseQueue.push_back(new InterconnectResponse(req, time));
00081         thisInterconnect->request(time, interfaceID);
00082     }
00083 }
00084 
00085 
00086 template<class MemType>
00087 bool
00088 InterconnectSlave<MemType>::grantData(){
00089     
00090     assert(responseQueue.size() > 0);
00091     InterconnectResponse* response = responseQueue.front();
00092     responseQueue.erase(responseQueue.begin());
00093     
00094     MemReqPtr req = response->req;
00095     
00096     // Update send profile
00097     updateProfileValues(req);
00098     
00099     thisInterconnect->send(req, curTick, interfaceID);
00100     
00101     delete response;
00102     
00103     return !responseQueue.empty();
00104 
00105 }
00106 
00107 template<class MemType>
00108 bool
00109 InterconnectSlave<MemType>::inRange(Addr addr)
00110 {
00111     assert(thisCache != NULL);
00112     
00113     if(thisCache->isModuloAddressedBank()){
00114         
00115         int bankID = thisCache->getBankID();
00116         int bankCount = thisCache->getBankCount();
00117         
00118         int localBlkSize = thisCache->getBlockSize();
00119         int bitCnt = 1;
00120         assert(localBlkSize != 0);
00121         while((localBlkSize >>= 1) != 1) bitCnt++;
00122         
00123         assert(bankID != -1);
00124         assert(bankCount != -1);
00125         
00126         Addr effectiveAddr = addr >> bitCnt;
00127         
00128         if((effectiveAddr % bankCount) == bankID) return true;
00129         return false;
00130     }
00131     else{
00132         for (int i = 0; i < ranges.size(); ++i) {
00133             if (addr == ranges[i]) {
00134                 return true;
00135             }
00136         }
00137         return false;
00138     }
00139 }
00140 

Generated on Tue Jun 5 12:55:20 2007 for M5InterconnectExtensions by  doxygen 1.4.7