Generic hardware access library
|
00001 #include "hal/VMEAddressTable.hh" 00002 #include <sstream> 00003 #include <iomanip> 00004 00005 HAL::VMEAddressTable::VMEAddressTable( std::string name, HAL::AddressTableReader& tableReader ) 00006 : HAL::AddressTable( name ) { 00007 HAL::AddressTableItem* newTableItem; 00008 // fill the itemMap 00009 while ( tableReader.next( &newTableItem ) ) { 00010 itemMap[newTableItem->getKey()] = newTableItem; 00011 } 00012 determineAddressBoundaries(); 00013 } 00014 00015 HAL::VMEAddressTable::~VMEAddressTable() {} 00016 00017 void HAL::VMEAddressTable::print( std::ostream& os ) const { 00018 00019 __gnu_cxx::hash_map<std::string, HAL::AddressTableItem*, HAL::HalHash<std::string> >::const_iterator it; 00020 os << "\n******************************************************************************************************" << std::endl; 00021 os << "* VME Address Table : " << name << std::endl; 00022 os << "* item AdrSpace map AM width address mask r w description"<< std::endl; 00023 os << "******************************************************************************************************" << std::endl; 00024 for( it=itemMap.begin(); it!=itemMap.end(); it++ ) { 00025 (*it).second->print(); 00026 } 00027 os << "******************************************************************************************************\n" << std::endl; 00028 } 00029 00030 void HAL::VMEAddressTable::getAddressBoundaries( std::vector<uint32_t>& minAddresses, 00031 std::vector<uint32_t>& maxAddresses ) const { 00032 minAddresses = minAddresses_; 00033 maxAddresses = maxAddresses_; 00034 } 00035 00036 void HAL::VMEAddressTable::checkAddressLimits( std::string item, uint32_t offset ) const 00037 throw ( HAL::NoSuchItemException, 00038 HAL::AddressOutOfLimitsException ) { 00039 // we have to be precise here: in the block transfer method the length 00040 // of the transfer is given in bytes. 00041 const HAL::GeneralHardwareAddress& hardwareAddress = getGeneralHardwareAddress( item ); 00042 uint32_t address = hardwareAddress.getAddress() + offset; 00043 uint32_t width = hardwareAddress.getDataWidth(); 00044 if ( hardwareAddress.isMemorySpace() ) { 00045 uint32_t functionId = hardwareAddress.getMapId(); 00046 if ( (address + width - 1) > maxAddresses_[functionId] || address < minAddresses_[functionId] ) { 00047 std::stringstream text; 00048 text << "The address is outside of the HAL::AddressTable range: \n" 00049 << " HAL::AddressTable : " << name << "\n" 00050 << " item : " << item << "\n" 00051 << " offset (hex): " << std::hex << offset << "\n" 00052 << std::ends; 00053 throw ( HAL::AddressOutOfLimitsException( text.str(), __FILE__, __LINE__, __FUNCTION__ ) ); 00054 } 00055 } else { 00056 if ( address > 0xffffff ) { 00057 std::stringstream text; 00058 text << "The address for configuration space access is outside of the configuration space of the module: \n" 00059 << " HAL::AddressTable : " << name << "\n" 00060 << " item : " << item << "\n" 00061 << " offset (hex): " << std::hex << offset << "\n" 00062 << std::ends; 00063 throw ( HAL::AddressOutOfLimitsException( text.str(), __FILE__, __LINE__, __FUNCTION__ ) ); 00064 } 00065 } 00066 } 00067 00068 void HAL::VMEAddressTable::checkAddressLimits( const HAL::GeneralHardwareAddress& hardwareAddress, 00069 uint32_t offset ) const 00070 throw ( HAL::AddressOutOfLimitsException ) { 00071 // we have to be precise here: in the block transfer method the length 00072 // of the transfer is given in bytes. 00073 uint32_t address = hardwareAddress.getAddress() + offset; 00074 uint32_t width = hardwareAddress.getDataWidth(); 00075 if ( hardwareAddress.isMemorySpace() ) { 00076 uint32_t functionId = hardwareAddress.getMapId(); 00077 if ( (address + width - 1) > maxAddresses_[functionId] || address < minAddresses_[functionId] ) { 00078 std::stringstream text; 00079 text << "The address is outside of the HAL::AddressTable range: \n" 00080 << " HAL::AddressTable : " << name << "\n" 00081 << " address (hex) : " << std::hex << hardwareAddress.getAddress() << "\n" 00082 << " offset (hex) : " << std::hex << offset << "\n" 00083 << std::ends; 00084 throw ( HAL::AddressOutOfLimitsException( text.str(), __FILE__, __LINE__, __FUNCTION__ ) ); 00085 } 00086 } else { 00087 if ( address > 0xffffff ) { 00088 std::stringstream text; 00089 text << "The address for configuration space access is outside of the configuration space of the module: \n" 00090 << " HAL::AddressTable : " << name << "\n" 00091 << " address (hex) : " << std::hex << hardwareAddress.getAddress() << "\n" 00092 << " offset (hex) : " << std::hex << offset << "\n" 00093 << std::ends; 00094 throw ( HAL::AddressOutOfLimitsException( text.str(), __FILE__, __LINE__, __FUNCTION__ ) ); 00095 } 00096 } 00097 } 00098 00099 void HAL::VMEAddressTable::determineAddressBoundaries( ) { 00100 __gnu_cxx::hash_map<std::string, HAL::AddressTableItem*, HAL::HalHash<std::string> >::const_iterator it; 00101 uint32_t address, maddress, functionId; 00102 std::string key; 00103 00104 // initialize the address boundary variables for the 00105 // sorting algorithm below. The AddressesBoundaries for 00106 // each function are, of course, determined separately. 00107 maxAddresses_.clear(); 00108 minAddresses_.clear(); 00109 for ( int ic = 0; ic < NUMBER_OF_VME64XFUNCTIONS; ic++ ) { 00110 maxAddresses_.push_back(0); 00111 minAddresses_.push_back(~0x00); 00112 } 00113 00114 // sort algorithm: scan all items in the AddressMap and 00115 // memorize the largest and smallest addresses for each 00116 // function. 00117 for ( it = itemMap.begin(); it != itemMap.end(); it++ ) { 00118 key = (*it).second->getKey(); 00119 const HAL::GeneralHardwareAddress& vmeAddress = getGeneralHardwareAddress( key ); 00120 // do not handle the configuration space here 00121 if ( vmeAddress.isMemorySpace() ) { 00122 address = vmeAddress.getAddress(); 00123 functionId = vmeAddress.getMapId(); 00124 maddress = address + vmeAddress.getDataWidth() - 1; 00125 if ( maddress > maxAddresses_[functionId] ) { 00126 maxAddresses_[functionId] = maddress; 00127 } 00128 if ( address < minAddresses_[functionId] ) { 00129 minAddresses_[functionId] = address; 00130 } 00131 } 00132 } 00133 } 00134